Рассмотрим простую программу:
#define kHiddenNumber 1234567
int main(void)
{
int i = kHiddenNumber;
return(i & 0xFF);
}
Скомпилируйте это:
gcc -o xx xx.c
Обратите внимание, что 1234567 10 = 0x12D687
Теперь напечатайте программу в шестнадцатеричном формате и найдите D6:
$ od -x xx | grep d6
0002700 6d65 422e 642e 6c79 6269 0000 0000 0000
0007460 45c7 87fc 12d6 0f00 45b6 c9fc 00c3 25ff
0020140 7265 4700 705f 6f72 6e67 6d61 0065 026c
$
Вы можете увидеть 0x12D687 там, в средней строке вывода. Это в забавном формате, но, тем не менее, присутствует в коде. Обратите внимание, что компиляция не была оптимизирована. Когда программа оптимизирована, свидетельство теряется - возможно, потому, что константа используется в таком простом контексте, что «i» можно оптимизировать, а возвращаемое выражение уменьшить до значения 0x87. Байт 0x87 появляется в оптимизированном коде примерно в одном и том же месте оптимизированной версии - вам нужно выполнить правильную работу по разборке, чтобы доказать, что это был последний байт значения, хотя я считаю его вероятным.
$ od -x xx | grep -i d6
0002320 e500 60d6 fdf5 ee77 10b8 e3d5 5834 7377
0002700 6d65 422e 642e 6c79 6269 0000 0000 0000
0020140 7265 4700 705f 6f72 6e67 6d61 0065 026c
$ od -x xx | grep -i 87
0007460 0000 f400 4855 e589 87b8 0000 c900 00c3
$
В более сложных программах - где «i» было передано функции (возможно, «printf ()»), оптимизация не может быть выполнена.
Следовательно, вы не можете полагаться на то, что компилятор скрывает значение. Название для значения будет отсутствовать, скорее всего. Но это значение вполне может присутствовать в найденной программе.
Между прочим, иногда вы можете найти ключи шифрования похожим - хотя и более сложным способом. Данные слишком случайные, чтобы быть естественными - поэтому они выделяются, как больной палец в программе.