macOS xpc_connection_get_audit_token Attack
Last updated
Last updated
Learn & practice AWS Hacking:HackTricks Training AWS Red Team Expert (ARTE) Learn & practice GCP Hacking: HackTricks Training GCP Red Team Expert (GRTE)
Для отримання додаткової інформації перегляньте оригінальну публікацію: https://sector7.computest.nl/post/2023-10-xpc-audit-token-spoofing/. Це резюме:
Якщо ви не знаєте, що таке Mach Messages, почніть з перегляду цієї сторінки:
macOS IPC - Inter Process CommunicationНа даний момент пам'ятайте, що (визначення звідси): Mach messages надсилаються через mach port, який є каналом зв'язку з одним приймачем і кількома відправниками, вбудованим у ядро mach. Кілька процесів можуть надсилати повідомлення на mach port, але в будь-який момент тільки один процес може читати з нього. Як і дескриптори файлів і сокети, mach ports виділяються та керуються ядром, а процеси бачать лише ціле число, яке вони можуть використовувати, щоб вказати ядру, який з їх mach ports вони хочуть використовувати.
Якщо ви не знаєте, як встановлюється XPC-з'єднання, перегляньте:
macOS XPCЦікаво знати, що абстракція XPC є з'єднанням один до одного, але вона базується на технології, яка може мати кілька відправників, тому:
Mach ports є одноразовим приймачем, кількома відправниками.
Аудитний токен з'єднання XPC є токеном аудиту скопійованим з найостаннішого отриманого повідомлення.
Отримання аудитного токена з'єднання XPC є критично важливим для багатьох перевірок безпеки.
Хоча попередня ситуація виглядає багатообіцяюче, є деякі сценарії, де це не викличе проблем (звідси):
Аудитні токени часто використовуються для перевірки авторизації, щоб вирішити, чи прийняти з'єднання. Оскільки це відбувається за допомогою повідомлення до сервісного порту, з'єднання ще не встановлено. Більше повідомлень на цьому порту просто обробляються як додаткові запити на з'єднання. Отже, будь-які перевірки перед прийняттям з'єднання не є вразливими (це також означає, що в межах -listener:shouldAcceptNewConnection:
аудитний токен є безпечним). Тому ми шукаємо XPC-з'єднання, які перевіряють конкретні дії.
Обробники подій XPC обробляються синхронно. Це означає, що обробник подій для одного повідомлення повинен бути завершений перед викликом для наступного, навіть на паралельних чергах. Тому всередині обробника подій XPC аудитний токен не може бути перезаписаний іншими звичайними (не-відповідь!) повідомленнями.
Два різні методи, які можуть бути вразливими:
Варіант 1:
Експлойт підключається до сервісу A та сервісу B
Сервіс B може викликати привілейовану функціональність у сервісі A, яку користувач не може
Сервіс A викликає xpc_connection_get_audit_token
під час не всередині обробника подій для з'єднання в dispatch_async
.
Отже, інше повідомлення може перезаписати аудитний токен, оскільки воно надсилається асинхронно поза обробником подій.
Експлойт передає сервісу B право ВІДПРАВКИ до сервісу A.
Отже, svc B фактично надсилає повідомлення до сервісу A.
Експлойт намагається викликати привілейовану дію. У RC svc A перевіряє авторизацію цієї дії, поки svc B перезаписує аудитний токен (надаючи експлойту доступ до виклику привілейованої дії).
Варіант 2:
Сервіс B може викликати привілейовану функціональність у сервісі A, яку користувач не може
Експлойт підключається до сервісу A, який надсилає експлойту повідомлення, що очікує на відповідь у конкретному порту відповіді.
Експлойт надсилає сервісу B повідомлення, передаючи цей порт відповіді.
Коли сервіс B відповідає, він надсилає повідомлення до сервісу A, поки експлойт надсилає інше повідомлення до сервісу A, намагаючись досягти привілейованої функціональності і очікуючи, що відповідь від сервісу B перезапише аудитний токен у потрібний момент (умова гонки).
Сценарій:
Два mach сервіси A
та B
, до яких ми можемо підключитися (на основі профілю пісочниці та перевірок авторизації перед прийняттям з'єднання).
A повинна мати перевірку авторизації для конкретної дії, яку B
може пройти (але наш додаток не може).
Наприклад, якщо B має деякі права або працює як root, це може дозволити йому попросити A виконати привілейовану дію.
Для цієї перевірки авторизації A
отримує аудитний токен асинхронно, наприклад, викликавши xpc_connection_get_audit_token
з dispatch_async
.
У цьому випадку зловмисник може викликати умову гонки, створюючи експлойт, який просить A виконати дію кілька разів, поки B надсилає повідомлення до A
. Коли RC є успішною, аудитний токен B буде скопійовано в пам'яті поки запит нашого експлойту обробляється A, надаючи доступ до привілейованої дії, яку тільки B могла б запитати.
Це сталося з A
як smd
і B
як diagnosticd
. Функція SMJobBless
з smb може бути використана для встановлення нового привілейованого допоміжного інструмента (як root). Якщо процес, що працює як root, контактує з smd, жодні інші перевірки не будуть виконані.
Отже, сервіс B є diagnosticd
, оскільки він працює як root і може бути використаний для моніторингу процесу, тому, як тільки моніторинг розпочато, він надсилає кілька повідомлень на секунду.
Щоб виконати атаку:
Ініціюйте з'єднання з сервісом, названим smd
, використовуючи стандартний протокол XPC.
Сформуйте вторинне з'єднання з diagnosticd
. На відміну від звичайної процедури, замість створення та надсилання двох нових mach ports, право на відправку клієнтського порту замінюється дублікатом права на відправку, пов'язаного з з'єднанням smd
.
В результаті XPC повідомлення можуть бути надіслані до diagnosticd
, але відповіді від diagnosticd
перенаправляються до smd
. Для smd
здається, що повідомлення як від користувача, так і від diagnosticd
походять з одного з'єднання.
Наступний крок полягає в тому, щоб дати вказівку diagnosticd
розпочати моніторинг вибраного процесу (можливо, власного користувача). Одночасно надсилається потік звичайних 1004 повідомлень до smd
. Намір полягає в установці інструмента з підвищеними привілеями.
Ця дія викликає умову гонки в функції handle_bless
. Таймінг критичний: виклик функції xpc_connection_get_pid
повинен повернути PID процесу користувача (оскільки привілейований інструмент знаходиться в пакеті додатка користувача). Однак функція xpc_connection_get_audit_token
, зокрема в підпрограмі connection_is_authorized
, повинна посилатися на аудитний токен, що належить diagnosticd
.
В середовищі XPC (міжпроцесна комунікація), хоча обробники подій не виконуються паралельно, обробка відповідей має унікальну поведінку. Зокрема, існує два різних методи для надсилання повідомлень, які очікують на відповідь:
xpc_connection_send_message_with_reply
: Тут XPC повідомлення отримується та обробляється на призначеній черзі.
xpc_connection_send_message_with_reply_sync
: Навпаки, у цьому методі XPC повідомлення отримується та обробляється на поточній черзі.
Ця відмінність є критично важливою, оскільки вона дозволяє можливість пакетів відповіді оброблятися паралельно з виконанням обробника подій XPC. Зокрема, хоча _xpc_connection_set_creds
реалізує блокування для захисту від часткової перезаписи аудитного токена, це не поширюється на весь об'єкт з'єднання. В результаті це створює вразливість, де аудитний токен може бути замінений під час інтервалу між обробкою пакета та виконанням його обробника подій.
Щоб експлуатувати цю вразливість, потрібна наступна установка:
Два mach сервіси, які називаються A
та B
, обидва з яких можуть встановити з'єднання.
Сервіс A
повинен включати перевірку авторизації для конкретної дії, яку може виконати лише B
(додаток користувача не може).
Сервіс A
повинен надіслати повідомлення, яке очікує на відповідь.
Користувач може надіслати повідомлення до B
, на яке він відповість.
Процес експлуатації включає наступні кроки:
Чекайте, поки сервіс A
надішле повідомлення, яке очікує на відповідь.
Замість того, щоб відповісти безпосередньо A
, порт відповіді захоплюється і використовується для надсилання повідомлення до сервісу B
.
Потім надсилається повідомлення, що стосується забороненої дії, з очікуванням, що воно буде оброблено паралельно з відповіддю від B
.
Нижче наведено візуальне зображення описаного сценарію атаки:
![https://sector7.computest.nl/post/2023-10-xpc-audit-token-spoofing/variant2.png](../../../../../../.gitbook/assets/image (1) (1) (1) (1) (1) (1) (1).png)
Складнощі в знаходженні екземплярів: Пошук екземплярів використання xpc_connection_get_audit_token
був складним, як статично, так і динамічно.
Методологія: Frida була використана для підключення до функції xpc_connection_get_audit_token
, фільтруючи виклики, які не походять з обробників подій. Однак цей метод був обмежений до підключеного процесу і вимагав активного використання.
Інструменти аналізу: Інструменти, такі як IDA/Ghidra, використовувалися для вивчення досяжних mach сервісів, але процес був трудомістким, ускладненим викликами, що стосуються спільного кешу dyld.
Обмеження скриптів: Спроби створити скрипт для аналізу викликів до xpc_connection_get_audit_token
з блоків dispatch_async
були ускладнені складнощами в парсингу блоків і взаємодією з спільним кешем dyld.
Повідомлені проблеми: Було подано звіт до Apple, в якому детально описано загальні та специфічні проблеми, виявлені в smd
.
Відповідь Apple: Apple вирішила проблему в smd
, замінивши xpc_connection_get_audit_token
на xpc_dictionary_get_audit_token
.
Природа виправлення: Функція xpc_dictionary_get_audit_token
вважається безпечною, оскільки вона отримує аудитний токен безпосередньо з mach повідомлення, пов'язаного з отриманим XPC повідомленням. Однак вона не є частиною публічного API, подібно до xpc_connection_get_audit_token
.
Відсутність більш широкого виправлення: Залишається незрозумілим, чому Apple не реалізувала більш комплексне виправлення, наприклад, відкидання повідомлень, які не відповідають збереженому аудитному токену з'єднання. Можливість легітимних змін аудитного токена в певних сценаріях (наприклад, використання setuid
) може бути фактором.
Поточний статус: Проблема залишається в iOS 17 та macOS 14, що становить виклик для тих, хто намагається виявити та зрозуміти її.
Learn & practice AWS Hacking:HackTricks Training AWS Red Team Expert (ARTE) Learn & practice GCP Hacking: HackTricks Training GCP Red Team Expert (GRTE)