محققای WIZ دو تا آسیب پذیری افزایش امتیاز با عنوان GameOver(lay) در ماژول OverlayFS در اوبونتو کشف و گزارش کردن که 40 درصد cloud workload رو تحت تاثیر قرار میده.
اگه یه برنامه کاربردی، سرویس، قابلیت یا بخشی از یه کار ، بتونه روی یه منبع ابری اجرا بشه، بهش Cloud Workload میگن . ماشینهای مجازی، دیتابیس ها، کانتینرها، گرههای Hadoop و برنامههای کاربردی همگی به عنوان Cloud Workload در نظر گرفته میشن.
آسیب پذیری ها در ماژول OverlayFS در کرنل اوبونتو کشف شدن که یه فایل سیستم پرکاربرد در لینوکس هستش و محبوبیتش بعد از معرفی کانتینرها بیشتر هم شد چون امکان استقرار فایل سیستم های داینامیک رو روی ایمیج های از پیش ساخته رو فراهم میکرد.
OverlayFS یه سطح حمله جذاب برای بازیگران تهدید هستش، چون قبلا آسیب پذیری های زیادی روش کشف شده که به راحتی هم اکسپلویت میشن.
اوبونتو در 24 جولای این آسیب پذیری ها رو اصلاح کرده و با بروزرسانی کرنل ، تحت تاثیر این آسیب پذیری نیستید.
نسخه های تحت تاثیر :
GameOver(lay) شامل دو آسیب پذیری CVE-2023-2640 و CVE-2023-32629 هستش.
با توجه به اینکه نسخه های زیادی برای اوبونتو منتشر شده، شناسایی نسخه های آسیب پذیر خودش چالش برانگیز هستش. اما طبق اعلام محققین، موارد زیر تحت تاثیر این آسیب پذیر هستن :
Release | نسخه | CVE-2023-2640 | CVE-2023-32629 |
---|---|---|---|
Ubuntu 23.04 (Lunar Lobster) | |||
6.2.0 | ✔ | ✔ | |
Ubuntu 22.10 (Kinetic Kudu) | |||
5.19.0 | ✔ | ✔ | |
Ubuntu 22.04 LTS (Jammy Jellyfish) | |||
5.19.0 | ✔ | ✔ | |
6.2.0 | ✔ | ✔ | |
5.15.0 | ✘ | ✘ | |
Ubuntu 20.04 LTS (Focal Fossa) | |||
5.15.0 | ✘ | ✘ | |
5.4.0 | ✘ | ✔ | |
Ubuntu 18.04 LTS (Bionic Beaver) | |||
5.4.0 | ✘ | ✔ |
البته اوبونتو هم در بولتن امنیتیش این نسخه هارو بروز میکنه که میتونید موارد جدید و بروز رو برای CVE-2023-32629 و CVE-2023-2640 مشاهده کنید.
GameOver(lay) چیه :
OverlayFS در لینوکس یه union filesystem هستش که یه فایل سیستم رو روی یه فایل سیستم دیگه قرار میده و امکان دستکاری فایلها رو بدون تغییر در فایل سیستم پایینی رو فراهم میکنه. فایل سیستم بالایی معمولا خواندنی-نوشتنی هستش و فایل سیستم پایینی، فقط خواندنی هستش. همه تغییرات روی فایل سیستم بالایی و قابل نوشتن ذخیره میشن. این مکانیزم رو روی live CD ها مشاهده کردید.
OverlayFS ، معمولا در سناریوهایی مانند کانتینرهای داکر استفاده میشه، در حالیکه تغییرات رو روی یه لایه جدا ذخیره میکنه، باعث میشه ایمیج اصلی دست نخورده باقی بمونه. این انعطاف پذیری، باعث نگرانی امنیتی و یه سطح حمله (attack surface) جذاب شده. این باعث میشه که مهاجمین از فایل سیستم های دیگه استفاده کنن و عملیاتشون رو انجام بدن. مثلا گزینه های مانت (mount) مانند nodev یا nosuid رو موقع دسترسی به فایل سیستم های USB/FUSE حذف کنن.
همچنین، به کاربران این امکان رو میده که فایلها را از دایرکتوری «پایین» به دایرکتوری «بالا» کپی کنن و در عین حال متادیتاهای مهم فایل (مانند sticky-bit) رو حفظ کنن، که در لینوکس ممکن نیست.
سیستم های سنتی یونیکس برای بررسی پرمیشن ها، پروسس ها رو به دو نوع تقسیم میکردن :
- پروسس های دارای امتیاز : UID شون برابر 0 هست و با عنوان superuser یا root شناخته میشن.
- پروسس های بدون امتیاز: UID شون غیر صفر هستش و توسط کاربر غیر root اجرا میشن.
پروسس های دارای امتیاز، بررسی های پرمیشن کرنل رو رد میکنن اما پروسس های بدون امتیاز براساس UID ، GID و لیست گروه ها ، پرمیشنشون بررسی میشه.
با معرفی Linux 2.2 ، لینوکس پرمیشن هایی که مرتبط با superuser هستش رو به واحدهای مجزایی تقسیم میکنه که بهش قابلیت (capabilities) میگن و هر کدوم بطور مستقل امکان فعال یا غیر فعال شدن رو دارن.
قبل از معرفی این قابلیتها، برای اینکه یه برنامه با امتیاز root اجرا بشه ، بدون اینکه وارد root بشیم، از Setuid استفاده میشد که در بیشتر اکسپلویتها برای افزایش امتیاز بکار میرفت.
بطور کلی هدف file capabilities اینه که پرمیشن های root رو کنترل کنه و دیگه نیازی به لاگین کردن بعنوان کاربر root برای انجام یه کاری و بعد دوباره برگشت به کاربر قبلی نیستیم. مثلا یه قابلیت با عنوان CAP_NET_BIND_SERVICE رو داریم که امکان اتصال به پورتهای زیر 1024 رو فراهم میکنه. لیست کامل file capabilitiesها رو میتونید از اینجا مشاهده کنید.
GameOver(lay) یه تکنیکی هستش که که در اون، میشه یه فایل اجرایی با قابلیت فایل محدود رو ایجاد کرد و کرنل لینوکس رو جوری فریب داد که اونو در یه جایی با قابلیت فایل نامحدود ،کپی کنه و هرکسی که اونو اجرا میکنه، امتیاز root میده.
در اصل GameOver(lay) از دو آسیب پذیری زیر تشکیل شده :
- آسیب پذیری CVE-2023-2640 : یه آسیب پذیری افزایش امتیاز در کرنل اوبونتو، با شدت بالا و امتیاز 7.8 هستش ،که به دلیل عدم بررسی کافی پرمیشن ها رخ میده.
- آسیب پذیری CVE-2023-32629 : یه آسیب پذیری با شدت متوسط و امتیاز 5.4 در سیستم مدیریت حافظه کرنل لینوکس هستش، که هنگام دسترسی به VMA ها، به دلیل race condition ، منجر به use-after-free میشه . مهاجم محلی امکان اجرای کد دلخواه رو داره.
OverlayFS قبلا آسیب پذیری های زیادی داشته و نکته جالب اینکه خیلی از اونا مشابه هم هستن و اکسپلویتشون مشابه هم عمل میکنه. آسیب پذیری های جدید هم مشابه آسیب پذیری های کرنل لینوکس هستش که از سال 2020 افشاء شدن. اکسپلویت CVE-2021-3493 بدون تغییر، روی آسیب پذیری کشف شده کار میکنه. سوالی که اینجا مطرحه اینه که اوبونتو چطوری برای آسیب پذیری که دو سال پیش اصلاح شده، همچنان آسیب پذیر هستش؟
اوبونتو چطوری آسیب پذیر شد ؟
اوبونتو یکی از توزیعهای محبوب و پرکاربرد لینوکس هستش و اغلب کرنل لینوکس رو برای مسائلی مانند سازگاری سخت افزاری و معرفی ویژگی های جدید، دستکاری میکنه. برخلاف پروژه لینوکس و سایر توزیعها، اوبونتو اولین بار دسترسی OverlayFS رو برای کاربران غیرمجاز فراهم کرد و منجر به ارتقاء اکوسیستم کانتینری شد اما ریسکهایی رو فراهم کرد.
اوبونتو یسری تغییرات در ماژول OverlayFS داد که اون زمان خطری نداشت. اما بعدها با تغییرات پروژه لینوکس وضعیت فرق کرد:
- در 29 ژوئن سال 2018 اوبونتو کرنل خودش رو دستکاری کرد و در اون تابع
__vfs_setxattr_noperm
رو بجایvfs_setxattr
تعریف کرد تا بتونه از اون که مسئول تنظیم extended attributes هستش، استفاده کنه. - در 14 دسامبر 2020 ، لینوکس یه آسیب پذیری جدید روی OverlayFS کشف و اصلاح کرد. در این اصلاحیه یسری موارد حفاظتی به
vfs_setxattr
اضافه کرد، اما چون اوبونتو از یه پیاده سازی شخصی ،__vfs_setxattr_noperm
، استفاده میکرد، آسیب پذیری همچنان وجود داشت. - در 28 آوریل 2022 ، به دلیل تغییراتی که لینوکس روی OverlayFS انجام داد، دومین آسیب پذیری به همون دلیل بالا ایجاد شد.
اقدامات کاهشی و تشخیص :
برای اکسپلویت نیاز به user namespace و یه مانت OverlayFS هستش. بنابراین برای دسترسی به اینها، نیاز به دسترسی لوکال داره و گزیته راه دور حذف میشه.
بهترین گزینه برای اینکه تحت تاثیر این آسیب پذیری نباشید، بروزرسانی کرنل اوبونتو هستش. اما اگه نتونستید این کار بکنید، میتونید با محدود کردن استفاده از user namespace برای کاربران با امتیاز پایین، از اکسپلویت جلوگیری کنید.
برای انجام این کار میتونید از دستور زیر استفاده کنید :
1 |
sudo sysctl -w kernel.unprivileged_users_clone=0 |
اگه بخوایین این تغییرات بعد از ریستارت سیستم هم باقی بمونه از دستور زیر استفاده کنید :
1 |
echo kernel.unprivileged_userns_clone=0 | sudo tee /etc/sysctl.d/99-disable-unpriv-userns.conf |
نحوه کشف آسیب پذیری :
کشف آسیب پذیری اینجوری بوده که اوایل سال یه آسیب پذیری با شناسه CVE-2023-0386 در OverlayFS در کرنل لینوکس اصلاح میشه. آسیب پذیری اینجوری بوده که مهاجم با سوء استفاده از OverlayFS میتونست کرنل رو دستکاری کنه تا فایلهایی رو از مانتی که تحت کنترلش هست به دایرکتوریهای معمولی کپی کنه. برای اکسپلویت مهاجم یه فایل SUID رو از یه مانت مخرب FUSE به یه دایرکتوری معمولی کپی میکرد. در نتیجه وقتی فایل از این دایرکتوری اجرا میشد، امتیاز root رو بهش میداد.
محققا از رو کنجکاوی اومدن نحوه اصلاح این آسیب پذیری رو بررسی کردن و متوجه شدن که لینوکس ، ایجاد فایل برای کاربران user namespace محدود کرده. با جلوگیری از ایجاد فایل ها به عنوان root، اصلاحیه بطور موثری ایجاد فایل های SUID رو مسدود میکنه.
namespaceها یسری ویژگی در کرنل لینوکس هستن که منابع کرنل رو جوری تقسیم بندی میکنن که یه مجموعه از پروسس ها یسری از منابع رو می بینن در حالی که مجموعه دیگه از پروسسها مجموعه متفاوتی از منابع رو میبینن. در کل هشت نوع namespace داریم که یکیش User namespace هستش.
User namespace ها شناسه ها و ویژگی های مرتبط با امنیت رو ، بخصوص UIDها و GID ها و قابلیتهارو (capabilities) از هم تفکیک میکنن. UID و GID یه پروسس میتونه در داخل و خارج از فضای نام کاربری متفاوت باشه. پروسس دارای پرمیشنهای کامل برای عملیات داخل فضای نام کاربری هستش، اما برای عملیات خارج از فضای نام فاقد پرمیشن هستش.
همونطور که بالا هم اشاره شد، علاوه بر SUID ، یه روش دیگه هم برای دادن ویژگی های امنیتی به فایلها وجود داره و اون استفاده از Linux file capabilities هستش. با این قابلیتها، مالک فایل میتونه یه کاربر با امتیاز پایین باشه، اما در حین اجرای فایل، امتیازش افزایش داده بشه. با این ویژگی ها این اصلاحیه رو میشه دور زد. با بررسی این آسیب پذیری در نهایت محققا به GameOver(lay) رسیدن .
آسیب پذیری CVE-2023-2640 (ovl_copy_xattr) :
محققا برای اینکه امکان دور زدن رو بررسی کنن، یه user namespace جدید ایجاد کردن. user namespace مهمه چون ما فقط در یه user namespace میتونیم file capabilities تنظیم کنیم و فایل سیستم OverlayFS رو مانت کنیم. برای اینکار از دستور unshare استفاده میکنیم.
1 |
unshare -rm bash |
در قدم بعدی محققا، file capabilities با قابلیت های بالا رو به یه فایل اجرایی در یه دایرکتوری، اضافه کردن ،که بعدا بعنوان لایه lower در OverlayFS استفاده میشه. برای اینکار از دستور setcap استفاده میکنیم.
1 |
setcap cap_sys_admin +eip lower/suid |
در دستور بالا، قابلیت cap_sys_admin ویژگی های زیادی رو در دسترس قرار میده از جمله عملیات مدیریت سیستمی مانند mount ، umount، pivot_root ، swapon و … ، انجام عملیات با امتیاز بالا در syslog ، امکان انجام عملیات روی extended attributes و … .
مرحله سوم مانت کردن فایل سیستم OverlayFS هستش. با مشخص کردن گزینه های مانت lowerdir و upperdir ، محققا lower رو برای دایرکتوری که فایل اجرایی هست در نظر گرفتن و upper رو برای دایرکتوری قابل نوشتن در نظر گرفتن.
1 |
mount -t overlay overlay -o rw,lowerdir=lower,upperdir=upper,workdir=workdir mount |
در نهایت ، محققا متادیتای فایل اجرایی رو تغییر دادن تا توسط کرنل در دایرکتوری upper کپی بشه و به این امید که file capabilities اون تغییر نکنه. در نهایت دستور زیر اجرا کردن :
1 |
touch mount/suid |
با این تست، محققا مشاهده کردن که file capabilities فایل اجرایی بدون تغییر باقی مونده و در نتیجه به آسیب پذیری رسیدن
1 2 3 4 5 |
sagi@localhost:/home/sagi$ getcap lower/suid lower/suid = cap_dac_override,cap_sys_admin+eip sagi@localhost:/home/sagi$ getfattr -d -m - lower/suid # file: lower/suid security.capability=0sAQAAAgIAIAACACAAAAAAAAAAAAA= |
بعد از بررسی ، محققا متوجه شدن که این آسیب پذیری، روی همه توزیعهای لینوکس کار نمیکنه و فقط مختص اوبونتو هستش. بنابراین رفتن سراغ بررسی پیاده سازی OverlayFS تا متوجه بشن که کرنل اوبونتو چطوری ویژگیهای extended attribute فایل رو بعد از دستکاری اونا کپی میکنه.
کپی در تابع ovl_copy_xattr با فراخوانی ovl_do_setxattr رخ میده. در برخی نسخه های کرنل اوبونتو، ovl_do_setxattr بطور مستقیم __vfs_setxattr_noperm رو برای تنظیم extended attributes بجای vfs_setxattr فراخوانی میکنه :
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 |
int ovl_copy_xattr(struct super_block *sb, struct path *oldpath, struct dentry *new) { // ... for (name = buf; list_size; name += slen) { // ... error = ovl_do_setxattr(OVL_FS(sb), new, name, value, size, 0); // <--- call to ovl_do_setxattr from ovl_copy_xattr if (error) { if (error != -EOPNOTSUPP || ovl_must_copy_xattr(name)) break; /* Ignore failure to copy unknown xattrs */ error = 0; } } // ... } static inline int ovl_do_setxattr(struct ovl_fs *ofs, struct dentry *dentry, const char *name, const void *value, size_t size, int flags) { // ... err = __vfs_setxattr_noperm(ovl_upper_mnt_userns(ofs), dentry, name, value, size, flags); // <--- call to __vfs_setxattr_noperm // ... } |
یکی از تفاوتهای کلیدی بین vfs_setxattr و __vfs_setxattr_noperm اینه که اولی قابلیتهای امنیتی فایلها رو قبل از کپی کردن در دایرکتوری upper از طریق cap_convert_nscap به user namespace محدود میکنه، اما دومی اونارو مستقیماً بدون تغییر ، کپی میکنه.
خروجی زیر اجرای getfattr رو روی نسخه کرنل آسیب پذیر و اصلاح شده نشون میده :
1 2 3 4 5 6 7 8 9 10 11 |
user@ubuntu:~$ getcap capable_file capable_file = cap_dac_override,cap_setuid,cap_sys_admin+eip user@ubuntu:~$ getfattr -d -m – capable_file # file : capable_file security.capability=0sAQAAAoIAIACCACAAAAAAAAAAAAA= <--- vulnerable version user@ubuntu:~$ getcap capable_file capable_file = cap_dac_override,cap_setuid,cap_sys_admin+eip user@ubuntu:~$ getfattr -d –m - capable_file # file: capable_file security.capability=0sAQAAA4IAIACCACAAAAAAAAAAAADoAwAA <--- non-vulnerable version |
در دستورات بالا، getcap برای نشون دادن file capabilities هستش و دستور getfattr برای نمایش extended attribute ها.
آسیب پذیری CVE-2023-32629 (ovl_copy_up_meta_inode_data) :
برای کشف این آسیب پذیری جریان کد برای تابع غیرامن ovl_do_setxattr رو بررسی کردن. هنگام مانت OverlayFS با metacopy=on ، لینوکس اگه متادیتای فایل تغییر کرده باشه، اونو کپی نمیکنه و بجاش متادیتاهایی که شامل file capabilities هستن رو کپی میکنه.
این کار توسط تابع ovl_copy_up_meta_inode_data انجام میشه که از تابع ovl_do_setxattr برای کپی اطلاعات قابلیت فایل استفاده میکنه.
با مانت OverlayFS با فلگ metacopy و دستکاری متادیتای فایل، به این بخش از کد رسیدن و تونستن یه فایل خالی با file capabilities دلخواه در دایرکتوری upper ایجاد کنن. بعد با دستور touch ، کرنل محتوای فایل رو در این فایل خالی کپی کرده و یه فایل اجرایی با قابلیتهای فایل با امتیاز بالا در خارج از user namespace داده.
منابع: