697 Stimmen

Lernen, einen Compiler zu schreiben

Bevorzugte Sprachen : C/C++, Java und Ruby.

Ich bin auf der Suche nach hilfreichen Büchern/Tutorials über das Schreiben eines eigenen Compilers, einfach zu Ausbildungszwecken. Ich kenne mich am besten mit C/C++, Java und Ruby aus, daher bevorzuge ich Quellen, die eine dieser drei beinhalten, aber jede gute Quelle ist akzeptabel.

26voto

Peter Burns Punkte 43323

Wenn Sie leistungsfähige Tools auf höherer Ebene verwenden möchten, anstatt alles Sie selbst, indem Sie die Projekte und Lesungen für dieser Kurs ist eine ziemlich gute Option. Es handelt sich um einen Sprachkurs des Autors der Java-Parser-Engine ANTLR. Sie können das Buch zum Kurs als PDF von die pragmatischen Programmierer .

Der Kurs befasst sich mit den Standardkompilern, die man auch anderswo sieht: Parsing, Typen und Typüberprüfung, Polymorphismus, Symboltabellen und Codegenerierung. So ziemlich das einzige, was nicht behandelt wird, sind Optimierungen. Das Abschlussprojekt ist ein Programm, das kompiliert eine Teilmenge von C . Da Sie Werkzeuge wie ANTLR und LLVM verwenden, ist es möglich, den gesamten Compiler an einem einzigen Tag zu schreiben (ich habe einen Existenzbeweis dafür, obwohl ich ~24 Stunden meine). Es ist stark auf die praktische Technik mit modernen Tools, ein bisschen leichter auf die Theorie.

LLVM ist übrigens einfach fantastisch. In vielen Situationen, in denen Sie normalerweise nach Assembler kompilieren würden, wäre es viel besser, wenn Sie nach LLVMs intermediäre Repräsentation stattdessen. Es ist auf höherer Ebene, plattformübergreifend und LLVM ist ziemlich gut darin, daraus optimierte Assembler zu erzeugen.

23voto

jochenleidner Punkte 83

Wenn Sie wenig Zeit haben, empfehle ich Niklaus Wirths "Compilerbau" (Addison-Wesley. 1996) ist ein winziges Büchlein, das man an einem Tag lesen kann, aber es erklärt die Grundlagen (einschließlich der Implementierung von Lexern, rekursiven Descent-Parsern und eigenen stackbasierten virtuellen Maschinen). Wenn Sie danach in die Tiefe gehen wollen, führt kein Weg an dem Dragon-Buch vorbei, wie andere Kommentatoren vorschlagen.

19voto

Zachary Murray Punkte 1210

Vielleicht möchten Sie sich Lex/Yacc (oder Flex/Bison, wie auch immer Sie sie nennen wollen) ansehen. Flex ist ein lexikalischer Analysator, der die semantischen Komponenten ("Token") Ihrer Sprache analysiert und identifiziert, und Bison wird verwendet, um zu definieren, was passiert, wenn jedes Token analysiert wird. Dies könnte z. B. die Ausgabe von C-Code für einen Compiler sein, der nach C kompiliert, oder die dynamische Ausführung der Anweisungen.

Diese FAQ sollte Ihnen helfen, und diese Anleitung sieht recht nützlich aus.

17voto

Im Allgemeinen gibt es kein Fünf-Minuten-Tutorial für Compiler, weil es ein kompliziertes Thema ist und das Schreiben eines Compilers Monate dauern kann. Sie müssen Ihre eigene Suche durchführen.

Python und Ruby werden in der Regel interpretiert. Vielleicht möchten Sie auch mit einem Interpreter beginnen. Das ist im Allgemeinen einfacher.

Der erste Schritt besteht darin, eine formale Sprachbeschreibung zu schreiben, die Grammatik Ihrer Programmiersprache. Dann müssen Sie den Quellcode, den Sie gemäß der Grammatik kompilieren oder interpretieren wollen, in einen abstrakten Syntaxbaum umwandeln, eine interne Form des Quellcodes, die der Computer versteht und mit der er arbeiten kann. Dieser Schritt wird in der Regel als Parsing bezeichnet, und die Software, die den Quellcode parst, heißt Parser. Häufig wird der Parser von einem Parsergenerator erzeugt, der eine formale Grammatik in Quell- oder Maschinencode umwandelt. Für eine gute, nicht-mathematische Erklärung des Parsens empfehle ich Parsing Techniques - A Practical Guide. Wikipedia hat einen Vergleich von Parsergeneratoren, aus dem Sie den für Sie geeigneten auswählen können. Je nach gewähltem Parser-Generator finden Sie im Internet Tutorials und für wirklich populäre Parser-Generatoren (wie GNU bison) gibt es auch Bücher.

Das Schreiben eines Parsers für Ihre Sprache kann sehr schwierig sein, aber das hängt von Ihrer Grammatik ab. Ich schlage daher vor, die Grammatik einfach zu halten (im Gegensatz zu C++); ein gutes Beispiel dafür ist LISP.

Im zweiten Schritt wird der abstrakte Syntaxbaum von einer Baumstruktur in eine lineare Zwischendarstellung umgewandelt. Als gutes Beispiel hierfür wird oft der Bytecode von Lua angeführt. Aber die Zwischendarstellung hängt wirklich von der jeweiligen Sprache ab.

Wenn Sie einen Interpreter bauen, müssen Sie lediglich die Zwischendarstellung interpretieren. Sie können ihn auch just-in-time kompilieren. Ich empfehle LLVM und libjit für die Just-in-Time-Kompilierung. Um die Sprache nutzbar zu machen, müssen Sie auch einige Ein- und Ausgabefunktionen und vielleicht eine kleine Standardbibliothek einfügen.

Wenn Sie die Sprache kompilieren wollen, wird es noch komplizierter. Sie müssen Backends für verschiedene Computerarchitekturen schreiben und Maschinencode aus der Zwischendarstellung in diesen Backends erzeugen. Ich empfehle LLVM für diese Aufgabe.

Es gibt ein paar Bücher zu diesem Thema, aber ich kann keines davon für den allgemeinen Gebrauch empfehlen. Die meisten von ihnen sind zu akademisch oder zu praktisch. Es gibt kein "Bringen Sie sich das Schreiben von Compilern in 21 Tagen bei", und daher müssen Sie mehrere Bücher kaufen, um ein gutes Verständnis für dieses gesamte Thema zu bekommen. Wenn Sie im Internet suchen, werden Sie auf einige Online-Bücher und Vorlesungsskripte stoßen. Vielleicht gibt es in Ihrer Nähe eine Universitätsbibliothek, in der Sie Bücher über Compiler ausleihen können.

Ich empfehle auch ein gutes Hintergrundwissen in theoretischer Informatik und Graphentheorie, wenn Sie Ihr Projekt ernsthaft angehen wollen. Ein Abschluss in Informatik ist ebenfalls hilfreich.

14voto

Taylor Leese Punkte 48438

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X