· Начало · Отвђтить · Статистика · Поиск · FAQ · Правила · Установки · Язык · Выход · WASM.RU · Noir.Ru ·

 WASM Phorum —› WASM.ASSEMBLER —› длина команд х86

. 1 . 2 . >>

Посл.отвђт Сообщенiе


Дата: Июн 25, 2004 03:17:24

хотелось бы научить небольшую программку определять длину инструкций (для начала можно только под 286)..

пытался разобраться с форматом этих самых инструкций, получается что придётся заводить таблицу со всеми начальными байтами команд, а потом ещё и флаги mod и r/m проверять..

может есть методы попроще (хотя я сомневаюсь) или где-то можно уже в готовом виде взять (на крайняк придётся какой-нибудь hiew расковырять)?


Дата: Июн 25, 2004 05:13:58

Глянь сайт z0mbie.host.sk
У него есть пара-тройка исходников такого рода, например LDE-32 -- Length-Disassembler Engine; XDE -- Extended length disassembler и др.


Дата: Июн 25, 2004 13:22:18

> придётся заводить таблицу со всеми начальными байтами команд, а потом ещё и флаги mod и r/m проверять..

Именно так все дизассемблеры и поступают.


Дата: Июн 25, 2004 17:27:20

Причём этого будет всё одно явно недостаточно для определения длины команды. Нужно прежде всего ещё убедится что это байта блока code а значит иметь ещё таблицу префиксов, колличество которых до этого блока в формате нефиксировано. Нужно будет анализировать бит S и наличие префикса 66 для того чтобы определить сколько ушло на непосредственный операнд, нужно будет определять не является ли первый "непрефикс" кодом указывающим на переключение группы. Нужно будет иметь два декодера modrm для 16и 32х битных форматов и разбираться какой из них подключать в зависимости от присутвствия префикса 67.
И много чего ещё надо будет, я перечислил только частичку которая никак ни к "таблице первых байт" ни "к флагам mod и r/m" не относится.
В ковычках поставил не только потому что это цитата, но и "термины" в таком звучании просто безграмотны.


Дата: Июн 25, 2004 18:57:11

