Ich beschloss, die Assemblersprache zu lernen. Der Hauptgrund dafür ist, disassemblierten Code verstehen zu können und möglicherweise effizientere Teile des Codes schreiben zu können (z. B. über c ++), Dinge wie Code-Höhlen usw. zu tun. Ich habe gesehen, dass es zig verschiedene Arten von Assemblierungen gibt Also, für die Zwecke, die ich erwähne, wie soll ich anfangen? Welche Art von Montage soll ich lernen? Ich möchte lernen, indem ich zuerst einige einfache Programme (z. B. einen Taschenrechner) mache, aber das Ziel selbst wird darin bestehen, sich damit vertraut zu machen, damit ich den Code verstehen kann, der beispielsweise von IDA Pro angezeigt wird.
Ich benutze Windows (wenn das einen Unterschied macht).
edit: Also, anscheinend zeigt jeder auf MASM. Obwohl ich den Punkt verstehe, dass es über Funktionen auf hohem Niveau verfügt, die alle gut für den Assembler-Code-Programmierer sind, ist das nicht das, wonach ich suche. Es scheint Anweisungen zu haben, die in gängigen Deassemblern (wie IDA) nicht angezeigt werden. Was ich also nach Möglichkeit hören möchte, ist die Meinung von jedem, der ASM für die von mir gewünschten Zwecke verwendet (Lesen des zerlegten exe-Codes in IDA), nicht nur von "allgemeinen" Assembly-Programmierern.
bearbeiten: OK. Ich lerne bereits Montage. Ich lerne MASM und benutze nicht die hochrangigen Dinge, die mir egal sind. Was ich gerade mache, ist das Ausprobieren meines Codes in __asm-Direktiven in C ++, damit ich die Dinge viel schneller ausprobieren kann, als wenn ich alles von Grund auf mit MASM machen müsste.
Antworten:
Beginnen Sie mit MASM32 und schauen Sie sich von dort aus FASM an . Aber du wirst Spaß mit MASM haben.
quelle
Ich habe das schon oft gemacht und mache das auch weiterhin. In diesem Fall, in dem Ihr primäres Ziel darin besteht, Assembler zu lesen und nicht zu schreiben, gilt dies meines Erachtens.
Schreiben Sie Ihren eigenen Disassembler. Nicht für den Zweck, den nächstgrößeren Disassembler herzustellen, ist dieser ausschließlich für Sie. Ziel ist es, den Befehlssatz zu lernen. Ob ich Assembler auf einer neuen Plattform lerne, mich an Assembler für eine Plattform erinnere, die ich einmal kannte. Beginnen Sie mit nur wenigen Codezeilen, fügen Sie beispielsweise Register hinzu und pingen Sie zwischen dem Zerlegen des Binärausgangs und dem Hinzufügen immer komplizierterer Anweisungen auf der Eingabeseite.
1) Lernen Sie den Befehlssatz für den jeweiligen Prozessor
2) Lernen Sie die Nuancen des Schreibens von Code in Assembler für diesen Prozessor, so dass Sie jedes Opcode-Bit in jedem Befehl wackeln können
3) Sie lernen den Befehlssatz besser als die meisten Ingenieure, die diesen Befehlssatz verwenden, um ihren Lebensunterhalt zu verdienen
In Ihrem Fall gibt es ein paar Probleme. Normalerweise empfehle ich zunächst den ARM-Befehlssatz. Heute werden mehr ARM-basierte Produkte ausgeliefert als alle anderen (einschließlich x86-Computer). Die Wahrscheinlichkeit, dass Sie ARM jetzt verwenden und nicht genügend Assembler kennen, um Startcode oder andere Routinen zu schreiben, die ARM kennen, kann jedoch helfen oder auch nicht, was Sie versuchen. Der zweite und wichtigere Grund für ARM ist, dass die Befehlslängen eine feste Größe haben und ausgerichtet sind. Das Zerlegen von Anweisungen mit variabler Länge wie x86 kann als erstes Projekt ein Albtraum sein. Ziel ist es, den Befehlssatz zu erlernen, um kein Forschungsprojekt zu erstellen. Der dritte ARM ist ein gut gemachter Befehlssatz, Register werden gleich erstellt und haben keine individuellen Spezialnuancen.
Sie müssen also herausfinden, mit welchem Prozessor Sie beginnen möchten. Ich schlage zuerst den msp430 oder ARM vor, dann zuerst den ARM oder dann das Chaos von x86. Unabhängig von der Plattform verfügt jede Plattform, die es wert ist, verwendet zu werden, über Datenblätter oder Referenzhandbücher für Programmierer, die vom Hersteller frei sind und den Befehlssatz sowie die Codierung der Opcodes (die Bits und Bytes der Maschinensprache) enthalten. Um zu lernen, was der Compiler tut und wie man Code schreibt, mit dem der Compiler nicht zu kämpfen hat, ist es gut, einige Befehlssätze zu kennen und zu sehen, wie bei jedem Optimierungssatz mit jedem Compiler bei jeder Optimierung derselbe Code auf hoher Ebene implementiert wird Rahmen. Sie möchten Ihren Code nicht nur optimieren, um festzustellen, dass Sie ihn für einen Compiler / eine Plattform besser, für jeden anderen jedoch viel schlechter gemacht haben.
Oh, zum Zerlegen von Befehlssätzen mit variabler Länge, anstatt einfach am Anfang zu beginnen und jedes 4-Byte-Wort linear durch den Speicher zu zerlegen, wie Sie es mit dem ARM oder alle zwei Bytes wie beim msp430 tun würden (Der msp430 verfügt über Befehle mit variabler Länge, aber Sie können trotzdem durchkommen linear durch den Speicher gehen, wenn Sie an den Einstiegspunkten aus der Interrupt-Vektortabelle beginnen). Für eine variable Länge möchten Sie einen Einstiegspunkt finden, der auf einer Vektortabelle oder dem Wissen darüber basiert, wie der Prozessor startet, und dem Code in der Ausführungsreihenfolge folgen. Sie müssen jeden Befehl vollständig dekodieren, um zu wissen, wie viele Bytes verwendet werden. Wenn der Befehl kein bedingungsloser Zweig ist, nehmen Sie an, dass das nächste Byte nach diesem Befehl ein anderer Befehl ist. Sie müssen auch alle möglichen Zweigadressen speichern und davon ausgehen, dass dies die Startbyte-Adressen für weitere Anweisungen sind. Als ich einmal erfolgreich war, habe ich mehrere Durchgänge durch die Binärdatei gemacht. Beginnend am Einstiegspunkt habe ich dieses Byte als Beginn eines Befehls markiert und dann linear durch den Speicher dekodiert, bis ich einen bedingungslosen Zweig getroffen habe. Alle Verzweigungsziele wurden als Startadressen einer Anweisung markiert. Ich habe mehrere Durchgänge durch die Binärdatei gemacht, bis ich keine neuen Verzweigungsziele gefunden hatte. Wenn Sie zu irgendeinem Zeitpunkt beispielsweise eine 3-Byte-Anweisung finden, aber aus irgendeinem Grund das zweite Byte als Beginn einer Anweisung markiert haben, liegt ein Problem vor. Wenn der Code von einem High-Level-Compiler generiert wurde, sollte dies nur geschehen, wenn der Compiler etwas Böses tut. Wenn der Code einen handgeschriebenen Assembler enthält (wie beispielsweise ein altes Arcade-Spiel), ist es durchaus möglich, dass es bedingte Verzweigungen gibt, die niemals wie r0 = 0 auftreten können, gefolgt von einem Sprung, wenn nicht Null. Möglicherweise müssen Sie diese aus der Binärdatei heraus bearbeiten, um fortzufahren. Für Ihre unmittelbaren Ziele, von denen ich annehme, dass sie auf x86 liegen, glaube ich nicht, dass Sie ein Problem haben werden.
Ich empfehle die gcc-Tools. Mingw32 ist eine einfache Möglichkeit, gcc-Tools unter Windows zu verwenden, wenn x86 Ihr Ziel ist. Wenn nicht, ist mingw32 plus msys eine hervorragende Plattform zum Generieren eines Cross-Compilers aus binutils und gcc-Quellen (im Allgemeinen ziemlich einfach). mingw32 hat einige Vorteile gegenüber Cygwin, wie deutlich schnellere Programme und Sie vermeiden die Hölle der Cygwin-DLL. Mit gcc und binutils können Sie in C oder Assembler schreiben und Ihren Code zerlegen. Es gibt mehr Webseiten als Sie lesen können, die Ihnen zeigen, wie Sie eine oder alle drei Methoden ausführen. Wenn Sie dies mit einem Befehlssatz variabler Länge tun, empfehle ich dringend, einen Werkzeugsatz zu verwenden, der einen Disassembler enthält. Ein Disassembler von Drittanbietern für x86 wird beispielsweise eine Herausforderung sein, da Sie nie wirklich wissen, ob er korrekt zerlegt wurde. Einiges davon hängt auch vom Betriebssystem ab. Ziel ist es, die Module in ein Binärformat zu kompilieren, das Anweisungen zum Markieren von Informationen aus Daten enthält, damit der Disassembler eine genauere Arbeit leisten kann. Ihre andere Wahl für dieses primäre Ziel ist es, ein Tool zu haben, das direkt zu Assembler für Ihre Inspektion kompiliert werden kann, und dann zu hoffen, dass es beim Kompilieren in ein Binärformat dieselben Anweisungen erstellt.
Die kurze (okay etwas kürzere) Antwort auf Ihre Frage. Schreiben Sie einen Disassembler, um einen Befehlssatz zu lernen. Ich würde mit etwas RISCY beginnen und leicht zu lernen wie ARM. Sobald Sie einen Befehlssatz kennen, lassen sich andere, oft in wenigen Stunden, viel einfacher erlernen. Mit dem dritten Befehlssatz können Sie fast sofort mit dem Schreiben von Code beginnen, indem Sie das Datenblatt / Referenzhandbuch für die Syntax verwenden. Alle Prozessoren, die es wert sind, verwendet zu werden, verfügen über ein Datenblatt oder ein Referenzhandbuch, das die Anweisungen bis auf die Bits und Bytes der Opcodes beschreibt. Lernen Sie einen RISC-Prozessor wie ARM und einen CISC wie x86 genug, um ein Gefühl für die Unterschiede zu bekommen, z. B. Register für alles durchlaufen zu müssen oder Operationen direkt im Speicher mit weniger oder keinen Registern ausführen zu können. Drei Operandenanweisungen gegen zwei usw. Während Sie Ihren High-Level-Code optimieren, Kompilieren Sie für mehr als einen Prozessor und vergleichen Sie die Ausgabe. Das Wichtigste, was Sie lernen werden, ist, dass unabhängig davon, wie gut der Code auf hoher Ebene geschrieben ist, die Qualität des Compilers und die getroffenen Optimierungsentscheidungen einen großen Unterschied in den tatsächlichen Anweisungen bewirken. Ich empfehle llvm und gcc (mit binutils), keine produzierenToller Code, aber sie sind Multi-Plattform und Multi-Target und beide haben Optimierer. Und beide sind kostenlos und Sie können problemlos Cross-Compiler aus Quellen für verschiedene Zielprozessoren erstellen.
quelle
Die Assembly, die Sie von Hand schreiben würden, und die von einem Compiler generierte Assembly unterscheiden sich häufig stark, wenn sie von einer hohen Ebene aus betrachtet werden. Natürlich sind die Innereien des Programms sehr ähnlich (es gibt schließlich nur so viele verschiedene Möglichkeiten zum Codieren
a = b + c
), aber sie sind nicht das Problem, wenn Sie versuchen, etwas zurückzuentwickeln. Der Compiler wird eine hinzufügen Tonne Standardcode zu selbst einfachen ausführbaren Dateien: letztes Mal , dass ich im Vergleich zu „Hallo Welt“ von GCC kompiliert wurde etwa 4 kB, während , wenn in der Montage von Hand geschrieben ist es rund 100 Bytes. Unter Windows ist es schlimmer: Beim letzten Vergleich (zugegebenermaßen war dies das letzte Jahrhundert) Die kleinste "Hallo Welt", die ich mit meinem Windows-Compiler meiner Wahl generieren konnte, war 52kB! Normalerweise wird dieses Boilerplate nur einmal ausgeführt, wenn überhaupt, so dass es die Programmgeschwindigkeit nicht wesentlich beeinflusst - wie ich oben sagte, ist der Kern des Programms, der Teil, in dem die meiste Ausführungszeit verbracht wird, normalerweise ziemlich ähnlich, ob kompiliert oder von Hand geschrieben.Am Ende des Tages, bedeutet dies , dass eine fachgerechte Montage Programmierer und Experte Disassembler zwei verschiedene Spezialitäten. Normalerweise befinden sie sich in derselben Person, aber sie sind wirklich getrennt, und das Erlernen, wie man ein ausgezeichneter Baugruppencodierer ist, hilft Ihnen nicht so viel, um Reverse Engineering zu lernen.
Sie möchten lediglich die Architekturhandbücher IA-32 und AMD64 (beide werden zusammen behandelt) von Intel und AMD herunterladen und die ersten Abschnitte mit Anweisungen und Opcodes lesen. Lesen Sie vielleicht ein oder zwei Tutorials zur Assemblersprache, um die Grundlagen der Assemblersprache zu verstehen. Dann schnapp dir einen kleinenBeispielprogramm, an dem Sie interessiert sind, und Zerlegen: Durchlaufen Sie den Kontrollfluss und versuchen Sie zu verstehen, was es tut. Überprüfen Sie, ob Sie es patchen können, um etwas anderes zu tun. Versuchen Sie es dann erneut mit einem anderen Programm und wiederholen Sie den Vorgang, bis Sie sich wohl genug fühlen, um ein nützlicheres Ziel zu erreichen. Sie könnten an Dingen wie "Crackmes" interessiert sein, die von der Reverse Engineering-Community produziert werden. Dies sind Herausforderungen für Leute, die sich für Reverse Engineering interessieren, um sich zu versuchen und hoffentlich etwas auf dem Weg zu lernen. Sie reichen von einfach (hier anfangen!) Bis unmöglich.
Vor allem müssen Sie nur üben . Wie in vielen anderen Disziplinen macht beim Reverse Engineering die Übung den Meister ... oder zumindest besser .
quelle
Ich werde gegen den Strich der meisten Antworten gehen und Knuths MMIX- Variante der MIPS RISC-Architektur empfehlen . Es wird nicht so praktisch nützlich sein wie x86- oder ARM-Assemblersprachen (nicht, dass sie heutzutage in den meisten realen Jobs so wichtig sind ... ;-), aber es wird für Sie die Magie von Knuths neuesten freischalten Version des bisher größten Meisterwerks zum tiefen Verständnis von Algorithmen und Datenstrukturen auf niedriger Ebene - TAOCP , "The Art of Computer Programming". Die Links von den beiden URLs, die ich zitiert habe, sind eine großartige Möglichkeit, diese Möglichkeit zu erkunden!
quelle
(Ich weiß nichts über dich, aber ich war begeistert von der Montage)
Auf Ihrem PC ist bereits ein einfaches Tool zum Experimentieren mit Baugruppen installiert.
Gehen Sie zu Startmenü-> Ausführen und geben Sie ein
debug
Debug (Befehl)
Tutorials:
Wenn Sie den Code verstehen möchten, den Sie in IDA Pro (oder OllyDbg ) sehen, müssen Sie lernen, wie kompilierter Code strukturiert ist. Ich empfehle das Buch Reversing: Secrets of Reverse Engineering
Ich habe ein paar Wochen lang experimentiert,
debug
als ich anfing, Montage zu lernen (vor 15 Jahren).Beachten Sie, dass
debug
auf Basismaschinenebene keine Assembly-Befehle auf hoher Ebene vorhanden sind.Und jetzt ein einfaches Beispiel:
Geben Sie
a
an, um mit dem Schreiben von Assembly-Code zu beginnen - gebeng
Sie das folgende Programm ein - und geben Sie schließlich an, um es auszuführen.(
INT 21
Zeigen Sie auf dem Bildschirm das imDL
Register gespeicherte ASCII-Zeichen an , wenn dasAH
Register auf2
-INT 20
das Programm beendet) eingestellt ist.)quelle
a
& [enter] ein, um mit dem Schreiben des Assemblycodes zu beginnen. Wenn Sie zweimal [Enter] drücken, verlassen Sie den Assembly-Modus.g
& [Enter], um es auszuführen (standardmäßig Offset 100).Ich fand, dass Hacking: The Art of Exploitation ein interessanter und nützlicher Weg in dieses Thema ist ... ich kann nicht sagen, dass ich das Wissen jemals direkt genutzt habe, aber das ist wirklich nicht der Grund, warum ich es gelesen habe. Sie erhalten ein viel besseres Verständnis für die Anweisungen, nach denen Ihr Code kompiliert wird, was gelegentlich hilfreich war, um subtilere Fehler zu verstehen.
Lassen Sie sich vom Titel nicht abschrecken. Der größte Teil des ersten Teils des Buches ist "Hacking" im Sinne von Eric Raymond: kreative, überraschende, fast hinterhältige Wege, um schwierige Probleme zu lösen. Ich (und vielleicht Sie) waren viel weniger an den Sicherheitsaspekten interessiert.
quelle
Ich würde mich nicht darauf konzentrieren, Programme in Assembly zu schreiben, zumindest zunächst nicht. Wenn Sie auf x86 arbeiten (was ich vermute, da Sie Windows verwenden), gibt es unzählige seltsame Sonderfälle, deren Erlernen sinnlos ist. Beispielsweise setzen viele Anweisungen voraus, dass Sie mit einem Register arbeiten, das Sie nicht explizit benennen, und andere Anweisungen funktionieren mit einigen Registern, anderen jedoch nicht.
Ich würde gerade genug über Ihre beabsichtigte Architektur lernen, um die Grundlagen zu verstehen, dann einfach direkt hineinspringen und versuchen, die Ausgabe Ihres Compilers zu verstehen. Bewaffne dich mit den Intel-Handbüchern aus und tauchen Sie direkt in die Ausgabe Ihres Compilers ein. Isolieren Sie den Code von Interesse in eine kleine Funktion, damit Sie sicher sein können, das Ganze zu verstehen.
Ich würde die Grundlagen wie folgt betrachten:
add eax, ebx
bedeutet "Fügen Sie ebx zu eax hinzu und speichern Sie das Ergebnis in eax".In den meisten Fällen wird es überraschend sein, was der Compiler ausgibt. Machen Sie es zu einem Rätsel, herauszufinden, warum zum Teufel der Compiler dies für eine gute Idee hielt. Es wird dir viel beibringen.
Es wird wahrscheinlich auch hilfreich sein, sich mit den Handbüchern von Agner Fog zu bewaffnen , insbesondere mit der Anleitung, in der eine aufgeführt ist. Es wird Ihnen ungefähr sagen, wie teuer jeder Befehl ist, obwohl dies auf modernen Prozessoren schwieriger direkt zu quantifizieren ist. Aber es wird helfen zu erklären, warum zum Beispiel der Compiler so weit aus dem Weg geht, um die Ausgabe eines zu vermeiden
idiv
Anweisung .Mein einziger anderer Rat ist, immer Intel-Syntax anstelle von AT & T zu verwenden, wenn Sie die Wahl haben. Ich war in diesem Punkt ziemlich neutral, bis mir klar wurde, dass einige Anweisungen zwischen den beiden völlig unterschiedlich sind (zum Beispiel
movslq
in der AT & T-Syntaxmovsxd
in der Intel-Syntax). Da die Handbücher alle mit Intel-Syntax geschrieben sind, bleiben Sie einfach dabei.Viel Glück!
quelle
Ich habe angefangen, MIPS zu lernen, eine sehr kompakte 32-Bit-Architektur. Es ist ein reduzierter Befehlssatz, aber das macht es für Anfänger leicht verständlich. Sie werden immer noch verstehen, wie die Montage funktioniert, ohne von der Komplexität überfordert zu sein. Sie können sogar eine nette kleine IDE herunterladen, mit der Sie Ihren MIPS-Code kompilieren können: clicky Sobald Sie den Dreh raus haben, ist es meiner Meinung nach viel einfacher, zu komplexeren Architekturen überzugehen . Zumindest dachte ich das :) An diesem Punkt haben Sie die wesentlichen Kenntnisse über Speicherzuweisung und -verwaltung, Logikfluss, Debugging, Testen usw.
quelle
Der Vorschlag, Debug zu verwenden, macht Spaß, damit können viele nette Tricks gemacht werden. Für ein modernes Betriebssystem kann das Erlernen der 16-Bit-Assemblierung jedoch etwas weniger nützlich sein. Verwenden Sie stattdessen ntsd.exe. Es ist in Windows XP integriert (es wurde leider in Server 2003 und höher gerissen), was es zu einem praktischen Lernwerkzeug macht, da es so weit verbreitet ist.
Die ursprüngliche Version in XP weist jedoch eine Reihe von Fehlern auf. Wenn Sie es wirklich verwenden möchten (oder cdb oder windbg, bei denen es sich im Wesentlichen um unterschiedliche Schnittstellen mit derselben Befehlssyntax und demselben Debugging-Backend handelt), sollten Sie das kostenlose Windows-Debugging- Toolpaket installieren .
Die in diesem Paket enthaltene Datei debugger.chm ist besonders nützlich, wenn Sie versuchen, die ungewöhnliche Syntax herauszufinden.
Das Tolle an ntsd ist, dass Sie es auf jedem XP-Computer in Ihrer Nähe anzeigen und zum Zusammenbauen oder Zerlegen verwenden können. Es ist ein / great / X86-Assembly-Lernwerkzeug. Zum Beispiel (mit cdb, da es in der dos-Eingabeaufforderung inline ist, ist es ansonsten identisch):
(Symbolfehler wurden übersprungen, da sie irrelevant sind - ich hoffe auch, dass diese Formatierung funktioniert, dies ist mein erster Beitrag)
Außerdem - während Sie mit IDA spielen, lesen Sie unbedingt das IDA Pro Book von Chris Eagle (nicht verbunden, da StackOverflow nicht zulässt, dass ich mehr als zwei Links für meinen ersten Beitrag poste). Es ist zweifellos die beste Referenz da draußen.
quelle
Ich habe kürzlich einen Kurs über Computersysteme besucht. Eines der Themen war Assembly als Werkzeug zur Kommunikation mit der Hardware.
Für mich wäre das Wissen über die Montage nicht vollständig gewesen, ohne die Details der Funktionsweise von Computersystemen zu verstehen. Wenn Sie dies verstehen, erhalten Sie ein neues Verständnis dafür, warum Montageanweisungen auf einer Prozessorarchitektur großartig sind, auf einer anderen Architektur jedoch schrecklich.
Vor diesem Hintergrund neige ich dazu, mein Lehrbuch zu empfehlen:
Computersysteme: Die Perspektive eines Programmierers .
(Quelle: cmu.edu )
Es behandelt zwar die x86-Assembly, aber das Buch ist viel umfassender. Es behandelt Prozessor-Pipe-Lining und Speicher als Cache, das virtuelle Speichersystem und vieles mehr. All dies kann sich darauf auswirken, wie die Baugruppe für die angegebenen Funktionen optimiert werden kann.
quelle
Ich denke, Sie möchten die ASCII-basierten Opcode-Mnemoniken (und ihre Parameter) lernen, die von einem Disassembler ausgegeben werden und die von einem Assembler verstanden werden (als Eingabe für einen Assembler verwendet werden können).
Jeder Assembler (zB MASM) würde dies tun.
Und / oder es ist vielleicht besser für Sie, ein Buch darüber zu lesen (es wurden Bücher zu SO empfohlen, ich weiß nicht mehr, welche).
quelle
Machst du andere Entwicklungsarbeiten an Windows? Auf welcher IDE? Wenn es sich um VS handelt, ist keine zusätzliche IDE erforderlich, um nur zerlegten Code zu lesen: Debuggen Sie Ihre App (oder hängen Sie sie an eine externe App an), und öffnen Sie dann das Demontagefenster (in den Standardeinstellungen ist dies Alt + 8). Schritt und beobachten Sie Speicher / Register wie durch normalen Code. Möglicherweise möchten Sie auch ein Registerfenster geöffnet lassen (standardmäßig Alt + 5).
Intel bietet kostenlose Handbücher an , die sowohl einen Überblick über die grundlegende Architektur (Register, Prozessoreinheiten usw.) als auch eine vollständige Referenz geben. Mit zunehmender Reife der Architektur und zunehmender Komplexität werden die Handbücher zur Basisarchitektur immer weniger lesbar. Wenn Sie eine ältere Version in die Hände bekommen können, haben Sie wahrscheinlich einen besseren Ausgangspunkt (sogar P3-Handbücher - sie erklären dasselbe besser grundlegende Ausführungsumgebung).
Wenn Sie in ein Buch investieren möchten, finden Sie hier einen schönen Einführungstext. Suchen Sie bei Amazon nach 'x86' und Sie erhalten viele andere. Sie können mehrere andere Richtungen von einer anderen Frage hier erhalten .
Schließlich können Sie von ziemlich viel profitieren lesen einige Low - Level Blogs. Diese Byte-Info-Bits funktionieren für mich persönlich am besten.
quelle
Dies wird Ihnen nicht unbedingt helfen, effizienten Code zu schreiben!
i86-Op-Codes sind mehr oder weniger ein "Legacy" -Format, das aufgrund des enormen Codevolumens und der ausführbaren Binärdateien für Windows und Linux bestehen bleibt.
Es ist ein bisschen wie bei den alten Gelehrten, die auf Latein schreiben, ein italienischer Sprecher wie Galileo würde auf Latein schreiben und seine Arbeit könnte von einem polnischen Sprecher wie Copernicus verstanden werden. Dies war immer noch die effektivste Art zu kommunizieren, obwohl niether besonders gut in Latein war und Latein eine Müllsprache ist, um mathematische Ideen auszudrücken.
Daher generieren Compiler standardmäßig x86-Code, und moderne Chips lesen die Anceint-Op-Codes und wandeln das, was sie sehen, in parallele Risc-Anweisungen um, wobei die Ausführung neu angeordnet, die spekulative Ausführung, das Pipelining usw. durchgeführt werden. Außerdem nutzen sie die 32- oder 64-Register des Prozessors vollständig aus hat tatsächlich (im Gegensatz zu der erbärmlichen 8, die Sie in x86-Anweisungen sehen.)
Jetzt wissen alle optimierenden Compiler, dass dies wirklich passiert, und codieren Sequenzen von OP-Codes, von denen sie wissen, dass der Chip sie effizient optimieren kann - obwohl einige dieser Sequenzen für einen .asm-Programmierer von ca. 1990 ineffizient erscheinen würden.
Irgendwann müssen Sie akzeptieren, dass sich die Zehntausende von Mannjahren, die Compiler-Autoren unternommen haben, ausgezahlt haben, und ihnen vertrauen.
Der einfachste und einfachste Weg, um eine effizientere Laufzeit zu erzielen, ist der Kauf des Intel C / C ++ - Compilers. Sie haben einen Nischenmarkt für Efficeint-Compiler und haben den Vorteil, dass sie die Chip-Designer fragen können, was im Inneren vor sich geht.
quelle
Um das zu tun, was Sie tun möchten, habe ich nur die Intel-Befehlssatzreferenz (möglicherweise nicht die genaue, die ich verwendet habe, aber sie sieht ausreichend aus) und einige einfache Programme, die ich in Visual Studio geschrieben habe, verwendet und sie in IDAPro / Windbg geworfen . Als ich meine eigenen Programme herauswuchs, war die Software bei crackmes hilfreich.
Ich gehe davon aus, dass Sie ein grundlegendes Verständnis dafür haben, wie Programme unter Windows ausgeführt werden. Aber wirklich, zum Lesen von Assemblys gibt es nur ein paar Anweisungen zu lernen und ein paar Varianten dieser Anweisungen (z. B. gibt es eine Sprunganweisung, Sprung hat ein paar Geschmacksrichtungen wie Sprung-wenn-gleich, Sprung-wenn-ecx-ist-Null , etc). Sobald Sie die grundlegenden Anweisungen gelernt haben, ist es ziemlich einfach, den Kern der Programmausführung zu erhalten. Die Grafikansicht von IDA hilft, und wenn Sie das Programm mit Windbg verfolgen, ist es ziemlich einfach herauszufinden, was die Anweisungen tun, wenn Sie sich nicht sicher sind.
Nachdem ich so ein bisschen gespielt hatte, kaufte ich Hacker Disassembly Uncovered . Im Allgemeinen halte ich mich von Büchern mit dem Wort "Hacker" im Titel fern, aber mir hat sehr gut gefallen, wie ausführlich darüber berichtet wurde, wie kompilierter Code zerlegt aussah. Er geht auch auf Compiler-Optimierungen und einige interessante Dinge zur Effizienz ein.
Es hängt wirklich davon ab, wie tief Sie das Programm auch verstehen wollen. Wenn Sie ein Ziel, das nach Schwachstellen sucht, rückentwickeln, Exploit-Code schreiben oder gepackte Malware auf Funktionen analysieren, benötigen Sie mehr Zeit, um die Dinge wirklich in Gang zu bringen (insbesondere bei fortgeschrittener Malware) ). Wenn Sie jedoch nur in der Lage sein möchten, das Level Ihres Charakters in Ihrem Lieblingsvideospiel zu ändern, sollten Sie in relativ kurzer Zeit gut abschneiden.
quelle
Eine der üblichen pädagogischen Assemblersprachen ist MIPS. Sie können MIPS-Simulatoren (Spim) und verschiedene Lehrmaterialien dafür erhalten.
Persönlich bin ich kein Fan. Ich mag IA32 lieber.
quelle
Mein persönlicher Favorit ist NASM, vor allem, weil es plattformübergreifend ist und MMX, SSE, 64-Bit ...
Ich fing an, eine einfache C-Quelldatei mit gcc zu kompilieren und die Assembler-Anweisung vom gcc-Format in das NASM-Format zu "transkodieren". Dann können Sie kleine Teile des Codes ändern und die damit verbundene Leistungsverbesserung überprüfen.
Die NASM-Dokumentation ist wirklich vollständig. Ich musste nie nach Informationen aus Büchern oder anderen Quellen suchen.
quelle
Einige Links, die Sie möglicherweise nützlich finden, um die Assembly zu erlernen - Quellcode-Zuordnung -
Montage und die Kunst des Debuggens
Debuggen - Code zur Laufzeit ändern
Ich hoffe, Sie finden diese nützlich.
quelle
Viele gute Antworten hier. Low-Level-Programmierung, Assembly usw. sind in der Sicherheitsgemeinschaft sehr beliebt. Es lohnt sich daher, dort nach Hinweisen und Tipps zu suchen, sobald Sie loslegen. Sie haben sogar einige gute Tutorials wie dieses auf x86-Assembly .
quelle
Um Ihr Ziel tatsächlich zu erreichen, sollten Sie mit der IDE beginnen, in der Sie sich befinden. Das Fenster ist im Allgemeinen ein Disassembler-Fenster, sodass Sie einen einzelnen Schritt durch den Code ausführen können. Normalerweise gibt es eine Art Ansicht, mit der Sie die Register sehen und in Speicherbereiche schauen können.
Die Untersuchung von nicht optimiertem c / c ++ - Code hilft dabei, einen Link zu der Art von Code zu erstellen, die der Compiler für Ihre Quellen generiert. Einige Compiler haben eine Art von ASM-reserviertem Wort, mit dem Sie Maschinenanweisungen in Ihren Code einfügen können.
Mein Rat wäre, eine Weile mit solchen Werkzeugen herumzuspielen, die Füße nass zu machen und dann aufzusteigen? Nieder? um den Assembler-Code auf jeder Plattform, auf der Sie ausgeführt werden, zu korrigieren.
Es gibt viele großartige Tools, aber vielleicht macht es mehr Spaß, die steile Lernkurve zunächst zu vermeiden.
quelle
Wir haben die Montage mit einem Mikrocontroller-Entwicklungskit (Motorola HC12) und einem dicken Datenblatt gelernt.
quelle
Ich weiß, dass es kein Thema ist, aber da Sie ein Windows-Programmierer sind, kann ich nicht anders, als zu glauben, dass es eine angemessenere und / oder bessere Nutzung Ihrer Zeit zum Erlernen von MSIL ist. Nein, es ist keine Assembly, aber in dieser .NET-Ära ist es wahrscheinlich relevanter.
quelle
Das Wissen über Assembly kann beim Debuggen hilfreich sein, aber ich würde mich nicht allzu sehr darüber freuen, sie zur Optimierung Ihres Codes zu verwenden. Moderne Compiler sind heutzutage in der Regel viel besser darin, einen Menschen zu optimieren.
quelle
Sie können sich den Videokurs xorpd x86 Assembly ansehen . (Ich schrieb es). Der Kurs selbst ist bezahlt, aber die Übungen sind Open-Source-Übungen auf Github. Wenn Sie Programmiererfahrung haben, sollten Sie in der Lage sein, nur mit den Übungen zu arbeiten und alles zu verstehen.
Beachten Sie, dass der Code für die Windows-Plattform bestimmt ist und mit dem Fasm-Assembler geschrieben wurde . Der Kurs und die Übungen enthalten keine Konstrukte auf hoher Ebene. Sie können jedoch Fasm verwenden, um sehr komplizierte Makros zu erstellen, falls Sie dies jemals möchten.
quelle