# Parrot

Parrot ist eine in Entwicklung befindliche registerbasierte virtuelle Maschine, die vor allem auf die Bedürfnisse dynamischer Programmiersprachen wie Perl oder Python ausgerichtet ist. Parrot wurde von Dan Sugalski vor allem als Interpreter für Perl 6 entworfen. Die Entwicklung wird von Allison Randal geleitet und von der Parrot Foundation unterstützt und koordiniert.

## Etymologie/Wortherkunft

Während der Planungsphase von Parrot veröffentlichte Simon Cozens am 1. April 2001 auf der Perl-Website des O’Reilly-Verlags einen aufwändigen Scherz-Artikel (samt Buchankündigung), mit der offiziellen Ankündigung von Larry Wall und Guido van Rossum, dass Perl und Python in Zukunft zu einer gemeinsamen Sprache namens Parrot verschmelzen würden. Diese Verschmelzung fand selbstverständlich nicht statt, aber der Name einer virtuellen Maschine, die für verschiedene Sprachen verwendbar sein soll, war geboren.

## Entwicklung

Ursprünglich wurde Parrot von Dan Sugalski entworfen und mehrere Jahre geleitet. Es war von Anfang an ein freies Softwareprojekt und wird unter der Artistic License 2.0 veröffentlicht. Allison Randal führt jetzt die Arbeit der Freiwilligen an, wobei die im Herbst 2008 gegründete und ebenfalls von ihr geführte Parrot Foundation im November die Unterstützung erster Firmen gewinnen konnte. Patrick Michaud, Hauptautor der PGE, leitet die Entwicklung der PCT (Parrot Compiler Tools) und Rakudo (Perl 6 Compiler).
Das Projekt befindet sich bereits seit mehreren Jahren in aktiver Entwicklung. Einzelne Teile wurden mehrmals neu geschrieben, bis eine zufriedenstellende Implementierung erreicht war. Es sind jedoch noch nicht alle Fähigkeiten für eine komplette VM vollständig implementiert. Aktuell ist Version 5.0.0, veröffentlicht am 29. Januar 2013.
Das bei O’Reilly erschienene Buch „Perl 6 and Parrot Essentials, 2nd edition“ bietet einen mittlerweile veralteten Überblick über Parrot und ist inzwischen unter einer Creative-Commons-Lizenz freigegeben worden, damit es leichter aktuell gehalten werden kann.

## Architektur

Im Gegensatz zu anderen virtuellen Maschinen, wie der JVM für Java, die stapelorientiert sind (0-Adress-Maschine), ist Parrot eine Registermaschine (3-Adress-Maschine). Dadurch erhofft man sich bessere Optimierungsmöglichkeiten und Parallelverarbeitung von Befehlen sowohl innerhalb eines Prozessors als auch verteilt auf mehreren Prozessoren.
Parrot erlaubt es, beliebig viele Register zu allozieren. Register sind nach Typen unterschieden, es gibt Register für ganze Zahlen, Gleitkommazahlen, Zeichenketten und für beliebige Objekte, sogenannte PMC. Soweit es die Plattform erlaubt, werden sie auf Hardwareregister abgebildet, um die Ausführungsgeschwindigkeit zu erhöhen.
Parrot ist in C geschrieben, um möglichst auf allen Plattformen verfügbar zu sein, auf denen auch Perl 5 läuft.

## Zwischencodes

Beim Kompilieren kann ein Programm mehrere Zwischenstufen durchlaufen. Im ersten Arbeitsschritt wird der Quelltext in den Syntaxbaum überführt, der noch sehr stark die Struktur des Quelltextes widerspiegelt. Der zweite Schritt besteht üblicherweise in der Übersetzung in einen Abstract Syntax Tree (AST), der sich mehr an der logischen als an der textuellen Struktur des Programms orientiert.
Parrot definiert eine Form des AST namens PAST (Parrot Abstract Syntax Tree), die von fast allen Programmiersprachen genutzt werden kann. Diese Form kann über eine weitere Zwischenstufe namens POST (Parrot Opcode Syntax Tree) in Bytecode umgewandelt werden. POST dient als Schnittstelle für Bytecodeoptimierer und Konverter in und aus Bytecode anderer virtueller Maschinen.
Wie bei Perl 5 kommt letztendlich ein Bytecode zur Ausführung, der direkt vor der Ausführung aus einem Quelltext oder Zwischencode erzeugt wird oder in einem separaten Schritt kompiliert werden kann. Neu ist für Perl mit Parrot die Möglichkeit, den Bytecode in Dateien (meist mit Endung .pbc) abzuspeichern, um sie später auszuführen.
Während PAST und POST als Datenstrukturen ohne direkte textuelle Repräsentation definiert sind, gibt es noch für Menschen schreibbare Zwischencodes namens PIR (Parrot Intermediate Representation) und PASM (Parrot Assembler). PIR ist in der Lesbarkeit des Codes traditionellen Programmiersprachen ähnlich, verzichtet jedoch auf Kontrollstrukturen. PASM hat die gleiche Struktur wie Bytecode und ist sehr stark Parrots interner Struktur angepasst.