The Svin
ты уже давно грозился написать статью на эту тему (помнишь, когда твой винт грохнулся)
было бы здорово, а то я уже сколько с опкодами работаю, но четкой систематизации так и не увидел :(
такое ощущение, что интел делал дешифратор с большого бодуна


Дата: Июн 28, 2004 21:23:09

2 The Svin
и вовсе ни к чему мне такие заморочки..
к тому же не понятно, почему термины просто безграмотны..

а по поводу статьи - было бы здорово если бы кто-нибудь написал..

P.S. чуть не забыл http://bugtraq.ru/cgi-bin/forum.mcgi?type=sb&b=2&m=106804


Дата: Июн 28, 2004 21:35:11

Я вообще никакой по дизассемблерам и формату маш-кодов. А Свин является лучшим специалистом в этой области из всех кого знаю. Поэтому ты эту инструкцию испытай. На каких-нибудь сложных случаях. Нетривиальных.
Самые лучшие известные мне дизассемблерные движки заложены в HIEW и в OllyDBG. И там, и там участвовал Свин.
А ИДА, кстати, обладает довольно паскудным дизассемблером. На эту тему redplait статью писал...

The Svin
А если честно, то у меня, как у новичка в этом вопросе, тоже возникают некоторые неуютные позывы после таких объяснений. Я не знаю, как это точно выразить... М-м-м-м...
Вот, скажем, хорошо бы пошел пример. Берем какой-нибудь дизассемблер. Из тех, что на MSDN описаны, в движок Dr.Watson или WinDBG заложены и т.п. Рассматриваем принцип в них заложенный (пока БЕЗ комментариев). Пропускаем его на частном случае (черт, мне теперь кажется, что там вообще одни только частные случаи) и смотрим, почему не так. Потом объясняем как надо сделать, чтобы было ТАК. И сразу многое станет понятным.


Дата: Июн 28, 2004 22:49:51

zelych
Эта задача (исходя из N статей в сети) решаеться уже очень давно.

Здесь (в аттаче) теория моих скромных трудов по поиску минимального дерева анализа.

P.S.
(Спасибо за это кое кому, ну буду говорить в слух. Технологии VX рулят!!!)



837825657__X86.rar


Дата: Июн 28, 2004 23:14:46

по поиску минимального дерева анализа.

Господи, какой штиль, какой штиль!


Дата: Июн 29, 2004 09:47:54 · Поправил: Edmond

volodya
Господи, какой штиль, какой штиль!

?Володя, ты в порядке? Тебе помочь? Тебя кто-то обидил?


Дата: Июн 29, 2004 10:47:43

ух.. не думал что вопрос вызовет столько эмоций..
всем большое спасибо.

лично мне хватило того, что было на багтраке, но, повторюсь, статейка не помешала бы - народ-то интересуется..


Дата: Июл 1, 2004 10:14:08

2 The Svin
и вовсе ни к чему мне такие заморочки..
к тому же не понятно, почему термины просто безграмотны..


Прошу пардону, я опять без инета. Напросился почту посмотреть.
zelych
Я может быть не слишком развёрнуто ответил, но всё же ответил и всё по существу. А вот твою фразу про "заморочки" - нужно догадываться - что ты имел ввиду.
Я морали читать тебе не собираюсь, но посмотри с практической точки зрения - тебе же самому выгодно если ты спрашиваешь или переспрашиваешь что-то, чтобы тебя поняли.

Как я должен понимать "какие заморочки тебе ни к чему?"
Должен ли я понимать, что то, что я указал тебе понадобится ПОМИМО modrm и таблицы первых байт на самом деле и не нужно тебе чтобы определить длину инструкции?
Если так то ты ошибаешься.
Без определения "префикс ли" ты не доберёшься до блока кода то есть вообще не поймёшь где начался постпрефиксный код. Префиксов при этом не поймёшь сколько по первому байту, да вообще не почему не поймёшь сколько их пока все байты от начала инструкции не переберёшь и не найдёшь первый "не префикс". В "нормальном опкоде" их должно быть от 0 до 4х, в реальности - может быть до 14и. Значит тебе мало таблицы первых байт,
тебе нужна будет таблица префиксов или битовая строка к примеру как отражение множества префиксов, или ещё что-то чтобы проверить не принадлежит ли текущий байт до кода множеству префиксов.
Не хочешь этой заморочки - твоё дело. Но никакого способа без этого сосчитать префиксы, которые тоже составляют длину инструкции и найти байт блока кода нет.
Дальше, без проверки присутсвовал ли префикс 66 в инструкции ты не поймёшь, например, сколько байт в теле инструкции занимает непосредственный операнд.
Элементарный пример, если ты в 32х битном режиме то
если у тебя просто
B9 xx ....
то ты определишь что после b9 ещё четыре байта занимает непосредственный операнд. И всего 1 + 4 = 5 байта в инструкции
а если
66 B9 ...
то после B9 только два байта непосредственного операнда
и всего 1+1+2=4 байта.
Причём 66 может быть не обязательно непосредственно перед b9. Главное чтобы он оказался среди префиксов предваряющих инструкцию.
Дальше ты говоришь про modrm и как ты поймёшь по каким правилам декодировать его 16и или 32х битного адреса если не проверишь на наличие префикса 67?
вот допустим у тебя в дампе:
8b 44 8D 00 xx xx
здесь префикса 67 нет и ты должен декодировать modrm по 32х битным правилам у тебя получится 4 байтная инструкция с группой расширения modrm в 3 байта а если был бы префикс
67 то modrm декодировался бы уже по другим правилам и его
группа заняла бы только два байта а последний 00 уже относился бы к следующей инструкции.
Бит s изменит длину непосредственного операнда а значит и всей инструкции на 3и байта.
Я на этом закончу, хотя "дополнительные заморочки" далеко не исчерпаны вышеизложенными примерами и есть ещё ряд дополнительных факторов которые надо учитывать.
Так, что если тебе эти заморочки ненужны, ради бога только ты без них не определишь длины инструкции.

PS. По поводу статей. Кое что лежит ведь в разделе Образовательные программы. Не всё конечно, остальное допишется потом. Но, Володя, там есть главное - обучалки - они как раз даже лучше картинок которые ты любишь. Они картинки которые ты можешь сам генерировать на стенде, да ещё с проверкой знаний.
Я работаю как раз сейчас над очередной статьёй по опкоду и програмками обучающими. Но выходит хуже чем хотелось бы, потому бесконечно переписываю :)


