Сейчас на форуме: tyns777 (+4 невидимых)

 eXeL@B —› Программирование —› MSDIS
Посл.ответ Сообщение


Ранг: 673.3 (! !), 400thx
Активность: 0.40.31
Статус: Участник
CyberMonk

Создано: 06 октября 2010 20:27 · Поправил: mak
· Личное сообщение · #1

Вопрос такой , тема собственно извечная и не раз подымалась , мне нужен дизасм двиг , их полно , но каждый не подходит по опеределенным причинам , то что подходит хорошо возможно имеет ошибки внутри. Но вопрос не в этом , в поисках решения хотел избежать написания Интерфейса врапера для дизасма , то есть выбор решений такой , выбрать двиг что больше подходит , сделать Врапер для дизасмов , или найти лучший вариант.

В лучший вариант попал двиг от майкросовта , под названием MSDIS170.dll, он имеет (вроде как по просмотру в иде) (диз)ассемблер , то есть похоже может собирать код , для меня это 50 процентов работы в программе. Но как пользоваться длл с первого взгляда не понятно , там сделано как то как с ООП , есть некоторые хидеры , которые вроде отчасти описывают интерфейс , но по вызову их напрямую их не существует и имена изменены в експорте. Не суть важно. Ктонибудь работал с этой библиотекой? Может подскажете , есть ли там ассемблер команд, и может с использованием что то по новее есть чем на рсдн?

На РСДН есть такой пример для версии старой

