لاگی که مدام رشد می‌کند، همان لحظه‌ای که چیزی آن را بازسازی می‌کند از رشد بازمی‌ایستد و پیام خطا می‌گوید دسترسی رد شد. نتیجه‌گیری وسوسه‌انگیز این است که خود فایل به مجوزهای بیشتری نیاز دارد، هرچند شاید همان حساب از قبل بتواند در فایل بنویسد. افزودن به یک نام موجود و ساختن یک نام تازه دو بررسی متفاوت‌اند و تنها دومی از پوشه می‌پرسد.

افزودن و ساختن دو بررسی متفاوت‌اند

باز کردن یک فایل موجود برای افزودن، به مجوز نوشتن روی آن فایل و مجوز جست‌وجو در هر پوشه مسیرش نیاز دارد. ساختن یک فایل به مجوز نوشتن و جست‌وجو در پوشه دربردارنده نیاز دارد، چون عملیات نامی به آن اضافه می‌کند. جایگزین کردن یک فایل از راه تغییر نام هم هر دو پوشه و قواعد sticky bit آن‌ها را درگیر می‌کند.

OperationWhat must permit itTypical failure message
Append to an existing logFile write access, path traversalPermission denied on the file
Create a missing logDirectory write and search accessPermission denied on the path
Rename a replacement into placeBoth directories, plus sticky restrictionsPermission denied or operation not permitted

توصیفگر از قبل بازشده یک حالت چهارم را اضافه می‌کند. یک فرایند می‌تواند دستگیره نوشتنی‌ای را نگه دارد که پیش از کنار گذاشتن امتیازهایش باز شده بود و با این حال نتواند همان مسیر را با هویت بعدی‌اش دوباره باز کند. افزودن‌های موفق و ساختن ناموفق می‌توانند هم‌زمان برای همان فرایند درست باشند.

ACL‌های پیش‌فرض ارث می‌رسند، اعطا نمی‌کنند

مدخلی که با پیشوند default آغاز می‌شود توصیف می‌کند اشیای تازه چه چیزی را از پوشه ارث می‌برند. این مدخل به خود پوشه چیزی اعطا نمی‌کند و ACL فایلی را که از قبل وجود دارد هم تعمیر نمی‌کند.

namei -l /var/log/openvpn/server.log
getfacl -p /var/log/openvpn
getfacl -p /var/log/openvpn/server.log

مدخل‌های دسترسی را جدا از مدخل‌های پیش‌فرض بخوانید و ماسک را هم بخوانید. مدخل نام‌داری که حقوق کامل را فهرست می‌کند باز هم می‌تواند با ماسک محدود شود، و به همین دلیل توضیح effective مهم‌تر از حروف خط اول است.

از مسیر حل‌شده استفاده کنید، نه از مسیری که در پیکربندی آمده است. یک پیوند نمادین، یک نقطه اتصال یا یک پوشه چرخیده می‌تواند فایل واقعی را جایی بگذارد که مجوز اعطاشده هرگز به آن نمی‌رسد. ابتدا مسیر را با namei بپیمایید و سپس هر سطح را با حساب مورد نظر مقایسه کنید. حدس زدن پوشه سطح بالا همان روشی است که یک اصلاح را یک سطح بیش از حد بالا می‌نشاند.

شناسایی کنید در آن لحظه چه کسی می‌نویسد

پیش از تغییر هر چیزی، واحد سرویس، قطعات drop-in آن و تنظیمات حساب خود دیمن را بررسی کنید. فرایندی که اضافه می‌کند و فرایندی که بازسازی می‌کند می‌توانند متفاوت باشند: یک کمک‌کننده چرخش، یک نویسنده وضعیت و یک خواننده وب به‌ندرت هویت مشترک دارند.

یک اجرای آزمایشی از پوسته root سرویس محدودشده را بازتولید نمی‌کند، و موفق می‌شود در حالی که سرویس همچنان شکست می‌خورد. عملیات ناموفق را زیر همان واحد، با همان حساب و همان تنظیمات sandbox بازتولید کنید. اگر نمی‌توانید، واحد را با یک پوسته موقت راه بیندازید و هویتی را که گزارش می‌کند بررسی کنید. هر چیز دیگری ترمینال شما را می‌سنجد، نه سرویس را.

اگر واقعاً ساختن لازم است، به نویسنده دسترسی به پوشه لاگ اختصاصی بدهید و دسترسی خواندن برای مصرف‌کنندگان را جدا نگه دارید. نوشتنی کردن یک حساب مشترک یا کل درخت یک برنامه برای برآورده کردن یک فراخوانی لاگ، مشکلی کوچک را با مشکلی بزرگ عوض می‌کند.

بدون بازگرداندن خطا بچرخانید

هر کس فایل را بازسازی می‌کند، مالک و حالت آن را برای چرخه بعد تعیین می‌کند، پس اصلاح را با پیکربندی چرخش هماهنگ کنید. جایگزینی که با حساب دیگری یا با ACL تازه ساخته شود، پس از یک اصلاح موفق خطا را برمی‌گرداند.

حالت و گروه را هنگام ساختن تنظیم کنید، نه بعد از آن، و چرخش بعدی را بررسی کنید نه افزودن بعدی را. یک افزودن فقط آزمونی را تکرار می‌کند که قبلاً قبول شده است. اگر ابزار چرخش تنظیمی برای حالت ساخت ارائه می‌دهد، از آن به جای chmod پس از ساخت استفاده کنید. شکاف میان ساخت و chmod دقیقاً زمانی است که نوشتن بعدی می‌تواند شکست بخورد.

وقتی بریدن به هر حال شکست می‌خورد، افزودن مجوزها را متوقف کنید

شکست در بریدن فایلی که می‌توانید در آن بنویسید با مجوزهای پوشه توضیح داده نمی‌شود و افزودن مجوزهای بیشتر کمکی نمی‌کند. به جای آن به ویژگی‌ها و محدودسازی نگاه کنید: ویژگی append-only نوشتن را فقط در حالت افزودن مجاز می‌کند و یک اتصال فقط‌خواندنی یا sandbox سرویس می‌تواند عملیاتی را که ACL مجاز می‌داند رد کند.

محدودیت‌های فایل‌سیستم واحد و گزینه‌های اتصال مسیر را بررسی کنید و سپس همان عملیاتی را که شکست خورد بازتولید کنید. گسترش دادن مجوزی که هرگز پرسیده نشد فقط پنهان می‌کند کدام محدودیت واقعی بوده است. هر بار یک محدودیت را در یک واحد یک‌بارمصرف بردارید و پیش از تغییر چیزی دائمی آن را برگردانید.

مقالات مرتبط