annotate interps/clc-intercal/CLC-INTERCAL-Base-1.-94.-2/INTERCAL/ByteCode.pm @ 12155:9e25c5563e7e draft

<b_jonas> `` /bin/sed -i \'s/humor,/humor, \\\\/\' "/hackenv/wisdom/rules of wisdom"
author HackEso <hackeso@esolangs.org>
date Mon, 18 Nov 2019 08:24:30 +0000
parents 859f9b4339e6
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
996
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
1 package Language::INTERCAL::ByteCode;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
2
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
3 # Definitions of bytecode symbols etc
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
4
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
5 # This file is part of CLC-INTERCAL
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
6
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
7 # Copyright (c) 2006-2008 Claudio Calvelli, all rights reserved.
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
8
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
9 # CLC-INTERCAL is copyrighted software. However, permission to use, modify,
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
10 # and distribute it is granted provided that the conditions set out in the
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
11 # licence agreement are met. See files README and COPYING in the distribution.
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
12
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
13 @@DATA ByteCode@@
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
14
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
15 use strict;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
16 use vars qw($VERSION $PERVERSION);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
17 ($VERSION) = ($PERVERSION = "CLC-INTERCAL/Base INTERCAL/ByteCode.pm 1.-94.-2") =~ /\s(\S+)$/;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
18
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
19 use Carp;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
20 use Language::INTERCAL::Exporter '1.-94.-2';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
21 use Language::INTERCAL::Splats '1.-94.-2', qw(:SP);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
22 use Language::INTERCAL::Numbers '1.-94.-2';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
23 use Language::INTERCAL::DoubleOhSeven '1.-94.-2';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
24 use Language::INTERCAL::SharkFin '1.-94.-2';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
25 use Language::INTERCAL::Arrays '1.-94.-2';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
26 use Language::INTERCAL::Whirlpool '1.-94.-2';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
27 use Language::INTERCAL::CrawlingHorror '1.-94.-2';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
28 use Language::INTERCAL::GenericIO '1.-94.-2',
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
29 qw($stdwrite $stdread $stdsplat $devnull);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
30
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
31 use constant BYTE_SIZE => 8; # number of bits per byte (must be == 8)
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
32 use constant NUM_OPCODES => 0x80; # number of virtual opcodes
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
33 use constant OPCODE_RANGE => 1 << BYTE_SIZE;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
34 use constant BC_MASK => OPCODE_RANGE - 1;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
35 use constant BIGNUM_SHIFT => BYTE_SIZE - 1;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
36 use constant BIGNUM_RANGE => 1 << BIGNUM_SHIFT;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
37 use constant BIGNUM_MASK => (BIGNUM_RANGE - 1) << 1;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
38 use constant BYTE_SHIFT => OPCODE_RANGE - NUM_OPCODES;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
39
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
40 use vars qw(@EXPORT @EXPORT_OK %EXPORT_TAGS);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
41 @EXPORT_OK = qw(
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
42 bytecode bytedecode bc_list BC BCget bc_bytype bc_match BC_MASK
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
43 BC_constants is_constant is_multibyte bc_xtype bc_skip bc_forall
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
44 @@FILL OPCODES BC_ NAME '' 76 ' '@@
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
45 reg_list reg_name reg_create reg_codetype reg_decode
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
46 reg_code
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
47 );
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
48
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
49 %EXPORT_TAGS = (
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
50 BC => [qw(
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
51 BC BCget BC_MASK bytecode bytedecode
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
52 @@FILL OPCODES BC_ NAME '' 76 ' '@@
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
53 )],
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
54 );
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
55
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
56 my %bytecodes = (
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
57 @@ALL OPCODES NAME@@ => ['@@'DESCR'@@', '@@TYPE@@', '@@NUMBER@@', '@@ARGS@@', @@CONST@@, @@ASSIGNABLE@@],
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
58 );
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
59
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
60 my %bytedecode = (
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
61 @@ALL OPCODES NUMBER@@ => '@@'NAME'@@',
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
62 );
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
63
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
64 my @bc_list = qw(
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
65 @@FILL OPCODES '' NAME '' 76 ' '@@
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
66 );
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
67
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
68 sub BC_@@ALL OPCODES NAME@@ () { @@NUMBER@@; }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
69
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
70 my @reg_list = qw(
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
71 @@FILL SPECIAL '' NAME '' 76 ' '@@
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
72 );
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
73
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
74 my %reg_list = (
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
75 @@ALL DOUBLE_OH_SEVEN NAME@@ => ['@@'CODE'@@', @@DEFAULT@@, BC_DOS, '%', @@NUMBER@@],
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
76 @@ALL SHARK_FIN NAME@@ => ['@@'CODE'@@', @@DEFAULT@@, BC_SHF, '^', @@NUMBER@@],
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
77 @@ALL WHIRLPOOL NAME@@ => ['@@'CODE'@@', @@DEFAULT@@, BC_WHP, '@', @@NUMBER@@],
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
78 );
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
79
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
80 my %reg_names = (
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
81 '%@@ALL DOUBLE_OH_SEVEN NUMBER@@' => '@@NAME@@',
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
82 '^@@ALL SHARK_FIN NUMBER@@' => '@@NAME@@',
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
83 '@@@ALL WHIRLPOOL NUMBER@@' => '@@NAME@@',
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
84 );
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
85
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
86 my %mulmap = map { ( $_ => 1 ) } BC_MUL, BC_STR;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
87
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
88 sub bc_list () {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
89 @bc_list;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
90 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
91
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
92 sub BC {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
93 @_ == 1 || croak "Usage: BC(value)";
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
94 my ($val) = @_;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
95 croak "Invalid undefined value" unless defined $val;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
96 my $orig = $val;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
97 $val < BYTE_SHIFT
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
98 and return ($val + NUM_OPCODES);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
99 $val < OPCODE_RANGE
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
100 and return (BC_HSN, $val);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
101 my $div = int($val / OPCODE_RANGE);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
102 $div < OPCODE_RANGE
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
103 and return (BC_OSN, $div, $val % OPCODE_RANGE);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
104 croak "Invalid value $orig: does not fit in one spot";
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
105 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
106
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
107 sub bytecode ($) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
108 my ($name) = @_;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
109 $name =~ /^\d+$/ && $name < BYTE_SHIFT ? ($name + NUM_OPCODES)
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
110 : $bytecodes{$name}[2];
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
111 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
112
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
113 sub bytedecode ($) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
114 my ($b) = @_;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
115 if ($b >= NUM_OPCODES) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
116 my $n = $b - NUM_OPCODES;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
117 return () if $n >= BYTE_SHIFT;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
118 return "#$n" unless wantarray;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
119 return ("#$n", 'Constant', '#', $b, '', 1, 1);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
120 } else {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
121 return () unless exists $bytedecode{$b};
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
122 return $bytedecode{$b} unless wantarray;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
123 return ($bytedecode{$b}, @{$bytecodes{$bytedecode{$b}}});
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
124 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
125 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
126
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
127 sub BCget {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
128 @_ == 3 or croak "Usage: BCget(CODE, \\POSITION, END)";
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
129 my ($code, $cp, $ep) = @_;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
130 $$cp >= $ep and faint(SP_INVALID, "end of code", "BCget");
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
131 my $byte = ord(substr($code, $$cp, 1));
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
132 $$cp++;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
133 if ($byte >= NUM_OPCODES) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
134 return $byte - NUM_OPCODES;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
135 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
136 if ($byte == BC_HSN) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
137 $$cp >= $ep and faint(SP_INVALID, "end of code", "BCget/HSN");
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
138 return ord(substr($code, $$cp++, 1));
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
139 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
140 if ($byte == BC_OSN) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
141 $$cp + 1 >= $ep and faint(SP_INVALID, "end of code", "BCget/OSN");
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
142 my $nx = unpack('n', substr($code, $$cp, 2));
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
143 $$cp += 2;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
144 return $nx;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
145 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
146 faint(SP_INVALID, sprintf("0x%02x", $byte), "BCget")
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
147 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
148
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
149 sub BC_constants () {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
150 (NUM_OPCODES..BC_MASK);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
151 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
152
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
153 sub is_constant ($) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
154 my ($byte) = @_;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
155 return 1 if $byte >= NUM_OPCODES ||
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
156 $byte == BC_HSN ||
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
157 $byte == BC_OSN;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
158 return 0;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
159 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
160
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
161 sub is_multibyte ($) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
162 my ($byte) = @_;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
163 return 1 if $byte == BC_HSN;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
164 return 2 if $byte == BC_OSN;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
165 0;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
166 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
167
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
168 sub bc_bytype {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
169 @_ or croak "Usage: bc_bytype(TYPES)";
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
170 my %types = ();
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
171 for my $type (@_) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
172 if ($type eq 'R' || $type eq 'S') {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
173 $types{$type} = 0;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
174 next;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
175 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
176 if ($type =~ /^[CEP<>L\[\]]$/) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
177 $types{E} = $types{R} = $types{'#'} = 0;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
178 next;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
179 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
180 if ($type eq 'V') {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
181 $types{R} = $types{V} = 0;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
182 next;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
183 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
184 if ($type eq 'O') {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
185 $types{S} = 0;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
186 next;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
187 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
188 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
189 my %values = exists $types{V} ? %mulmap : ();
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
190 map {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
191 my ($desc, $type, $value, $args, $function) = @{$bytecodes{$_}};
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
192 if (exists $types{$type} || exists $values{$value}) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
193 $value;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
194 } else {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
195 ();
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
196 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
197 } keys %bytecodes;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
198 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
199
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
200 sub bc_match {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
201 @_ >= 2 && @_ <= 4
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
202 or croak "Usage: bc_match(PATTERN, CODE [,START [,END]])";
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
203 my ($pattern, $code, $start, $end) = @_;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
204 $start ||= 0;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
205 $end = length($code) if not defined $end;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
206 _match($pattern, $code, $start, $end, undef);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
207 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
208
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
209 sub bc_skip {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
210 @_ >= 1 && @_ <= 3
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
211 or croak "Usage: bc_skip(CODE [,START [,END]])";
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
212 my ($code, $start, $end) = @_;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
213 $start ||= 0;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
214 $end = length($code) if not defined $end;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
215 return undef if $start >= $end || $start < 0;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
216 my $byte = ord(substr($code, $start, 1));
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
217 return 1 if $byte >= NUM_OPCODES;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
218 return undef if ! exists $bytedecode{$byte};
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
219 my $name = $bytedecode{$byte};
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
220 my $pattern = $bytecodes{$name}[1];
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
221 _match($pattern, $code, $start, $end, undef);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
222 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
223
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
224 sub bc_forall {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
225 @_ == 5
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
226 or croak "Usage: bc_forall(PATTERN, CODE, START, END, CLOSURE)";
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
227 my ($pattern, $code, $start, $end, $closure) = @_;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
228 $start ||= 0;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
229 $end = length($code) if not defined $end;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
230 return undef if $start >= $end || $start < 0;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
231 my $np = '';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
232 while ($pattern =~ s/^(.*?)C\(/(/) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
233 my $a = $1;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
234 $a =~ s/(.)/$1\x01/g;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
235 $np .= $a . 'C';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
236 $np .= '(' . _args('forall', \$pattern) . ')';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
237 $np .= "\01";
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
238 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
239 $pattern =~ s/(.)/$1\x01/g;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
240 $pattern = "\x01" if $pattern eq '';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
241 $np .= $pattern;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
242 _match($np, $code, $start, $end, $closure);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
243 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
244
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
245 sub bc_xtype {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
246 @_ == 1 or croak "Usage: bc_xtype(\\PATTERN)";
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
247 my ($pattern) = @_;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
248 _args('xtype', $pattern);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
249 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
250
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
251 my %typemap = (
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
252 'S' => { 'S' => 0 },
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
253 'O' => { 'S' => 0 },
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
254 'E' => { 'E' => 0, 'R' => 0, '#' => 0 },
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
255 'A' => { 'E' => 0, 'R' => 0, '#' => 0 },
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
256 'R' => { 'R' => 0 },
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
257 'V' => { 'R' => 0, 'V' => 0 },
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
258 '#' => { '#' => 0 },
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
259 'C' => { '#' => 0 },
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
260 'Z' => { 'S' => 0, 'E' => 0, 'R' => 0, '#' => 0 },
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
261 '*' => { 'S' => 0, 'E' => 0, 'R' => 0, '#' => 0 },
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
262 );
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
263
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
264 sub _args {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
265 my ($name, $pattern) = @_;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
266 faint(SP_BCMATCH, $name, 'Missing (') if $$pattern !~ s/^\(//;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
267 my $count = 1;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
268 my $result = '';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
269 while ($count > 0) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
270 $$pattern =~ s/^([^\(\)]*)([\(\)])//
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
271 or faint(SP_BCMATCH, $name, 'Missing )');
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
272 $count++ if $2 eq '(';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
273 $count-- if $2 eq ')';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
274 $result .= $1 . ($count ? $2 : '');
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
275 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
276 $result;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
277 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
278
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
279 sub _match {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
280 my ($pattern, $code, $sc, $ep, $closure) = @_;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
281 my $osc = $sc;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
282 MATCH: while ($pattern ne '') {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
283 my $e = substr($pattern, 0, 1, '');
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
284 if ($e eq "\x00") {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
285 $closure->(undef, '>') if $closure;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
286 next MATCH;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
287 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
288 if ($e eq "\x01") {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
289 $closure->($sc, undef) if $closure;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
290 next MATCH;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
291 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
292 faint(SP_INVALID, 'end of code', '_match') if $sc >= $ep;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
293 my $v = ord(substr($code, $sc, 1));
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
294 if (exists $typemap{$e}) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
295 # check next opcode is correct type
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
296 my ($op, $desc, $type, $value, $args, $const) = bytedecode($v);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
297 faint(SP_INVALID, $v, "_match: $e")
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
298 unless defined $type;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
299 faint(SP_INVALID, $type, "_match: $e")
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
300 unless exists $typemap{$e}{$type} ||
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
301 (exists $mulmap{$v} && exists $typemap{$e}{V});
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
302 if ($e eq 'O' && $const) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
303 BCget($code, \$sc, $ep);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
304 } elsif ($type eq '#' && $e ne '*') {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
305 my $num = BCget($code, \$sc, $ep);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
306 $closure->($v, "#$num") if $closure;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
307 if ($e eq 'C') {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
308 $args = _args('count', \$pattern) x $num;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
309 $args .= "\x00";
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
310 $closure->(undef, '<') if $closure;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
311 } else {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
312 $args = '';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
313 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
314 } else {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
315 $sc++;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
316 $args = '' if $e eq 'O' || $e eq '*';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
317 $closure->($v, $op) if $closure;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
318 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
319 $pattern = $args . $pattern;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
320 next MATCH;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
321 } elsif ($e eq 'N') {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
322 # any nonzero number
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
323 return undef if $v == 0;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
324 $closure->($v, "N$v") if $closure;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
325 $sc++;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
326 } elsif ($e eq '<') {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
327 # left grammar element
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
328 my $count = BCget($code, \$sc, $ep);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
329 my $num = BCget($code, \$sc, $ep);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
330 if ($num == 0) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
331 $closure->(undef, '?<') if $closure;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
332 } elsif ($num == 1 || $num == 2) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
333 $closure->(undef, ',<') if $closure;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
334 } else {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
335 $closure->(undef, ',!<') if $closure;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
336 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
337 if ($count && $closure) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
338 $closure->(undef, $count == 65535 ? '*' : $count);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
339 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
340 $pattern = "E\x00" . $pattern;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
341 next MATCH;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
342 } elsif ($e eq '>') {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
343 # right grammar element
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
344 my $num = BCget($code, \$sc, $ep);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
345 if ($num == 0 || $num == 6) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
346 my $count = BCget($code, \$sc, $ep);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
347 if ($count && $closure) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
348 $closure->(undef, $count);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
349 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
350 $closure->($v, $num ? '!<' : '?<') if $closure;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
351 $pattern = "E\x00" . $pattern;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
352 next MATCH;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
353 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
354 if ($num == 1 || $num == 2) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
355 $closure->($v, ',<') if $closure;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
356 my $count = BCget($code, \$sc, $ep);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
357 if ($count && $closure) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
358 $closure->(undef, $count);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
359 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
360 $pattern = "E\x00" . $pattern;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
361 next MATCH;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
362 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
363 if ($num == 3 || $num == 7) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
364 $closure->($v, ',!<') if $closure;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
365 my $count = BCget($code, \$sc, $ep);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
366 if ($count && $closure) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
367 $closure->(undef, $count);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
368 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
369 $pattern = "E\x00" . $pattern;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
370 next MATCH;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
371 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
372 if ($num == 4) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
373 $num = BCget($code, \$sc, $ep);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
374 my $se = $sc + $num;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
375 $se <= $ep
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
376 or faint(SP_INVALID, '???', '_match: >');
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
377 if ($closure) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
378 $closure->(undef, '=<');
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
379 while ($sc < $se) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
380 $sc += _match('*', $code, $sc, $se, $closure);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
381 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
382 $closure->(undef, '>');
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
383 } else {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
384 $sc = $se;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
385 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
386 next MATCH;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
387 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
388 if ($num == 15) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
389 $closure->($v, '*') if $closure;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
390 next MATCH;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
391 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
392 faint(SP_INVALID, $num, "_match: >");
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
393 } elsif ($e eq '[') {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
394 # XXX left optimise element
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
395 faint(SP_TODO, 'match on [');
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
396 } elsif ($e eq ']') {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
397 # XXX right optimise element
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
398 faint(SP_TODO, 'match on ]');
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
399 } else {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
400 faint(SP_BCMATCH, 'type', $e);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
401 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
402 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
403 $sc - $osc;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
404 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
405
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
406 sub reg_list () {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
407 @reg_list;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
408 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
409
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
410 sub reg_create {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
411 @_ == 2 || @_ == 3
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
412 or croak "Usage: reg_create(REGISTER, OBJECT [, VALUE])";
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
413 my ($rn, $object, @value) = @_;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
414 $rn = $reg_names{$rn} if exists $reg_names{$rn};
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
415 if (exists $reg_list{$rn}) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
416 @value = $reg_list{$rn}[1] if ! @value;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
417 my $rt = $reg_list{$rn}[3];
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
418 my $dt = $reg_list{$rn}[0];
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
419 return Language::INTERCAL::DoubleOhSeven->new($dt, $object, @value)
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
420 if $rt eq '%';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
421 return Language::INTERCAL::SharkFin->new($dt, $object, @value)
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
422 if $rt eq '^';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
423 return Language::INTERCAL::Whirlpool->new(@value)
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
424 if $rt eq '@';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
425 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
426 $rn =~ /^\./
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
427 and return Language::INTERCAL::Numbers::Spot->new(@value || 0);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
428 $rn =~ /^:/
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
429 and return Language::INTERCAL::Numbers::Twospot->new(@value || 0);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
430 $rn =~ /^,/
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
431 and return Language::INTERCAL::Arrays::Tail->new(@value || []);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
432 $rn =~ /^;/
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
433 and return Language::INTERCAL::Arrays::Hybrid->new(@value || []);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
434 $rn =~ /^\@/
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
435 and return Language::INTERCAL::Whirlpool->new();
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
436 $rn =~ /^\_[12]$/
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
437 and return Language::INTERCAL::CrawlingHorror->new();
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
438 faint(SP_SPECIAL, $rn);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
439 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
440
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
441 sub reg_codetype {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
442 @_ == 1 or croak "Usage: reg_codetype(REGISTER)";
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
443 my ($rn) = @_;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
444 exists $reg_list{$rn} and return $reg_list{$rn}[0];
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
445 if (exists $reg_names{$rn}) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
446 $rn = $reg_names{$rn};
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
447 return $reg_list{$rn}[0];
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
448 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
449 $rn =~ /^\./ and return 'spot';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
450 $rn =~ /^:/ and return 'twospot';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
451 $rn =~ /^,/ and return 'tail';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
452 $rn =~ /^;/ and return 'hybrid';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
453 $rn =~ /^\@/ and return 'whirlpool';
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
454 faint(SP_SPECIAL, $rn);
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
455 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
456
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
457 sub reg_name {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
458 @_ == 1 or croak "Usage: reg_name(REGISTER)";
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
459 my ($rn) = @_;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
460 exists $reg_list{$rn}
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
461 and return $reg_list{$rn}[3] . $reg_list{$rn}[4];
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
462 if (exists $reg_names{$rn}) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
463 $rn = $reg_names{$rn};
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
464 return $reg_list{$rn}[3] . $reg_list{$rn}[4];
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
465 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
466 $rn =~ /^([%^\@])(.*)$/ && exists $reg_list{$2} && $reg_list{$2}[3] eq $1
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
467 and return $reg_list{$2}[3] . $reg_list{$2}[4];
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
468 $rn =~ s/^([\.:,;\@^%])0*(\d+)$/$1$2/ and return $rn;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
469 undef;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
470 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
471
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
472 sub reg_code {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
473 @_ == 1 or croak "Usage: reg_code(REGISTER)";
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
474 my ($rn) = @_;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
475 exists $reg_list{$rn}
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
476 and return ($reg_list{$rn}[2], BC($reg_list{$rn}[4]));
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
477 if (exists $reg_names{$rn}) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
478 $rn = $reg_names{$rn};
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
479 return ($reg_list{$rn}[2], BC($reg_list{$rn}[4]));
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
480 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
481 $rn =~ /^([%^\@])(.*)$/ && exists $reg_list{$2} && $reg_list{$2}[3] eq $1
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
482 and return ($reg_list{$2}[2], BC($reg_list{$2}[4]));
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
483 $rn =~ /^\.(\d+)$/ and return (BC_SPO, BC($1));
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
484 $rn =~ /^:(\d+)$/ and return (BC_TSP, BC($1));
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
485 $rn =~ /^,(\d+)$/ and return (BC_TAI, BC($1));
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
486 $rn =~ /^;(\d+)$/ and return (BC_HYB, BC($1));
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
487 $rn =~ /^\@(\d+)$/ and return (BC_WHP, BC($1));
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
488 $rn =~ /^\%(\d+)$/ and return (BC_DOS, BC($1));
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
489 $rn =~ /^\^(\d+)$/ and return (BC_SHF, BC($1));
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
490 undef;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
491 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
492
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
493 sub reg_decode {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
494 @_ == 1 or croak "Usage: reg_name(REGISTER)";
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
495 my ($rn) = @_;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
496 return $rn if $rn =~ /^[.,:;\@_]/;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
497 if ($rn =~ /^[%^]\d+$/) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
498 return undef unless exists $reg_names{$rn};
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
499 $rn = $reg_names{$rn};
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
500 } elsif ($rn =~ s/^([%^])//) {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
501 return undef unless exists $reg_list{$rn};
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
502 return undef if $1 ne $reg_list{$rn}[3];
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
503 } else {
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
504 return undef unless exists $reg_list{$rn};
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
505 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
506 $reg_list{$rn}[3] . $rn;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
507 }
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
508
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
509 1;
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
510
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
511 __END__
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
512
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
513 =pod
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
514
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
515 =head1 TITLE
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
516
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
517 Language::INTERCAL::Bytecode - intermediate language
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
518
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
519 =head1 DESCRIPTION
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
520
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
521 The CLC-INTERCAL compiler works by producing bytecode from the
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
522 program source; this bytecode can be interpreted to execute the
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
523 program immediately; alternatively, a backend can produce something
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
524 else from the bytecode, for example C or Perl source code which can
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
525 then be compiled to your computer's native object format.
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
526
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
527 The compiler itself is just some more bytecode. Thus, to produce the
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
528 compiler you need a compiler compiler, and to produce that you need
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
529 a compiler compiler compiler; to produce the latter you would need
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
530 a compiler compiler compiler compiler, and so on to infinity. To
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
531 simplify the programmer's life (eh?), the compiler compiler is able
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
532 to compile itself, and is therefore identical to the compiler compiler
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
533 compiler (etcetera).
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
534
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
535 The programmer can start the process because a pre-compiled compiler
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
536 compiler, in the form of bytecode, is provided with the CLC-INTERCAL
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
537 distribution; this compiler compiler then is able to compile all
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
538 other compilers, as well as to rebuild itself if need be.
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
539
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
540 See the online manual or the HTML documentation included with the
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
541 distribution for more information about this.
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
542
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
543 =head1 SEE ALSO
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
544
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
545 A qualified psychiatrist
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
546
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
547 =head1 AUTHOR
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
548
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
549 Claudio Calvelli - intercal (whirlpool) sdf.lonestar.org
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
550 (Please include the word INTERLEAVING in the subject when emailing that
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
551 address, or the email may be ignored)
859f9b4339e6 <Gregor> tar xf egobot.tar.xz
HackBot
parents:
diff changeset
552