Code:
  1. #ifdef MSDIS110_EXPORTS
  2. #define MSDIS110_API __declspec(dllexport)
  3. #else
  4. #define MSDIS110_API __declspec(dllimport)
  5. #endif
  6.  
  7. // This class is exported from the MsDIS110.dll
  8. class __declspec(novtable) MSDIS110_API DIS
  9. {
  10. public:
  11.     enum DIST {Smth = 1};
  12.     enum REGA {eax, ecx, edx, ebx, esp, ebp, esi, edi};
  13.  
  14.     typedef unsigned int (__stdcall* PfncchaddrSetCallBack)(DIS const *,unsigned __int64,char *,unsigned int,unsigned __int64 *);
  15.     typedef unsigned int (__stdcall* PfncchconstSetCallBack)(DIS const *,unsigned long,char *,unsigned int);
  16.     typedef unsigned int (__stdcall* PfncchfixupSetCallBack)(DIS const *,unsigned __int64,unsigned int,char *,unsigned int,unsigned __int64 *);
  17.     typedef unsigned int (__stdcall* PfncchregrelSetCallBack)(DIS const *,REGA,unsigned long,char *,unsigned int,unsigned long *);
  18.     typedef unsigned int (__stdcall* PfncchregSetCallBack)(DIS const *,REGA,char *,unsigned int);
  19.     typedef unsigned __int64 (__stdcall* PfndwgetregSetCallBack)(DIS const *,REGA);
  20.  
  21. public:
  22.     unsigned __int64 Addr() const;
  23.     unsigned int CchFormatAddr(unsigned __int64 Address, char *szBuffer, unsigned int nMaxLen) const;
  24.     unsigned int CchFormatInstr(char *szBuffer, unsigned int nMaxLen) const;
  25.  
  26.     DIST Dist(void) const;
  27.     static DIS * __stdcall PdisNew(DIST dist);
  28.  
  29.     PfncchaddrSetCallBack PfncchaddrSet(PfncchaddrSetCallBack);
  30.     PfncchconstSetCallBack PfncchconstSet(PfncchconstSetCallBack);
  31.     PfncchfixupSetCallBack PfncchfixupSet(PfncchfixupSetCallBack);
  32.     PfncchregrelSetCallBack PfncchregrelSet(PfncchregrelSetCallBack);
  33.     PfncchregSetCallBack PfncchregSet(PfncchregSetCallBack);
  34.     PfndwgetregSetCallBack PfndwgetregSet(PfndwgetregSetCallBack);
  35.  
  36.     void * PvClient(void) const;
  37.     void * PvClientSet(void *);
  38.  
  39.     virtual Method2() = 0;
  40.     virtual ~DIS() = 0;
  41.     //    returns addres for jmp dword ptr or call dword ptr ops
  42.     virtual unsigned __int64 GetRefTarget() = 0;
  43.     /*
  44.         dwParam must be null
  45.     */
  46.     virtual BOOL IsStackModifierBelowZeror(DWORD dwParam) = 0;
  47.     
  48.     //    returns addres for jmp or call ops
  49.     virtual unsigned __int64 GetTarget() = 0;
  50.  
  51.     //    returns instruction size
  52.     virtual unsigned int GetInstrSize() = 0;
  53.  
  54.     virtual unsigned int GetNextInstr(unsigned __int64 nAddress, const LPVOID pBuffer, unsigned int nMaxLen) = 0;
  55.  
  56.     //    ????
  57.     virtual unsigned int Method8(DWORD a, DWORD b, DWORD c, DWORD d) = 0;
  58.  
  59.     //    returns 4 for 32 bit code, 2 for 16 bit
  60.     virtual unsigned int GetSize() = 0;
  61.     /*
  62.         dwParam must be null
  63.     */
  64.     virtual unsigned int GetStackModifierSize(DWORD dwParam) = 0;
  65.  
  66.     virtual unsigned int GetCodeBytes(char *szBuffer, unsigned int nMaxLen) = 0;
  67.  
  68.     //    Always return 44
  69.     virtual unsigned int GetVersion() = 0;
  70.  
  71.     //    Always return 1
  72.     virtual unsigned int GetOne() = 0;
  73.     /*
  74.         GetNumArgs()
  75.         returns:
  76.             3 for    shld    ebx,esi,1
  77.             2 for    mov        eax, cr0
  78.             1 for    pus        ds
  79.             0 for    ret
  80.     */
  81.     virtual unsigned int GetNumArgs() = 0;
  82.     /*
  83.         ???? Always GPF
  84.     */
  85.     virtual unsigned int Method15(DWORD a, DWORD b, DWORD c) = 0;
  86.     /*
  87.         ???? Always GPF
  88.     */
  89.     virtual unsigned int Method16(DWORD a) = 0;
  90.  
  91.     /*
  92.         IsNull()
  93.         returns 1 if arg is NULL, 0    otherwise
  94.     */
  95.  
  96.     virtual BOOL IsNull(LPVOID pAddress) = 0;
  97.     
  98.     /*
  99.         returns:
  100.             2 for call, push
  101.             1 for ret, pop
  102.             0 otherwise
  103.  
  104.         dwParam must be null
  105.     */
  106.     virtual unsigned int IsStackModified(DWORD dwParam) = 0;
  107.  
  108.     /*
  109.         DWORD GetInstructionClass()
  110.         returns:
  111.             call dword ptr                =    0x09
  112.             call                        =    0x08
  113.             iret                        =    0x07
  114.             jmp near                    =    0x05
  115.             jmp                            =    0x04
  116.             div                            =    0x03
  117.             int                            =    0x02
  118.             all other                    =    0x01
  119.     */
  120.     virtual unsigned int GetInstructionClass() = 0;
  121.     
  122.     /*
  123.         DWORD GetInstructionType()
  124.         returns:
  125.             call    dword ptr            =    0x11
  126.             call    far                    =    0x10
  127.             call                        =    0x0F
  128.             call    near                =    0x0E
  129.             jecxz                        =    0x0D
  130.             loop                        =    0x0C
  131.             cjmp                        =    0x0B
  132.             cjmp    near                =    0x0A
  133.             iret                        =    0x09
  134.             ret                            =    0x08
  135.             jump    dword ptr            =    0x07
  136.             jmp        far                    =    0x06
  137.             jmp                            =    0x05
  138.             jmp        near                =    0x04
  139.             div                            =    0x03
  140.             int                            =    0x02
  141.             all other                    =    0x01
  142.     */
  143.     virtual unsigned int GetInstructionType() = 0;
  144.  
  145.     //    Always    return 0xFFFFFFFF
  146.     virtual unsigned int GetUINTMax() = 0;
  147. };
  148.  


Саму либу приложу внизу , если когото заинтересует ..

В файле msdis.h описано , может и достаточно , не знаю , но понять сразу не получилось , может от перегрузки работой.

