Это будет почти невозможно. Продолжайте читать, почему.
Компилятор будет выигрывать эту игру каждый раз ...
Компиляция одного и того же проекта два раза подряд, даже без внесения каких-либо изменений в исходный код или настройки проекта, всегда будет приводить к разным исполняемым файлам.
Одна из причин этого заключается в том, что формат PE (Portable Executable), который Windows использует для файлов EXE, включает в себя временную метку, указывающую дату и время создания EXE-файла, которая обновляется компилятором VB6 при каждой сборке проекта. Помимо «основной» временной метки для EXE-файла в целом, каждый каталог ресурсов в EXE-файле (где в EXE-файле хранятся значки, растровые изображения, строки и т. Д.) Также имеет временную метку, которую компилятор также обновляет при создании новой версии. EXE. В дополнение к этому, файлы EXE также имеют поле контрольной суммы, которое компилятор пересчитывает на основе необработанного двоичного содержимого EXE. Поскольку временные метки обновляются до текущей даты / времени, контрольная сумма для EXE также будет меняться при каждой перекомпиляции проекта.
Но, но ... Я нашел этот действительно крутой инструмент редактирования EXE, который может отменить эту хитрость компилятора!
Существуют инструменты редактирования EXE, такие как PE Explorer , которые утверждают, что могут устанавливать все временные метки в файле EXE на фиксированное время. На первый взгляд вы можете подумать, что можете просто установить временные метки в двух копиях EXE на одну и ту же дату и получить эквивалентные файлы (при условии, что они были созданы из одного и того же исходного кода), но все сложнее: Компилятор может свободно записывать ресурсы (строки, значки, информацию о версии файла и т. д.) каждый раз, когда вы компилируете код, и вы не можете предотвратить это. Ресурсы хранятся в виде независимых «порций» данных, которые можно переставить в результирующем EXE-файле, не влияя на поведение программы во время выполнения.
Если этого недостаточно, возможно, компилятор создает файл EXE в области неинициализированной памяти, поэтому некоторые части EXE-файла могут содержать кусочки того, что было в памяти во время работы компилятора, создавая еще больше различий.
Что касается MD5 ...
Вы не ошиблись в понимании хеширования MD5: MD5 будет всегда давать один и тот же хеш при одинаковом вводе. Проблема здесь в том, что входные данные в этом случае (файлы EXE) постоянно меняются.
Вывод: контроль источников - ваш друг
Что касается решения вашей текущей дилеммы, я оставлю вас с этим: ассоциирование конкретного EXE-файла с конкретной версией исходного кода - это скорее вопрос политики, который должен быть как-то реализован, чем что-либо еще. Попытка выяснить, какой EXE-файл пришел из какой версии без какого-либо контекста, просто не будет надежной. Вы должны отслеживать это с помощью других инструментов. Например, убедитесь, что каждая сборка создает свой номер версии для вашего EXE-файла, и что эта версия может быть легко сопряжена с определенной ревизией / branch / tag / что угодно в вашей системе управления версиями. С этой целью в «бесплатной для всех» ситуации, когда некоторые разработчики используют контроль исходного кода, а другие используют «ту копию исходного кода 1997 года, которую я храню в своей сетевой папке, потому что это мой код В любом случае, контроль за исходными кодами для сестер не поможет. Я хотел бы, чтобы все пили исходный код Kool-Aid и придерживались стандартной политики для создания сборок сразу.
Всякий раз, когда мы собираем проекты, наш сервер сборки (мы используем Hudson ) гарантирует, что скомпилированная версия EXE обновляется и включает текущий номер сборки (мы используем плагин Version Number и пользовательский скрипт сборки для этого), и когда мы выпускаем сборку, мы создаем тег в Subversion, используя номер версии в качестве имени тега. Сервер сборки архивирует выпускаемые сборки, поэтому мы всегда можем получить конкретный EXE (и программу установки), которые были переданы клиенту. Для внутреннего тестирования мы можем выбрать извлечение заархивированного EXE-файла с сервера сборки или просто указать серверу сборки перестроить EXE из тега, который мы создали в Subversion.
Мы также никогда не выпускаем двоичные файлы для QA или для клиентов с любого компьютера, кроме сервера сборки. Это предотвращает ошибки «работает на моей машине» и гарантирует, что мы всегда компилируем из «известной» копии исходного кода (он только извлекает и собирает код, который находится в нашем хранилище Subversion), и что мы всегда можем связать данный двоичный файл с точной версией кода, из которого он был создан.