## Werkzeuge

Die Parrot Compiler Tools (kurz PCT) sind eine größtenteils in PIR geschriebene Sammlung von Software, die mit Parrot ausgeliefert wird, um die Erzeugung von Parsern und Compiler für Parrot erheblich zu erleichtern.
PCT besteht aus folgenden Bestandteilen:
* Parrot Grammar Engine (kurz PGE), einer Bibliothek, die mit Hilfe von Kontextfreien Sprachen (meist Perl 6 rules) Quelltext in einen Syntaxbaum umwandeln kann
* Not Quite Perl (NQP), einer Untermenge von Perl 6, die benutzt wird, um aus einem Syntaxbaum einen Abstract Syntax Tree zu erzeugen und statische Analysen durchführen zu können
* Einem Compiler, der PAST in POST übersetzt
* Einem Compiler, der POST in Bytecode übersetzt
Alle diese Komponenten sind modular gehalten und können unabhängig voneinander benutzt werden.

## Unterstützung anderer Programmiersprachen

Parrot wurde entworfen, um auch eine große Anzahl anderer Sprachen wie Python, Ruby, Tcl oder BASIC zu unterstützen. Compiler, die diese Programmiersprachen in Perl6-Zwischencode übersetzen, der von Parrot ausgeführt wird, wurden in Angriff genommen. Da Parrot selbst jedoch noch nicht vollständig war und von diesen Compilern verwendete Features teilweise wieder entfernt wurden, funktionieren nicht mehr alle diese Compiler und deren Entwicklung wurde auch teilweise wieder eingestellt. Trotzdem sind noch viele andere Compiler für den Parrot-Zwischencode in Arbeit, wie Parrot selbst sind jedoch nur wenige fertiggestellt.
In der finalen Version sollen alle diese Sprachen gemeinsam verwendbar sein, das heißt jede Sprache soll die Module jeder anderen Sprache verwenden können.
Die Entwicklung von Ponie, einem Übersetzer, der existierenden Perl5-Code unter Parrot ausführbar machen sollte, wurde mittlerweile abgebrochen.

## Stand November 2006

Parrot ist derzeit:
* Ein hochoptimierter Interpreter, der wesentlich effizienter als der aktuelle Perl5-Interpreter arbeitet. Optimierten Zwischencode führt er derzeit je nach Benchmark zum Beispiel dreimal so schnell aus wie perl5 ein entsprechendes Perl-Programm. Er ist zwar noch etwas langsamer als nativ ausgeführter C-Code, jedoch in manchen Benchmarks nicht mehr um mehrere Faktoren langsamer, als es das derzeitige Perl 5 ist.
* Es war ein JIT-Compiler vorhanden, der Code zur Laufzeit in Maschinencode umwandelte, der das Programm schneller ausführen sollte. Jedoch hatte die JIT-Implementierung praktisch keine Performancesteigerung bewirkt. Da ihr Design außerdem die Entwicklung der restlichen Komponenten von Parrot behinderte, wurde sie vor dem Release von Parrot 1.7 entfernt. Seit September 2009 besteht der Plan, den JIT-Compiler von LLVM in Parrot zu verwenden.
* Ein Code-Generator für kompilierte, ausführbare Dateien. Dieser Generator verwendet den JIT-Compiler und kann daher nur auf Plattformen zur Verfügung stehen, auf denen es auch einen JIT-Compiler gibt. Derzeit gibt es dieses „Native exec“ genannte Funktion nur auf i386/Linux und i386/BSD. Zumindest auf i386/Linux, scheint diese Funktion derzeit jedoch einen Fehler zu haben: Programme die von dem JIT-Compiler einwandfrei kompiliert werden, lösen bei der Umwandlung in Objektcode einen Segmentierungsfehler in Parrot aus.