В любом случае вызвать функцию
Code:
  1. CbDisassemble proto  :ADDR, :ptr , :size_t
  2. ;// CbGenerateLoadAddress generates one or more instructions to load
  3. ;// the address of the memory operand from the last disassembled
  4. ;// instruction into a register. UNDONE: This register is currently hard
  5. ;// coded for each architecture. When pibAddress is non-NULL, this method
  6. ;// will store the offset of a possible address immediate in this location.
  7. ;// The value stored is only valid if the AddrAddress method returns a
  8. ;// value other than addrNil. It is not valid to call this method after
  9. ;// a call to CbDisassemble that returned 0 or when the return value of
  10. ;// Memreft is memreftNone. It is architecture dependent whether this
  11. ;// method will succeed when the return value of Memreft is memreftOther.
  12. ;// UNDONE: Add reg parameter.


напрямую не получилось.

Что касается врапера , то вполне вероятно он будет выполнен в любом раскладе , рано или поздно, смысл его таков , он должен представлять из себя Мульти интерфейс врапер для разных двигов , то есть само использование в программе будет всегда стандартизовано к интерфейсу , там же должно быть так чтобы можно было динамически подгружать дизасм дллки , причем так , чтобы структуры предоставляемые пользователю имели одинаковые офсеты , а также были доступные свободные слоты с детекцией функционала.

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

Вторая причина такого интерфейса , это то что код может разбираться не только под виндовс .... но и скажем под теже вм , этот модуль будет просто подключаем , а все остальное уже реализовано в главном модуле.

Возможно третья причина это подсветка =) , но это уже так ..

По подобной архитектуре не удалось найти инфы , кто нибудь может указать пальцем как такое может быть реализовано???

П.С. Возможно , что нужно будет паралельное использование 2 разных двигов , это еще одна функциональная черта врапера в моем случае. Спасибо за советы заранее. Вроде все

-----
RE In Progress [!] Coding Hazard [!] Stay Clear of this Cube





Ранг: 673.3 (! !), 400thx
Активность: 0.40.31
Статус: Участник
CyberMonk

Создано: 06 октября 2010 20:37 · Поправил: mak
· Личное сообщение · #2

Что то тупняк с добавлением кода

6f9c_06.10.2010_CRACKLAB.rU.tgz - msdis.rar

-----
RE In Progress [!] Coding Hazard [!] Stay Clear of this Cube





Ранг: 793.4 (! !), 568thx
Активность: 0.740
Статус: Участник
Шаман

Создано: 06 октября 2010 21:25
· Личное сообщение · #3

mak я использую двиг от OllyDbg он умеет и дизасмить и ассемблить. Я делаю и то и то. Баг был только с декодированием префиксов у джампов, но это решаемо на раз-два.

-----
Yann Tiersen best and do not fuck





Ранг: 673.3 (! !), 400thx
Активность: 0.40.31
Статус: Участник
CyberMonk

Создано: 06 октября 2010 22:01
· Личное сообщение · #4

PE_Kill забыл приписать , это был первый выбор двиг от OllyDbg , но как быть с x64 ? Можно конечно поменять под 64 , но тогда врапер интерфейса самое то , но двигов тоже не разгонишься под 64 с ассемблированием , в мсдис есть 64 , есть 32 , и если бы добить его структуру и узнать про ассемблирование , почему бы не попробовать.

-----
RE In Progress [!] Coding Hazard [!] Stay Clear of this Cube





Ранг: 793.4 (! !), 568thx
Активность: 0.740
Статус: Участник
Шаман

Создано: 06 октября 2010 22:43 · Поправил: PE_Kill
· Личное сообщение · #5

Ну тут да, оля не катит. Тогда я ничем не подскажу. А что от самого MS'а нет мануалов?

PS Глянул мануал. Это OLE объект, его надо регистрировать regsvr32 если он еще не пореган, потом через TypeLib использовать. Что то ты меня заинтересовал, надо посмотреть будет.

-----
Yann Tiersen best and do not fuck




Ранг: 101.0 (ветеран), 344thx
Активность: 1.150
Статус: Участник

Создано: 06 октября 2010 23:48
· Личное сообщение · #6

Собственно есть два нормальных дизасма UDIS86 и Mediana. Первый хорош тем, что расширяем. Второй быстро развивается и фиксится.




Ранг: 1053.6 (!!!!), 1078thx
Активность: 1.060.81
Статус: Участник

Создано: 07 октября 2010 03:38 · Поправил: reversecode
· Личное сообщение · #7

mak
у crypto IDR на этом двиге, может у него спросить?

еще вопрос, у тебя есть полный интерфейс в msdis? там для других платорм
начиная от MIPS и еще штук 6 было(правда это в первых версиях MSDIS)

могу кстати идой глянуть как msdis юзается
только нужно найти комплект который работает именно с этой длл
то что под рукой - VC6, но он работает с msdis110


ps посмотрел на IDR у crypto тоже используется msdis110



Ранг: 369.8 (мудрец), 400thx
Активность: 0.390
Статус: Участник

Создано: 07 октября 2010 06:42
· Личное сообщение · #8

mak пишет:
Вопрос такой , тема собственно извечная и не раз подымалась , мне нужен дизасм двиг , их полно , но каждый не подходит по опеределенным причинам

Пробовал двиг mediana? Весьма удобная штука, автор оперативно фиксит баги и добавляет фичи по запросу. Я делал не нем эмуль, впечатления самые положительные.

-----
PGP key <0x1B6A24550F33E44A>





Ранг: 2014.5 (!!!!), 1278thx
Активность: 1.340.25
Статус: Модератор
retired

Создано: 07 октября 2010 08:20
· Личное сообщение · #9

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



Ранг: 590.6 (!), 408thx
Активность: 0.360.18
Статус: Модератор

Создано: 07 октября 2010 10:08
· Личное сообщение · #10

Если говорить о дизасме, то чем плох distorm?
Активно развивается, открытый, поддерживает и 32 и 64.

-----
старый пень





Ранг: 673.3 (! !), 400thx
Активность: 0.40.31
Статус: Участник
CyberMonk

Создано: 07 октября 2010 10:42 · Поправил: mak
· Личное сообщение · #11

PE_Kill Доки искал , но особо ничего не нарыл , с оле последний раз лет 7 назад наскоком из за написания прог на делфи работал. Это из дока ? или на глаз определил?

reversecode Да , нужно спросить у крипто , спасибо за заметку , в остальных версиях тоже самое , там есть МИПС и другие , интерфейсы взял с исходников ВИНДБГ , которые лежат в исходниках винды , внизу прилепил все остальное. Версия что выше приложена , она создана в 2007 году , то есть так понимаю ничего не меняли. msdis110 нету в наличии , так можно былоб просто год посмотреть ради интереса.

Archer,ntldr,int это нужно сейчас , а не потом, итак медленно идет, но учитывая предпочтения , есть повод задуматься над универсальным переходником. Появилось новое альтернативное решение , использовать Дизасм + asmjit , нужно попробовать , там и попробую медиану в том числе.

В медиане , табличный формат нравится , осталось автоматом делать линкед листы , сейчас просто дизасмом никого не удивишь. В майкрософте команды разбиты на блоки и типы , таким образом это удобно для создания псевдоязыка. Приятные мелочи как в оллидбг Disassembleback или Checkcondition, то есть большинство этих функций нужны для определенных целей , например бэктрассы , там нужно делить на блоки , основная идея в дисторме может быть доработана , там есть с чем работать в плане кондишн стопов созданных для графа. Есть еще много мелочей казалось бы, но типичный ответ , в чем проблема? Реализуй сам ... с таким подходом хочется сразу сказать .. куда ты лезишь тогда с рекламой своего двига)))

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

Mediana под пристальным взглядом многих реверсеров , которые активно помогают в развитии , это хорошо , а пока можно и MSDIS глянуть , внутри как мне кажется есть интересные функции ...

r_e у него нет ассемблера

1c41_07.10.2010_CRACKLAB.rU.tgz - dis.rar

-----
RE In Progress [!] Coding Hazard [!] Stay Clear of this Cube





Ранг: 527.7 (!), 381thx
Активность: 0.160.09
Статус: Участник
Победитель турнира 2010

Создано: 07 октября 2010 12:07 · Поправил: OKOB
· Личное сообщение · #12

Вот тут --> CLR Command-Line Debugger (cordbg) Sample <-- MSDIS тоже используется в качестве двига (пример от самих МелкоМягких)

