Blog. Just Blog

Работа с GUID на Ассемблере

Версия для печати Добавить в Избранное Отправить на E-Mail | Категория: Образ мышления: Assembler | Автор: ManHunter
Работа с GUID на Ассемблере
Работа с GUID на Ассемблере

GUID (Глобальный уникальный идентификатор) - это 128-битное значение, представленное в виде 32 шестнадцатеричных символов, разделенных дефисами на пять блоков. Формат стандартизирован для обеспечения читаемости, компактности и кроссплатформенной совместимости. Структура классического формата: 8-4-4-4-12 символов. Каждый блок содержит цифры и буквы латинского алфавита от A до F. Такая организация позволяет генерировать практически уникальные идентификаторы, что делает GUID надежным ключом для объектов и данных в различных областях программирования.

Причины выбора формата заключаются в том, что представление GUID с дефисами было принято в рамках технологий OLE/COM от Microsoft, где важна читаемость при отладке и хранении значений в текстовом виде (например, в реестре Windows). Шестнадцатеричная запись с разделителями упрощает визуальный контроль, снижает вероятность ошибок при ручном копировании и облегчает сравнение строк. Фиксированная длина (128 бит) обеспечивает теоретически огромное адресное пространство - порядка 2128 возможных значений, что делает коллизии практически невозможными при корректной генерации. Такой текстовый формат оказался удобен для логирования, конфигурационных файлов и текстовых протоколов, что способствовало его широкому распространению. Хотя изначально формат использовался в реализации Microsoft (GUID), он был стандартизирован как UUID в спецификации RFC 4122, где закреплен канонический вид записи: 8-4-4-4-12 шестнадцатеричных символов, разделенных дефисами (например, 550e8400-e29b-41d4-a716-446655440000). Сегодня этот формат стал де-факто стандартом для представления 128-битных уникальных идентификаторов.

Хотя на первый взгляд GUID может восприниматься как случайная последовательность, его структура содержит служебные поля. В каноническом представлении:

xxxxxxxx-xxxx-Mxxx-Nxxx-xxxxxxxxxxxx
символ M (14-я позиция в строке, нумерация с 0) кодирует версию алгоритма генерации (4 бита), а символ N (19-я позиция) - вариант формата (старшие биты поля варианта). Например, в UUID 550e8400-e29b-41d4-a716-446655440000 значение "4" в позиции M указывает на версию 4 (генерация на основе случайных чисел), а значение "A" (бинарно 10xx) в позиции N соответствует варианту 1 по спецификации RFC 4122. Можете изучить какой-нибудь GUID или попробовать самостоятельно сделать валидный GUID. Для удобства можете использовать мою программу GUID Helper.

Теперь перейдем к программированию. Как я и обещал, мы будем использовать Ассемблер. Для удобства работы с GUID применяется следующая структура:
  1. ; Структура GUID (RFC 4122 / Windows)
  2. struct GUID
  3.     Data1 dd ?        ; 4 байта (32 бита)
  4.     Data2 dw ?        ; 2 байта (16 бит)
  5.     Data3 dw ?        ; 2 байта (16 бит)
  6.     Data4 db 8 dup(?) ; 8 байт (64 бита)
  7. ends
Начнем с проверки GUID. В структуре GUID поле версии занимает старшие 4 бита поля Data3 (смещение +6 в бинарном представлении). Это соответствует 14-й позиции в строковом формате xxxxxxxx-xxxx-Mxxx-xxxx-xxxxxxxxxxxx, где символ M отражает значение версии. Для извлечения версии из бинарного представления необходимо: загрузить 16-битное значение Data3, сдвинуть его вправо на 12 бит - останутся только биты версии (15-12), полученное 4-битное значение интерпретировать согласно спецификации RFC 4122:
  1.         ; my_guid - данные для работы с GUID
  2.  
  3.         ; Загружаем Data3 (смещение 6)
  4.         movzx   eax,word[my_guid.Data3]
  5.         ; Сдвигаем вправо на 12 бит, остаются биты 15-12
  6.         shr     eax,12
  7.  
  8.         ; EAX определяет версию
  9.         ; 0 -> Nil GUID (00000000-0000-0000-0000-000000000000)
  10.         ; 1 -> Time-based (на основе временной метки и MAC-адреса)
  11.         ; 2 -> DCE Security (устаревший, с UID домена)
  12.         ; 3 -> Name-based с хешем MD5
  13.         ; 4 -> Random (на основе криптографически стойких случайных чисел)
  14.         ; 5 -> Name-based с хешем SHA-1
  15.    &n