У меня есть exe файл, и я декомпилировал его с помощью Ida. Мне сказали, что программа закодирована в Delphi, поэтому я попытался декомпилировать с DeDe, но это не удалось, никакого вывода и ошибок. И мне интересно, можно ли найти язык, используемый при создании exe, попробовав разные декомпиляторы, написанные специально для языка программирования? Или они могут потерпеть неудачу по другой причине?
Можно ли узнать, на каком языке написан exe файл?
Ответ 1
Во многих случаях можно идентифицировать компилятор, используемый для компиляции кода, и из этого исходного языка.
Большинство языковых реализаций включают некоторую библиотеку времени выполнения для реализации различных операций на высоком уровне языка. Например, C имеет CRT, который реализует операции ввода-вывода файлов (fopen
, fread
и т.д.), Delphi имеет помощники компилятора для своего типа string
(конкатенация, назначение и другие), ADA имеет различные низкоуровневые функции обеспечения безопасности языка и т.д. Сравнивая код программы и библиотеки времени исполнения компиляторов-кандидатов, вы можете найти совпадение.
IDA реализует этот подход в технологии FLIRT. Используя сигнатуры, IDA может определить большинство основных компиляторов для DOS и Windows. Это несколько сложнее для Linux, потому что для него нет единого поставщика бинарных файлов компилятора, поэтому для каждого дистрибутива необходимо будет подписывать.
Однако, даже прибегая к использованию кода библиотеки времени выполнения, может быть возможно определить используемый компилятор. Многие компиляторы используют очень четкие идиомы для представления различных операций. Например, я смог угадать, что компилятором, используемым для вируса Duqu, был Visual С++, который позже был подтвержден .
Ответ 2
Компиляция - это процесс с потерями, поэтому вообще невозможно декомпилировать исполняемый файл (или другой скомпилированный программный модуль, например .so
или .dll
), и восстановить исходный код на языке оригинала или даже недвусмысленно определить, что такое исходный язык. Даже не обязательно, что существует только один исходный язык исходного кода, поскольку возможно, что перед связыванием разные модули были написаны на разных языках. Обычно вы можете дизассемблировать двоичный файл и восстановить язык ассемблера, хотя это может быть очень ограниченным.
Во многих случаях вы можете что-то сказать об исходном языке при условии, что двоичный файл не был удален (из символов). Например, вы обычно можете сказать, был ли бинарный файл изначально написан на С++, просмотрев символы в двоичном формате (в Linux, используя objdump
, не знаю, что эквивалент может быть в Windows): символы С++ искажены в определенном путь. Это не 100% гарантия, а высокая вероятность.
Тем не менее, некоторые декомпиляторы делают довольно разумную работу по очень сложной задаче. Вывод вероятных высокоуровневых конструкций из двоичного файла непросто. В моем (очень ограниченном) опыте они, как правило, работают для довольно тривиальных программ или для программного обеспечения, составленного с узким диапазоном версий исходного компилятора, но задыхаются от чего-либо существенного: автору декомпилятора очень сложно идти в ногу с изменения в компиляторах, и для нее может быть очень мало стимулов сделать это.
Даже в тех случаях, когда декомпиляция очень успешна, результатом является, по существу, полностью раскоментированный код с бессмысленными именами переменных, которые чрезвычайно трудно понять. Декомпиляция - это одно, а извлечение намеченного семантического значения из результата - другое. Помните, что многие переменные, ветки, петли и функции будут полностью оптимизированы, многие функции будут встроены и т.д. Таким образом, "исходный код", даже если вы можете получить его таким образом, может быть не совсем использования для вас.