string val_str;
int val_int;
int state = 0;
while (1) {
switch(state) {
case 0:
if (*in >= 'a' && *in <= 'z') {
val_str = *(in++);
state = 1;
} else if (*in >= '0' && *in <= '9') {
val_int = *(in++)-'0';
state = 2;
} else if (*in == '=') {
in++;
return (ASSIGN, NULL);
}
else
return (EOT, NULL);
break;
case 1:
if ((*in >= 'a' && *in <= 'z') || (*in >= '0' && *in <= '9')
val_str += *(in++);
else
return (IDENT, val_str);
break;
case 2:
if (*in >= '0' && *in <= '9')
val_int = val_int*10+(*(in++)-'0');
else
return (INTEGER, val_int);
break;
}
}
Прочитать 2 байта по смещению 0, убедиться, что записано 'MZ'.
Прочитать DWORD по смещению 0x3C от начала exe-файла, получим смещение PE-заголовка (PE_offset).
Прочитать 4 байта по смещению PE_offset, убедиться что записано 'PE\0\0'.
Прочитать WORD по смещению PE_offset+0x6, получим количество секций NumberOfSections.
Прочитать WORD по смещению PE_offset+0x14, получим размер необязательного заголовка SizeOfOptionalHeader.
Начало заголовков секций StartOfSectionHeaders = PE_offset+0x18+SizeOfOptionalHeader.
Для sectionNumber от 0 до NumberOfSections-1 {
Прочитать DWORD по смещению StartOfSectionHeaders+sectionNumber*0x28+0x24, получим атрибуты секции Characteristic.
Если в Characteristic не установлен бит 0x40, то секция не содержит инициализированные переменные - переходим к следующей секции.
Прочитать DWORD по смещению StartOfSectionHeaders+sectionNumber*0x28+0x10, получим длину секции в файле SizeOfRawData.
Прочитать DWORD по смещению StartOfSectionHeaders+sectionNumber*0x28+0x14, получим смещение секции в файле PointerToRawData.
Прочитать SizeOfRawData по смещению PointerToRawData - это и есть инициализированные глобальные переменные, текстовые константы и, возможно, вещественные константы.
}