Дата: Июл 1, 2004 11:37:50

Max
такое ощущение, что интел делал дешифратор с большого бодуна
Да кончай ты делать мне смешно :)
У меня ребёнок в 7 лет за неделю не напрягаясь всё освоил.
Просто с уже готовыми современными программистами сложнее
в объяснениях.
Привыкли
1. Мыслить байтами и типам которые кратны им.
2. Привыкли к форматам фиксированной длины.
3. Привыкли что если относится функционально к одному то рядышком должно быть.

И не привыкли к динамическим бинарным картежам с "пустыми" членами.
Главное разобраться с составными частями (функциональными блоками)
опкода. Сначала порознь. Потом вместе. Это есть в обучалках,
вплоть до самого сложного блока - Modrm.
Я даже декодер его кидал прямо на форум. Вместе с исходником и тестирующей прогой.
modrm самый сложный из блоков, остальные вообще простые.

Дальше смотришь в конец второго тома Intel, там даны форматы в битовых полях.
Группируюешь их по сходному вхождению общих блоков и единству последовательности
этих блоков. И всё. Просто ожидается (и это ложное ожидание) что
последовательность какая-то единая, а их несколько, но конечное и небольшое число.
например группа однобайтная:
xxxxxreg
Чтобы визуально понять что такое группа - каждая обучалка использует
только коды одной какой нить группы.
Нет только обучалок по использованию бита S в командами использующими
его с непосредственными операндами, и нет примеров эскейпкодами опкодов
FPU и других вроде MMX, SSE и т.п.
В будущем будут, если будет интерес.
Все кто тыкался в обучалки и почитали сопровождающие статейки, говорят,
что очень быстро разобрались, хотя до этого ни в зуб ногой.
Я даже начал слышать фразы про то, что modrm - это детские вопросы,
хотя до этого и у Касперски и у Юрова и у Зубкова - у всех видел ошибки
в правильной трактовке. Так, что если это уже кажется "детским", то чего
"распознание групп" то сложность вызывает (это всё меня спрашивают в последнее время),
мне в лом сейчас писать про это, я другое пишу.
А если modrm кажется простым - то 2ой том, сортировать по общности форматов
в группы. Искать битовый определитель в ID кода.
Ну если не в терпёж - можно самостоятельно сделать.
Не получается - ждите, я может и много слов пишу иногда, но медленно
их подбираю, как может странно это и не кажется.
Потому как сжато и общё и малопонятно - итак уже есть у Intel.
А чтобы понятней написать, нужно подобрать лучше слова, примеры и методику
чем те кто писал доки для Intel.
Для меня не так просто, тем более учебные зарисовки и всякие обучающие
приёмы у меня погибли.
Это когда в обучалки тыкаешь всё просто, а чтоб придумать чтоб было
понятно и просто и даже (лучше всего) вобще банально - для меня непросто
было. Это потом эти воры которые накатали Art of Disassebmly писали свои
обучалки содрав с моих всё что в них было. А до этого и у Intel этого небыло
даже. Да и та команда, тестирующую часть несмогла повторить, хотя я даже
исходники им подарил.
А если другие тут разбирающиеся есть, пусть напишут сами,
мне только легче будет. Самое сложное в этом не фичи и не
декодеры. Самое сложное в таких прогах - найти интерфейс.