-----
127.0.0.1, sweet 127.0.0.1





Ранг: 1053.6 (!!!!), 1078thx
Активность: 1.060.81
Статус: Участник

Создано: 07 октября 2010 14:29
· Личное сообщение · #13

mak
о то что надо
странно но этих хидеров в соурсах win2k я не видел



Ранг: 369.8 (мудрец), 400thx
Активность: 0.390
Статус: Участник

Создано: 07 октября 2010 14:36
· Личное сообщение · #14

mak пишет:
это нужно сейчас , а не потом

А оно работает сейчас. Библиотека открытая, документированная, работает нормально. Дает достаточно информации об инструкциях.

mak пишет:
а пока можно и MSDIS глянуть

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

-----
PGP key <0x1B6A24550F33E44A>





Ранг: 1053.6 (!!!!), 1078thx
Активность: 1.060.81
Статус: Участник

Создано: 07 октября 2010 15:18 · Поправил: reversecode
· Личное сообщение · #15

mak
у меня была идея в реверсе MSDIS для приватного испльзования
в нём как то кода по сравнению с другими дизасмами поменьше
лучше что ли спроектирован


Code:
  1. static uint32_t tq_1(uint8_t *origin_offset, uint8_t *offset, struct INSTRUCTION *instr, int op_index, struct OPERAND_SIZE *opsize, struct INTERNAL_DATA *idata, uint8_t mode);

хоть бы уменьшили количество не нужных символов
в INTERNAL_DATA_(t/T) *idata
преобразовали ...




Ранг: 673.3 (! !), 400thx
Активность: 0.40.31
Статус: Участник
CyberMonk

Создано: 07 октября 2010 16:12
· Личное сообщение · #16

OKOB Супер , посмотрю , спасибо)

reversecode не сразу их заметил , но они там есть ... Сколько времени на это уйдет? И зачем , хотел сначала выдрать код , на асме не разон, Vamit помог еще определиться , но потом оставил так как есть. Открытых двигов полно , а если ставить конкретные цели то в конце станет ясно что не нужно это. У меня возник такой вопрос из за мании ассемблера , типо чем меньше тем лучше)))) поэтому уж оч урезать хотелось лишнее... но потом прошло

ntldr может не так выразился , имел ввиду что там нет ассемблера , выше описана проблема. Солидарен по поводу либ

Кому нужно архив с дебагом что указал OKOB



c52d_07.10.2010_CRACKLAB.rU.tgz - debugger.rar

-----
RE In Progress [!] Coding Hazard [!] Stay Clear of this Cube





Ранг: 1053.6 (!!!!), 1078thx
Активность: 1.060.81
Статус: Участник

Создано: 07 октября 2010 16:25
· Личное сообщение · #17

mak пишет:
Сколько времени на это уйдет?

еще не знаю, я давно изучал этот вопрос
и меня интересовал не только x86
меня интересовало полностью msdis реверснуть

если доставать только X86 может совсем не много
у меня pdb не качались ни для одной MSDIS, если кому то удалось их моиметь - поделитесь

так вы с Vamit реверснули? или я что то не понял, с чем он помог




Ранг: 1053.6 (!!!!), 1078thx
Активность: 1.060.81
Статус: Участник

Создано: 07 октября 2010 16:34
· Личное сообщение · #18

mak пишет:
В лучший вариант попал двиг от майкросовта , под названием MSDIS170.dll, он имеет (вроде как по просмотру в иде) (диз)ассемблер

сечас смотрю msdis160 от 9 студии которая под рукой
link.exe использует msdis
cde.dll и msvsmon.exe

насколько можно быть увереным что msdis работает и как ассемблер? я почему то в этом пока что сомниваюсь..



Ранг: 369.8 (мудрец), 400thx
Активность: 0.390
Статус: Участник

Создано: 07 октября 2010 16:59
· Личное сообщение · #19

В качестве ассемблера можно использовать libyasm

-----
PGP key <0x1B6A24550F33E44A>





Ранг: 1053.6 (!!!!), 1078thx
Активность: 1.060.81
Статус: Участник

Создано: 07 октября 2010 19:17 · Поправил: reversecode
· Личное сообщение · #20

