• XSS.stack #1 – первый литературный журнал от юзеров форума

Статья Python+IDA

KraZz

(L3) cache
Пользователь
Регистрация
18.06.2009
Сообщения
196
Реакции
7
Gray Hat Python
Я из нищебродской (в прошлом aka буржуйской) литературы читаю только оффдокументацию
И эта "книга" тоже не стала исключением, но...
Как-то случайно наткнулся на вот это:
http://forum.reverse4you.org/showthread.php?t=1186
Очень понравилось оформление, да и вообще с удовольствием почитал перевод
Но разочаровало то, что у нас тупо (в большинстве случаев), на что способны так это сделать перевод.. при этом бывает, что русский парень пишет на инглеше занятное чтиво, а потом с этого ломаного инглиша переводят на наш русский %))))
Короче, когда смотрел, обратил внимание на дату книги 2009 - эт когда ее писали, был 2008
И вот получается, какбы.. актуальна тема (раз переводят) и значит нужно
Вот и вспомнил, что когда-то сам начинал и че-то там...
Решил написать об этом здесь, скажу сразу "преамбула" начала здесь:
А это какбэ должно было быть продолжением, писалось для версии ИДЫ 5.1 или 5.2 (точно не помню) но "релиза" так и не было, и вот немного подшаманил и причесал под "новую" версию ИДЫ 6.1, решил выложить здесь - может кому-то и пригодится...

Стал замечать значительное количество постов советующих и нахваливающих Python и это естественно радует, плюсов миллион с тележкой и наверное, всех преимуществ не сосчитать, но есть и те кто (просто уверен) никак не может себя заставить подсесть на Python
Я тоже был таким, никак не хотел пересаживаться на Python, я кодил в то время на lua и мне казалось, что такой монстр как Python не достоин моего внимания
Но как-то раз случайно попал на античат, а там есть девочко с мужским именем, ну вот она рассказывала в статье про Python и мне так стало обидно - мля, что "какая-та баба" знает и умеет кодить на питоне, а мну как последний парень на деревне еще танцевать с бубном не научился...