Я пишу сейчас маленькое дополнение к статье о modrm посвящённое
альтернативному кодированию, и использованию картежей.
И вот в подвешенном опять состоянии - писать ли развёрнуто вообще
о генерации картежей или просто упоминуть.
С сопроваждающими утилями
Вроде тема простая, а поди ты не в одном ассемблере это не обобщили.
Хотя альтернативное кодирование может дать хороший эффект при выравнивании
избегая вставок пустых инструкций.
Получается по практике и не очень простая.


Дата: Июл 1, 2004 19:51:59

The Svin
проблемы тут в следующем (и не только у меня)
есть, например:
   C6 /0    mov r/m8,imm8

тут поле reg должно быть равно нулю (для данной команды). есть еще порядка 30 команд, в которых поле reg должно принимать строго определенное значение.

косяк в том, что далеко не все это принимают во внимание, например ида забивает на это поле болт и "правильно" дизассемблирует команды, которые при исполнении вызовут эксепшн (т.к. имеют неверное значение поля reg). есть и другие товарищи - borg например, да и hiew одно время этим страдал.

возникает вопрос, как систематизировать эти команды?

в сорцах того-же borg'а, команда идентифицируется по первому байту (в данном случае, причем я не говорю щас о разного рода префиксах). по этому первому байту из таблицы выбирается набор флагов, которые и позволяют дешифровать команду. но значение поля reg второго(modrm) байта не проверяются(!), что и приводит к подобного рода ошибкам.
в иде, я подозреваю, происходит тоже самое.

olly например дизассемблирует такие команды правильно, но каждая команда в таблице описывается не кислым по размерам рекордом, а учитывая всяческое отсутствие в сорцах комментариев, и массу ни с чем не ассоциируемых аббревиатур, я задолбался с ними разбираться, и в конце концов забил...

короче говоря, хотелось бы услышать твои умные мысли о том, как написать дизассемблер, точнее, как сгруппировать опкоды, в каком виде (оптимальном) их(опкоды) описывать и т.п., желательно в виде статьи.

з.ы. дело то не в том, чтобы понять(и запомнить) структуру опкода, которую не описывал разве что ленивый, а без мануала определить, что db 0c6h, 0c7h, 0 работает, а db 0c6h, 0cfh, 0 - нет
или твой малой на память помнит, что для push (0xff) поле reg должно обязательно равняться шести?


Дата: Июл 1, 2004 21:26:17

Max> поле reg должно быть равно нулю

Да, мы это уже много раз обсуждали... Кстати, в новой версии Большого Мануала опкоды с7\с8 вынесены в отдельную "группу", для которой валидна только кодировка reg=000 (а вот опкод 8f до сих пор нет). И кстати, тема называется "длина команд х86"; что должен делать декодер длин (не дизассемблер), встретив "инвалида"?

Max> возникает вопрос, как систематизировать эти команды?

Значит так... ;)

Кодировки codr очень хорошо документированы intel (см. Table A-4. Opcode Extensions for One- and Two-byte Opcodes by Group Number).

Наибольшие трудности вызывает то, что в основном опкоде бывают различные поля.

Среди них:

Биты d, s, w - внимательно разгляди таблицу опкодов, и постарайся определить, у каких опкодов где эти биты расположены. ;)

Регистр - его кодировка располагается в младших трёх битах следующих опкодов: 010xxreg, 10010reg, 1011wreg

Код команды - располагается в "средних" трёх битах (3 - 5) в следующих опкодах:
00cod0dw, 00cod10w; или двух битах (3 - 4) в 010xxreg

Сегментный регистр (один из четырёх, существовавших на момент проектирования структуры опкодов) - в битах 3 - 4 в опкодах: 001sr110 (это префиксы), 000sr11c

Код условия - располагается в четырёх младших битах опкода в формате tttN, хорошо проиллюстрированном в одной из свинских обучалок.

Это - основные моменты. И у меня есть подозрение, что они всегда будут вызывать непонимание, если не будут "увидены" человеком в результате "пристального разглядывания таблицы опкодов", а будут преподноситься разжёванными на блюдечке (потому что будут вызывать вопрос "а почему так?").

. 1 . 2 . >>


Powered by miniBB 1.6 © 2001-2002
Время загрузки страницы (сек.): 0.072