Защита программ
Доброкачественность
Правдивая реклама, доступность результатов независимой экспертизы, доступность информации о побочных эффектах, полная информация о СЗ для конечного пользователя.В целом, общая картина взаимодействия агентов рынка программного обеспечения может быть представлена на схеме на
Из четырёх указанных выше видов среды взаимодействия защищающейся стороне подконтрольны (или частично подконтрольны) три вида - организационная, техническая и экономическая среда. По нашему мнению, важнейшей средой взаимодействия является экономическая среда, так как экономическое взаимодействие, в данном случае, является первопричиной и целью всего взаимодействия. При разработке и анализе защиты программного обеспечения необходимо учитывать существующую законодательную базу, при этом нужно проводить подробный экономический анализ ситуации, применяя различные критерии оценки, а затем создавать стратегию защиты, включающую применение технических и организационных мер защиты программного обеспечения.
Использованная литература:
D. Hsiao, D. Kerr, S. Madnick "Computer Security" Academic Press, 1979.
Г. А. Черней, С. А. Охрименко, Ф. С. Ляху Ruxanda, 1996.
Pavel V. Semjanov
С. Середа
Экономические
Соотношение потерь от пиратства и общего объёма прибыли, соотношение потерь от пиратства и стоимости СЗПО и её внедрения, соотношение стоимости ПО и стоимости СЗПО, соответствие стоимости СЗПО и её внедрения поставленным целям.Неудобства для конечного пользователя ПО
Необходимость и сложность дополнительной настройки системы защиты, доступность документации, доступность информации об обновлении модулей системы защиты из-за ошибок/несовместимости/нестойкости, доступность сервисных пакетов, безопасность сетевой передачи пароля/ключа, задержка из-за физической передачи пароля/ключа, нарушения прав потребителя.Независимость от конкретных реализаций ОС
Использование недокументированных возможностей, "вирусных" технологий и "дыр" ОСОценка эффективности систем защиты программного обеспечения
, Движение ПОтребительРассматривается комплекс вопросов, связанных с исследованием систем защиты программного обеспечения (ПО). Проведен анализ существующих средств и методов защиты ПО. Разработан и предложен ряд критериев оценки эффективности систем защиты ПО.
Системы защиты ПО широко распространены и находятся в постоянном развитии, благодаря расширению рынка ПО и телекоммуникационных технологий. Необходимость использования систем защиты (СЗ) ПО обусловлена рядом проблем, среди которых следует выделить: незаконное использование алгоритмов, являющихся интеллектуальной собственностью автора, при написании аналогов продукта (промышленный шпионаж); несанкционированное использование ПО (кража и копирование); несанкционированная модификация ПО с целью внедрения программных злоупотреблений; незаконное распространение и сбыт ПО (пиратство).
Существующие системы защиты программного обеспечения можно классифицировать по ряду признаков, среди которых можно выделить метод установки, используемые механизмы защиты и принцип функционирования.
Системы защиты ПО по методу установки можно подразделить на системы, устанавливаемые на скомпилированные модули ПО; системы, встраиваемые в исходный код ПО до компиляции; и комбинированные.
Системы первого типа наиболее удобны для производителя ПО, так как легко можно защитить уже полностью готовое и оттестированное ПО (обычно процесс установки защиты максимально автоматизирован и сводится к указанию имени защищаемого файла и нажатию "Enter"), а потому и наиболее популярны. В то же время стойкость этих систем достаточно низка (в зависимости от принципа действия СЗ), так как для обхода защиты достаточно определить точку завершения работы "конверта" защиты и передачи управления защищенной программе, а затем принудительно ее сохранить в незащищенном виде.
Системы второго типа неудобны для производителя ПО, так как возникает необходимость обучать персонал работе с программным интерфейсом (API) системы защиты с вытекающими отсюда денежными и временными затратами.
Кроме того, усложняется процесс тестирования ПО и снижается его надежность, так как кроме самого ПО ошибки может содержать API системы защиты или процедуры, его использующие. Но такие системы являются более стойкими к атакам, потому что здесь исчезает четкая граница между системой защиты и как таковым ПО.
Наиболее живучими являются комбинированные системы защиты. Сохраняя достоинства и недостатки систем второго типа, они максимально затрудняют анализ и дезактивацию своих алгоритмов.
По используемым механизмам защиты СЗ можно классифицировать на: системы, использующие сложные логические механизмы; системы, использующие шифрование защищаемого ПО; и комбинированные системы.
Системы первого типа используют различные методы и приёмы, ориентированные на затруднение дизассемблирования, отладки и анализа алгоритма СЗ и защищаемого ПО. Этот тип СЗ наименее стоек к атакам, так как для преодоления защиты достаточно проанализировать логику процедур проверки и должным образом их модифицировать.
Более стойкими являются системы второго типа. Для дезактивации таких защит необходимо определение ключа дешифрации ПО.
Самыми стойкими к атакам являются комбинированные системы.
Для защиты ПО используется ряд методов, таких как:
В свою очередь злоумышленники так же применяют ряд методов и средств для нарушения систем защиты. Ситуация противостояния разработчиков СЗПО и злоумышленников постоянно изменяется за счет комбинирования уже известных методов защиты и нападения, а так же за счет создания и использования новых методов.
В целом это взаимодействие может быть описано схемой на По принципу функционирования СЗ можно подразделить на упаковщики/шифраторы; СЗ от несанкционированного копирования и СЗ от несанкционированного доступа (НСД).
Организационные
Распространённость и популярность ПО, условия распространения и использования ПО, уникальность ПО, наличие угроз, вероятность превращения пользователя в злоумышленника, роль документации и поддержки при использовании ПО.Отказоустойчивость (надёжность)
Вероятность отказа защиты (НСД), время наработки на отказ, вероятность отказа программы защиты (крах), время наработки на отказ, частота ложных срабатываний.Парольные защиты
Этот класс СЗПО, на сегодняшний день, является самым распространённым. Основной принцип работы данных систем заключается в идентификации и аутентификации пользователя ПО путём запроса дополнительных данных, это могут быть название фирмы и/или имя и фамилия пользователя и его пароль либо только пароль/регистрационный код. Эта информация может запрашиваться в различных ситуациях, например, при старте программы, по истечении срока бесплатного использования ПО, при вызове процедуры регистрации либо в процессе установки на ПК пользователя. Процедуры парольной защиты просты в реализации и, поэтому, очень часто применяются производителями ПО. Большинство парольных СЗПО использует логические механизмы, сводящиеся к проверке правильности пароля/кода и запуске или не запуске ПО, в зависимости от результатов проверки. Существуют так же системы, шифрующие защищаемое ПО и использующие пароль или производную от него величину как ключ дешифрации, большинство таких систем использует слабые или простейшие алгоритмы шифрования, нестойкие к направленным атакам. Это происходит из-за сложности корректной реализации стойких криптоалгоритмов и нецелесообразности их применения для защиты недорогих условно-бесплатных программных продуктов, составляющих большинство ПО, использующего парольные защиты. Лишь в последнее время разработаны парольные СЗПО, реализующие стойкие криптоалгоритмы типа DES и RSA, они реализованы в виде защитного модуля и вспомогательных библиотек и устанавливаются на уже скомпилированные модули ПО.Слабым звеном парольных защит является блок проверки правильности введённого пароля/кода. Для такой проверки можно сравнивать введённый пароль с записанным в коде ПО правильным либо с правильно сгенерированным из введённых дополнительных данных паролем. Возможно так же сравнение производных величин от введённого и правильного паролей, например их ХЭШ-функций, в таком случае в коде можно сохранять только производную величину, что повышает стойкость защиты. Путём анализа процедур проверки можно найти реальный пароль, записанный в коде ПО, найти правильно сгенерированный пароль из введённых данных либо создать программу для перебора паролей для определения пароля с нужной ХЭШ-суммой.
Кроме того, если СЗПО не использует шифрования, достаточно лишь принудительно изменить логику проверки для получения беспрепятственного доступа к ПО.
Шифрующие системы более стойки к атакам, но при использовании простейших или некорректно реализованных криптоалгоритмов есть опасность дешифрации ПО.
Для всех парольных систем существует угроза перехвата пароля при его вводе авторизованным пользователем. Кроме того, в большинстве СЗПО данного типа процедура проверки используется лишь единожды, обычно при регистрации или установке ПО, затем система защиты просто отключается, что создаёт реальную угрозу для НСД при незаконном копировании ПО.
Положительные стороны:
Отрицательные стороны:
Побочные эффекты
Перегрузка траффика, отказ в обслуживании, замедление работы защищаемого ПО, замедление работы ОС, захват системных ресурсов, перегрузка ОЗУ, нарушение стабильности ОС.Программно-аппаратные средства защиты ПО с электронными ключами
Этот класс СЗПО в последнее время приобретает все большую популярность среди производителей программного обеспечения (ПО). Под программно-аппаратными средствами защиты, в данном случае, понимаются средства, основанные на использовании так называемых "аппаратных (электронных) ключей". Электронный ключ - это аппаратная часть системы защиты, представляющая собой плату с микросхемами памяти и, в некоторых случаях, микропроцессором, помещенную в корпус и предназначенную для установки в один из стандартных портов ПК (COMM, LPT, PCMCIA, USB ... ) или слот расширения материнской платы. Так же в качестве такого устройства могут использоваться СМАРТ-карты. По результатам проведенного анализа, программно-аппаратные средства защиты в настоящий момент являются одними из самых стойких систем защиты ПО от НСД.Электронные ключи по архитектуре можно подразделить на ключи с памятью
(без микропроцессора) и ключи с микропроцессором (и памятью).
Наименее стойкими (в зависимости от типа программной части) являются системы с аппаратной частью первого типа. В таких системах критическая информация (ключ дешифрации, таблица переходов) хранится в памяти электронного ключа. Для дезактивации таких защит в большинстве случаев необходимо наличие у злоумышленника аппаратной части системы защиты (основная методика: перехват диалога между программной и аппаратной частями для доступа к критической информации).
Самыми стойкими являются системы с аппаратной частью второго типа. Такие комплексы содержат в аппаратной части не только ключ дешифрации, но и блоки шифрации/дешифрации данных, таким образом при работе защиты в электронный ключ передаются блоки зашифрованной информации, а принимаются оттуда расшифрованные данные. В системах этого типа достаточно сложно перехватить ключ дешифрации так как все процедуры выполняются аппаратной частью, но остается возможность принудительного сохранения защищенной программы в открытом виде после отработки системы защиты. Кроме того, к ним применимы методы криптоанализа.
Положительные факторы:
Отрицательные факторы:
Системы "привязки" ПО
Системы этого типа при установке ПО на ПК пользователя осуществляют поиск уникальных признаков компьютерной системы либо они устанавливаются самой системой защиты. После этого модуль защиты в самом ПО настраивается на поиск и идентификацию данных признаков, по которым в дальнейшем определяется авторизованное или неавторизованное использование ПО. При этом возможно применение методик оценки скоростных и иных показателей процессора, материнской платы, дополнительных устройств, ОС, чтение/запись в микросхемы энергонезависимой памяти, запись скрытых файлов, настройка на наиболее часто встречаемую карту использования ОЗУ и т.п.Слабым звеном таких защит является тот факт, что на ПК пользователя ПО всегда запускается на выполнение, что приводит к возможности принудительного сохранения ПО после отработки системы защиты, исследование самой защиты и выявление данных, используемым СЗПО для аутентификации ПК пользователя.
Положительные факторы:
Отрицательные факторы:
Совместимость
Отсутствие конфликтов с системным ПО, отсутствие конфликтов с прикладным ПО, отсутствие конфликтов с существующим АО, максимальная совместимость с будущим АО и ПО.Средства защиты ПО с "ключевыми дисками"
В настоящий момент этот тип систем защиты мало распространён, ввиду его морального устаревания. СЗПО этого типа во многом аналогичны системам с электронными ключами, но здесь критическая информация хранится на специальном, ключевом, носителе. Так же много общего есть и с системами защиты от копирования, так как используются те же методы работы с ключевым носителем.Основной угрозой для таких СЗПО является перехват считывания критической информации, а так же незаконное копирование ключевого носителя.
Положительные и отрицательные стороны данного типа СЗПО практически полностью совпадают с таковыми у систем с электронными ключами:
Положительные факторы:
Отрицательные факторы:
Необходимо отметить, что пользователем явно ощущаются лишь отрицательные стороны систем защит. А производители ПО рассматривают только относящиеся к ним "плюсы" и "минусы" систем защиты и практически не рассматривают факторы, относящиеся к конечному потребителю.
По результатам исследования был разработан набор показателей применимости и критериев оценки СЗПО.
Стоимость
Стоимость/эффективность, стоимость/цена защищаемого ПО, стоимость/ликвидированные убытки.Стойкость к исследованию/взлому
Применение стандартных механизмов, новые/нестандартные механизмыСЗ от несанкционированного копирования
СЗ от несанкционированного копирования осуществляют "привязку" ПО к дистрибутивному носителю (гибкий диск, CD ...). Данный тип защит основывается на глубоком изучении работы контроллеров накопителей, их физических показателей, нестандартных режимов разбивки, чтения/записи и т.п. При этом на физическом уровне создаётся дистрибутивный носитель, обладающий (предположительно) неповторимыми свойствами (обычно это достигается при помощи нестандартной разметки носителя информации или/и записи на него дополнительной информации - пароля или метки), а на программном - создаётся модуль, настроенный на идентификацию и аутентификацию носителя по его уникальным свойствам. При этом возможно применение приёмов, используемых упаковщиками/шифраторами.Положительные факторы:
Отрицательные факторы:
СЗ от НСД
СЗ от НСД осуществляют предварительную или периодическую аутентификацию пользователя ПО или его компьютерной системы путём запроса дополнительной информации. К этому типу СЗ можно отнести системы парольной защиты ПО, системы "привязки" ПО к компьютеру пользователя, системы с " ключевыми дисками" и аппаратно-программные системы с электронными ключами. В первом случае "ключевую" информацию вводит пользователь, во втором - она содержится в уникальных параметрах компьютерной системы пользователя, в третьем - она хранится на диске и в четвертом случае "ключевая" информация считывается с микросхем электронного ключа.Технические
Соответствие СЗПО функциональным требованиям производителя ПО и требованиям по стойкости, системные требования ПО и системные требования СЗПО, объём ПО и объём СЗПО, функциональная направленность ПО, наличие и тип СЗ у аналогов ПО - конкурентов.Упаковщики/шифраторы
Первоначально, основной целью упаковщиков/шифраторов являлось уменьшение объема исполняемого модуля на диске без ущерба для функциональности программы, но позднее на первый план вышла цель защиты ПО от анализа его алгоритмов и несанкционированной модификации. Для достижения этого используются алгоритмы компрессии данных; приёмы, связанные с использованием недокументированных особенностей операционных систем (ОС) и процессоров; шифрование данных, алгоритмы мутации, запутывание логики программы, приведение ОС в нестабильное состояние на время работы ПО и др.Положительные стороны:
Отрицательные стороны:
Защита как таковая
Затруднение нелегального копирования, затруднение нелегального доступа, защита от мониторинга, отсутствие логических брешей и ошибок в реализации системы.Защита программ
Анализ средств преодоления систем защиты программного обеспечения
, Движение ПОтребительВ работе рассмотрены вопросы анализа и классификации средств преодоления систем программной защиты ПО. Приведены функциональные возможности и способ применения конкретных видов программных средств. Описаны угрозы системам защиты ПО. По результатам проведенного анализа предметной области сделаны общие выводы о характере применения систем защиты ПО.
Проблемы защиты авторских прав на программное обеспечение в области контроля над его использованием и дальнейшим распространением в настоящее время принято решать при помощи программно-технических средств - систем защиты ПО. Анализ и классификация подобных средств приводятся в [ и др.]. В то же время для обхода и отключения подобных систем защиты существует множество инструментальных средств. Возникает задача сопоставить возможности средств защиты ПО (СЗПО) с возможностями средств их преодоления. Результаты такого анализа будут полезны для оценки рисков при производстве программных продуктов, а так же планировании и оценке уровня стойкости систем защиты ПО.
В рамках исследования проблем защиты программного обеспечения можно рассматривать три следующих глобальных вопроса:
1. Что защищать?
Вопрос связан с классификацией ПО и оценкой возможностей по защите ПО.
2. Как защищать?
Вопрос связан с анализом и классификацией мер и средств защиты ПО.
3. От чего защищать?
Вопрос связан с анализом и классификацией угроз ПО и средств их реализации.
Если первые два вопроса в настоящее время освещены хотя бы частично, третий вопрос представляет собой серьезное "белое пятно" в области исследований в сфере защиты ПО, хотя определенные исследования по этой теме велись []. С другой стороны, без четкого понимания угроз безопасности ПО и возможностей средств реализации подобных угроз сложно вообще говорить об эффективной защите программного обеспечения, что подтверждается существующей практикой в области защиты информационных систем. Следовательно, для серьезного исследования вопросов защиты ПО необходимо осуществить анализ и классификацию средств реализации атак на программное обеспечение.
Данная работа является попыткой осветить вышеописанные вопросы и рассматривает технические (программные) средства преодоления СЗПО.
Следует сразу отметить, что лишь малая часть из рассматриваемых типов программного обеспечения является специфическими программными средствами, предназначенными для несанкционированного отключения систем защиты ПО. Большинство же указанных средств относится к системному программному обеспечению и рассматривается как "инструментарий злоумышленника" в силу двойственности технологий.
В настоящее время существуют лишь неформальные классификации средств преодоления СЗПО, они основываются на традиционно сложившемся разделении программных средств в предметной области и в силу этого являются не совсем полными и частично противоречивыми.
В данной работе предлагается классификация по функциональному признаку (она частично совпадает с "традиционной" классификацией средств преодоления СЗПО), в ее рамках средства упорядочены по степени сложности и стадии анализа исследуемого ПО.
Программы-каталогизаторы, или файловые оболочки ОС.
В стандартные возможности таких программ входят функции просмотра атрибутов файлов (тип, дата создания/модификации, размер, флаги доступа и др.), подсчета их количества и общего объема в каталоге приложения, просмотра файлов и т.п. При помощи этого типа программных средств, как правило, реализуется предварительный анализ защищенных продуктов и первичная локализация СЗПО.Примером подобного использования может быть сравнение дат создания всех файлов в каталоге установленного приложения (или системном каталоге). В случае использования системой защиты каких-либо динамических библиотек разница в датах их создания позволит легко локализовать файлы, относящиеся к СЗПО (как правило, даты создания "рабочих" файлов пакета совпадают, дата создания модулей СЗПО отличается от них, так как СЗПО часто поставляются отдельно как внешняя библиотека).
Аналогичным же образом локализуются и файлы, хранящие счетчики количества запусков ПО, даты этих файлов постоянно обновляются. А при помощи обычного текстового просмотра объектного модуля можно довольно легко определить тип и производителя СЗПО, так как обычно эта информация включается в тело защищенного модуля самой СЗПО.
Программы копирования областей ОЗУ в ВЗУ (Memory Dumpers)
Указанный тип программных средств предназначен для сохранения областей оперативной памяти, в том числе памяти выполняемых программ, на диск. В рамках исследования СЗПО данные средства позволяют произвести принудительное сохранение образа памяти защищенного приложения.В случае использования механизмов шифрования/упаковки объектного кода защищаемого ПО, сохранение памяти активного процесса ОС позволяет получить копию (незначительно модифицированного загрузчиком ОС) кода защищаемого ПО в "открытом виде". В результате таких действий возможно либо сразу получить экземпляр незащищенного программного продукта, либо получить важную для дальнейшего анализа СЗПО информацию.
Очень большое число "защищенных" программных продуктов представляет собой упакованные и/или зашифрованные объектные модули без какой-либо серьезной внутренней алгоритмической защиты ПО.
Программы - мониторы активных задач, процессов, потоков и окон (Process/Windows Managers)
Указанный тип программных средств предназначен для отслеживания и управления объектами ОС (задачами, процессами, потоками, окнами и др.). Подобные программы обычно предоставляют возможности поиска необходимого объекта ОС, переключения на него управления, изменения его приоритета, уничтожения объекта, сохранения его параметров (а иногда и содержимого) на диске.Применение мониторов задач дает возможность производить анализ модульной структуры СЗПО. Подобный анализ позволяет выяснить подробности организации СЗПО во время ее работы. Список динамически загружаемых процессом библиотек, данные о количестве создаваемых и уничтожаемых приложением потоков и окон, поведение ППр при попытке принудительно завершить процесс, содержащий СЗПО, позволяют существенно дополнить картину анализа функционирования системы защиты.
Программы - мониторы файловой системы (File Monitors)
Этот тип ПО позволяет отслеживать изменения, происходящие в файловой системе при запуске определенных программ. В большинстве таких программ предусмотрена система фильтров для формирования протоколов работы отдельных приложений. При помощи данного типа средств реализуется анализ работы СЗПО с файлами.Например, подобные программы позволяют выяснить, что именно и где изменяют распознанные на этапах первичного и вторичного анализа модули СЗПО, либо определить модуль, производящий изменения в определенном файле. Эта информация позволяет точно локализовать счетчики количества запусков ПО, скрытые файлы систем "привязки" ПО, "ключевые файлы", файлы с информацией о функциях ПО, разрешенных для использования в рамках данной лицензии на продукт и т.п., а также модули и конкретные процедуры СЗПО, работающие с этими данными.
Программы - мониторы конвейеров
Средства данного типа предназначены для отслеживания сообщений, данных и вызовов подпрограмм, которыми обмениваются объекты ОС. Применение мониторов сообщений позволяет производить анализ межмодульного взаимодействия в рамках СЗПО (более специфично для ОС семейства Windows).В результате такого анализа получается информация о протоколах обмена данными между различными частями системы защиты, условиях ее срабатывания и отключения, динамике функционирования защиты.
Программы - мониторы обмена данными с системными устройствами (портами) (Port Monitors)
В современной архитектуре ОС доступ ко всем системным устройствам (их контроллерам) осуществляется через т.н. "порты ввода/вывода". Все современные ОС виртуализируют эти порты, организуя таким образом совместный доступ нескольких приложений к одному и тому же порту (используя механизм очереди), а также осуществляя контроль доступа к портам в целях обеспечения безопасности ОС. Использование этого типа программных средств позволяет проводить анализ взаимодействия СЗПО с системными устройствами. Контролируя доступ и обмен данными через порты ввода/вывода программной и аппаратной частей СЗПО, можно анализировать и преодолевать механизмы таких типов защит, как СЗПО с электронными ключами, СЗПО с ключевыми дисками и СЗПО "привязки" к ЭВМ пользователя. См.Программы - мониторы сетевого обмена данными (Network Traffic Monitors)
Рассматриваемый тип программ предназначен для отслеживания сетевой активности приложений в рамках ОС. Как правило, такие программы позволяют фильтровать/выделять приложения или сетевые соединения по вводимым критериям. Использование сетевых мониторов позволяет проводить анализ сетевого обмена СЗПО.Целый ряд современных программных продуктов реализует проверку аутентичности пользователя путем запроса данных о состоянии лицензии для данной рабочей станции с "сервера лицензий" в ЛВС. Также в последнее время появились программные продукты, проверяющие аутентичность пользователя или срок своего использования через Интернет. Кроме указанных видов ПО, существуют также условно бесплатные программные продукты (ППр), в которых временные или функциональные ограничения заменены обязательным просмотром рекламной информации, получаемой через Интернет. Отслеживая сетевой обмен подобных ППр, можно анализировать механизмы систем их защиты.
Программы - мониторы системных файлов ОС (Registry Monitors)
Программные средства этого типа предназначены для отслеживания изменений, вносимых приложениями в конфигурационные файлы ОС. В рассматриваемом контексте данные программы позволяют реализовать анализ работы СЗПО с системными файлами (более специфично для ОС семейства Windows).Рассматриваемые средства позволяют определять, работает ли СЗПО с файлами конфигурации ОС, какие изменения она туда вносит и какие данные использует. В результате подобного анализа становится возможным обнаружить скрытые счетчики количества запусков ПО, сохраненные даты первой установки ПО на ЭВМ пользователя, записи с лицензионными ограничениями функциональности ПО и т.п. Такой анализ дает результаты, подобные результатам анализа работы СЗПО с файлами.
Программы - мониторы вызовов подпрограмм ОС (API Monitors)
ПО этого типа предназначено для отслеживания вызова системных функций одним или несколькими приложениями с возможностью фильтрации/выделения групп отслеживаемых системных функций или приложений. Применение таких программ позволяет проводить анализ использования СЗПО системных функций.Учитывая, что все действия ПО (и СЗПО), связанные с работой с файловой системой, работой с конфигурацией ОС, реализацией диалога с пользователем, работой с сетью и многим другим, реализуются посредством вызова функций ОС. Анализ использования СЗПО системных функций позволяет довольно подробно изучить механизмы работы систем защиты, найти их слабые места и разработать пути их обхода.
Например, практически все современные системы защиты от копирования оптических дисков базируются на довольно небольшом наборе системных функций по работе с данным видом накопителей информации, отслеживание этих функций позволяет найти и нейтрализовать механизмы проверки типа носителя внутри СЗПО.
Программы перехвата и протоколирования клавиатурного ввода (Keyboard Loggers)
Данный тип программных средств предназначен для сохранения информации, введенной в ЭВМ с клавиатуры в специальные файлы протокола, возможна фильтрация сохраняемых данных по дополнительно вводимым критериям. "Клавиатурные шпионы" никак не связаны с анализом СЗПО, но предоставляют возможность осуществить незаконное получение ключа регистрации/пароля к ПО, защищенному парольной СЗПО.Программы побайтового копирования
Данный тип программных средств предназначен для создания максимально точных копий физической структуры носителей данных без учета их логической структуры. Обычно подобные программы предоставляют возможность сохранения таких "слепков" в виде файлов на диске. При помощи приведенного типа средств реализуется преодоление СЗПО от копирования, СЗПО с ключевыми дисками и СЗПО с "привязкой" к компьютерной системе пользователя (к жесткому диску).В настоящий момент чрезвычайно популярными являются СЗПО от копирования для компьютерных игр, распространяемых на оптических дисках формата CD и Sony PS. Не меньшей популярностью пользуются и средства побайтового копирования оптических дисков (для создания "пиратских" дисков) и средства сохранения содержимого оптических дисков в виде файлов на жестких дисках (для получения возможности использования ПО, не занимая накопитель).
Программы поиска файлов и текстовых и двоичных последовательностей в текстовых и двоичных файлах.
Данный тип программ позволяет производить поиск заданной последовательности (маски поиска) в одном или сразу нескольких файлах с выдачей результатов в виде списка смещений относительно начала файла, по которым был найден искомый фрагмент; а также всех файлов, удовлетворяющих определенному критерию или содержащих вышеописанную последовательность. При помощи указанных средств реализуется вторичный анализ СЗПО и локализация ключевых фрагментов СЗПО.Обычно средства файлового поиска используются для следующих целей: поиска известных сигнатур СЗПО в объектных модулях; поиска строк с сообщениями СЗПО (например, "Программа не зарегистрирована!" или "Спасибо за регистрацию!"), поиска файлов СЗПО с известными именами/сигнатурами.
Первый и последний виды использования рассматриваемого типа ПО ориентированы на отыскание стандартных элементов СЗПО, исследованных ранее и адаптации "типовых решений" к исследуемой версии СЗПО. Второй вид использования поисковых программ ориентирован на локализацию процедур СЗПО, отвечающих за идентификацию и аутентификацию легального пользователя ПО.
Большинство СЗПО реализует в процессе своей работы диалог с пользователем (как минимум на уровне сообщений об ошибках), локализация элементов этого диалога позволяет довольно легко локализовать "ядро" СЗПО, а иногда даже определить пароль легального пользователя.
Программы - распаковщики/дешифраторы (Unpackers/Decryptors)
Средства распаковки/дешифрации объектных модулей позволяют получать копии указанных модулей в том виде (или близком к таковому), в каком они были до их упаковки/шифрации. По функциональному содержанию эти программы близки к средствам сохранения областей ОЗУ на диске, но данный тип программных средств, во-первых, отличается высокой специализацией (то есть направленностью на какой-то один тип или класс средств упаковки/шифрации), а во-вторых, не всегда требует загрузки обрабатываемого объектного модуля в ОЗУ как процесса ОС.При использовании подобных программ реализуется преодоление СЗПО пакующего или шифрующего типа. Как правило, распаковка/дешифрация защищенных объектных модулей ПО производится для получения возможности более глубокого дальнейшего анализа СЗПО.
Программы симуляции аппаратных
Программы симуляции аппаратных средств предназначены для создания виртуальных устройств, необходимых для функционирования ПО типов, а также обеспечения доступа к ним как к реальной аппаратуре.Применение подобного ПО к защищенным программным продуктам делает возможным преодоление: СЗПО от копирования, СЗПО с электронными ключами, СЗПО с ключевыми дисками, СЗПО с "привязкой" к ЭВМ пользователя и СЗПО с ключевыми файлами и парольных СЗПО с авторизацией через сеть. Использование данного типа ПО также является совершенно легальным.
Программы восстановления удаленных файлов (Unerase/Undelete Utilities)
Подобные программные средства предназначены для восстановления файлов, которые были (ошибочно) удалены из доступной пользователю области файловой системы ОС и не были еще перезаписаны новыми данными.Применение программ указанного типа к СЗПО позволяет принудительно восстанавливать временные файлы СЗПО, использованные ими в процессе работы; восстанавливать в полном объеме распакованные и частично удаленные дистрибутивы ПО и временные файлы ОС. Так реализуется повторное использование объектов СЗПО. Например, ряд СЗПО производит распаковку/дешифрацию объектных модулей ПО в специальные временные файлы, которые затем запускаются на выполнение, а после отработки стираются. Восстановление таких файлов позволяет преодолеть защиту ПО.
Средства декомпиляции объектных модулей ПО (Decompilers)
Декомпилирующие программы сходны дизассемблерам и даже иногда их используют в качестве своих подпрограмм. Задачей, стоящей перед данным типом программных средств, является "детрансляция" объектных модулей из машинного кода в исходный код на языке высокого уровня. Применение декомпиляторов к исследуемому ПО реализует статический анализ алгоритмов СЗПО по исходному коду.Большинство существующих современных декомпиляторов ориентировано на обработку объектных модулей, написанных на языках интерпретирующего типа (FoxPro, Clipper, Visual Basic, Java), декомпиляторы для языков компилирующего типа встречаются крайне редко и обладают ограниченными возможностями в силу технических особенностей процесса компиляции.
Декомпиляция ПО дает доступ к его исходному коду (или его эквиваленту) и позволяет полностью распоряжаться программным продуктом, включая внесение в него функциональных изменений и повторную компиляцию.
Средства дизассемблирования объектных модулей ПО (Disassemblers)
Программы этого типа предназначены для "детрансляции" объектных модулей из машинного кода в мнемокод ассемблера. При применении средств дизассемблирования производится статический анализ алгоритмов СЗПО по мнемокоду.Получение доступа к мнемокоду СЗПО дает превосходную возможность детального анализа программного и алгоритмического исполнения процедур СЗПО, а также нахождения конкретных путей обхода или модификации ключевых фрагментов СЗПО. Иногда появляется возможность использования элементов СЗПО во вновь создаваемых средствах их преодоления.
Средства генерации паролей и серийных ключей (Key Generators)
Средства подобного типа используются для генерации ключевых последовательностей, удовлетворяющих критериям используемых в СЗПО криптоалгоритмов. Указанный тип средств реализует преодоление парольных СЗПО, а также СЗПО с электронными ключами и ключевыми файлами.Программы-генераторы различных ключей, кодов возврата и т.п., как правило, являются результатом предварительно проведенного криптоанализа СЗПО и позволяют получать "подходящие" к СЗПО значения ключей для "легального" отключения СЗПО.
Средства криптоанализа (Password Crackers/Bruteforcers)
Указанный тип программных средств предназначен для анализа и преодоления систем криптографического закрытия информации. Обычно в них реализуется несколько видов атак на шифры: атака с использованием известного открытого текста, исчерпывающий перебор, направленный перебор с эвристикой, перебор по словарю. Используя подобные средства, можно производить криптоанализ СЗПО с шифрацией и парольных СЗПО.Так как объектные модули ПО состоят из инструкций машинного кода и последовательность таких инструкций иногда возможно предугадать, в ряде случаев возможно произвести атаку по известному открытому тексту, а также ряд других атак для преодоления СЗПО, использующих методы шифрации.
Средства ОС по контролю доступа к программам и данным (Access Rights Managers)
Средства обеспечения контроля и разделения доступа к данным и приложениям являются одной из основополагающих частей системы безопасности ОС. Данный тип программных средств, как правило, основывается на так называемой "матрице доступа", создаваемой администратором системы. Эта матрица содержит права на доступ к системным ресурсам различных категорий пользователей и прикладных программ (то есть пользователь трактуется как один из процессов ОС).Применение подобных средств к защищенному ПО реализует системный мониторинг СЗПО. В частности, в ОС Windows NT, например, возможно блокирование доступа к файлам с данными СЗПО или доступа к файлам системной конфигурации (ключам реестра), блокирование созданных СЗПО временных файлов и т.п.
Как уже было отмечено выше, практически все перечисленные программные средства относятся к обычному пользовательскому или системному программному обеспечению. К "незаконным" средствам можно частично отнести лишь средства протоколирования клавиатурного ввода, средства статической модификации файлов и средства генерации серийных номеров ПО. В то же время даже эти типы программных средств способны использоваться (и реально используются) в областях, никак не относящихся к исследованию и преодолению СЗПО и нарушению авторских прав. Средства протоколирования клавиатурного ввода используются для обработки нажатий комбинаций клавиш в рамках функционирования пользовательских интерфейсов ПО, а также систем компьютерного обучения. Кроме того, они могут использоваться для архивирования всей информации, набранной с клавиатуры, с целью восстановления утерянной при сбое информации.
Средства модификации файлов используются в большом количестве областей, например, для оперативной модификации собственных программных проектов, служебных файлов и др.
Средства же генерации ключевых последовательностей могут легально использоваться для восстановления утерянной легальным пользователем ключевой информации (в случае отказа со стороны владельца авторских прав) либо в образовательных целях.
Таким образом, можно утверждать, что необдуманное запрещение использования перечисленных типов ПО (по аналогии с вредоносными программами) будет неэффективной мерой, так как повлечет за собой серьезные трудности либо полную невозможность использования ПО, необходимого для нормального функционирования компьютерных систем. Естественно, подобное запрещение неТаким образом, можно утверждать, что необдуманное запрещение использования перечисленных типов ПО (по аналогии с вредоносными программами) будет неэффективной мерой, так как повлечет за собой серьезные трудности либо полную невозможность использования ПО, необходимого для нормального функционирования компьютерных систем. Естественно, подобное запрещение не будет соблюдаться на практике из-за его невыполнимости.
Возможно законодательное запрещение "нецелевого использования" приведенных типов ПО, но на законодательном уровне практически невозможно регламентировать "целевые" и "нецелевые" виды использования ПО, что ведет к практической неприменимости (или высокой сложности и неоднозначности применения) подобных законодательных норм.
Из всего вышеперечисленного можно сделать вывод, что одни только технические меры защиты ПО, даже с учетом их законодательной поддержки, не способны обеспечить надлежащий уровень безопасности защищаемых программных продуктов. Следовательно, необходим более комплексный подход к защите ПО, с учетом многих других аспектов распространения, реализации и использования программного обеспечения.
Использованная литература:
Средства отладки объектных модулей (Debuggers)
В состав стандартных функций отладчиков входят возможности пошагового выполнения объектного кода, установки точек останова (в т.ч. срабатывающих по условию), просмотра объектного кода ПО в дизассемблированном виде, изменения последовательности выполнения объектного кода, редактирования памяти отлаживаемого процесса, отслеживания изменения данных процесса и др.В рамках исследования СЗПО использование отладчиков реализует
динамический анализ алгоритмов СЗПО. Преодоление практически любой СЗПО в большинстве случаев невозможно без использования отладочных средств. При этом большая часть отладочных функций реализуется в архитектуре центрального процессора ЭВМ.
Средства пакетной обработки команд (Batch Processors/Script Engines)
Данный тип программных средств позволяет выполнять (последовательно или параллельно) сразу целый набор команд, предварительно заданный пользователем. В рамках пакетов заданий поддерживаются операторы цикла и ветвления. Подобные средства позволяют осуществлять создание виртуального окружения на время работы СЗПО.Условно бесплатные ППр доступны для использования до их приобретения как такового. Как правило, такие продукты содержат ограничения по времени их использования, числу запусков либо функциональному наполнению. При помощи средств пакетной обработки команд возможно создание необходимого программного окружения (установка системной даты, изменение файлов данных СЗПО, изменение параметров ОС и др.) до запуска защищенного ПО с возможностью возврата к предыдущему состоянию окружения по завершении работы ППр.
Средства поиска и замены текстовых
Функционально такие программные средства предназначены для оперативного и простого внесения желаемых изменений в один файл или группу файлов. Многие подобные средства могут производить поиск по заданной маске.При помощи средств поиска и замены выполняется статическая модификация кода СЗПО. Как правило, модификация СЗПО с целью лишения ее функциональности состоит в замене нескольких байт объектного кода. В то же время существуют СЗПО, для дезактивации которых требуется модификация большого числа (иногда непостоянных) последовательностей байт, что становится возможным при использовании этого типа программ.
Средства редактирования "ресурсов" объектных модулей (Resource Editors)
Подобные программы используются для редактирования текстовых, диалоговых, графических, аудио-, видео- и других ресурсов, содержащихся в области данных объектных модулей ПО. В рамках исследования СЗПО подобные средства позволяют производить редактирование ресурсов СЗПО.Как правило, содержимое всех пунктов меню интерфейса программы, все текстовые сообщения и диалоги, выдаваемые программой, графические элементы интерфейса и др. содержатся в секции ресурсов области данных объектного модуля. Модификация этих ресурсов позволяет изменить интерфейс программы, в том числе активировать отключенные в рамках данной лицензии на ПО пункты меню, предотвратить выдачу приложением предупреждающих надписей о необходимости приобретения ПО, изменить диалоги и т.п. Иногда в текстовых ресурсах содержатся пароли/серийные номера защищенного ПО.
Средства симуляции центрального процессора и подпрограмм ОС (CPU/API Emulators)
Программы указанного типа производят виртуализацию центрального процессора ЭВМ и/или определенных функций ОС на время выполнения одного или группы приложений.Данные средства реализуют изменение процесса выполняемой СЗПО. Симуляторы процессора или сервисов ОС производят предварительный анализ инструкций процессора или вызовов функций операционной системы и затем обрабатывают и выполняют (или игнорируют) их в соответствии с заложенными заранее правилами.
Средства симуляции операционных систем или ЭВМ целиком (OS/PC/Mac/... Emulators)
ПО этого типа предназначено для обеспечения выполнения приложений, созданных для одной программной/аппаратной платформы, на другой платформе. Большая часть подобных программ предоставляет также и отладочные возможности (сопоставимые с возможностями аппаратной отладки, а иногда и превосходящие их по функциональности).Применение указанного типа программных средств к защищенному ПО позволяет осуществлять преодоление СЗПО произвольного типа.
Симуляторы ОС производят динамический анализ вызовов системных функций обрабатываемого приложения, их конверсию в вызовы текущей ОС и обратную конверсию кодов возврата в коды симулируемой ОС. Симуляторы процессоров делают то же самое, но на уровне машинного кода процессоров.
Несмотря на совершенно "мирные" цели, заключающиеся в обеспечении переносимости приложений между различными платформами, нестандартное использование средств этого типа позволяет преодолевать не только системы защиты программного обеспечения, но и схемы "управления цифровыми правами" (Digital Rights Management) на доступ к авторским произведениям, основанные на "привязке" к ЭВМ пользователя.
Средства загрузки и/или модификации контекста объектных модулей в регистрах ЦП
Этот тип программных средств предназначен для изменения состояния регистров центрального процессора ЭВМ во время выполнения определенного объектного модуля ПО. Данные средства реализуют изменение контекста процесса выполняемой СЗПО.При помощи подобных средств возможно влиять на процесс выполнения объектного кода, не внося в него изменений. С юридической точки зрения, подобное управление центральным процессором не нарушает (да и не может нарушить) никаких законодательных норм, так как оно никак не затрагивает объектный код защищенного ПО, в то же время совершенно аналогичные действия являются составной частью работы ОС.
Средства загрузки объектных модулей
Этот тип программных средств предназначен для модификации памяти процесса ОС во время его выполнения в ОЗУ. За исключением особенностей модификации объектного кода в оперативной памяти, данные средства функционально подобны средствам поиска и замены в файлах.При помощи таких программ осуществляется динамическая модификация кода СЗПО.
Обычно средства динамической модификации кода используются при высокой сложности или нерациональности распаковки/дешифрации объектных модулей защищенного ПО.
Защита программ
Четвёртый этап - предварительный
Проводя поверхностное исследование кода программного продукта, в большинстве случаев злоумышленник определяет тип, а иногда и производителя системы защиты. Становится возможным установить наиболее вероятное физическое расположение кода системы защиты в коде программного продукта. Для подобного исследования кода программы обычно используется шестнадцатеричный редактор с возможностью дизассемблирования машинных инструкций, поиска заданных байтовых последовательностей и др. Но, кроме средств просмотра машинного кода, злоумышленники используют и автоматические анализаторы исполняемых файлов. Эти программные средства по заложенным в них сигнатурам способны распознавать большинство популярных систем защиты ПО, а также определять производителя и версию компилятора, при помощи которого программа была собрана.Полученная в результате информация, вкупе с данными мониторинга работы программного продукта, даёт злоумышленнику полную обзорную информацию об используемой в программном продукте системе защиты. Нередки случаи, когда дальнейший анализ системы защиты уже на данном этапе становится излишним и собранной информации достаточно для обхода или преодоления защиты.
Этапы преодоления систем защиты программного обеспечения
, Движение ПОтребительВ статье описывается обобщённая процедура анализа и деактивации систем защиты программного обеспечения (ПО) от несанкционированного использования и копирования. Знание методик, которые используются злоумышленниками ('crackers') для преодоления систем программной защиты, позволяет более точно определить слабые места существующих систем, а так же проектировать новые, более устойчивые к атакам. Нами предлагается описание унифицированной методики анализа и преодоления систем программной защиты, являющейся результатом обобщения и систематизации многочисленных приёмов "взлома" программ, публикуемых в современной литературе [], а также, доступных в глобальной сети. По итогам проведённого исследования предложен комплексный критерий оценки устойчивости систем защиты программного продукта.
В настоящее время наиболее популярным средством борьбы с нелегальным распространением коммерческих программных продуктов остаётся программная защита их двоичного кода. Существуют системы защиты программного обеспечения разных типов [], все они постоянно развиваются. В то же время, имеются и средства, позволяющие исследовать защищённые программы и отключать системы их защиты []. В условиях такого динамического равновесия важным фактором, влияющим на стойкость систем защиты, является методическое обеспечение как специалистов по защите ПО, так и злоумышленников.
Мы считаем, что изучению методов, используемых для анализа и преодоления систем защиты ПО, не уделялось достаточного внимания, в то время как их знание позволяет в значительной мере сократить количество уязвимых мест в системах защиты.
Нами было проведено исследование современных подходов к программно-технической защите программных продуктов, а также подходов к преодолению такой защиты. В результате можно сделать вывод, что как с одной (защита), так и с другой ("взлом") стороны основное внимание уделялось и до сих пор уделяется прикладным приёмам защиты ПО или её преодоления []. В то же время, нам не удалось отыскать ни обобщённых методик проектирования и реализации систем программной защиты, ни аналогичных методик анализа и преодоления таких систем.
Анализ приёмов преодоления систем программной защиты различных типов позволил выявить ряд общих закономерностей. В данном случае, положительную роль сыграло многообразие описываемых злоумышленниками методик, различный уровень их сложности, а также их принадлежность к различным стадиям анализа систем защиты ПО. Таким образом, стало возможным систематизировать информацию по данному вопросу и описать обобщённую процедуру анализа и преодоления систем защиты программных продуктов.
По нашему мнению, любые приёмы и методы анализа и преодоления систем защиты ПО можно свести к ряду стандартных этапов. (См. блок-схему на )
Первый этап - определение цели атаки.
В первую очередь злоумышленнику необходимо определить цель, для достижения которой он будет атаковать систему защиты программного продукта. Среди возможных целей можно выделить следующие три: личное использование программного продукта; распространение средств, отключающих систему защиты продукта ('crack-files'); несанкционированное распространение самого программного продукта ('warez'). В зависимости от перечисленных целей подход к "взлому" системы защиты того или иного программного продукта может варьироваться. В частности, если злоумышленник планирует использовать программный продукт в личных целях, он может воспользоваться методами, требующими высокой квалификации пользователя, необходимой для работы с отключенной системой защиты. Если предполагается распространение средств отключения системы защиты конкретного продукта злоумышленнику необходимо ориентироваться на неквалифицированного в вопросах защиты ПО пользователя. Это может потребовать дополнительных усилий и затрат времени. Наконец, если злоумышленник планирует распространять "взломанный" программный продукт, ему, как правило, необходимо осуществить прямое отключение системы защиты, что значительно сложнее, чем просто её обход.Пятый этап - оценка стойкости
После сбора информации о системе защиты производится оценка её стойкости и слабых мест, а также возможности применения стандартных средств и приёмов преодоления систем защиты данного типа. Злоумышленник, используя доступную информацию об устройстве и стойкости различных систем программной защиты, определяет стойкость системы защиты, реализованной в атакуемом программном продукте. Например, если в атакуемом продукте используется система защиты, ограничивающая время его использования, то уязвимостью является необходимость получения системного времени и даты. В системах с запросом регистрационного кода и/или ограничением функциональности продукта слабым местом является блок проверки корректности регистрационного кода. Системы, использующие ключевые файлы, диски или электронные ключи могут иметь слабые места в блоках проверки корректности ключевых данных или в блоках обмена данными. Другой уязвимостью для любых типов защиты является использование стандартных библиотек подпрограмм, при помощи которых реализуется система защиты ПО.Оценив стойкость системы защиты, злоумышленник затем выбирает один или несколько эффективных способов её преодоления. На этот выбор влияет и исходная постановка цели, как это было указано выше. В частности, для случая с ограничением времени функционирования продукта злоумышленник может избрать три различных пути:
В зависимости от выбранного способа преодоления защиты изменяется и дальнейшее её исследование.
Седьмой этап - преодоление системы защиты.
На финальном этапе, учитывая поставленную цель, выбранный способ преодоления защиты и найденную техническую процедуру её обхода или преодоления, злоумышленник реализует преодоление защиты на практике. Под обходом системы защиты понимаются действия, напрямую не относящиеся к противодействию системе защиты атакуемого программного продукта. В качестве примера можно привести периодическую реинсталляцию программных продуктов с ограниченным сроком использования; изменение системной даты до запуска программы и установка корректной даты по завершении её работы; удаление/замену скрытых файлов со счётчиками запуска; удаление/замену соответствующих строк в системных файлах; написание и использование генераторов регистрационных кодов; отслеживание и автоматическое завершение диалогов с напоминанием о необходимости регистрации продукта и т.п.Преодоление системы защиты может осуществляться тремя основными путями:
В первом случае в объектный код программного продукта вносятся изменения, дезактивирующие систему его защиты. Как правило, они касаются команд условного перехода типа "зарегистрированная версия/незарегистрированная версия" или "верный регистрационный код/неверный регистрационный код". Иногда модифицируются элементы данных программы, содержащие определённые флаги, по которым система защиты судит о наличии регистрации программного продукта. Нередко, для статической модификации кода требуется его предварительная дешифрация или восстановление по образу в оперативной памяти. Такая операция часто обладает значительной трудоёмкостью и требует дополнительного исследования системы защиты. Поэтому злоумышленники прибегают к статической модификации объектного кода атакуемого продукта либо при условии, что код ПО не зашифрован, либо когда преследуют цель "пиратского" распространения ПО.
При этом распространяться может как программное средство, выполняющее статическую модификацию продукта, так и просто данные, позволяющие выполнить это вручную.
К динамической модификации кода злоумышленники прибегают в случаях, когда дешифрация или восстановление объектного кода программы требует слишком высоких затрат. Под динамической модификацией понимается изменение кода программы в оперативной памяти во время выполнения. Подобная модификация должна производиться при каждом новом запуске программы. Для реализации этого процесса злоумышленниками используются специальные программные средства, осуществляющие загрузку целевого приложения как своего дочернего процесса. Такая загрузка даёт доступ к адресному пространству приложения в оперативной памяти, а соответственно и возможность динамического изменения его кода. Как правило, программные средства, ориентированные на конкретный программный продукт, распространяются злоумышленниками в глобальной сети отдельно или вместе с самим продуктом.
Эмуляция используется, в основном, если система защиты включает в себя электронный ключ, реже, если присутствует ключевой диск или ключевой файл. Суть данного метода заключается в подделке ответов на запросы защищённого приложения к отсутствующему ключу, диску или файлу таким образом, что система защиты не обнаруживает его отсутствия. С одной стороны, использование эмуляции требует значительных усилий, связанных с исследованием протоколов обмена данными между блоками системы защиты, и программированием эмулятора (нередко в виде драйвера). С другой же стороны, эмуляция, как правило, не требует модификации кода ПО, а следовательно избавляет злоумышленника от необходимости дешифрации или исправления значительных участков программного кода. Чаще всего эмуляторы распространяются отдельно либо вместе с "пиратскими" копиями ПО.
Преодоление системы защиты атакуемого продукта является последним этапом процесса анализа и преодоления систем защиты. После этого злоумышленник начинает использование программного продукта, распространение средства отключения системы защиты или самого продукта.
Знание последовательности действий злоумышленника позволяет разрабатывать гибкую политику программно-технической защиты программных продуктов. Значительная доля современных систем защиты ориентирована на затруднение лишь части из описанных этапов их анализа и преодоления. Например, нередки случаи, когда система защиты обладает мощными механизмами противодействия дизассемблированию кода защищённого приложения и его отладке, но не способна противостоять мониторингу. Существуют, также, системы защиты, базирующиеся на шифровании объектного кода приложения, но обладающие чрезвычайно простой логикой, что позволяет злоумышленникам легко осуществлять динамическую модификацию кода. Кроме того, львиная доля систем защиты не только не маскирует своего присутствия, но и активно информирует о нём пользователя. Подобная стратегия в значительной мере облегчает злоумышленникам предварительный анализ системы защиты и её локализацию.
Таким образом, можно заключить, что правильно спроектированная система защиты, по крайней мере, должна затруднять своё первичное обнаружение, противодействовать мониторингу работы приложения, его отладке, дизассемблированию и/или декомпиляции, обладать сложной логикой работы, трудно поддающейся анализу, а так же создавать значительные трудности для динамической и/или статической модификации кода защищаемого программного продукта.
На основе высказанных выше соображений можно сформулировать частные критерии устойчивости защищаемого продукта к атакам. По нашему мнению, можно предложить следующие критерии:
Исходя из данного набора частных критериев, можно построить комплексный критерий устойчивости программного продукта к атакам. Этот критерий формулируется следующим образом:
| Kкомпл. = | n ∑ i=1 |
αi ki , |
Таким образом, с помощью метода экспертных оценок становится возможным сравнивать между собой различные варианты защиты одного программного продукта либо сравнивать реализации защиты различных программных продуктов одного класса. Сама реализация метода экспертных оценок может быть осуществлена двумя основными способами:
Среди возможных направлений дальнейших исследований в данной сфере, по нашему мнению, следует отметить подробное изучение отдельных этапов преодоления систем программной защиты; выявление зависимости между сроком преодоления систем защиты разных типов и набором используемого злоумышленником программного инструментария; сбор статистических данных по стойкости систем защиты разных типов; разработку методик оценки стойкости систем защиты ПО и сроков гарантированной устойчивости подобных систем к атакам.
Литература:
Шестой этап - направленное исследование системы защиты.
На данной стадии злоумышленник выполняет статический и/или динамический анализ системы защиты атакуемого продукта. Статический анализ, в зависимости от языка программирования, на котором написана программа, может осуществляться при помощи дизассемблирования объектного кода или при помощи его декомпиляции. Применение дизассемблера даёт злоумышленнику возможность работы с последовательностью инструкций целевого процессора, в которую исходный текст программы был превращён при компиляции. В случае же декомпиляции объектного кода злоумышленник получает текст на языке высокого уровня в максимально близком к исходному виде. Получив текст программы на языке ассемблера или языке высокого уровня, злоумышленник анализирует его и определяет алгоритм преодоления защиты продукта.В случае затруднений, связанных со статическим анализом, например, когда объектный код зашифрован или динамически изменяется, прибегают к его динамическому анализу. Как правило, динамический анализ систем защиты выполняется при помощи программного отладчика. При этом исследуемое приложение запускается в среде программы-отладчика и выполняется в пошаговом режиме или с использованием заданных точек останова. В режиме отладки становится возможным отслеживать изменения состояния программы, происходящие в процессе её выполнения (например, изменение содержимого регистров процессора, срабатывание команд условного перехода, параметры вызова подпрограмм, получаемые или передаваемые через порты ввода/вывода данные и др.). В этом же режиме выполняется прохождение алгоритмов, например, проверки/генерации корректного регистрационного кода.
Динамический анализ может также выполняться при помощи уже упоминавшихся выше мониторов активности приложения. Если на этапе предварительного анализа при помощи этих средств отслеживается общая направленность работы программы, то на этапе динамического анализа системы защиты отслеживается не только факты обращения к файлам, портам и системным сервисам, но и все параметры этих обращений: данные, записываемые/считываемые из скрытых и системных файлов, параметры вызова системных сервисов, протоколы обмена с портами ввода/вывода и др. В случае применения мониторов активности не имеет значения, реализованы ли в рамках системы защиты блоки противодействия отладке приложения или нет.
По завершении данного этапа анализа системы защиты злоумышленник обладает полной информацией о том, как технически осуществить обход или преодоление системы защиты программного продукта.
Третий этап - предварительный анализ работы защищённого продукта.
На начальном уровне исследования системы защиты злоумышленник отслеживает активность программы, связанную с созданием и удалением обычных и скрытых файлов; обращением к системным файлам, портам ввода/вывода. Также контролируется строка запуска программы, используемые сервисы операционной системы и другие параметры. При помощи подобного мониторинга работы программного продукта злоумышленник получает общее представление об используемом механизме защиты и возможных путях её преодоления. Как правило, системы защиты используют какой-то один из указанных видов активности программы для реализации своих функций. Например, для реализации ограничения времени использования продукта используется либо создание скрытых файлов, либо запись данных в системные файлы. В этом случае мониторинг работы защищённого приложения с различными файлами даёт важную информацию для дальнейшего исследования системы защиты. Некоторые системы защиты записывают данные в область ППЗУ, в неиспользуемые участки дорожек жёсткого диска или используют электронный ключ. Мониторинг работы приложения с портами ввода/вывода даёт возможность обнаружить подобные факты. Аналогичным образом, системы защиты, использующие регистрационный код, как правило, сохраняют его в собственных или системных файлах. Отслеживание неудачных попыток найти файл или найти запись в системном файле также даёт злоумышленникам предварительную информацию о механизме защиты программного продукта.Второй этап - поиск проявлений системы защиты.
Проявления работы систем защиты могут иметь следующий вид:Возможны и комбинации перечисленных проявлений. В зависимости от этих проявлений злоумышленник может применять различные подходы к исследованию системы защиты, а так же затрачивать разное время и усилия на её преодоление. Например, напоминания о необходимости регистрации направлены на чисто психологическое воздействие и их отключение обычно не представляет большой сложности. Программные продукты с ограничениями времени использования всегда уязвимы для атак. Продукты с ограничениями функциональности уязвимы, если есть возможность снять ограничения с помощью регистрационного кода, и отключённые подпрограммы не зашифрованы. Системы, отключающие защиту при вводе верного регистрационного номера, можно преодолеть при отсутствии шифрования кода ПО стойкими криптоалгоритмами (DES, RSA, IDEA, etc.). Что же касается систем, генерирующих внутренние или системные ошибки, собирающих персональные данные или осуществляющих вредоносные действия, их анализ и преодоление, как правило, требуют дополнительных затрат времени, так как подобные проявления систем защиты носят неявный и нелокализованный характер.
Защита программ
Анализ исходных текстов продукта
. Целью данного этапа является поиск потенциальных мест размещения элементов системы защиты, определение оптимального режима её маскировки, выявление возможных слабых мест в коде продукта, определение основных алгоритмов продукта, степени влияния на них системы защиты и возможности их модификации для использования для дополнительной защиты. Кроме этого, определяется язык программирования, на котором реализован программный продукт, а также стиль программирования и основные соглашения по построению исходного кода. В частности, нередко так называемые демонстрационные версии программных продуктов, распространяемые бесплатно, строятся из исходного кода полнофункциональных версий с внесением незначительных изменений, отключающих расширенную функциональность. В этом случае злоумышленники получают возможность, обратив эти изменения, получить аналог полнофункционального продукта. Проводимый анализ позволяет избежать подобных ситуаций.Анализ предполагаемого протокола передачи ПО пользователю
. На данном этапе уточняется состав организационных мер, связанных с коммерческой реализацией программного продукта: сбор персональных данных о пользователе или сохранение его анонимности, розничная (или наложенным платежом) продажа продукта за наличные либо продажа через глобальную сеть с электронными расчётами, наличие скидок на новые версии для зарегистрированных пользователей либо скидки на "кумулятивное" обновление для пользователей, перешедших с конкурирующих программных продуктов. Все эти данные позволяют оценить реально необходимый уровень стойкости системы защиты: если продукт распространяется индивидуально, то несанкционированное распространение такого "именного" продукта приведёт к уличению соответствующего пользователя (соответственно, уровень технической защиты продукта может быть средним), при распространении ПО через сеть Интернет и анонимности пользователей такая вероятность минимальна (следовательно, СЗПО должна иметь максимальный уровень стойкости).Анализ возможных и вероятных угроз безопасности ПО
. Этот этап представляет собой процедуру оценки и управления рисками, связанными с защитой программного продукта от несанкционированного использования и распространения []. Данная процедура включает: определение множества возможных угроз; выделение подмножества вероятных угроз; определение потенциального ущерба по каждой угрозе; выработка контрмер; разработку общей стратегии поведения в условиях риска. Среди угроз несанкционированного распространения продукта можно выделить: распространение похищенной у легального пользователя аутентичной информации (пароль, серийный код); подбор этой информации; преодоление системы технической защиты продукта; сетевую атаку на сервер глобальной сети с целью завладения дистрибутивом продукта; похищение дистрибутива у легального пользователя; превращение легального пользователя в злоумышленника; приобретение продукта злоумышленниками "в складчину"; и приобретение продукта по украденной или фальшивой кредитной карте.Документирование и сопровождение СЗПО
. Завершающим этапом процесса разработки СЗПО является окончательное оформление документации (разработка которой должна вестись на всех перечисленных этапах проектирования и реализации системы защиты) на разработанную систему и переход к сопровождению этой системы. В рамках сопровождения необходимо выполнять работы по внесению усовершенствований в разработанную СЗПО, расширению её функциональности, повышению стойкости и т.п. В результате будет получена корректно спроектированная и реализованная система программно-технической защиты программного обеспечения с заданными параметрами.По нашему мнению разработка систем защиты программного обеспечения по приведённой схеме (с её упрощением или усложнением в зависимости от конкретной ситуации) позволит получать качественные, надёжные и устойчивые к атакам программные продукты, которые вкупе с законодательными и организационными "антипиратскими" мерами смогут успешно противостоять попыткам несанкционированного использования и распространения.
Доработка спецификаций СЗПО либо приобретение сторонней разработки, удовлетворяющей спецификации
. В случае, если расчётные затраты на разработку СЗПО превышают сумму выигрыша от внедрения защиты, возможны два варианта. Первым вариантом является уточнение и оптимизация требований к СЗПО, в результате проведения которых стоимость системы защиты станет удовлетворительной. Другим вариантом может быть приобретение разработанной другими производителями системы защиты, удовлетворяющей спецификациям и требованиям по стоимости. Как правило, в недорогих программных продуктах используются приобретённые системы защиты (внешнего типа), в программных продуктах с высокой стоимостью часто применяются системы защиты собственной разработки или доработанные приобретённые системы защиты комплексного типа (электронный ключ).Три последующих этапа (Разработка и оптимизация алгоритма СЗПО, Выбор языка программирования для реализации СЗПО, Программная реализация СЗПО и её тестирование) относятся к реализации системы защиты собственными силами производителя ПО. В целом, разработка программной системы защиты ПО практически не отличается от разработки произвольного программного продукта системного уровня, за исключением специфических требований по надёжности и устойчивости к статическому и динамическому анализу. Что же касается тестирования, то кроме свойственных обычным приложениям тестов, призванных выявить ошибки программирования, СЗПО должна подвергаться серии интенсивных тестов на устойчивость к атакам. Эти тесты основаны на так называемом "диверсионном подходе", который предполагает исследование системы защиты с позиций злоумышленника с использованием соответствующего инструментария [], с целью её преодоления []. Для подобного тестирования СЗПО применяют к тестовой программе (либо написанной самостоятельно, либо стандартной, например, "Блокнот Windows").
Доработка СЗПО (повышение стойкости к атакам)
. Если уровень защиты не соответствует спецификациям, необходимо произвести доводку системы защиты с целью доведения её устойчивости к атакам до запланированного уровня. Примерами доработки СЗПО могут служить: шифрация текстовых сообщений системы защиты (по которым легко можно локализовать СЗПО), использование стойких криптоалгоритов для шифрования кода ПО, отказ от хранения эталонного пароля в теле программы, использование упаковки объектного кода, использование антиотладочных механизмов, затруднение дизассемблирования объектного кода и т.п. []. После доработки СЗПО должна быть вновь протестирована на предмет побочных эффектов.Доработка СЗПО (устранение побочных эффектов)
. В случае выявления побочных эффектов, оказывающих значительное влияние на функциональность и потребительские свойства ПО, необходимо выполнить доработку системы защиты, с целью ликвидировать или минимизировать указанные побочные эффекты. Примером негативного влияния СЗПО на качество программного продукта может служить снижение надёжности (повышение вероятности сбоя), повышение системных требований, конфликты с другими (прикладными или системными) программами, замедление работы ПО, необходимость особой настройки системы защиты и т.п. После доработки СЗПО тестирование на побочные эффекты повторяется.Определение соответствующего требованиям уровня защиты
. Требования к уровню защиты можно оценивать двояко: либо определять значения частных критериев устойчивости защиты к атакам и их весовые коэффициенты, чтобы рассчитать комплексный критерий устойчивости []; либо определять временной интервал, в течение которого СЗПО гарантированно будет препятствовать теневому распространению защищаемого продукта []. Эти два вида оценки уровня защиты сильно взаимосвязаны, в то же время, более наглядным, а также более удобным для сопоставления с запланированным уровнем потерь от является второй. Обладая данными о динамике продаж во времени, нетрудно рассчитать необходимый временной интервал живучести СЗПО, который позволит сократить потери до запланированного уровня.Определение стратегии защиты программного продукта (меры и средства)
. На основе полученных на предыдущих этапах аналитических данных необходимо определить оптимальное для данной ситуации сочетание мер и средств защиты программного продукта. В рамках законодательных мер можно говорить лишь о механизмах повышения раскрываемости нарушений прав производителя продукта, организационные меры определяются оговоренным ранее протоколом передачи продукта пользователю. В рамках же технических мер можно говорить не только о как таковой СЗПО, но и средствах отслеживания фактов появления нелицензионных версий продукта в глобальной сети, технических средствах выявления злоумышленников и т.п. Таким образом, данный этап определяет роль и место СЗПО в комплексе мер по защите продукта.Первичное тестирование программного продукта
. На данном этапе определяются наиболее важные потребительские характеристики программного продукта, набор его важнейших функций, подлежащие тестированию. Результаты тестов являются эталоном, с которым впоследствии будут сравниваться результаты тестов защищённого программного продукта. Разумеется, первичным это тестирование является для процесса разработки системы защиты ПО. Определённая часть тестов должна проводиться в рамках процесса разработки самого программного продукта. Таким образом, значительная часть этого этапа должна быть уже выполнена ранее.Следующие три этапа (Оценка общих планируемых затрат на разработку и внедрение СЗПО, Оценка планируемого снижения потерь от "пиратства" и Принятие решения о целесообразности применения проектируемой СЗПО) сильно связаны друг с другом и преследуют цель - оценить реальные затраты на разработку системы защиты и сравнить их с дополнительным доходом, который будет получен в результате её применения. То есть, указанные этапы включают оценку ожидаемой экономической эффективности разрабатываемой СЗПО и принятие решения о применимости системы с найденной расчётной эффективностью. Оценка затрат на разработку СЗПО выполняется по существующим методикам расчёта стоимости разработки системного ПО. Сумма дополнительного дохода от снижения уровня "пиратства" рассчитывается на основе данных о разнице между текущим и планируемым процентом потерь. Решение же о целесообразности применения спроектированной СЗПО принимается исходя из общепринятого в экономике предположения о рациональном поведении экономических агентов, т.е. применение системы принимается целесообразным, если затраты на СЗПО не превышают выигрыша от её применения.
Применение СЗПО к продукту и проверка влияния защиты на показатели функциональности защищаемого ПО
. На этом этапе выполняются проверки на побочные эффекты применения системы защиты к реальному защищаемому продукту. В данном случае должны быть повторены все тесты, выполненные на этапе первичного тестирования программного продукта. Затем, результаты повторных тестов должны сравниваться с результатами первичных тестов с анализом выявленных расхождений. В идеальном случае расхождений быть не должно. При наличии подобных расхождений необходимо провести оценку их влияния на потребительские свойства программного продукта. Анализ побочных эффектов системы защиты очень важен, так как в результате его проведения оценивается влияние защиты на конкурентоспособность продукта на рынке.Процедура разработки систем программно-технической защиты программного обеспечения
,Впервые опубликовано в сборнике
Инновации в процессе обучения: Сборник научных трудов Академического Совета МЭСИ. - М. 2004. - 212 с. С. 160-173.
В статье описывается краткая история проблемы теневого оборота программных продуктов, а также приводится обобщённая процедура проектирования и разработки систем программно-технической защиты программного обеспечения. Предложенная процедура является реализацией технологического подхода к разработке систем защиты, позволяющей спроектировать и программно реализовать систему защиты с заранее заданными характеристиками и минимальными побочными эффектами.
Проблема несанкционированного использования и распространения программного обеспечения (ПО) стала объектом исследований ещё в конце 70-х годов XX столетия и не теряет своей актуальности до сих пор. Причиной этому послужило стремительное развитие рынка персональных ЭВМ и, в особенности, признание IBM-совместимых компьютеров стандартом de facto для пользователей ПЭВМ. Таким образом, была разрешена проблема аппаратной и программной совместимости в рамках парка персональных компьютеров, что стимулировало появление программных продуктов "широкого пользования", которые стали разрабатываться и распространяться в отрыве от конкретных систем автоматизированной обработки данных. Подобные продукты были, фактически, реализацией типовых программных решений в наиболее популярных областях автоматизации обработки данных (обработка текстов, создание расчётных таблиц, работа с базами данных, редактирование графических изображений, компьютерные игры; позднее появились системы трёхмерного моделирования и анимации, мультимедийные приложения, системы распознавания текста и речи и мн.др.). Таким образом, производители программного обеспечения получили возможность перейти от индивидуального проектирования систем обработки данных к типовому, что позволило существенно снизить расходы на разработку ПО, а также распределить расходы на его приобретение между значительным количеством пользователей.
С другой стороны, высокая распространённость микрокомпьютерных систем, персональное пользование программными средствами и фактическая неподконтрольность индивидуальных пользователей создали предпосылки (и техническую возможность) для интенсивного несанкционированного обмена программами между владельцами персональных компьютеров. Этому же способствовало и отсутствие устоявшихся моральных норм в отношении программных продуктов, несовершенство правовой базы, а также инерционное восприятие программного обеспечения как бесплатного компонента (включённого в стоимость) приобретённых аппаратных средств.
Экономические потери производителей программных продуктов, выражающиеся в виде упущенной выгоды и морального ущерба, обусловили необходимость разработки и применения мер, препятствующих теневому обороту программных продуктов. Указанные меры можно условно подразделить на законодательные
(лоббирование законов, регламентирующих ответственность за несанкционированное использование и распространение ПО), организационные (установление контроля над пользователями путём регистрации их персональных данных, персонального режима обновления версий продукта и т.п.) и технические
(использование программно-технических средств, препятствующих несанкционированному использованию и/или копированию программных продуктов).
В силу того, что лоббирование законов возможно лишь для крупных компаний или объединений производителей ПО, а организационные меры требуют значительных затрат на реорганизацию торговой инфраструктуры и могут привести к переходу части клиентов на продукты конкурентов, не применяющих таких мер, самыми популярными стали технические меры противодействия теневому обороту ПО. Таким образом, получили широкое распространение системы программной защиты ПО, основной целью которых было техническое противодействие несанкционированному использованию и распространению программных продуктов. Такое положение дел сохранилось, в целом, и до настоящего времени, не смотря на то, что производителями достаточно активно используются законодательные и организационные меры защиты своих программных продуктов.
По проблемам программно- технической защиты программного обеспечения от несанкционированного введения в хозяйственный оборот было опубликовано очень значительное число работ []. В то же время, в многочисленных публикациях описывается техника, приёмы, но не технология (методология) защиты программных продуктов. Автору до настоящего времени не удалось найти публикации, которые были бы посвящены описанию обобщённой процедуры проектирования и реализации систем защиты программного обеспечения (СЗПО), как это делается, например, в области разработки программного обеспечения или проектирования подсистем защиты информации в системах обработки данных. По нашему мнению, отсутствие подобного описания в значительной мере затрудняет разработку СЗПО отдельными производителями, не имеющими соответствующего опыта, ведёт к многократному дублированию проводимых НИОКР, а также может быть причиной низкой стойкости разрабатываемых систем защиты.
Настоящий материал призван ликвидировать существующее "белое пятно" в исследованиях, посвящённых программно-технической защите программных продуктов.
По нашему мнению, процесс проектирования и разработки СЗПО можно логически разбить на следующие этапы:
Опишем указанные этапы более подробно.
Согласование допустимого процента потерь от "пиратства"
. Данный этап, вкупе с первым, позволяет определить основное направление работы по созданию системы защиты. Как правило, фирма-производитель ПО обладает данными о теневом распространении своих продуктов. Кроме того, производители регулярно проводят маркетинговые исследования, дающие информацию о плановом объёме продаж продукта. Сведения о теневом распространении продукта, а также о разнице между планировавшимся и реальным объёмами продаж позволяют достаточно точно оценивать фактический процент потерь от "пиратства". На указанном же этапе определяется процент потерь, с которым производитель готов смириться (это может быть и 0%) [].Тестирование фактического уровня защиты, обеспечиваемого СЗПО
. На данном этапе проводится тестирование фактического уровня защиты конкретного программного продукта. Фактически, здесь повторяются тесты, основанные на "диверсионном подходе", которые проводились для тестового защищаемого приложения. Результаты проведённых на этом этапе тестов определяют фактическую стойкость созданной СЗПО (применительно к данному продукту). На их основе можно оценить требуемую квалификацию злоумышленника и инструментарий, требуемые для преодоления системы защиты. Соответственно, у разработчиков появляется возможность оценить затраты времени и средств, которые злоумышленник должен будет понести, преодолевая защиту. Если по итогам тестов полученный уровень стойкости защиты соответствует спецификациям, разработку СЗПО можно считать завершённой.Выбор оптимального типа СЗПО
. Системы внешнего типа наиболее удобны для производителя ПО, так как легко можно защитить уже полностью готовый и оттестированный продукт. С другой стороны стойкость этих систем достаточно низка (в зависимости от принципа действия СЗПО), так как для обхода защиты достаточно определить точку завершения работы "конверта" защиты и передачи управления защищенной программе. Встраиваемые системы менее удобны для производителя ПО, так как возникает необходимость обучать персонал работе с программным интерфейсом системы защиты с вытекающими отсюда денежными и временными затратами, кроме того, усложняется процесс тестирования ПО и снижается его надежность. Но такие системы являются более стойкими к атакам, потому что здесь исчезает четкая граница между системой защиты и как таковым продуктом. Комбинированные же системы содержат элементы обоих типов [].Выбор оптимального вида СЗПО
. На данном этапе производится выбор конкретного вида системы защиты. Иными словами, разработчики выбирают: устанавливать систему защиты от копирования ("привязка" к ПК пользователя, к дистрибутивному носителю, физической дорожке жёсткого диска пользователя и т.п.) или систему защиты от использования (запрос пароля/серийного кода, ключевого файла, ключевого диска, электронного ключа). Например, львиная доля компьютерных игр использует "привязку" к дистрибутивному носителю (оптический диск), популярные отечественные программы ведения бухгалтерского и финансового учёта, ПО для разработки смет, архитектурного и инженерного проектирования используют защиту с электронным ключом, офисные пакеты используют защиты серийным кодом. Как правило, выбор зависит от большого числа факторов, определённых на более ранних этапах процесса разработки СЗПО. Многое, также, зависит и от соотношения стоимости копии программного продукта и стоимости копии системы его защиты.Выявление целей и задач, стоящих перед производителем ПО
. На этом этапе необходимо определить начальные условия, исходя из которых будет разрабатываться система защиты ПО. Среди возможных целей, преследуемых производителем ПО, могут быть: максимизация прибыли от продаж программного продукта, минимизация потерь от "пиратства", вытеснение конкурирующих продуктов с сегмента рынка, выход на новый сегмент рынка и др. Задачами же могут являться: защита единичного продукта, защита серии продуктов, создание системы защиты, которую в дальнейшем можно было бы предложить как самостоятельный продукт и др. Информация о целях и задачах определяет весь дальнейший процесс разработки СЗПО.Выявление функциональной направленности защищаемого продукта
. Данная информация позволяет оценивать нетехнические факторы, связанные с возможностью теневого распространения защищаемого программного продукта. К таким факторам можно отнести: распространённость и популярность продукта, условия использования, вероятность превращения пользователя в злоумышленника, вероятность уличения недобросовестных пользователей, роль документации и поддержки при использовании продукта. В частности, широко распространённый и популярный продукт вызывает у злоумышленников намного больший интерес, нежели продукт, используемый ограниченной группой пользователей, кроме того, для менее популярных продуктов снижается вероятность быстрого попадания продукта в руки злоумышленников; нелегальное использование программного продукта юридическим лицом гораздо легче выявить, чем подобное использование лицом физическим и т.п. Функциональная же направленность продукта во многом определяет озвученные нетехнические факторы. Например, программная система ведения бухгалтерского учёта находится в значительной зависимости от документации и сопровождения, менее популярна, чем текстовые реакторы и табличные процессоры, в то же время, подобные системы относятся к распространённым, наиболее вероятный пользователь - юридическое лицо, место установки - компьютер в офисе и т.д.Выработка рекомендаций по модификации исходных кодов для соответствия требованиям безопасности
. Принятые ранее решения по типу и виду разрабатываемой СЗПО дают возможность формирования конкретных рекомендаций по видоизменению исходного кода продукта (без изменения функциональности) в соответствии с требованиями системы защиты. При этом изменению могут подлежать не только конструкции языка программирования, но и параметры компиляции исходных текстов. Например, статическое подключение библиотечных модулей вместо динамического или наоборот. Как правило, подобные изменения в исходном коде, кроме касающихся непосредственного размещения элементов системы защиты, связаны с затруднением анализа общей логики работы продукта и маскировкой расположения и проявлений СЗПО [].Защита программ
Аннотация.
В статье рассматривается метод защиты программного обеспечения от изучения с помощью переноса защищаемого кода в виртуальную среду исполнения. Проводится анализ эффективности, а так же недостатков метода. Предлагается вариант реализации, позволяющий снизить себестоимость разработки.Методы защиты ПО от изучения
Рассмотрим, какие методы существуют для защиты ПО от изучения:Существуют и другие методы, а так же их комбинации и разновидности, однако, нетрудно заметить, что все они основаны на одной простой идее: избыточности. В самом деле, что такое запутывание, как не избыточное кодирование программы? Лишние переходы, лишние параметры, лишние инструкции - ключевое слово метода "лишние". То же касается любого из перечисленных методов, и, вероятно, было бы естественным объединить все эти методы в одну группу "Методов избыточного кодирования". Чем же так хороша избыточность, ведь интуитивно понятно, что она увеличивает размер программы и снижает скорость ее работы? Дело в том, что во всех этих разновидностях защиты используется понимание "человеческого фактора" - человеку тем сложнее понять логику какого-либо процесса, чем больше ресурсов этот процесс использует. Например, функциональность одной простой инструкции загрузки константы на регистр может быть "размазана" на десятки, а то и сотни инструкций, и проследить связь всех используемых ресурсов (регистров, памяти и др.) в этой последовательности человеку довольно сложно. Метод шифрования с этой точки зрения не является чем-то особенным - так же, как и в других методах, для выполнения простой инструкции (или группы) требуется избыточная последовательность команд - в данном случае это операции расшифровки, плюс операции расшифрованного кода.
Однако то, что автоматически "запутано" или усложнено, может быть так же автоматически приведено в первоначальное состояние - разработчики механизмов запутывания обычно паралельно разрабатывают и "распутыватели", а методы мутации и шифрования и вовсе подразумевают содержание обратного механизма в защищенном коде. Особняком в этой группе методов стоит лишь метод симуляции виртуального процессора, который, во-первых, приводит к высокой и неснижаемой степени запутанности результирующего кода, а, во вторых (при определенном подходе к реализации), защищенный код не содержит в явном виде методов восстановления оригинального кода. Рассмотрим этот метод подробнее.
Реализация метода
Одним из недостатков метода является высокая стоимость его реализации, однако она может быть заметно снижена. В основе системы защиты, реализующей данный метод, мог бы лежать компилятор с языка высокого уровня. Необходимо машинно-зависимая фаза в любом компиляторе всего одна - кодогенерация, от зависимостей в других фазах, как правило, можно избавиться.Если же компилятор изначально разрабатывается как мультиплатформенный, в нем, как правило, максимально упрощен процесс перенастройки на другую целевую платформу. Например, это может быть достигнуто автоматической генерацией кодогенератора по специальному описанию целевой машины. В этом случае разработчикам для смены платформы достаточно лишь изменить это описание. Но даже если собственного компилятора нет, можно воспользоваться свободнораспространяемыми с открытым кодом, например, GCC.
А чтобы максимально упростить для пользователя работу с описываемой системой защиты, ее можно снабдить механизмами встраивания в популярные среды разработки, такие как MSVC. В этом случае схема работы такого комплекса могла бы выглядеть так, как изображено на .
Соответственно, функционирование защищенного таким способом образом продукта происходило бы по схеме на Рис. 2.