Предположим что у вас в ИДЕ 6.1 уже установлен плагин IDAPython
Но если вдруг еще нет 0_o, то скачать соответствующую версию можно здесь:
http://code.google.com/p/idapython/downloads/list
и здесь соответствующую версию Python`а:
http://www.python.org/ftp/python/
как установить?, читаем в файле README.txt (раздел INSTALLATION FROM BINARIES) + гугл

Я знал, что меня на все сразу не хватит, поэтому решил сразу запостить начало, а на днях выложу здесь вторую часть..
ЗЫ: Кто отгадает, про что будет написано в статье - с меня "пять золотых монеток"+"конфетко" %)))
 
Apocalypse пишет:
Деобфускатор или декомпилятор ВМПрота?
Не-не, эт инфа приватна и релизить я ее точно не буду, может потом когда уже станет неактуальна только в качестве экспоната :)
ЗЫ: все просто дальше некуда и инфа рассчитана для начинающих и вообще просто показать тем, кто еще не знает, что существует такой вариант.. + обновить инфу, а то там в книге (Глава 11 - IDAPython) написано про питон для версии 5.2, слишком поздновато как-то для такого перевода будет ;) %)))

Я НЕ хотел бы здесь рассказывать об.. вернее разжевывать и переписывать (кстати, что делают в большинстве книг) то, что хорошо описано в официальной "документации" к ИДЕ , а хочу показать как относительно просто можно добавить свой код в питон и потом его юзать в скриптах
Иногда бывает, что некоторые вещи кажутся очень страшными и сложными для изучения на первый взгляд, но потом может оказаться, что все проще некуда
Первый шаг - это разбить сложную задачу на несколько простых
Самый простой шаг - это создать базовый код, впоследствии который мы будем "допиливать"
В ИДЕ есть шаблон плагина, с него мы и начнем:
Код:
#include <windows.h> 

#include "include/typeinf.hpp"
#include "include/loader.hpp"

#pragma comment(linker, "/entry:DllMain")

int idaapi init(void)
{
   return PLUGIN_KEEP;
}// end « init »

void idaapi term(void)
{
   return;
}// end « term »

void idaapi run(int arg)
{
   msg("Test\n");
   return;
}// end « run »

///////////////////////////////////////////////////////////////////////////////////////////////
char comment[] = "";
///////////////////////////////////////////////////////////////////////////////////////////////
char help[] = "";
///////////////////////////////////////////////////////////////////////////////////////////////
char name[] = "Python Test";
///////////////////////////////////////////////////////////////////////////////////////////////
char hotkey[] = "";
///////////////////////////////////////////////////////////////////////////////////////////////
plugin_t PLUGIN =
{
   IDP_INTERFACE_VERSION,
   0,
   init, // initialize
   term, // terminate. this pointer may be NULL.
   run, // invoke plugin
   comment,
   help, // multiline help about the plugin
   name,  // the preferred short name of the plugin
   hotkey  // the preferred hotkey to run the plugin
};

BOOL WINAPI DllMain(HINSTANCE hInstance, DWORD fdwReason, PCONTEXT pContext)
{
   return TRUE;
}// end « DllMain »
И def для экспорта
Код:
EXPORTS
PLUGIN
Создадим в студии проект для DLL и определим в свойствах проекта (Preprocessor Definitions) __IDP__ и __NT__
И добавим в проект файлы из SDK 6.1 из папки include
Еще желательно установить плагин для студии: (чтобы удобнее было)
http://exelab.ru/download.php?action=get&n=OTQw - Whole Tomato Visual Assist X v10.6.1859.0 скачать
Из кода видно, что все проще некуда
Компилим и копируем в директорию ИДЫ с плагинами, можно еще проще сделать и автоматизировать процесс, прописав в студии в свойствах проекта в Build Events->Post-Build Event в поле Command Line команду: (для примера)
COPY "С:\IDA6.1\Plugins\pyida\pyida.dll" "С:\Program Files\IDA\plugins\pyida.plw" /Y /B
Теперь откроем в ИДЕ 6.1 какой-нибудь тестовый test.idb и лезем в меню Edit->Plugins->Python Test и запускаем
В результате в окне Output window ИДЫ появится слово Test
Стало быть, первый этап пройден и у нас есть базовый рабочий код..
Важно довести стадию компиляции до автоматизма, чтобы не возникало ошибок, и почитать обязательно что-нибудь (http://www.opensc.ws/showthread.php?t=18471 - IDA Pro Book, 2nd Edition - 2011), чтобы иметь базовые знания, в принципе вся основная инфа находится в комментариях в коде SDK ИДЫ, а книги по ИДЕ я хз. для чего вообще нужны...

P. S.
Следующую часть выложу позже, чет опять меня на все не хватило.. %)))
 
http://habrahabr.ru/company/PENXY/blog/139655/ - Интеграция Python и C++
Гы-ы-ы, прикольно, а я как раз примерно это и хотел тут запостить %)))
Ну, собственно если эту инфу в кучу собрать, как раз можно написать что-то лучше, чем IDAPython и получить от ильфака фулку+премию %)))
Вот так элементарно изучив азы Python`а и C++ можно стать "элитой" и писссать книжки %)))
Ладно, эт даже будет интересным в плане сравнения написанных книг и вот таких статеек писаных на коленках с дрожащими руками %)))
 
Код:
#include <windows.h> 
#include "include/typeinf.hpp"
#include "include/loader.hpp"
#include "include/Python.h"

#pragma comment(linker, "/entry:DllMain")

#pragma comment(lib, "python26.lib") //python 2.6
#pragma comment(lib, "ida.lib") //sdk 6.1

