Kod bajtowy Perla używany w Perlu 5 jest maszyną stosową z operacjami umiarkowanie wysokiego poziomu. Perl 6 używać będzie maszyny wirtualnej Parrot.
Wynikiem kompilacji: print "Hello, world!\n"; jest następujący bytecode: OP enter COP nextstate OP pushmark SVOP const PV "Hello, world!\n" LISTOP print LISTOP leave
Klasy opcodów Opcody są pogrupowane w kilka klas zależnie od tego na jakich argumentach działają. Klasy te to: OP – ogólna klasa, COP – informacja dla debugera, SVOP – operacje na skalarach, PADOP, UNOP – operacje unarne, LOGOP – operacje logiczne (sterujące), BINOP – operacje binarne, LISTOP – operacje działające na listach, PMOP – operacje na wyrażeniach regularnych, LOOPOP – operacje pętli, …
Stos Stos nie zawiera obiektów, a jedynie wskaźniki do nich.
Żeby wywołać operacje unarną lub binarną umieszczamy jej argumenty na stosie i wywołujemy ją.
Na przykład operacja unarna UNOP negate pobierze najwyższy element ze stosu i wstawi na stos jego zanegowaną wartość, operacja binarna BINOP add pobierze dwa najwyższe elementy ze stosu i wstawi ich sumę.
Żeby wywołać operację wymagającą większej ilości argumentów: zaznaczamy za pomocą OP pushmark, że zaczyna się nowa ramka stosu, umieszczamy na stosie wszystkie argumenty zaczynając od pierwszego, wywołujemy odpowiednią operację (np. LISTOP print), lub umieszczamy na stosie adres funkcji do wywołania (PADOP gv GV *foo), po czym ją wywołujemy za pomocą UNOP entersub.
Przykład wywołania $x = "Hello, world!\n": COP nextstate SVOP const PV "Hello, world!\n" PADOP gvsv GV *x BINOP sassign
Przykład wywołania $x = -$y: PADOP gvsv GV *y UNOP negate PADOP gvsv GV *x BINOP sassign
Przykład wywołania $x = $y + $z: PADOP gvsv GV *y PADOP gvsv GV *z BINOP add PADOP gvsv GV *x BINOP sassign
Przykład wywołania print(1,2,3): OP pushmark SVOP const IV 1 SVOP const IV 2 SVOP const IV 3 LISTOP print
Przykład wywołania foo(1,2,3): COP nextstate OP pushmark SVOP const IV 1 SVOP const IV 2 SVOP const IV 3 PADOP gv GV *foo UNOP entersub
Operacje na zmiennych skalarnych Opcode PADOP gvsv umieszcza na stosie adres zmiennej. Opcode SVOP const umieszcza na stosie stałą.
Opcode BINOP sassign przypisuje zmiennej, odnośnik do której adres znajduje się na najwyższej pozycji stosu. Adres zostaje zdjęty ze stosu, ale wartość zostaje.
Przykład wywołania $x = $y: PADOP gvsv GV *y PADOP gvsv GV *x BINOP sassign
Przykład wywołania $x = $y = $z: PADOP gvsv GV *z PADOP gvsv GV *y BINOP sassign PADOP gvsv GV *x BINOP sassign
Operacje na liczbach Podstawowe operacje arytmetyczne to: OperacjaPerlBytecodedodawanie$x + $yBINOP addodejmowanie$x – $yBINOP substractmnożenie$x * $yBINOP multiplydzielenie$x / $yBINOP dividereszta modulo$x % $yBINOP modulobitowe AND$x & $yBINOP bit_andbitowe OR$x | $yBINOP bit_orbitowe XOR$x ^ $yBINOP bit_xornegacja arytmetyczna-$xUNOP negatenegacja bitowa~$xUNOP complementsinussin($x)UNOP sincosinuscos($x)UNOP cosfunkcja wykładniczaexp($x)UNOP explogarytmlog($x)UNOP logpierwiasteksqrt($x)UNOP sqrtwiększe$x > $yBINOP gtwiększe równe$x >= $yBINOP gemniejsze$x < $yBINOP ltmniejsze równe$x <= $yBINOP lerówne$x == $yBINOP eqnierówne$x != $yBINOP neporównanie$x <=> $yBINOP ncmpprzesunięcie bitowe w lewo$x << $yBINOP left_shiftprzesunięcie bitowe w prawo$x >> $yBINOP right_shiftpreinkrementacja++$xUNOP preincpredekrementacja--$xUNOP predecpostinkrementacja$x++UNOP postincpostdekrementacja$y--UNOP postdec Operatory ++ i -- działają też na łańcuchach. Wersje pre- i post- różnią się tym, co zostaje na stosie.
Operacje na łańcuchach znaków OperacjaPerlBytecodesklejenie$x . $yBINOP concatdługośćlength($x)UNOP lengthzamiana wszystkich liter na wielkieuc($x)UNOP uczamiana wszystkich liter na małelc($x)UNOP lczamiana pierwszego znaku na wielką literęucfirst($x)UNOP ucfirstzamiana pierwszego znaku na małą literęlcfirst($x)UNOP lcfirstwiększe$x gt $yBINOP sgtwiększe równe$x ge $yBINOP sgemniejsze$x lt $yBINOP sltmniejsze równe$x le $yBINOP slerówne$x eq $yBINOP seqnierówne$x ne $yBINOP sneporównanie$x cmp $yBINOP scmp
Kategoria:Asembler Kategoria:Perl Kategoria:Wirtualizacja