Схема работы защищенного программного
Схема работы защищенного программного продуктаСпецифика использования компилятора налагает ряд особых требований к виртуальному процессору, тем не менее все они могут быть легко реализованы. Требований немного - нужно лишь обеспечить возможность доступа к внешней, относительно виртуальной машины, памяти, а так же возможность вызова внешних функций - это необходимо для взаимодействия защищенного и незащищенного кода. В остальном архитектура виртуального процессора может быть совершенно произвольной, и чем запутаннее и оригинальней она будет, тем более высокий уровень защиты будет достигнут.
Сам компилятор, кроме изменения кодогенерационной фазы, нужно доработать для приобретения им возможностей:
Последнюю возможность следует описать подробнее. Как было отражено в схеме на Рис. 2, функционал защищенных функций будет реализован через вызов симулятора, с указанием, какую из защищенных функций нужно интерпритировать. Однако, до этого, необходимо выполнить специальный код, подготавливающий для защищенной функции параметры - "переместить" их с реальных регистров и памяти на виртуальные, способом, соответствующим архитектуре виртуального процессора. Всем этим будут заниматься специальные функции, сгенерированные нашим компилятором - "оболочки". Оболочки, в свою очередь, будут использовать специальные функции симулятора для доступа к виртуальным регистрам и памяти. Характерно, что наш компилятор будет генерировать оболочки на языке высокого уровня, которые, в свою очередь, будут компилироваться стандартным компилятором, использующимся пользователем для сборки незащищенной части своего проекта. Итак, вызов защищенной функции из незащищенного модуля может выглядеть так, как изображено на .
Конечно, конкретная реализация метода виртуального процессора может быть несколько отличной от описываемой, как и схема работы защищенного им продукта. Тем не менее, описанный вариант вполне жизнеспособен, и, кроме того, относительно прост.
Сердце защищенного продукта - симулятор. Он будет включаться в любую сборку защищенного продукта. Однако не будем подробно рассматривать его реализацию, т.к. специальных требований к нему практически не предъявляется - он должен лишь симулировать архитектуру нашего виртуального процессора, включая операции доступа к внешней памяти. Стоит, однако, отметить, что с учетом специфики его применения, необходимо максимально автоматизировать процесс перенастройки симулятора на новые виртуальные архитектуры.
Недостатки же метода - следствие его достоинств:
Впрочем, последний недостаток несущественен, т.к. размер увеличится незначительно, а в некоторых случаях может даже снижаться. Первый же недостаток принципиален, и налагает некоторые очевидные ограничения на использование метода.
Виртуальный процессор в защите ПО
Суть метода такова: некоторые функции, модули, или программа целиком, компилируются под некий виртуальный процессор, с неизвестной потенциальному взломщику системой команд и архитектурой. Выполнение обеспечивает встраиваемый в результирующий код симулятор. Таким образом, задача реинжиниринга защищенных фрагментов сводится к изучению архитектуры симулятора, симулируемого им процессора, созданию дизассемблера для последнего, и, наконец, анализу дизассемблированого кода. Задача эта нетривиальна даже для специалиста, имеющего хорошие знания и опыт в работе с архитектурой целевой машины. Взломщик же не имеет доступа ни к описанию архитектуры виртуального процессора, ни к информации по организации используемого симулятора. Стоимость взлома существенно возрастает.Почему же, учитывая высокую теоретическую эффективность, данный метод до сих пор не используется повсеместно? Видимо по двум основным причинам. Во-первых, метод имеет особенности, что сужает области его потенциального применения - об этом будет сказано ниже. Во-вторых, и, возможно, это более серьезная причина, сложность (а следовательно и стоимость) реализации метода весьма высока. Если же учесть принципиальную возможность утечки информации о только что созданной системе, которая моментально приведет к ее неэффективности и обесцениванию, становится понятно, почему фирмы-производители защитного ПО не спешат реализовывать этот метод. Стоит, однако, отметить, что с теми или иными вариациями и ограничениями данный метод все же реализован в таких новейших продуктах как StarForce3, NeoGuard, VMProtect и др. Видимо таких продуктов будет становиться все больше и больше, а существующие будут развиваться, т.к. появляющиеся реализации подтверждают высокую эффективность метода, хоть и имеют пока слабые стороны.
Рассмотренный метод защиты ПО весьма
Рассмотренный метод защиты ПО весьма эффективен, учитывая то, что затраты на его разработку можно существенно сократить. Однако, особенности метода не позволяют рекомендовать его для защиты программ полностью. Так, метод не может применяться для защиты функций, критичных ко времени выполнения, а так же функций, замедление работы которых может заметно снизить эффективность использования программы пользователем. Тем не менее, аккуратное применение данного метода позволяет добиться очень высокого уровня защиты от изучения. Всвязи с этим, основной областью его применения видится повышение стойкости к изучению отдельных алгоритмов других систем защиты ПО. Кроме того, метод применим для защиты нересурсоемких алгоритмов ноу-хау, а так же для сокрытия содержания в защищаемой программе некоторых специальных данных, например, сведений об авторстве.Защита программ
Анализ на основе линейных зависимостей
Многие условия корректности операций в программе представляют собой линейные соотношения (равенства либо неравенства) между значениями числовых атрибутов объектов программы. Например, при обращении к массиву проверяется, лежит ли индекс, по которому происходит обращение, в пределах массива. В случае если и длина массива, и значение индекса в широких пределах произвольны, ответить на вопрос о возможности выхода за пределы массива при отсутствии информации о зависимости между индексом и длиной массива невозможно.Подход, предлагаемый нами к использованию в рамках разрабатываемой системы обнаружения уязвимостей, состоит в поддержании системы линейных неравенств, выполняющихся для числовых атрибутов в данной точке программы.
При потоково-чувствительном анализе потока данных в каждой точке программы (контексте) хранится информация о большом количестве числовых атрибутов. Так как одной из задач разрабатываемой системы являлась возможность анализа программ промышленного масштаба, были применены различные методы, ограничивающие вычислительные издержки, возникающие при учете линейных зависимостей.
Если при анализе требуется определить соотношение между значениями атрибутов (проверить некоторое равенство или неравенство), то переносом всех атрибутов в одну часть соотношения задача сводится к определению множества возможных значений атрибута, равного полученному в этой части выражению. Например, при проверке выхода за пределы массива требуется проверить, меньше ли индекс в массиве x размера массива l, x
Граф линейных связей
Введем для дальнейшего рассмотрения ориентированный граф линейных связей (ГЛС). Вершинам этого графа сопоставлены атрибуты, ребро (u,v) присутствует в графе, когда в систему линейных связей атрибута u входит атрибут v.Структура ГЛС существенно зависит от метода выделения системы линейных связей из многогранного множества, полученного в качестве результата преобразования. Этот вопрос будет раскрыт далее. За счет структуры ГЛС для выделения приемлемого многогранного множества, описывающего данный атрибут, достаточно собрать систему из линейных связей вершин ГЛС, встречающихся при обходе ГЛС в ширину, начиная с описываемого атрибута. Добавление линейных связей прекращается, как только одна из оценок сложности получаемого многогранного множества превышает соответствующее пороговое значение.
Для многогранного множества вводятся две оценки сложности: количество атрибутов и количество существенных ограничений неравенствами.
Предельное количество атрибутов влияет на степень вершин ГЛС. Чрезмерное повышение этого порога приводит к тому, что при обходе в ширину в ГЛС быстро собирается большое количество посторонних линейных связей (поднимая вторую оценку сложности), до того как в строящееся многогранное множество включается достаточное количество связей, важных для описываемого атрибута. Эксперименты на тестовом наборе программ показали, что оптимальным значением является порог порядка 15 атрибутов.
Количество существенных ограничений неравенствами определяет вычислительную сложность операций над многогранным множеством. Для тестового набора программ порог, приводящий к удвоению времени анализа программ при учете линейных связей по сравнению с анализом без учета линейных связей, составляет порядка 20 ограничений.
Будем далее называть операцию выделения многогранного множества из ГЛС для данного атрибута замыканием атрибута.
Использование информации о линейных
Несов В.С., Маликов О.Р., Труды Института системного программирования РАНМногогранное множество
Многогранным называется множество, задаваемое системой линейных неравенств. Каждое многогранное множество может быть представлено двумя способами: в виде системы неравенств, либо в виде множества образующих вершин и лучей (геометрическое представление). В геометрическом представлении многогранное множество равно сумме выпуклого замыкания множества вершин и конического замыкания множества лучей. На рисунке {a,b} - множество вершин, {q,s} - множество лучей.
Наличие обоих представлений и возможность перехода между ними позволяет производить различные преобразования многогранных множеств при помощи простых алгоритмов. Например, пересечение многогранных множеств задается объединением систем неравенств. Выпуклая оболочка объединения многогранных множеств задается объединением соответствующих множеств геометрического представления.
Для перехода между представлениями многогранного множества используется алгоритм Черниковой с оптимизацией Ле Вержа (H. Le Verge) [].
Сложность различных операций над многогранными множествами не позволяет применять их к многогранному множеству, описываемому всей системой линейных связей контекста. Поэтому для применения операций, требующих представления в виде многогранного множества, необходимо выделять подсистему линейных связей.
и значения атрибутов при проведении
В приведен код примера и значения атрибутов при проведении итераций статического анализа. Для каждой строки кода для данной итерации приведены ограничения, справедливые на выходе из инструкций строки, либо, в случае ветвления, ограничения на входе и выходе из инструкции. Например, в приведенном примере контекст на входе в инструкции строки 4 получается в результате объединения контекстов на выходе из инструкций строк 3 и 6.В примере имя атрибута s.len ссылается на атрибут длина строки s. Выписываются не все ограничения, а лишь важные для окончательных выводов.
Как видно, в результате анализа данного примера определяются оценки значений атрибутов, позволяющие исключить ошибки переполнения массивов. При анализе на основе интервальных оценок такие ошибки исключены не были бы.
Примеры устраненных ложных предупреждений
bftpd, mystring.c, строка 16: void cutto(char *str, int len) { memmove(str, str + len, strlen(str) - len + 1); }При корректных вызовах функции переполнения буфера не возникает. Требуемое условие в данном случае str.size>str.len-len, где str.size и str.len - соответственно атрибуты массива str, отражающие его длину и длину хранящейся в нем строки.
popclient, socket.c, строка 112: int SockWrite(socket,buf,len) int socket; char *buf; int len; { int n; while (len) { n = write(socket, buf, len); if (n <= 0) return -1; len -= n; buf += n; } return 0; }
В данном случае при вызове функции всегда len<=buf.size, при изменении len и buf на одну и ту же величину соотношение не нарушается. Так как возвращаемое значение функции write n<=len, так же сохраняется условие len>=0 (уточняемое условием цикла до len>0). За счет выполнения этих соотношений вызов функции write происходит корректно.
Результаты
На тестовом наборе из 7 программ с открытым исходным кодом были получены следующие результаты. В таблице 2 указано количество истинных и ложных предупреждений, выдающихся системой обнаружения уязвимостей до и после использования учета линейных зависимостей между атрибутами.и значения атрибутов при проведении
Код примера и значения атрибутов при проведении итераций статического анализаРезультаты тестирования
| bftpd | 54 | 20 | 34 | 7 |
| lhttpd | 22 | 5 | 17 | 0 |
| muh | 47 | 12 | 35 | 2 |
| pgp4pine | 45 | 16 | 29 | 3 |
| popclient | 34 | 7 | 27 | 12 |
| sharutils | 49 | 11 | 38 | 7 |
| troll-ftpd | 47 | 2 | 45 | 2 |
Выделение системы линейных связей из многогранного множества
После выполнения преобразования многогранного множества необходимо сохранить результат в атрибуте. Многогранное множество часто получается в результате замыкания атрибута и содержит слишком большое количество линейных связей. Так как при всех операциях каждый раз модифицируется только небольшое количество атрибутов, то, вообще говоря, изменяются только линейные связи, содержащие эти атрибуты. Поэтому из многогранного множества извлекаются только линейные связи, включающие в себя данные атрибуты.Так как системы линейных связей хранятся отдельно для различных атрибутов, часть полученных линейных связей может оказаться следствием связей, получаемых из окружающих вершин ГЛС. Сохранение таких связей излишне, так как при замыкании линейные связи окружающих вершин и так будут учтены. Поэтому такие связи исключаются.
Защита программ
Аннотация. В статье даётся краткое
В настоящее время в комплексном программном обеспечении широко применяются программные приложения, разработанные сторонними производителями. В ряде случаев такие приложения предоставляются без исходного кода на языке высокого уровня, необходимого для их аудита с точки зрения информационной безопасности их использования. Несмотря на это, такие приложения обязательно должны быть исследованы для оценки рисков их использования. Ни бинарный код, ни ассемблерный листинг, полученный в результате дизассемблирования, не позволяют с приемлемыми трудозатратами оценить взаимосвязь элементов программы, а также идентифицировать в программе стандартные алгоритмические конструкции. Восстановление программы на языке высокого уровня дает возможность преодолеть указанные выше трудности. Программные приложения, представленные в виде исполняемых файлов или на языке ассемблера, сложны для анализа их специалистами в области информационной безопасности, криптографии и т.д. и должны быть предоставлены им для анализа на более высоком уровне представления. В качестве одного из инструментальных средств повышения уровня абстракции представления программы может использоваться декомпилятор.Под декомпилятором мы будем понимать инструментальное средство, получающее на вход программу на языке ассемблера и выдающее на выход эквивалентную ей программу на некотором языке высокого уровня.
Задача декомпиляции была поставлена в 60-е годы XX века сразу же, когда стали широко применяться компиляторы с языков высокого уровня, но не утратила своей актуальности и по сей день [2]. Эта задача не решена в полной мере из-за наличия ряда трудностей принципиального характера. В частности, при компиляции программы из языка высокого уровня в язык ассемблера характерно отображение "многие к одному" концепций языка высокого уровня в концепции языка ассемблера, и, как следствие, однозначное восстановление программы на языке высокого уровня становится зачастую невозможным.
В силу указанных выше причин полностью автоматический декомпилятор реализовать принципиально невозможно.
Поэтому системы декомпиляции программ должны работать во взаимодействии с аналитиком, который (зачастую методом проб и ошибок) управляет процессом декомпиляции. В ходе декомпиляции программы решаются следующие задачи: выделение структурных единиц программы, в частности, подпрограмм в однородном ассемблерном листинге, выявление параметров подпрограмм и возвращаемых ими значений, структурный анализ, то есть восстановление операторов циклов, ветвлений и т. п., восстановление типов данных, как базовых, так и производных и другие. Поскольку все эти задачи достаточно трудоемки и алгоритмически неразрешимы, на сегодняшний день нет известных декомпиляторов, восстанавливающих программы в какой-либо язык высокого уровня, которые качественно справлялись бы со всеми перечисленными выше задачами. Для решения задач посредством использования декомпиляторов требуется хорошо представлять возможности используемого инструмента, и для достижения наилучшего результата, возможно, потребуется использовать набор декомпиляторов в некоторой композиции. В данной работе предлагается обзор наиболее известных декомпиляторов в язык Си из бинарных файлов, рассматривается набор тестов, на основе которого можно сделать сравнительный анализ работоспособности декомпиляторов, и выполняется этот анализ.
В данной работе в качестве процессорной архитектуры, с которой ведётся декомпиляция, выбрана архитектура Intel i386, наиболее распространённая в настоящее время. В листингах фрагментов программ на языке ассемблера используется синтаксис AT&T [3].
Предлагаемая работа имеет следующую структуру. Поскольку и в литературе, и на практике зачастую смешиваются понятия дизассемблирования программы и декомпиляции программы, уместно рассмотреть различия этих задач. Этому посвящен второй раздел статьи. В третьем разделе статьи дается описание основных подзадач декомпиляции с описанием возникающих трудностей при их решении. В четвертом разделе приводится обзор языка Си с точки зрения обратной инженерии. Пятый раздел посвящен описанию существующих декомпиляторов для языка Си.В пятом разделе представлены результаты сравнительного тестирования декомпиляторов на разработанном наборе тестовых примеров. В заключении сформулированы выводы работы и направления дальнейших исследований.
Boomerang
Декомпилятор Boomerang [5] является программным обеспечением с открытым исходным кодом (open source). Разработка этого декомпилятора активно началась в 2002 году, но сейчас проект развивается достаточно вяло. Изначально задачей проекта была разработка такого декомпилятора, который восстанавливает исходный код из исполняемых файлов, вне зависимости от того, с использованием какого компилятора и с какими опциями исполняемый файл был получен. Для этого в качестве внутреннего представления было решено использовать представление программы со статическими одиночными присваиваниями (SSA). Однако, несмотря на поставленную цель, в результате декомпилятор не сильно адаптирован под различные компиляторы и чувствителен к применению различных опций, в частности, опций оптимизации. Еще одной особенностью, затрудняющей использование декомпилятора Boomerang, является то, что в нем не поддерживается распознавание стандартных функций библиотеки Си.DCC
Проект по разработке этого декомпилятора [8] был открыт в 1991 году и закрыт в 1994 году с получением главным разработчиком степени PhD. В качестве входных данных декомпилятор DCC принимает 16-битные исполняемые файлы в формате DOS EXE. Алгоритмы декомпиляции, реализованные в этом декомпиляторе, основаны на теории графов (анализ потока данных и потока управления). Для распознавания библиотечных функций используется сигнатурный поиск, для которого была разработана библиотека сигнатур. Однако надо заметить, что, несмотря на это, декомпилятор плохо справляется с выявлением функций стандартной библиотеки.Декомпиляция и дизассемблирование
Рассмотрим независимо друг от друга задачу дизассемблирования и задачу декомпиляции программ. Под декомпиляцией понимается построение программы на языке высокого уровня, эквивалентной исходной программе на языке низкого уровня (языке ассемблера). Под дизассемблированием понимается построение программы на языке ассемблера, эквивалентной исходной программе в машинном коде. Программа в машинном коде представляется либо в виде исполняемого модуля в стандартном для целевой операционной системы формате (например, для Win32 в формате PE [16], а для Linux – в формате ELF [15]), либо в виде дампа содержимого памяти, либо в виде трассы исполнения программы.Традиционно декомпиляция рассматривается в более широком смысле, а именно, как построение программы на языке высокого уровня по программе в машинном коде. Очевидно, что в такой постановке задача декомпиляции поглощает задачу дизассемблирования. Такое "широкое" понимание декомпиляции излишне, поскольку дизассемблирование и декомпиляция решают разные по сути задачи, хотя и используют схожие методы (в частности, построение графа потока управления и исполняемого покрытия программы). Так, при дизассемблировании выполняется трансляция исполняемого файла, представляемого в виде набора машинных команд, в программу на языке ассемблера. При декомпиляции программа с представления низкого уровня транслируется в представление высокого уровня. Дальнейшим этапом повышения уровня абстракции программы может быть рефакторинг, посредством которого из программы на языке Си можно, например, получить программу на языке Си++.
Рассмотрим разбиение задач декомпиляции и дизассемблирования на подзадачи. Так, при дизассемблировании требуется решать следующие основные задачи:
Замена абсолютных адресов на символические.
При декомпиляции должны быть решены следующие основные задачи:
Выявление параметров и возвращаемых значений.
Восстановление структурных конструкций языка высокого уровня.
Замена всех обращений к памяти на конструкции языка высокого уровня (в частности, сюда входит идентификация обращения к локальным переменным и параметрам и их замена на символические имена, идентификация обращений к массивам и их замена на операции с массивами и т. д.).
В дальнейшем мы будем рассматривать задачу декомпиляции в узкой постановке, то есть как задачу трансляции программы, представленной на языке низкого уровня, в частности, на языке ассемблера, в программу на языке высокого уровня, в частности, на Си.
Декомпиляторы в язык Си
В данном разделе дается краткое описание существующих на сегодняшний момент декомпилятров в язык Си. Это – декомпиляторы Boomerang [5], DCC [8], REC [14] и плагин Hex-Rays [10] к дизассемблеру IdaPro [11]. Все рассматриваемые декомпиляторы, кроме плагина Hex-Rays, на вход принимают исполняемый файл, и выдают программу на языке Си. В том случае, когда декомпилятор оказывается не в состоянии восстановить некоторый фрагмент исходной программы на языке Си, этот фрагмент сохраняется в виде ассемблерной вставки. Надо заметить, что даже небольшие исходные программы после декомпиляции зачастую содержат очень много ассемблерных вставок, что практически сводит на нет эффект от декомпиляции.В отличие от этого, плагин Hex-Rays принимает на вход программу, являющуюся результатом работы дизассемблера Ida Pro, то есть схему программы на ассемблеро-подобном языке программирования. В качестве результата Hex-Rays выдает восстановленную программу в виде схемы на Си-подобном языке программирования. Тем не менее, для простоты мы в дальнейшем объединим процесс дизассемблирования с использованием Ida Pro и последующей декомпиляции.
Языки высокого уровня с точки зрения обратной инженерии
Языки высокого уровня позволяют повысить уровень абстракции представления реализуемого алгоритма, избавляя программиста от необходимости заботиться о низкоуровневых деталях. Эти языки соперничают друг с другом по простоте использования и гибкости, а разработчики компиляторов соперничают по производительности сгенерированного ими кода. Следовательно, имеется большое количество разнообразных языков высокого уровня, и для каждого из них существует множество компиляторов.При восстановлении программ по программе на языке низкого уровня, имея широкое представление о языке высокого уровня, нужно с достаточной точностью восстановить то, что было написано на языке высокого уровня в исходном тексте программы. Точность и трудозатраты восстановления программы сильно зависят от языка высокого уровня, на котором была написана исходная программа.
Язык Си формально считается языком высокого уровня, однако в нем присутствует много черт языка низкого уровня. В частности, в языке Си поддерживается прямой доступ к памяти и работа с указателями. При обращении к элементам массива не контролируется выход за его пределы, то есть возможен доступ к областям памяти, не имеющим никакого отношения к массиву. С другой стороны, в языке Си поддерживаются такие высокоуровневые конструкции, как производные типы данных: массивы, структуры, объединения, а также условные операторы, циклы и т. д.
На практике особую значимость имеют декомпиляторы, транслирующие ассемблерный листинг в язык Си. Во-первых, восстанавливать программы, написанные изначально на языке Си, удобно, потому что это процедурный язык и у него много низкоуровневых особенностей. Во-вторых, язык Си широко применяется в промышленном программировании, и большое количество системных приложений написано именно на языке Си. С другой стороны, восстанавливать программу из ассемблера в объектно-ориентированный язык принципиально сложнее, да и к тому же программа, реализованная на основе процедурной парадигмы программирования, может быть переведена в объектно-ориентированную программу посредством рефакторинга ее кода. Следовательно, в данной работе ограничим множество рассматриваемых декомпиляторов теми, которые восстанавливают на языке Си программы, представленные либо на языке ассемблера, либо в виде исполняемых файлов.
О некоторых задачах обратной инженерии
, , Труды Института системного программирования РАНОбзор основных подзадач декомпиляции
Рассмотрим основные задачи декомпиляции и подходы к их решению.Структурный анализ
Одним из результатов предыдущих фаз анализа ассемблерного листинга программы является разбиение потока инструкций ассемблерного листинга на отдельные функции и выявление точек входа в функции и возврата из функций.Инструкции ассемблерной программы в функции могут рассматриваться как представление нижнего уровня (Low-level intermediate representation) [12]. В частности, представление низкого уровня отличается от представления высокого уровня (программы на языке Си) отсутствием структурных управляющих конструкций (if, for и т. п.).
Для восстановления управляющих конструкций сначала строится граф потока управления программы. По графу потока управления строится дерево доминаторов, затем дуги графа потока управления классифицируются на "прямые", "обратные" и "косые".
На основании этой информации уже можно выполнять непосредственно структурный анализ, то есть восстановление высокоуровневых управляющих конструкций [6]. Поиском в глубину в графе выделяются шаблоны основных структурных конструкций, которые затем организуются в иерархическую структуру.
Восстановление типов
Задача автоматического восстановления типов данных на настоящее время – одна из задач в области декомпиляции, наименее проработанных с теоретической точки зрения. Ее можно условно разделить на подзадачу восстановления базовых типов данных языка, таких как char, unsigned long и т. п., и на подзадачу восстановления производных типов, таких как типы структур, массивов и указателей. В работе [13] рассматривается восстановление как базовых, так и производных типов при декомпиляции, однако этот подход имеет ряд существенных недостатков, и отсутствует его практическая реализация. В работе [4] описан подход к автоматическому восстановлению производных типов языка по исполняемому файлу. Такой подход используется для анализа на уязвимость программ в виде исполняемых файлов и поэтому не применим напрямую к задаче восстановления типов при декомпиляции.На практике же все декомпиляторы, кроме Hex-Rays, вообще не восстанавливают даже базовые типы переменных, а в выражениях используют явное приведение типов, что делает восстановленные выражения сложными для понимания и модификации.
Выделение функций
Одной из основных структурных единиц программ на языке Си являются функции, которые могут принимать параметры и возвращать значения. Откомпилированная программа, однако, состоит из потока инструкций, функции в котором никак структурно не выделяются. Как правило, компиляторы генерируют код с одной точкой входа в функцию и одной точкой выхода из функции. При этом в начало кода, генерируемого для функции, помещается последовательность машинных инструкций, называемая прологом функции, а в конец кода – эпилог функции. И прологи, и эпилоги функций, как правило, стандартны для каждой архитектуры и лишь незначительно варьируются. Например, стандартный пролог и эпилог функции для архитектуры i386 показаны ниже:Пролог: pushl %ebp movl %esp, %ebp
Эпилог: movl %ebp, %esp popl %ebp ret
Прологи и эпилоги функций могут быть легко выделены в потоке инструкций. Кроме того, при работе с трассами можно считать, что инструкции, на которые управление передается с помощью инструкции call, являются точками входа в функции, а инструкции ret завершают функции. Возникает соблазн считать инструкции, расположенные между прологом и эпилогом, или между точками входа и выходом, телом функции, однако в этом случае можно натолкнуться на ряд сложностей. Во-первых, при компиляции программы могут быть указаны опции, влияющие на форму пролога и эпилога функции. Например, опция компилятора GCC –fomit-frame-pointer подавляет использование регистра %ebp в качестве указателя на текущий стековый кадр, когда это возможно. В этом случае пролог и эпилог функции будут, как таковые, отсутствовать. Во-вторых, отдельные оптимизационные преобразования могут разрушать исходную структуру функций программы. Очевидным примером такого оптимизационного преобразования является встраивание тела функции в точку вызова. Встроенная функция не существует как отдельная структурная единица программы, и ее автоматическое выделение представляется затруднительным.
Существуют оптимизирующие преобразования, которые приводят к появлению в машинном коде конструкций, принципиально невозможных в языках высокого уровня.
Таким оптимизирующим преобразованием является, например, sibling call optimization. Если список параметров двух функций идентичен, и первая функция вызывает вторую с этими параметрами, то инструкция вызова подпрограммы call может быть преобразована в инструкцию безусловного перехода jmp в середину тела второй функции. Результатом такого рода "неструктурных" оптимизаций будет появление переходов из одной функции в другую, появление функций с несколькими точками входа или несколькими точками выхода. Другим источником "неструктурных" конструкций в машинной программе являются операторы обработки исключений в таких языках, как Си++.
Таким образом, хотя в типичном случае компилятор генерирует хорошо структурированный код, поддающийся разбиению на функции, достаточно легко может быть получен и "неструктурированный" код. Следует отметить, что в этом случае влияние программиста, пишущего программу на языке Си, на структуру генерируемого кода ограничено возможностями языка Си, не позволяющего бесконтрольной передачи управления между функциями и не поддерживающего механизм исключений. Поэтому можно предполагать, что если восстанавливается программа с языка ассемблера, полученная в резу-льтате компиляции программы на языке Си, то она не содержит "неструк-турных" особенностей, описанных выше, и может быть разбита на функции.
Выявление параметров и возвращаемых значений
В языках высокого уровня, в частности, Си поддерживается передача параметров в функции и возврат значений. В языке Си существует только передача параметров по значению, в других языках могут поддерживаться и другие механизмы. Заметим, что здесь мы рассматриваем только механизмы передачи параметров, отображаемые в генерируемый машинный код. Передача параметров по имени, передача параметров в шаблоны и другие механизмы периода компиляции программы здесь не рассматриваются.Способы передачи параметров и возврата значений для каждой платформы специфицированы и являются составной частью так называемого ABI (application binary interface). Под платформой здесь понимается, как обычно, тип процессора и тип операционной системы, например, Win32/i386 или Linux/x86_64. Одной из задач ABI является обеспечение совместимости по вызовам приложений и библиотек, скомпилированных разными компиляторами одного языка или написанных на разных языках.
Так, для платформы win32/i386 используется несколько соглашений о передаче параметров. Соглашение о передаче параметров _cdecl
используется по умолчанию в программах на Си и Си++ и имеет следующие особенности [9]:
Параметры выравниваются в стеке по границе 4 байт, и адреса всех параметров кратны 4. То есть параметры типа char
и short передаются как int, но и дополнительное выравнивание для размещения, например, double
не производится.
Очистку стека производит вызывающая функция.
Регистры %ebx, %esi, %edi, %ebp не должны модифицироваться в результате работы функции.
Значения целых типов, размер которых не превосходит 32 бит, возвращаются в регистре %eax, 64-битных целых типов – в регистрах %eax и %edx, вещественных типов – в регистре %st(0).
Если функция возвращает результат структурного типа, то место под возвращаемое значение должно быть зарезервировано вызывающей функцией. Адрес этой области памяти передается как (скрытый) первый параметр.
Отметим, что этот набор правил – это именно соглашения, которые "добровольно" выполняются в сгенерированном коде. Пока речь не заходит об интерфейсе с независимо скомпилированными сторонними модулями, программист может в определенной мере модифицировать эти правила, существенно затрудняя задачу автоматического восстановления функций.
Опять же можно предполагать, что если программа декомпилируется из автоматически полученного ассемблерного кода (либо компилятором, либо дизассемблером), то в ней используются только соглашения о передаче параметров из некоторого предопределенного множества. Причем в одной программе для разных функций не могут использоваться разные соглашения о передаче параметров.
На первом этапе решения задачи выявления параметров функций следует определить следующие особенности вызова функций:
Размер области параметров функции. Почти все соглашения о передаче параметров могут быть достаточно надежно идентифицированы по используемым инструкциям. Так, соглашение о передаче параметров stdcall требует, чтобы параметры из стека удалялись вызываемой функцией. Для этого может использоваться единственная инструкция системы команд i386 – ret N, где N
– размер удаляемых из стека параметров. Таким образом, использование этой инструкции для возврата из функции указывает как на соглашение о передаче параметров, так и на размер параметров функции.
В случае вызова функции по указателю при статическом анализе нам может быть неизвестен адрес вызываемой функции. В этом случае не представляется возможным отследить, как возвращается управление из вызываемой функции. Определение соглашения о вызовах тогда должно быть отложено на фазы последующего анализа.
Итак, на фазе выявления параметров и возвращаемых значений определяется размер передаваемых в функцию параметров и способ возврата значения из функции. В дальнейшем эта информация используется как начальная при восстановлении символических имен и восстановлении типов.
Работа с информацией: Безопасность - Защита - Софт - Криптография
- Информационная безопасность
- Аспекты информационной безопасности
- Системы информационной безопасности
- Софт и информационная безопасность
- IInternet Information Services
- Защита и безопасность
- Защита с Firewall
- Атаки и информационная безопасность
- Информационная безопасность в интернет
- Борьба с вирусами
- Антивирусы против вирусов
- Хакеры и информационная безопасность
- Криптография