-
Notifications
You must be signed in to change notification settings - Fork 6
Expand file tree
/
Copy pathTypeConversions.asm
More file actions
378 lines (321 loc) · 18.3 KB
/
TypeConversions.asm
File metadata and controls
378 lines (321 loc) · 18.3 KB
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
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
;;<< TYPE CONVERSIONS AND ROUNDING
;;< (from numbers to numbers)
;;========================================================
;; function ABS
;ABS(<numeric expression>)
;Returns absolute value (i.e. negates if negative)
function_ABS: ;{{Addr=$fdb0 Code Calls/jump count: 0 Data use count: 1}}
call get_raw_abs_of_accumulator_with_reg_preserve;{{fdb0:cdc4fd}}
ret p ;{{fdb3:f0}}
;;=negate accumulator
negate_accumulator: ;{{Addr=$fdb4 Code Calls/jump count: 1 Data use count: 0}}
call return_accumulator_value_if_int_or_address_if_real;{{fdb4:cd4fff}}
jp nc,REAL_UNARY_MINUS;{{fdb7:d291bd}} firmware REAL negate
call negate_HL_and_test_if_INT;{{fdba:cdeddd}} negate HL
ld (accumulator),hl ;{{fdbd:22a0b0}}
call nc,set_accumulator_as_REAL_from_unsigned_INT;{{fdc0:d489fe}} Not a valid INT so convert to a REAL
ret ;{{fdc3:c9}}
;;=get raw abs of accumulator with reg preserve
get_raw_abs_of_accumulator_with_reg_preserve:;{{Addr=$fdc4 Code Calls/jump count: 5 Data use count: 0}}
push bc ;{{fdc4:c5}}
push hl ;{{fdc5:e5}}
call get_raw_abs_of_accumulator;{{fdc6:cdccfd}}
pop hl ;{{fdc9:e1}}
pop bc ;{{fdca:c1}}
ret ;{{fdcb:c9}}
;;=get raw abs of accumulator
;returns A = negative, 0 or positive
get_raw_abs_of_accumulator: ;{{Addr=$fdcc Code Calls/jump count: 1 Data use count: 0}}
call return_accumulator_value_if_int_or_address_if_real;{{fdcc:cd4fff}}
jp c,unknown_test_HL ;{{fdcf:daf9dd}}
jp REAL_SIGNUMSGN ;{{fdd2:c394bd}}
;;=round accumulator
round_accumulator: ;{{Addr=$fdd5 Code Calls/jump count: 1 Data use count: 0}}
push hl ;{{fdd5:e5}}
ld a,c ;{{fdd6:79}}
call copy_atHL_to_accumulator_type_A;{{fdd7:cd6cff}}
pop de ;{{fdda:d1}}
call return_accumulator_value_if_int_or_address_if_real;{{fddb:cd4fff}}
ld a,b ;{{fdde:78}}
jr nc,_round_accumulator_12;{{fddf:300b}} (+$0b)
or a ;{{fde1:b7}}
ret p ;{{fde2:f0}}
call set_accumulator_as_positive_REAL_from_HL;{{fde3:cd93fe}}
call _round_accumulator_16;{{fde6:cdf4fd}}
jp function_CINT ;{{fde9:c3b6fe}}
_round_accumulator_12: ;{{Addr=$fdec Code Calls/jump count: 1 Data use count: 0}}
or a ;{{fdec:b7}}
jr nz,_round_accumulator_16;{{fded:2005}} (+$05)
ld de,REAL_TO_BINARY ;{{fdef:116dbd}} firmware REAL to bin
jr _function_int_3 ;{{fdf2:1826}} (+$26)
_round_accumulator_16: ;{{Addr=$fdf4 Code Calls/jump count: 2 Data use count: 0}}
push de ;{{fdf4:d5}}
push bc ;{{fdf5:c5}}
ld a,b ;{{fdf6:78}}
call REAL_10A ;{{fdf7:cd79bd}}
call c,REAL_TO_BINARY ;{{fdfa:dc6dbd}} firmware REAL to bin
ld a,b ;{{fdfd:78}}
pop bc ;{{fdfe:c1}}
pop de ;{{fdff:d1}}
jr nc,_round_accumulator_29;{{fe00:3008}} (+$08)
call BINARY_TO_REAL ;{{fe02:cd67bd}} firmware bin to REAL
xor a ;{{fe05:af}}
sub b ;{{fe06:90}}
jp REAL_10A ;{{fe07:c379bd}} firmware REAL exp A
_round_accumulator_29: ;{{Addr=$fe0a Code Calls/jump count: 1 Data use count: 0}}
ex de,hl ;{{fe0a:eb}}
jp copy_atHL_to_accumulator_using_accumulator_type;{{fe0b:c36fff}}
;;========================================================
;; function FIX
;FIX(<numeric expression>)
;Truncate value to an integer. Returns a float with no fractional part, rounding towards zero.
function_FIX: ;{{Addr=$fe0e Code Calls/jump count: 0 Data use count: 1}}
ld de,REAL_FIX ;{{fe0e:1170bd}} firmware REAL fix
jr _function_int_1 ;{{fe11:1803}} (+$03)
;;========================================================
;; function INT
;INT(<numeric expression>)
;Rounds the value to the nearest smaller integer (round towards minus infinity)
;Does not convert to integer, merely removes fractional part
function_INT: ;{{Addr=$fe13 Code Calls/jump count: 0 Data use count: 1}}
ld de,REAL_INT ;{{fe13:1173bd}} firmware REAL int
_function_int_1: ;{{Addr=$fe16 Code Calls/jump count: 1 Data use count: 0}}
call return_accumulator_value_if_int_or_address_if_real;{{fe16:cd4fff}}
ret c ;{{fe19:d8}}
_function_int_3: ;{{Addr=$fe1a Code Calls/jump count: 1 Data use count: 0}}
call JP_DE ;{{fe1a:cdfeff}} JP (DE)
ret nc ;{{fe1d:d0}}
ld a,(accumulator_data_type);{{fe1e:3a9fb0}}
call _function_int_11 ;{{fe21:cd2cfe}}
ret c ;{{fe24:d8}}
call get_accumulator_type_in_c_and_addr_in_HL;{{fe25:cd45ff}}
ld a,b ;{{fe28:78}}
jp BINARY_TO_REAL ;{{fe29:c367bd}} firmware BIN to REAL
_function_int_11: ;{{Addr=$fe2c Code Calls/jump count: 2 Data use count: 0}}
ld a,c ;{{fe2c:79}}
cp $03 ;{{fe2d:fe03}}
ret nc ;{{fe2f:d0}}
ld a,(hl) ;{{fe30:7e}}
inc hl ;{{fe31:23}}
ld h,(hl) ;{{fe32:66}}
ld l,a ;{{fe33:6f}}
call unknown_maths_fixup;{{fe34:cd37dd}}
ret nc ;{{fe37:d0}}
jp store_HL_in_accumulator_as_INT;{{fe38:c335ff}}
;;=========================================
;;convert accum and param to same numeric type
;(error if either is string).
;C=type of param
convert_accum_and_param_to_same_numeric_type:;{{Addr=$fe3b Code Calls/jump count: 5 Data use count: 0}}
ld a,c ;{{fe3b:79}} C contains a type specifier
cp $03 ;{{fe3c:fe03}}
jr z,raise_type_mismatch_error_B;{{fe3e:282d}} (+$2d) if string?
ld a,(accumulator_data_type);{{fe40:3a9fb0}}
cp $03 ;{{fe43:fe03}}
jr z,raise_type_mismatch_error_B;{{fe45:2826}} (+$26) if string
cp c ;{{fe47:b9}}
jr z,_convert_accum_and_param_to_same_numeric_type_22;{{fe48:2817}} (+$17) if same type as C
jr nc,_convert_accum_and_param_to_same_numeric_type_17;{{fe4a:300c}} (+$0c) accum is real C is int
push hl ;{{fe4c:e5}} else accum is int, C is real...
ld hl,accumulator_data_type;{{fe4d:219fb0}} ...so convert accum to real
ld (hl),c ;{{fe50:71}}
inc hl ;{{fe51:23}}
call convert_INT_atHL_to_positive_REAL_atHL;{{fe52:cd8cfe}}
pop de ;{{fe55:d1}}
or a ;{{fe56:b7}}
ret ;{{fe57:c9}}
_convert_accum_and_param_to_same_numeric_type_17:;{{Addr=$fe58 Code Calls/jump count: 1 Data use count: 0}}
call convert_INT_atHL_to_positive_REAL_atHL;{{fe58:cd8cfe}}
or a ;{{fe5b:b7}}
_convert_accum_and_param_to_same_numeric_type_19:;{{Addr=$fe5c Code Calls/jump count: 1 Data use count: 0}}
ex de,hl ;{{fe5c:eb}}
ld hl,accumulator ;{{fe5d:21a0b0}}
ret ;{{fe60:c9}}
_convert_accum_and_param_to_same_numeric_type_22:;{{Addr=$fe61 Code Calls/jump count: 1 Data use count: 0}}
xor $02 ;{{fe61:ee02}}
jr nz,_convert_accum_and_param_to_same_numeric_type_19;{{fe63:20f7}} (-$09)
ld e,(hl) ;{{fe65:5e}}
inc hl ;{{fe66:23}}
ld d,(hl) ;{{fe67:56}}
ld hl,(accumulator) ;{{fe68:2aa0b0}}
scf ;{{fe6b:37}}
ret ;{{fe6c:c9}}
;;=raise Type mismatch error
raise_type_mismatch_error_B: ;{{Addr=$fe6d Code Calls/jump count: 2 Data use count: 0}}
jp raise_type_mismatch_error_C;{{fe6d:c362ff}}
;;==================================
;;convert accum and param to REAL
convert_accum_and_param_to_REAL: ;{{Addr=$fe70 Code Calls/jump count: 1 Data use count: 0}}
ld a,(accumulator_data_type);{{fe70:3a9fb0}}
or c ;{{fe73:b1}}
cp $02 ;{{fe74:fe02}}
jr nz,convert_accum_and_param_to_same_numeric_type;{{fe76:20c3}} (-$3d)
;;=convert INT accum and INT param to REAL
convert_INT_accum_and_INT_param_to_REAL:;{{Addr=$fe78 Code Calls/jump count: 3 Data use count: 0}}
ld hl,(accumulator) ;{{fe78:2aa0b0}}
call set_accumulator_as_positive_REAL_from_HL;{{fe7b:cd93fe}}
ld hl,(execution_stack_next_free_ptr);{{fe7e:2a6fb0}}
call convert_INT_atHL_to_positive_REAL_atHL;{{fe81:cd8cfe}}
ex de,hl ;{{fe84:eb}}
ld hl,accumulator ;{{fe85:21a0b0}}
ret ;{{fe88:c9}}
;;======================================
;;set accumulator as REAL from unsigned INT
set_accumulator_as_REAL_from_unsigned_INT:;{{Addr=$fe89 Code Calls/jump count: 5 Data use count: 0}}
xor a ;{{fe89:af}}
jr set_accumulator_from_HL_with_possible_invert;{{fe8a:1808}} (+$08)
;;=======================================
;;convert INT atHL to positive REAL atHL
convert_INT_atHL_to_positive_REAL_atHL:;{{Addr=$fe8c Code Calls/jump count: 3 Data use count: 0}}
ld e,(hl) ;{{fe8c:5e}}
inc hl ;{{fe8d:23}}
ld d,(hl) ;{{fe8e:56}}
dec hl ;{{fe8f:2b}}
ld a,d ;{{fe90:7a}}
jr set_atHL_from_DE_with_possible_invert;{{fe91:1808}} (+$08)
;;=======================================
;;set accumulator as positive REAL from HL
;HL=int value
set_accumulator_as_positive_REAL_from_HL:;{{Addr=$fe93 Code Calls/jump count: 3 Data use count: 0}}
ld a,h ;{{fe93:7c}}
;;=set accumulator from HL with possible invert
;invert if bit 7 of a is set
set_accumulator_from_HL_with_possible_invert:;{{Addr=$fe94 Code Calls/jump count: 1 Data use count: 0}}
ex de,hl ;{{fe94:eb}}
ld hl,accumulator_data_type;{{fe95:219fb0}}
ld (hl),$05 ;{{fe98:3605}}
inc hl ;{{fe9a:23}}
;;=set atHL from DE with possible invert
;invert if bit 7 of a is set
set_atHL_from_DE_with_possible_invert:;{{Addr=$fe9b Code Calls/jump count: 1 Data use count: 0}}
ex de,hl ;{{fe9b:eb}}
push af ;{{fe9c:f5}}
or a ;{{fe9d:b7}}
call m,negate_HL_and_test_if_INT;{{fe9e:fceddd}}
pop af ;{{fea1:f1}}
jp INTEGER_TO_REAL ;{{fea2:c364bd}} firmware INT to REAL
;;===================================
;;store int to accumulator
store_int_to_accumulator: ;{{Addr=$fea5 Code Calls/jump count: 1 Data use count: 0}}
ld (accumulator),hl ;{{fea5:22a0b0}}
;;=====================================
;;set accumulator as REAL from BINARY zero or minus one
;binary in HL only. (useful only for -1 and zero??)
ex de,hl ;{{fea8:eb}}
ld (accumulator_plus_2),hl;{{fea9:22a2b0}}
ld hl,accumulator_data_type;{{feac:219fb0}}
ld (hl),$05 ;{{feaf:3605}}
inc hl ;{{feb1:23}}
xor a ;{{feb2:af}}
jp BINARY_TO_REAL ;{{feb3:c367bd}} firmware BIN to REAL
;;========================================================
;; function CINT
;CINT(<numeric expression>)
;Converts the value to an integer
;Expression must be -32768..+32767
function_CINT: ;{{Addr=$feb6 Code Calls/jump count: 10 Data use count: 1}}
call _function_cint_3 ;{{feb6:cdbcfe}}
ret c ;{{feb9:d8}}
jr raise_Overflow_error;{{feba:183f}} (+$3f)
_function_cint_3: ;{{Addr=$febc Code Calls/jump count: 1 Data use count: 0}}
call convert_accumulator_to_int;{{febc:cdcefe}}
ld (accumulator),hl ;{{febf:22a0b0}}
ret ;{{fec2:c9}}
;;-=============================================
;;=convert atHL with type C and accumulator to ints
convert_atHL_with_type_C_and_accumulator_to_ints:;{{Addr=$fec3 Code Calls/jump count: 5 Data use count: 0}}
ld a,c ;{{fec3:79}}
call convert_atHL_with_type_C_to_int;{{fec4:cdd5fe}}
ex de,hl ;{{fec7:eb}}
call c,convert_accumulator_to_int;{{fec8:dccefe}} carry here means we had a pointer to an int
ret c ;{{fecb:d8}}
jr raise_Overflow_error;{{fecc:182d}} (+$2d)
;;===============================================
;;=convert accumulator to int
convert_accumulator_to_int: ;{{Addr=$fece Code Calls/jump count: 2 Data use count: 0}}
ld hl,accumulator_data_type;{{fece:219fb0}}
ld a,(hl) ;{{fed1:7e}}
ld (hl),$02 ;{{fed2:3602}}
inc hl ;{{fed4:23}}
;;=convert atHL with type C to int
convert_atHL_with_type_C_to_int: ;{{Addr=$fed5 Code Calls/jump count: 1 Data use count: 0}}
cp $03 ;{{fed5:fe03}}
jr c,_convert_athl_with_type_c_to_int_9;{{fed7:380d}} (+$0d) if type is int treat it as a pointer to the actual real and redo
jp z,raise_type_mismatch_error_C;{{fed9:ca62ff}} error if string
push bc ;{{fedc:c5}}
call REAL_TO_INTEGER ;{{fedd:cd6abd}} firmware REAL to INT
ld b,a ;{{fee0:47}}
call c,unknown_maths_fixup;{{fee1:dc37dd}}
pop bc ;{{fee4:c1}}
ret ;{{fee5:c9}}
_convert_athl_with_type_c_to_int_9:;{{Addr=$fee6 Code Calls/jump count: 1 Data use count: 0}}
ld a,(hl) ;{{fee6:7e}}
inc hl ;{{fee7:23}}
ld h,(hl) ;{{fee8:66}}
ld l,a ;{{fee9:6f}}
ret ;{{feea:c9}}
;;========================================================
;; function UNT
;UNT(<address expression>)
;Converts to an unsigned integer in the range -32768..32767
function_UNT: ;{{Addr=$feeb Code Calls/jump count: 4 Data use count: 1}}
call return_accumulator_value_if_int_or_address_if_real;{{feeb:cd4fff}}
ret c ;{{feee:d8}}
call REAL_TO_INTEGER ;{{feef:cd6abd}}
jr nc,raise_Overflow_error;{{fef2:3007}} (+$07)
ld b,a ;{{fef4:47}}
call m,unknown_maths_fixup;{{fef5:fc37dd}}
jp c,store_HL_in_accumulator_as_INT;{{fef8:da35ff}}
;;=raise Overflow error
raise_Overflow_error: ;{{Addr=$fefb Code Calls/jump count: 3 Data use count: 0}}
call byte_following_call_is_error_code;{{fefb:cd45cb}}
defb $06 ;Inline error code: Overflow
;;=====================================
;;convert accumulator to type in A
;int to real or real to int only
convert_accumulator_to_type_in_A: ;{{Addr=$feff Code Calls/jump count: 5 Data use count: 0}}
push hl ;{{feff:e5}}
push de ;{{ff00:d5}}
push bc ;{{ff01:c5}}
ld hl,accumulator_data_type;{{ff02:219fb0}}
cp (hl) ;{{ff05:be}}
call nz,_convert_accumulator_to_type_in_a_10;{{ff06:c40dff}}
pop bc ;{{ff09:c1}}
pop de ;{{ff0a:d1}}
pop hl ;{{ff0b:e1}}
ret ;{{ff0c:c9}}
_convert_accumulator_to_type_in_a_10:;{{Addr=$ff0d Code Calls/jump count: 1 Data use count: 0}}
sub $03 ;{{ff0d:d603}}
jr c,function_CINT ;{{ff0f:38a5}} (-$5b)
jp z,error_if_accumulator_is_not_a_string;{{ff11:ca5eff}}
;;========================================================
;; function CREAL
;CREAL(<numeric expression>)
;Converts the value to a real
function_CREAL: ;{{Addr=$ff14 Code Calls/jump count: 4 Data use count: 1}}
call return_accumulator_value_if_int_or_address_if_real;{{ff14:cd4fff}}
jp c,set_accumulator_as_positive_REAL_from_HL;{{ff17:da93fe}}
ret ;{{ff1a:c9}}
;;========================================
;;zero accumulator
zero_accumulator: ;{{Addr=$ff1b Code Calls/jump count: 2 Data use count: 0}}
push hl ;{{ff1b:e5}} ##LIT##
ld hl,RESET_ENTRY ;{{ff1c:210000}}
ld (accumulator),hl ;{{ff1f:22a0b0}}
ld (accumulator_plus_2),hl;{{ff22:22a2b0}}
ld (accumulator_plus_3),hl;{{ff25:22a3b0}}
pop hl ;{{ff28:e1}}
ret ;{{ff29:c9}}
;;========================================================
;; function SGN
;SGN(<numeric expression>)
;Returns -1 if expression < 0, 0 if expression = 0, +1 if expression > 0
function_SGN: ;{{Addr=$ff2a Code Calls/jump count: 0 Data use count: 1}}
call get_raw_abs_of_accumulator_with_reg_preserve;{{ff2a:cdc4fd}}
;;----------------------------------
;;=store sign extended byte in A in accumulator
store_sign_extended_byte_in_A_in_accumulator:;{{Addr=$ff2d Code Calls/jump count: 2 Data use count: 0}}
ld l,a ;{{ff2d:6f}}
add a,a ;{{ff2e:87}}
sbc a,a ;{{ff2f:9f}}
jr store_AL_in_accumulator_as_INT;{{ff30:1802}} (+$02)