Из Википедии, бесплатной энциклопедии
Перейти к навигации Перейти к поиску

В вычислении , то Win32 Тема информационного блока (ИРТ) представляет собой структуру данных в Win32 на x86 , которая хранит информацию о запущенной в данный момент потоке . Он также известен как блок среды потока (TEB) для Win32. Он произошел от аналогичной структуры OS / 2 и имеет обратную совместимость с 32-разрядными системами . [1]

TIB официально не документирован для Windows 9x. DDK серии Windows NT (а также реализация MinGW / ReactOS) включает структуру NT_TIB в winnt.h, которая документирует независимую от подсистемы часть. Еще до того, как TIB был эффективно задокументирован, многие приложения уже начали использовать его поля, которые фактически являются частью API . В частности, на первое поле, содержащее фрейм SEH, напрямую ссылается код, созданный собственным компилятором Microsoft. [1] Специфическая для подсистемы Win32 часть TEB недокументирована, но Wine включает определение TEB в winternl.h. [2]

TIB можно использовать для получения большого количества информации о процессе без вызова Win32 API. Примеры включают эмуляцию GetLastError (), GetVersion (). С помощью указателя на PEB можно получить доступ к таблицам импорта (IAT), аргументам запуска процесса, имени образа и т. Д. Доступ к нему осуществляется из регистра сегмента FS в 32-битной Windows и GS в 64-битной Windows.

Содержание TIB в Windows [ править ]

Эта таблица основана на работе Wine над внутренними компонентами Microsoft Windows . [2]

FS (для 32-разрядной версии) или GS (для 64-разрядной версии) сопоставляется с TIB, который встроен в блок данных, известный как TDB (база данных потоков). TIB содержит цепочку обработки исключений, зависящую от потока, и указатель на TLS (локальное хранилище потока). Локальное хранилище потока не то же самое, что локальное хранилище C.

Информация о стеке хранится в TIB [ править ]

Процесс должен иметь возможность перемещать стек своих потоков до тех пор, пока он соответствующим образом обновляет информацию, хранящуюся в TIB. Несколько полей являются ключевыми в этом вопросе: база стека, предел стека, стек освобождения и гарантированные байты стека, соответственно сохраненные со смещениями 0x8, 0x10, 0x1478 и 0x1748 в 64 битах. Различные функции ядра Windows читают и записывают эти значения, особенно для того, чтобы отличать переполнение стека от других ошибок страницы чтения / записи (чтение или запись на страницу, защищенную ограничениями стека в гарантированных байтах стека, будут генерировать исключение переполнения стека вместо доступа нарушение). Стек освобождения важен, потому что Windows API позволяет изменять количество защищаемых страниц: функция SetThreadStackGuarantee позволяет как читать текущее пространство, так и увеличивать его. Чтобы прочитать его, он читает поле GuaranteedStackBytes,и для его увеличения он использует для отмены фиксации страниц стека. Установка пределов стека без установки DeallocationStack, вероятно, вызовет странное поведение в SetThreadStackGuarantee. Например, он перезапишет пределы стека на неправильные значения. Различные библиотеки вызывают SetThreadStackGuarantee, например .NET CLR использует его для настройки стека своих потоков.

Доступ к TIB [ править ]

Доступ к TIB текущего потока можно получить как смещение сегментного регистра FS (x86) или GS (x64).

Не принято обращаться к полям TIB по смещению от FS:[0], а сначала получить линейный указатель на него, ссылающийся на него, хранящийся в FS:[18h]. Этот указатель может использоваться с арифметикой указателя или быть приведен к указателю структуры .

Используя Microsoft Windows SDK или аналогичный, программист может использовать встроенную функцию, определенную в winnt.hnamed, NtCurrentTebкоторая возвращает адрес текущего информационного блока потока как NT_TIB *. [4]

Альтернативные методы доступа для архитектур IA-32 следующие:

// gcc (встроенная сборка в стиле AT&T). void  * getTIB ( void )  {  регистр  void  * pTIB ; #if defined (__ x86_64__) || определено (__ amd64__)  __asm__ ( "movq %% gs: 0x30,% 0"  :  "= r"  ( pTIB )); #elif defined (__ i386__)  __asm__ ( "movl %% fs: 0x18,% 0"  :  "= r"  ( pTIB )); #else #ERROR неподдерживаемый архитектура #endif  возвратного  pTIB ; }
// gcc (именованные адресные пространства, такие же, как встроенная версия сборки на -O1 или -ftree-ter). void  * getTIB ( void )  { #if defined (__ x86_64__) || defined (__ amd64__) #ifndef __SEG_GS #error неподдерживаемая версия GCC #endif  return  * ( void  * __seg_gs  * )  0x30 ; #elif defined (__ i386__) #ifndef __SEG_FS #error неподдерживаемая версия GCC #endif  return  * ( void  * __seg_fs  * )  0x18 ; #еще#error неподдерживаемая архитектура #endif }
// Microsoft C __declspec ( голый ) void  * getTIB ()  {  __asm  mov  EAX ,  FS : [ 18 h ]  __asm  ret }
// Использование встроенных функций Microsoft вместо встроенной сборки (работает как для архитектуры X86, так и для X64) void  * getTIB ()  { #ifdef _M_IX86  return  ( void  * ) __readfsdword ( 0x18 ); #elif _M_AMD64  return  ( void  * ) __readgsqword ( 0x30 ); #else #error неподдерживаемый архитектура #endif }

См. Также [ править ]

  • Структурированная обработка исключений

Ссылки [ править ]

  1. ^ a b Пьетрек, Мэтт (май 1996 г.). «Под капотом» . Журнал Microsoft Systems . Архивировано из оригинала на 2009-06-14 . Проверено 7 июля 2010 . CS1 maint: обескураженный параметр ( ссылка )
  2. ^ a b c d "вино winternl.h: typedef struct _TEB" . GitHub . вино-зеркало. 29 октября 2019.
  3. ^ Чапелл, Джефф. «ТЭБ» .
  4. ^ "Функция NtCurrentTeb" . Документы Microsoft . Проверено 20 ноября 2019 года . CS1 maint: обескураженный параметр ( ссылка )

Дальнейшее чтение [ править ]

  • Пьетрек, Мэтт (март 1996). Секреты программирования Windows 95 (pdf) . IDG. С.  136–138 . ISBN 978-1-56884-318-6. Проверено 17 июля 2010 . CS1 maint: обескураженный параметр ( ссылка )

Внешние ссылки [ править ]

  • Макет TEB на NTinternals.net
  • Структурированная обработка исключений и TIB
  • Описание первых слотов БИБ
  • Описание TEB, поле за полем
  • Определения TEB для различных версий Windows