HWND GetWindowMessageHandle(DWORD IdaWindow)
{
   //MD: 1b66134e3491139bb9eb032abda9efc0 (idag.exe)
   //00443550 _TIdaWindow_MessageClearExecute proc
   //00443550    mov eax, dword ptr [eax+0EFCh] <<----
   //00443556    mov edx, dword ptr [eax]
   //00443558    call dword ptr [edx+0DCh]
   //0044355E    retn
   //0044355E _TIdaWindow_MessageClearExecute endp
   return (HWND)*(DWORD*)((*(DWORD*)((*(DWORD*)IdaWindow)+0xEFC))+0x180);
}

static PyObject *pyida_msg_clear(PyObject *self, PyObject *args)
{
   if(!PyArg_ParseTuple(args, "")) return NULL;
   
   HWND hRichEditOutput = NULL;
   DWORD IdaWindow = (DWORD)GetProcAddress(GetModuleHandle(NULL), "_IdaWindow");
   if(IdaWindow)
   {
      hRichEditOutput = GetWindowMessageHandle(IdaWindow);
      if(hRichEditOutput)
      {
         SetWindowText(hRichEditOutput, "");
      }
   }
   return Py_BuildValue("I", hRichEditOutput);
}

static PyMethodDef pyidaMethods[] = {
   {"msg_clear", pyida_msg_clear, METH_VARARGS, "msg clear"},
   {NULL, NULL, 0, NULL}
};

int idaapi init(void)
{
   Py_Initialize();

   if(!Py_IsInitialized())
   {
      warning("Error: Py_Initialize() failed");
      return PLUGIN_SKIP;
   }

   Py_InitModule("pyida", pyidaMethods);

   return PLUGIN_KEEP;
}

void idaapi term(void)
{
   Py_Finalize();
   return;
}// end « term »

void idaapi run(int arg) 
{
   return;
}// end « run »

///////////////////////////////////////////////////////////////////////////////////////////////
char comment[] = "";
///////////////////////////////////////////////////////////////////////////////////////////////
char help[] = "";
///////////////////////////////////////////////////////////////////////////////////////////////
char name[] = "pyida Test";
///////////////////////////////////////////////////////////////////////////////////////////////
char hotkey[] = "";
///////////////////////////////////////////////////////////////////////////////////////////////
plugin_t PLUGIN =
{
   IDP_INTERFACE_VERSION,
   0,
   init, // initialize
   term, // terminate. this pointer may be NULL.
   run, // invoke plugin
   comment,
   help, // multiline help about the plugin
   name,  // the preferred short name of the plugin
   hotkey  // the preferred hotkey to run the plugin
};

BOOL WINAPI DllMain(HINSTANCE hInstance, DWORD fdwReason, PCONTEXT pContext)
{
   return TRUE;
}// end « DllMain »
Теперь описание того что делает этот код

Нужно выставить в опциях компилятора __cdecl - это нужно для питона!

Код:
#include "include/Python.h"
Нужно обязательно добавить в проект файлы из питона 2.6 из папки include

Код:
#pragma comment(lib, "python26.lib") //python 2.6
#pragma comment(lib, "ida.lib") //sdk 6.1
:) Это те либы, которые надо добавить для компиляции (пока ограничимся python 2.6) :)

Код:
int idaapi init(void)
{
   Py_Initialize();

   if(!Py_IsInitialized())
   {
      warning("Error: Py_Initialize() failed");
      return PLUGIN_SKIP;
   }

   Py_InitModule("pyida", pyidaMethods);

   return PLUGIN_KEEP;
}
ИДА вызывает init для того чтобы плагин инициализировал какие-либо данные, вот это и есть то место где и нужно инициализировать код питона с помощью Py_Initialize
Функция Py_Initialize должна всегда вызываться первой, т. е. до использования какого-либо питоновского кода
Py_InitModule "создает пи-модуль" с нашим кодом и с именем pyida
Потом мы можем в скрипте его "вызвать" так:
Код:
import pyida
или так:
Код:
from pyida import *

