1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
| Numeric Operations
----------------
add TGT SRC1 SRC2
Let TGT become SRC1 + SRC2
bitand TGT SRC1 SRC2
Let TGT become SRC1 & SRC2
bitnot TGT SRC
Let TGT become ~SRC
bitor TGT SRC1 SRC2
Let TGT become SRC1 | SRC2
bitxor TGT SRC1 SRC2
Let TGT become SRC1 ^ SRC2
div TGT SRC1 SRC2
Let TGT become SRC1 / SRC2
eq TGT SRC1 SRC2
Let TGT become SRC1 == SRC2
expon TGT SRC1 SRC2
Let TGT become SRC1 ** SRC2
ge TGT SRC1 SRC2
Let TGT become SRC1 >= SRC2
gt TGT SRC1 SRC2
Let TGT become SRC1 > SRC2
le TGT SRC1 SRC2
Let TGT become SRC1 <= SRC2
lshift TGT SRC1 SRC2
Let TGT become SRC1 << SRC2
lt TGT SRC1 SRC2
Let TGT become SRC1 < SRC2
mod TGT SRC1 SRC2
Let TGT become SRC1 % SRC2
mult TGT SRC1 SRC2
Let TGT become SRC1 * SRC2
neq TGT SRC1 SRC2
Let TGT become SRC1 != SRC2
not TGT SRC
Let TGT become !SRC
rshift TGT SRC1 SRC2
Let TGT become SRC1 >> SRC2
sub TGT SRC1 SRC2
Let TGT become SRC1 - SRC2
uminus TGT SRC
Let TGT become -SRC
String Operations
--------------
free {} SRC
Marks that SRC is no longer used.
regexp TGT SRC1 SRC2 SRC3
Let TGT become the result of matching the regular expression in SRC2 to
the string in SRC3. SRC1 contains the flags. Note that this produces a
'Maybe INT' result; the RE engine is not failure-free.
strcase TGT SRC1 ENUM2
Let TGT become the string SRC1 with the case conversion in ENUM2. ENUM2 is
an enumeration and expected to be literal; 0 means convert to upper case,
1 means convert to lower case, and 2 means convert to title case.
strcat TGT SRC1 ...
Let TGT become the concatenation of the SRCs. Variadic.
strclass TGT SRC1 ENUM2
Let TGT become whether string SRC1 is in the class ENUM2, which is an
enumeration and expected to be literal. The enum is this:
=alnum 0 =alpha 1 =ascii 2 =control 3
=digit 4 =graph 5 =lower 6 =print 7
=punct 8 =space 9 =upper 10 =word 11
=xdigit 12
strcmp TGT SRC1 SRC2
Let TGT become the comparison (-1, 0, 1) of strings SRC1 and SRC2.
streq TGT SRC1 SRC2
Let TGT become whether string SRC1 equals string SRC2
strfind TGT SRC1 SRC2
Let TGT be the first index at which string SRC1 is located in SRC2, or -1
if not found.
strindex TGT SRC1 SRC2
Let TGT be the single-character string containing the character of SRC1 at
index SRC2, or the empty string if SRC2 is out of range.
strlen TGT SRC
Let TGT become strlen(SRC)
strmap TGT SRC1 SRC2 SRC3
Let TGT become SRC3 with all non-empty substrings that equal SRC1 replaced
with SRC2.
strmatch TGT ENUM1 SRC2 SRC3
Let TGT be whether the pattern in SRC2 matches the string in SRC3. ENUM1
is a boolean (true = match in case-insensitive mode) and is expected to be
a literal.
strrange TGT SRC1 SRC2 SRC3
Let TGT be the substring of SRC1 from index SRC2 to index SRC3.
strreplace TGT SRC1 SRC2 SRC3 SRC4
Let TGT be the string SRC1 with the characters from index SRC2 to index
SRC3 replaced with the content of the string SRC4.
strrfind TGT SRC1 SRC2
Let TGT be the last index at which string SRC1 is located in SRC2, or -1
if not found.
strtrim TGT SRC1 SRC2 ENUM3
Let TGT be the result of trimming the set of characters in the string in
SRC2 from the string in SRC1. ENUM3 says which end to trim from, and is
expected to be literal; -1 means from the left, 1 means from the right,
and 0 means both.
List Operations
---------------
NOTE: THESE CURRENTLY PRODUCE THE WRONG TYPE!
list TGT SRC1...
Let TGT be the result of constructing a list from the SRCs. Variadic.
listAppend TGT SRC1 SRC2
Let TGT be the list formed by appending element SRC2 to the list SRC1.
listConcat TGT SRC1 SRC2
Let TGT be the list formed by concatenating lists SRC1 and SRC2.
listIn TGT SRC1 SRC2
Let TGT be whether string SRC1 is an element of list SRC2.
listIndex TGT SRC1 SRC2...
Let TGT be the element in SRC1 identified by the index path in SRC2, etc.
Variadic.
listLength TGT SRC
Let TGT be the length of the list in SRC.
listRange TGT SRC1 SRC2 SRC3
Let TGT be the sublist of SRC1 from index SRC2 to index SRC3.
listSet TGT SRC1 SRC2 SRC3...
Let TGT be the list in SRC1 with the element in SRC2 set at the location
indicated by the index path in SRC3... Variadic.
unshareList TGT SRC
Let TGT be an unshared copy of the list in SRC. ASSUMES that we know for
sure that SRC contains a list.
foreachStart TGT SRC1 SRC2...
Let TGT be a FOREACH token (or a failure) that describes how to iterate
over the lists SRC2... Variadic. SRC1 is a literal (in the format used in
the decompilation of the original foreach_start's aux data) used to
describe the structure of the assignment targets being iterated over; the
structure of this list of lists is used, but the values are not.
foreachIter TGT SRC
Let TGT be the iteration step index from the FOREACH token in SRC.
foreachMayStep TGT SRC
Let TGT be whether the FOREACH token in SRC has reached the end; a true
value indicates that it has not.
foreachAdvance TGT SRC
Let TGT be the next value of the FOREACH token in SRC.
Dictionary Operations
---------------------
NOTE: THESE CURRENTLY PRODUCE THE WRONG TYPE!
dictExists TGT SRC1 SRC2...
Let TGT be whether the key path SRC2... exists in the dictionary SRC1.
Variadic.
dictGet TGT SRC1 SRC2...
Let TGT be what the key path SRC2... maps to in the dictionary SRC1.
Variadic.
dictSet TGT SRC1 SRC2 SRC3...
Let TGT be dictionary SRC1 with the key path SRC3... mapped to SRC2.
Variadic.
dictUnset TGT SRC1 SRC2...
Let TGT be dictionary SRC1 with the key path SRC2... removed. Variadic.
dictIterStart TGT SRC
Let TGT be an iteration token for dictionary in SRC.
dictIterNext TGT SRC
Let TGT be the token for the next step of the iteration in SRC.
dictIterDone TGT SRC
Let TGT be whether the iteration in SRC has finished.
dictIterKey TGT SRC
Let TGT be the key from the current step of the interation in SRC.
dictIterValue TGT SRC
Let TGT be the value from the current step of the interation in SRC.
Error-Related Operations List Operations
--------------------
extractMaybe TGT SRC
Given a Maybe in SRC which contains a Just X, let TGT become the X.
initException TGT SRC1 SRC2 ?SRC3 SRC4?
Set up an exception. TGT is a Maybe of the result value. SRC1 is the
result value. SRC2 is the options dictionary. SRC3 is the return code
override, and SRC4 is the return level override. Both SRC3 and SRC4 may be
omitted.
jumpMaybe BLK SRC
If the Maybe in SRC contains a Nothing, transfer execution to the block
with address BLK.
jumpMaybeNot BLK SRC
If the Maybe in SRC contains a Just X, transfer execution to the block
with address BLK.
result TGT
Let TGT contain the current interpreter result. Note that this is only
expected to be used in situations where the interpreter result is an error
message, where the code is handling an error case.
returnCode TGT
Let TGT contain the current interpreter exception code (0 for TCL_OK, 1
for TCL_ERROR, etc.) Note that this is only expected to be used in
situations where the code is handling an error case.
returnOptions TGT SRC
Let TGT contain the current interpreter return options, given that SRC
contains the exception code, as obtained by 'returnCode'.
returnException {} SRC
Generate an error that the caller can see. SRC should be the exception
code, but is currently unused. Note that the use of this instruction
triggers the overall type of the function to become a Maybe type.
setReturnCode {} SRC
Sets the current return code to SRC.
General/Structural Operations
-----------------------
confluence
Comes at the start of a block that has execution flowing in from multiple
other blocks.
copy TGT SRC
Let TGT become SRC
entry
Marks the entry to the function.
exists TGT SRC
Sets TGT to 1 if SRC has a value, and 0 otherwise
extractExists TGT SRC
Given a SRC value that is of type {NEXIST SOMETHING}, let TGT become
just the SOMETHING.
invoke TGT SRC1 ...
Let TGT become the invoke of the given command with the given arguments.
The command is given by SRC1 and the arguments are given by SRC2...
Variadic.
jump BLK
Transfer execution to the block with address BLK.
jumpFalse BLK SRC
Transfer execution to the block with address BLK if SRC is false, otherwise
transfer execution to the "next" block.
jumpTrue BLK SRC
Transfer execution to the block with address BLK if SRC is true, otherwise
transfer execution to the "next" block.
param TGT PARAM
Transfer the parameter value from parameter PARAM to internal variable TGT
phi TGT SRC1 BLK1 SRC2 BLK2 ...
Let TGT become the SRCn that corresponds to the BLKn that we entered this
block from.
return {} SRC
Return from this function with result SRC
unset TGT
Unset the value of TGT. Result is of type NEXIST.
{widenTo TYPECODE TYPENAME} TGT SRC
Transfer SRC to TGT, changing the data type to the type identified by
the numeric code TYPECODE (equivalently, the name TYPENAME)
Operations for common codebursts for variable existence.
initIfNotExists TGT SRC DEFAULT
Let TGT become SRC if SRC exists, otherwise, let TGT become DEFAULT.
throwIfNotExists PC SRC VARNAME
If SRC does not exist, initialize an exception with a 'variable does
not exist' error message and transfer control to PC (which is the enclosing
catch). Otherwise, let execution fall through.
throwNotExists PC VARNAME
VARNAME is known not to exist. Format an error message about it and jump to
PC.
Operations for managing data type checking
{checkFunctionParam N} PC FN SRC
If SRC is not suitable as the Nth parameter of function FN, initializes
an exception and transfers control to PC (which is the enclosing catch).
Otherwise, lets execution fall through. This operation is a placeholder
that is rewritten as 'checkArithDomain' once the function's parameter
types are known. It should never leak into code generation.
{checkArithDomain TYPECODE TYPENAME} PC SRC OPNAME
If SRC is not an instance of the type identified by TYPECODE (whose
name is TYPENAME), initializes an exception 'can't use non-numeric string
(or floating-point number) as argument to OPTNAME', and transfers control
to PC (which is the enclosing catch). Otherwise, lets execution fall
through.
{throwArithDomainError TYPECODE TYPENAME} PC SRC OPNAME
The same as above, except that SRC is known a priori not to be an instance
of the given type, so that the exception is unconditional.
{narrowToType TYPECODE TYPENAME} TGT SRC
Narrows the SRC operand to the given type and places the result in TGT.
The SRC operand is known to be an instance of the appropriate type.
{narrowToParamType N} TGT FN SRC
Narrows the SRC operand to the type required for the Nth parameter
of FN. This operation is a placeholder that is rewritten as
'checkArithDomain' once the function's parameter types are
known. It should never leak into code generation.
{narrowToNotParamType N} TGT FN SRC
Narrows the SRC operand to the complement of the type required for
the Nth parameter of FN. This operation is a placeholder that is
rewritten as 'checkArithDomain' once the function's parameter types
are known. It should never leak into code generation.
{instanceOf TYPECODE TYPENAME} TGT SRC
Tests whether SRC is an instance of the given type, and sets TGT to
1 or 0 according to the result.
For these operations, the data types that must be implemented are INT32,
INT, ENTIER, DOUBLE; the same four data types unioned with EMPTY; and the
complements of these eight types, so there are sixteen variants in all.
|