Part 2/2 Так какая же функция содержит реальную ошибку, и как можно это использовать? Первопричина в win32k!xxxCreateWindowEx(). Грубо говоря, эта объёмная процедура ответственна за выделение памяти под оконную структуру и её инициализацию, в т.ч. прилепление окна в нужное место оконного пространства. На некотором этапе своего выполнения ф-ия проверяет, установлен ли хук WH_CBT на поток\десктоп, и, если это истинно, вызывает процедуру win32k!xxxCallHook() с параметром HCBT_CREATEWND. Далее поток выполнения попадает в юзермод – функция обработки хука получает управление. Здесь, в хуковой процедуре, можно указать окно hwndInsertAfter, после которого нужно расположить текущее, создаваемое окно (имеется в виду Z-Order – т.е., пользователь имеет возможность задать левого сиблинга). Далее управление возвращается к xxxCreateWindowEx(). Переданный из хуковой процедуры хендл "hwndInsertAfter" валидируется (из хендла превращается в указатель, с базовыми проверками), затем выполняется ещё сто тысяч инструкций и вызывается функция LinkWindow() для прилепления окна в определённому родителю и после определённого сиблинга. Вот здесь-то и кроется ошибка – перед вызовом функции LinkWindow() процедура xxxCreateWindowEx() не проверяет, совпадают ли у создаваемого окна pwnd и его будущего сиблинга pwndInsertAfter родительские окна. Теоретическую недопустимость различных парентов подчёркивает тот факт, что в дебажной версии LinkWindow() имеется ассерт, проверяющий совпадаемость родителей. (На самом деле, для того чтобы xxxCreateWindowEx() не отказалась от переданного через хуковую процедуру сиблинга для создаваемого окна, необходимо соблюсти несколько дополнительных условий – однако быстрое правило здесь будет таково: у создаваемого окно должен отсутствовать стильбит WS_CHILD и в качестве его родителя должен быть передан NULL (NULL превратиться в Desktop Window)). Окей, значит можно создавать ужасающие, невалидные раскладки окон. Но может ли это дать что-нибудь, помимо осинений? Да и вообще, применяемая система подсчёта ссылок и защита от повторного вызова процедур уничтожения позволяет оконной раскладке чуть ли не самовосстанавливаться (нет, серьёзно – если бы не ошибка в ValidateParentDepth(), то бсод, по идее, так бы и не проявился). Ладно, посмотрим: Если создать такую раскладку, а затем уничтожить два окна из трёх в указанном порядке, то spwndChild у первого окна будет указывать в никуда. Точнее, будет указывать на то место, где было третье окно. Т.е. в страничный сессионный пул. Теперь можно создать кучу USER-объектов – таким образом, чтобы занять это свободное пространство. Заранее зная внутреннюю структуру объектов, а также получив их адреса благодаря массиву HANDLEENTRY, находящемуся секции, вид которой отображён на юзермодное пространство, можно попытаться создать такое состояние, при котором реинтерпретация ранее занятой третьим окном памяти в качестве окна могла бы привести к выполнению произвольно кода с привилегиями ядра. Начать интерпретацию памяти в качестве окна можно запустив уничтожение win1 – ведь в этом случае его воображаемый потомок (бывший win3) тоже должен начать "уничтожение". Это непроверенный вариант, к которому мы пришли – может быть, кто-нибудь предложит более простое\надёжное решение. Не сработает. Память не деаллоцируется до обнуления числа ссылок. Число ссылок на win3 не достигнет нуля, потому что на неё будет ссылка из win1 TLDR: Недостаточная валидация полученных из юзермода параметров в функции xxxCreateWindowEx() потенциально может быть использована для локальной эскалации. Подавление: vendor-side: проверять родительскую принадлежность окна, полученного процедурой xxxCreateWindowEx() посредством функции xxxCallHook(). Опционально: изменить граничное условие функции ValidateParentDepth(). client-side: решения в настоящее время отсутствуют. P.S. Надеемся увидеть рабочий эксплоит в течение 4х дней
Sol_Ksacap Крайне интересно. Спасибо! По-моему, это готовая замечательная статья, причем одна из очень немногих на эту тему, и даже если в ней самой есть ошибки, - прямо в данном виде и опубликовать бы. Ну, и потом продолжить, по обстоятельствам Между прочим, я сейчас параллельно переписываюсь с Mark Rusinovich по данной проблеме (она его весьма заинтересовала). У вас не будет eng варианта вашей заметки ?
Sol_Ksacap Да, и еще. Вот вы все время пишете - "мы". А сколько "вас"? Кто "вы", если не секрет? Mark сообщил, что "forwarded this to the Win32k team". Не вам ?
Между прочим, можно и деликатнее: (на грубом примере с MB) Код (Text): .data _wnd db "wnd",0 .data? hhook dd ? .code EnCh proc hWnd:HWND,lParam:LPARAM mov edx,lParam mov eax,hWnd mov dword ptr[edx],eax ret EnCh endp HookProc proc uses ebx edi nCode:UINT,wParam:WPARAM,lParam:LPARAM local var:DWORD .if nCode==HCBT_CREATEWND mov ebx,lParam assume ebx:PTR CBT_CREATEWND mov edi,[ebx].lpcs assume edi:PTR CREATESTRUCT .if [edi].lpszClass==WC_DIALOG invoke GetDesktopWindow mov edx,eax invoke EnumChildWindows,edx,offset EnCh,addr var mov eax,var mov [ebx].hWndInsertAfter,eax .endif assume edi:nothing assume ebx:nothing xor eax,eax .else invoke CallNextHookEx,hhook,nCode,wParam,lParam .endif ret HookProc endp start: invoke GetModuleHandle,0 invoke SetWindowsHookEx,WH_CBT,offset HookProc,eax,0 mov hhook,eax invoke MessageBox,0,offset _wnd,offset _wnd,0 invoke UnhookWindowsHookEx,hhook invoke ExitProcess,eax end start
kero верно, предыдущий пост был к #2 варианту. вариант #3: запуск нормально, бсод по win+D на xp sp3.
XPSP2, http://tinyurl.com/y8hz5mb Походу не юзабельно, а дров совсем дырявый, эскалации не будет. Хотя шадова хуки имеют иный дырки.
kero >Mark сообщил, что "forwarded this to the Win32k team". Не вам ? >Вот вы все время пишете - "мы" Мы являемся единой сущностью. Используем множественное лицо лишь для того, чтобы подчеркнуть наше превосходство над жалкими людишками. Было предполагаемо (и является предпочитаемым), что в обращениях со стороны будет таки использоваться единственное число Насчёт статьи – вряд ли. Мы считаем, что в данном виде это описание не является достаточно законченным – требуется более подробное описание оконной подсистемы в целом и исследование путей эксплуатации. К концу недели решим, стоит ли этим заниматься. >даже если в ней самой есть ошибки Уупс. Не указали важные связи в основной "картине мира". Первый и второй рисунки в ожидании минорного изменения. Посмотрели в отладчике на предложенный путь эскалации. Ха. После "уничтожения" win3 помечается как уничтожаемое, однако память не освобождается, пока счётчик ссылок на окно не достигнет нуля – а он и не достигнет, ведь мы не учли, что после уничтожения win2 на win3 начинает ссылаться win1 и счётчик ссылок не уменьшается благодаря этому. Впрочем, нельзя исключить возможность нахождения каких-либо других решений. >eng Описание формулировалось изначально на русском, но можно переотобразить ключевые моменты (первый придравшийся к качеству слога будет забанен):
Так, на всякий случай: вот здесь - Скрытный запуск приложений (NB: скрытно - значит без промелькиваний) - потомок демки, наведшей на переZагруZку
Вчера, как известно, был Лоскутный Вторник. По этому случаю сегодня мы планировали сделать diff-картинку пропатченной области win32k, и, запостив её сюда, поставить некий сорт точки в этой теме. Однако Microsoft преподнесла сюрприз. Как можно видеть, опубликовано всего одно исправление для основной ветки, причём не имеющее отношения к обсуждаемой проблеме. (Хоть ему и присвоен статус критического; данная же Z-уязвимость, будучи эксплуатируемой "лишь" в качестве локальной эскалации, должна получить статус важной). Если кто-нибудь видит некий реальный барьер, препятствующий добавлению несложной проверки в xxxCreateWindowEx (проблемы с обратной совместимостью? наличие связанных уязвимостей?), то было бы здорово узнать об этом.
Sol_Ksacap Может, такая политика: гром грянет, тогда и перекрестятся? Никто ж пока не воспользовался Лучше выкладывайте "некий сорт точки", не томите. --- А что за "Лоскутный Вторник"? Никогда не слышал, и не гуглится. Не экспромт ли мистификация?
kero "Лоскутный Вторник" - день выпуска бюллетеня безопасности MS, насколько я понимаю. microsoft.com/technet/security/bulletin/ms10-jan.mspx
RamMerLabs Нет, меня заинтересовал этот "Лоскутный Вторник" в прямом смысле: может, у верующих какой особенный день? но везде тишина Ox8BFF55 Поскольку у меня самого XP SP2, да и по всем предшествующим вашему сообщениям - работает, стоило бы изложить поподробнее.
Сошел сума, точнее остановилась винда!! Проверял первую, оказывается ненужно просто клатсать на окно )) То и есть если нажать внизу(на таск баре) то винда както это рефрешит....
Ox8BFF55 А... Это "както" можете получить наглядным в два счета: "Прицеп к Spy++", и там пример работы спая с прицепом:
>Лоскутный Вторник Действительно, всего лишь день выпуска бюллетеней Издержки перевода, ага. >Лучше выкладывайте "некий сорт точки" Ох, нечего выкладывать. В течение нескольких дней за последним декабрьским сообщением был проведён дополнительный разбор, после чего, увы, интерес был потерян. Впрочем, сейчас опять стало любопытно
В ms10-032 пофиксили? Или раньше? С установленным патчем ms10-032 win7 не bsod-ит. Да и изменения в функции xxxCreateWindowEx как-бы намекают =)
Да, три недели назад – MS10-032, "Window Creation Vulnerability". KB979559, CVE-2010-0485. Всё никак не доходят руки выложить полное разоблачение. Наверное, всё же завтра-послезавтра зальём доку.