хм удивительно
дествительно в msdis160 только для платформы x86 есть и ассемблер
но входной поток для ассемблирования не текстовый файл ASM команд
а бинарный поток чисел которые стоят в соответсвии с их тестовыми значениями

тоесть к примеру
код mov eax,eax должен пройти в FEncode() как поток бит
тоесть нужен еще какойто препроцессор который тестовые ASM команды преобразуют в поток бит

что бы понять каким командам стоит в соответсвие какой бит и как они складываются, нужно реверсить

вот вроде так, может кто по другому что то понял...

Code:
  1. bool __thiscall DISX86::FEncode(unsigned __int64, struct DIS::INSTRUCTION const *, struct DIS::OPERAND const *, unsigned int, unsigned int)


ps нужна программа которая использует msdis как ассемблер..



Ранг: 188.1 (ветеран), 419thx
Активность: 0.140
Статус: Участник

Создано: 10 октября 2010 12:46
· Личное сообщение · #21

mak
msdis110 нету в наличии , так можно былоб просто год посмотреть ради интереса.
Возьми dis.dll от IDR, это он и есть
Мне лениво было писать свой дизассемблер, а Мелкософтовский я когда-то поковырял, понял, что там к чему, и решил воспользоваться. Если нужны подробности, могу отписаться в личку.




Ранг: 1053.6 (!!!!), 1078thx
Активность: 1.060.81
Статус: Участник

Создано: 25 октября 2010 04:45 · Поправил: reversecode
· Личное сообщение · #22

разобрались
есть и ассемблер(X86(16,32,64) и ARM(каких то два режима)), начиная с msdis160

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

итого кратко

для дизассемблирования используется такой алго

Code:
  1. while ( d->CbDisassemble(addr, buf, len) ) //происходит диассемблирование
  2. {
  3.         //для вывода инструкций обычно используется такой набор
  4.           d->CchFormatInstr(...)
  5.           d->CchFormatAddr(...)
  6.           d->CchFormatBytes(...)
  7.  
  8.        //но так же можно уже получить дизассемблированые данные в структурах
  9.         // DIS::INSTRUCTION, DIS::OPERAND
  10.         //которые используется в функциях выше
  11.         d->FDecode(DIS::INSTRUCTION *instr, DIS::OPERAND *opa, uint opaCnt);
  12. }


вот восстановленая функция FDecode
Code:
  1. bool DISX86::FDecode(DIS::INSTRUCTION *inst, DIS::OPERAND *opa, unsigned int opaCnt)
  2. {
  3.   unsigned int copa;
  4.   bool res;
  5.  
  6.   copa = Coperand();
  7.   if ( copa <= opaCnt )
  8.   {
  9.     inst->opa = Opa();
  10.     inst->dwModifiers = DwModifiers();
  11.     inst->coperands = Coperand();
  12.     InnerDecode();
  13.     memcpy(opa, &m_rgoperand[0], sizeof(m_rgoperand[0]) * copa);
  14.     res = 1;
  15.   } else
  16.     res = 0;
  17.   return res;
  18. }


для ассемблирования еще проще

Code:
  1. do {
  2.  
  3.   //здесь нужно заполнять instr, opa
  4.  
  5.  d->FEncode(uint64 addr, DIS::INSTRUCTION const *instr, DIS::OPERAND const *opa, uint opaCnt, uint someLen = 1);
  6.  
  7. }while ( d->cbAssemble(buf, len) );


итого
проблема только с лексическим анализатором который бы заполнял данные *instr, *opa
которого в msdis и нет
и нет пока еще всех данных которые нужны для заполнения тех сткрутур для режима ассемблирования
хотя это все табличные данные которые содержатся в dis.h disx86.h файлах
но от версии к версии msdis, они немного увеличиваются(добавляются разные режимы и инструкции)


 eXeL@B —› Программирование —› MSDIS
:: Ваш ответ
Жирный  Курсив  Подчеркнутый  Перечеркнутый  {mpf5}  Код  Вставить ссылку 
:s1: :s2: :s3: :s4: :s5: :s6: :s7: :s8: :s9: :s10: :s11: :s12: :s13: :s14: :s15: :s16:


Максимальный размер аттача: 500KB.
Ваш логин: german1505 » Выход » ЛС
   Для печати Для печати