در وبلاگ قبلی از آزمایشگاه FortiGuard در این سری، ما درباره نحوه نظارت بر اجرای فرآیند با استدلال خط فرمان با استفاده از MACF در macOS بحث کردیم. در این وبلاگ ما همچنان به بحث در مورد نحوه نظارت بر رویدادهای سیستم فایل (از جمله فایل باز کردن، خواندن، نوشتن، تغییر نام و حذف عملیات) و بارگذاری کتابخانه پویا از طریق MACF در macOS ادامه خواهد داد. من تمام جزئیات فنی را در زیر ارائه خواهم کرد. بیا شروع کنیم

زمینه

برای یک برنامه منظم برای انجام عملیات فایل در طول عمر آن بسیار رایج است.


بدافزار در MacOS یکسان است. به طور کلی، نرم افزارهای مخرب می توانند فضای کاری فایل را ایجاد کنند. علاوه بر این، نرم افزارهای مخرب اغلب به صورت پویا دایلبی را به عنوان اصلی ترین اصلی برای انجام فعالیت های مخرب اولیه خود بارگیری می کنند. همانطور که از وبلاگ قبلی ما دیده می شود، MACF یک چارچوب قدرتمند برای نظارت بر انواع رویدادهای سیستم در هسته در macOS است. این قطعا قادر به نظارت بر سیستم فایل و رویدادهای بارگذاری Dylib بسیار خوب است.

مانیتور رویدادهای سیستم فایل

ابزار من توسعه می تواند تمام رویدادهای سیستم فایل معمولی، از جمله فایل باز، خواندن، نوشتن، تغییر نام و حذف عملیات نظارت داشته باشد. همانطور که در فایل هدر bsd / security / mac_policy.h نشان داده شده است، ساختار mac_policy_ops شامل بیش از 300 عملیات ماژول خط مشی است. عملیات مربوط به رویدادهای سیستم فایل در زیر ذکر شده است.

من پنج بازخورد عملیات فایل را به دو دسته تقسیم کردم. یکی شامل فایل باز کردن، خواندن، نوشتن و حذف عملیات، و یکی دیگر از عملیات تغییر نام فایل است. برای دسته اول، ما پرونده حذف فایل را انتخاب کردیم تا به عنوان مثال برای نمایش جزئیات فنی استفاده کنیم. عملیات های دیگر در این دسته شبیه به callback برای عملیات حذف فایل است. فراخوان عملیات حذف فایل mpo_vnode_check_unlink است. اعلامیه آن در زیر نشان داده شده است. این به شش پارامتر نیاز دارد.

ما می توانیم از vn_getpath تابع استفاده کنیم تا مسیر را برای یک vnode حذف کنیم. این مسیر فایل حذف شده است. و همچنین ما می توانیم با استفاده از توابع kauth_getuid ()، proc_selfpid ()، و proc_selfppid ()، به ترتیب، uid، pid، ppid را دریافت کنیم. سپس نام فرآیند را با فراخوانی تابع proc_selfname بدست می آوریم و نام پروتکل parent را با فراخوانی پروتکل proc_name بدست می آوریم. بعد، بافر داده ها را با اطلاعات مفید دریافت شده توسط ما پر می کنیم. در نهایت، بافر داده ها را با استفاده از تابع ctl_enqueuedata ارسال می کنیم.


بعد، ما همچنان به فراخوانی عملیات تغییر نام پرونده نگاه خواهیم کرد.