Код:
static PyMethodDef pyidaMethods[] = {
   {"msg_clear", pyida_msg_clear, METH_VARARGS, "msg clear"},
   {NULL, NULL, 0, NULL}
};
PyMethodDef - эта структура (вернее массив структур :)), которую нужно предварительно заполнить
msg_clear - это имя функции, которое мы будем писать в питоновском скрипте при ее вызове
пример:
pyida.msg_clear()

pyida_msg_clear - эта собственно та функция, которая вызовется и выполнится (подробнее чуть ниже)
об остальных параметрах этой структуры более подробно можно узнать из справки питона

Код:
static PyObject *pyida_msg_clear(PyObject *self, PyObject *args)
{
   if(!PyArg_ParseTuple(args, "")) return NULL;
   
   HWND hRichEditOutput = NULL;
   DWORD IdaWindow = (DWORD)GetProcAddress(GetModuleHandle(NULL), "_IdaWindow");
   if(IdaWindow)
   {
      hRichEditOutput = GetWindowMessageHandle(IdaWindow);
      if(hRichEditOutput)
      {
         SetWindowText(hRichEditOutput, "");
      }
   }
   return Py_BuildValue("I", hRichEditOutput);
}
Иногда (при частом использовании скриптов в ИДА) нужно перед запуском скрипта очистить окно лога (Output window), так как при большом потоке данных трудно что-то найти нужное среди "старого хлама", а каждый раз через меню очищать...

В ИДЕ есть экспортируемый указатель _IdaWindow на класс...
Мы этот указатель получаем и передаем в функцию GetWindowMessageHandle, а там в НЕ есть тру хаке (это нам помогает избежать написания массы нах не нужного кода) находим хендл окна Output window
Окно это ничто иное, как RichEdit поэтому шлем ему "привет" с пустой строкой, тем самым очищаем Output window
Раньше в ИДЕ там был ListBox и чтобы очистить, нужно было юзать примерно такой код:
Код:
HWND GetWindowMessageHandle(DWORD IdaWindow)
{
   return (HWND)*(DWORD*)((*(DWORD*)((*(DWORD*)((*(DWORD*)((*(DWORD*)IdaWindow)+0x7D8))+0x218))+0x10))+0x180);
}
[…]
SendMessage(hListBox, LB_RESETCONTENT, 0, 0);
С ListBox`ом была масса ограничений в юзалибити, например нельзя было выделить и скопировать непосредственно нужную часть текста
С RichEdit это ограничение было снято и появились новые "фичи", к примеру, стало возможным выводить в одну строку ряд адресов и при двойном клике на нужном переходить сразу на него в окне дизасма (IDA View)...

Код:
void idaapi term(void)
{
   Py_Finalize();
   return;
}// end « term »
При "выгрузке" плагина деинициализируем питон, вызвав функцию Py_Finalize

Юзаем в скрипте так:
Код:
import pyida
pyida.msg_clear()

Меня опять не хватило на еще большую оставшуюся часть, да и смысла я, честно говоря, не вижу, просмотров мало, плюсов не было - стало быть, тема нах никому здесь не интересна...
 
Ой!Не надо так делать! :( Очень интересно всё о чём ты пишешь.Если нет обсуждений и комментов,ещё не означает,что информация не нашла своего слушателя.Быть может просто нечего сказать.Я вот как раз делаю потуги в освоении питона +IDA и кто то ещё подчерпнёт
для себя из этого топика.
 
Меня опять не хватило на еще большую оставшуюся часть, да и смысла я, честно говоря, не вижу, просмотров мало, плюсов не было - стало быть, тема нах никому здесь не интересна...
да, я тебя прекрасно понимаю =) Что касаемо плюсов, то, я думаю, многие бы поставили, но тут не всем это доступно =) (ограничение в 50 сообщений)
 


Напишите ответ...
  • Вставить:
Прикрепить файлы
Верх