Subversion Repositories Kolibri OS

Rev

Rev 2665 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
31 halyavin 1
 
2
; Copyright (c) 1999-2013, Tomasz Grysztar.
4039 heavyiron 3
; All rights reserved.
31 halyavin 4
5
 
6
	mov	edi,characters
2665 dunkaist 7
	xor	al,al
8
      make_characters_table:
31 halyavin 9
	stosb
2665 dunkaist 10
	inc	al
11
	jnz	make_characters_table
12
	mov	esi,characters+'a'
13
	mov	edi,characters+'A'
14
	mov	ecx,26
15
	rep	movsb
16
	mov	edi,characters
17
	mov	esi,symbol_characters+1
18
	movzx	ecx,byte [esi-1]
19
	xor	eax,eax
20
      mark_symbol_characters:
31 halyavin 21
	lodsb
2665 dunkaist 22
	mov	byte [edi+eax],0
23
	loop	mark_symbol_characters
24
	mov	edi,locals_counter
25
	mov	ax,1 + '0' shl 8
26
	stos	word [edi]
27
	mov	edi,[memory_start]
28
	mov	[include_paths],edi
29
	mov	esi,include_variable
30
	call	get_environment_variable
31
	xor	al,al
32
	stos	byte [edi]
33
	mov	[memory_start],edi
34
	mov	eax,[additional_memory]
35
	mov	[free_additional_memory],eax
36
	mov	eax,[additional_memory_end]
37
	mov	[labels_list],eax
38
	xor	eax,eax
39
	mov	[source_start],eax
40
	mov	[tagged_blocks],eax
4039 heavyiron 41
	mov	[hash_tree],eax
2665 dunkaist 42
	mov	[error],eax
43
	mov	[macro_status],al
44
	mov	esi,[input_file]
45
	mov	edx,esi
46
	call	open
47
	jc	main_file_not_found
48
	mov	edi,[memory_start]
49
	call	preprocess_file
50
	mov	eax,[error_line]
51
	mov	[current_line],eax
52
	cmp	[macro_status],0
53
	jne	incomplete_macro
54
	mov	[source_start],edi
55
	ret
56
31 halyavin 57
 
58
	push	[memory_end]
2665 dunkaist 59
	push	esi
60
	mov	al,2
61
	xor	edx,edx
62
	call	lseek
63
	push	eax
64
	xor	al,al
65
	xor	edx,edx
66
	call	lseek
67
	pop	ecx
68
	mov	edx,[memory_end]
69
	dec	edx
70
	mov	byte [edx],1Ah
71
	sub	edx,ecx
72
	jc	out_of_memory
73
	mov	esi,edx
74
	cmp	edx,edi
75
	jbe	out_of_memory
76
	mov	[memory_end],edx
77
	call	read
78
	call	close
79
	pop	edx
80
	xor	ecx,ecx
81
	mov	ebx,esi
82
      preprocess_source:
31 halyavin 83
	inc	ecx
2665 dunkaist 84
	mov	[current_line],edi
85
	mov	eax,edx
86
	stos	dword [edi]
87
	mov	eax,ecx
88
	stos	dword [edi]
89
	mov	eax,esi
90
	sub	eax,ebx
91
	stos	dword [edi]
92
	xor	eax,eax
93
	stos	dword [edi]
94
	push	ebx edx
95
	call	convert_line
96
	call	preprocess_line
97
	pop	edx ebx
98
      next_line:
31 halyavin 99
	cmp	byte [esi-1],0
2665 dunkaist 100
	je	file_end
101
	cmp	byte [esi-1],1Ah
102
	jne	preprocess_source
103
      file_end:
31 halyavin 104
	pop	[memory_end]
2665 dunkaist 105
	clc
106
	ret
107
31 halyavin 108
 
109
	push	ecx
2665 dunkaist 110
	test	[macro_status],0Fh
111
	jz	convert_line_data
112
	mov	ax,3Bh
113
	stos	word [edi]
114
      convert_line_data:
31 halyavin 115
	cmp	edi,[memory_end]
2665 dunkaist 116
	jae	out_of_memory
117
	lods	byte [esi]
118
	cmp	al,20h
119
	je	convert_line_data
120
	cmp	al,9
121
	je	convert_line_data
122
	mov	ah,al
123
	mov	ebx,characters
124
	xlat	byte [ebx]
125
	or	al,al
126
	jz	convert_separator
127
	cmp	ah,27h
128
	je	convert_string
129
	cmp	ah,22h
130
	je	convert_string
131
	mov	byte [edi],1Ah
132
	scas	word [edi]
133
	xchg	al,ah
134
	stos	byte [edi]
135
	mov	ebx,characters
136
	xor	ecx,ecx
137
      convert_symbol:
31 halyavin 138
	lods	byte [esi]
2665 dunkaist 139
	stos	byte [edi]
140
	xlat	byte [ebx]
141
	or	al,al
142
	loopnzd convert_symbol
143
	neg	ecx
144
	cmp	ecx,255
145
	ja	name_too_long
146
	mov	ebx,edi
147
	sub	ebx,ecx
148
	mov	byte [ebx-2],cl
149
      found_separator:
31 halyavin 150
	dec	edi
2665 dunkaist 151
	mov	ah,[esi-1]
152
      convert_separator:
31 halyavin 153
	xchg	al,ah
2665 dunkaist 154
	cmp	al,20h
155
	jb	control_character
156
	je	convert_line_data
157
      symbol_character:
31 halyavin 158
	cmp	al,3Bh
2665 dunkaist 159
	je	ignore_comment
160
	cmp	al,5Ch
161
	je	backslash_character
162
	stos	byte [edi]
163
	jmp	convert_line_data
164
      control_character:
31 halyavin 165
	cmp	al,1Ah
2665 dunkaist 166
	je	line_end
167
	cmp	al,0Dh
168
	je	cr_character
169
	cmp	al,0Ah
170
	je	lf_character
171
	cmp	al,9
172
	je	convert_line_data
173
	or	al,al
174
	jnz	symbol_character
175
	jmp	line_end
176
      lf_character:
31 halyavin 177
	lods	byte [esi]
2665 dunkaist 178
	cmp	al,0Dh
179
	je	line_end
180
	dec	esi
181
	jmp	line_end
182
      cr_character:
31 halyavin 183
	lods	byte [esi]
2665 dunkaist 184
	cmp	al,0Ah
185
	je	line_end
186
	dec	esi
187
	jmp	line_end
188
      convert_string:
31 halyavin 189
	mov	al,22h
2665 dunkaist 190
	stos	byte [edi]
191
	scas	dword [edi]
192
	mov	ebx,edi
193
      copy_string:
31 halyavin 194
	lods	byte [esi]
2665 dunkaist 195
	stos	byte [edi]
196
	cmp	al,0Ah
197
	je	no_end_quote
4039 heavyiron 198
	cmp	al,0Dh
2665 dunkaist 199
	je	no_end_quote
4039 heavyiron 200
	or	al,al
2665 dunkaist 201
	jz	no_end_quote
4039 heavyiron 202
	cmp	al,1Ah
2665 dunkaist 203
	je	no_end_quote
4039 heavyiron 204
	cmp	al,ah
2665 dunkaist 205
	jne	copy_string
206
	lods	byte [esi]
207
	cmp	al,ah
208
	je	copy_string
209
	dec	esi
210
	dec	edi
211
	mov	eax,edi
212
	sub	eax,ebx
213
	mov	[ebx-4],eax
214
	jmp	convert_line_data
215
      backslash_character:
31 halyavin 216
	mov	byte [edi],0
2665 dunkaist 217
	lods	byte [esi]
218
	cmp	al,20h
219
	je	concatenate_lines
220
	cmp	al,9
221
	je	concatenate_lines
222
	cmp	al,1Ah
223
	je	unexpected_end_of_file
224
	or	al,al
225
	jz	unexpected_end_of_file
226
	cmp	al,0Ah
227
	je	concatenate_lf
228
	cmp	al,0Dh
229
	je	concatenate_cr
230
	cmp	al,3Bh
231
	je	find_concatenated_line
232
	mov	al,1Ah
233
	stos	byte [edi]
234
	mov	ecx,edi
235
	mov	ax,5C01h
236
	stos	word [edi]
237
	dec	esi
238
      group_backslashes:
31 halyavin 239
	lods	byte [esi]
2665 dunkaist 240
	cmp	al,5Ch
241
	jne	backslashed_symbol
242
	stos	byte [edi]
243
	inc	byte [ecx]
244
	jmp	group_backslashes
245
      no_end_quote:
4039 heavyiron 246
	mov	byte [ebx-5],0
247
	jmp	missing_end_quote
248
      backslashed_symbol:
31 halyavin 249
	cmp	al,1Ah
2665 dunkaist 250
	je	unexpected_end_of_file
251
	or	al,al
252
	jz	unexpected_end_of_file
253
	cmp	al,0Ah
254
	je	extra_characters_on_line
255
	cmp	al,0Dh
256
	je	extra_characters_on_line
257
	cmp	al,20h
258
	je	extra_characters_on_line
259
	cmp	al,9
260
	je	extra_characters_on_line
261
	cmp	al,22h
262
	je	extra_characters_on_line
263
	cmp	al,27h
264
	je	extra_characters_on_line
265
	cmp	al,3Bh
266
	je	extra_characters_on_line
267
	mov	ah,al
268
	mov	ebx,characters
269
	xlat	byte [ebx]
270
	or	al,al
271
	jz	backslashed_symbol_character
272
	mov	al,ah
273
      convert_backslashed_symbol:
31 halyavin 274
	stos	byte [edi]
2665 dunkaist 275
	xlat	byte [ebx]
276
	or	al,al
277
	jz	found_separator
278
	inc	byte [ecx]
279
	jz	name_too_long
280
	lods	byte [esi]
281
	jmp	convert_backslashed_symbol
282
      backslashed_symbol_character:
31 halyavin 283
	mov	al,ah
2665 dunkaist 284
	stos	byte [edi]
285
	inc	byte [ecx]
286
	jmp	convert_line_data
287
      concatenate_lines:
31 halyavin 288
	lods	byte [esi]
2665 dunkaist 289
	cmp	al,20h
290
	je	concatenate_lines
291
	cmp	al,9
292
	je	concatenate_lines
293
	cmp	al,1Ah
294
	je	unexpected_end_of_file
295
	or	al,al
296
	jz	unexpected_end_of_file
297
	cmp	al,0Ah
298
	je	concatenate_lf
299
	cmp	al,0Dh
300
	je	concatenate_cr
301
	cmp	al,3Bh
302
	jne	extra_characters_on_line
303
      find_concatenated_line:
31 halyavin 304
	lods	byte [esi]
2665 dunkaist 305
	cmp	al,0Ah
306
	je	concatenate_lf
307
	cmp	al,0Dh
308
	je	concatenate_cr
309
	or	al,al
310
	jz	concatenate_ok
311
	cmp	al,1Ah
312
	jne	find_concatenated_line
313
	jmp	unexpected_end_of_file
314
      concatenate_lf:
31 halyavin 315
	lods	byte [esi]
2665 dunkaist 316
	cmp	al,0Dh
317
	je	concatenate_ok
318
	dec	esi
319
	jmp	concatenate_ok
320
      concatenate_cr:
31 halyavin 321
	lods	byte [esi]
2665 dunkaist 322
	cmp	al,0Ah
323
	je	concatenate_ok
324
	dec	esi
325
      concatenate_ok:
31 halyavin 326
	inc	dword [esp]
2665 dunkaist 327
	jmp	convert_line_data
328
      ignore_comment:
31 halyavin 329
	lods	byte [esi]
2665 dunkaist 330
	cmp	al,0Ah
331
	je	lf_character
332
	cmp	al,0Dh
333
	je	cr_character
334
	or	al,al
335
	jz	line_end
336
	cmp	al,1Ah
337
	jne	ignore_comment
338
      line_end:
31 halyavin 339
	xor	al,al
2665 dunkaist 340
	stos	byte [edi]
341
	pop	ecx
342
	ret
343
31 halyavin 344
 
109 heavyiron 345
	mov	edi,converted
2665 dunkaist 346
	mov	ebx,characters
347
      convert_case:
109 heavyiron 348
	lods	byte [esi]
2665 dunkaist 349
	xlat	byte [ebx]
350
	stos	byte [edi]
351
	loop	convert_case
352
      case_ok:
109 heavyiron 353
	ret
2665 dunkaist 354
109 heavyiron 355
 
356
	push	edi
2665 dunkaist 357
	mov	edx,esi
358
	mov	ebp,ecx
359
	call	lower_case
360
	pop	edi
361
      scan_directives:
109 heavyiron 362
	mov	esi,converted
2665 dunkaist 363
	movzx	eax,byte [edi]
364
	or	al,al
365
	jz	no_directive
366
	mov	ecx,ebp
367
	inc	edi
368
	mov	ebx,edi
369
	add	ebx,eax
370
	mov	ah,[esi]
371
	cmp	ah,[edi]
372
	jb	no_directive
373
	ja	next_directive
374
	cmp	cl,al
375
	jne	next_directive
376
	repe	cmps byte [esi],[edi]
377
	jb	no_directive
378
	je	directive_ok
379
      next_directive:
109 heavyiron 380
	mov	edi,ebx
2665 dunkaist 381
	add	edi,2
382
	jmp	scan_directives
383
      no_directive:
109 heavyiron 384
	mov	esi,edx
2665 dunkaist 385
	mov	ecx,ebp
386
	stc
387
	ret
388
      directive_ok:
109 heavyiron 389
	lea	esi,[edx+ebp]
2665 dunkaist 390
	call	directive_handler
391
      directive_handler:
1189 heavyiron 392
	pop	ecx
2665 dunkaist 393
	movzx	eax,word [ebx]
394
	add	eax,ecx
395
	clc
396
	ret
397
109 heavyiron 398
 
31 halyavin 399
	mov	eax,esp
2665 dunkaist 400
	sub	eax,100h
401
	jc	stack_overflow
402
	cmp	eax,[stack_limit]
403
	jb	stack_overflow
404
	push	ecx esi
405
      preprocess_current_line:
31 halyavin 406
	mov	esi,[current_line]
2665 dunkaist 407
	add	esi,16
408
	cmp	word [esi],3Bh
409
	jne	line_start_ok
410
	add	esi,2
411
      line_start_ok:
31 halyavin 412
	test	[macro_status],0F0h
2665 dunkaist 413
	jnz	macro_preprocessing
414
	cmp	byte [esi],1Ah
415
	jne	not_fix_constant
416
	movzx	edx,byte [esi+1]
417
	lea	edx,[esi+2+edx]
418
	cmp	word [edx],031Ah
419
	jne	not_fix_constant
420
	mov	ebx,characters
421
	movzx	eax,byte [edx+2]
422
	xlat	byte [ebx]
423
	ror	eax,8
424
	mov	al,[edx+3]
425
	xlat	byte [ebx]
426
	ror	eax,8
427
	mov	al,[edx+4]
428
	xlat	byte [ebx]
429
	ror	eax,16
430
	cmp	eax,'fix'
431
	je	define_fix_constant
432
      not_fix_constant:
31 halyavin 433
	call	process_fix_constants
2665 dunkaist 434
	jmp	initial_preprocessing_ok
435
      macro_preprocessing:
31 halyavin 436
	call	process_macro_operators
2665 dunkaist 437
      initial_preprocessing_ok:
31 halyavin 438
	mov	esi,[current_line]
2665 dunkaist 439
	add	esi,16
440
	mov	al,[macro_status]
441
	test	al,2
442
	jnz	skip_macro_block
443
	test	al,1
444
	jnz	find_macro_block
445
      preprocess_instruction:
31 halyavin 446
	mov	[current_offset],esi
2665 dunkaist 447
	lods	byte [esi]
448
	movzx	ecx,byte [esi]
449
	inc	esi
450
	cmp	al,1Ah
451
	jne	not_preprocessor_symbol
452
	cmp	cl,3
453
	jb	not_preprocessor_directive
454
	push	edi
455
	mov	edi,preprocessor_directives
456
	call	get_directive
457
	pop	edi
458
	jc	not_preprocessor_directive
459
	mov	byte [edx-2],3Bh
460
	jmp	near eax
461
      not_preprocessor_directive:
31 halyavin 462
	xor	ch,ch
2665 dunkaist 463
	call	get_preprocessor_symbol
464
	jc	not_macro
465
	mov	byte [ebx-2],3Bh
466
	mov	[struc_name],0
467
	jmp	use_macro
468
      not_macro:
31 halyavin 469
	mov	[struc_name],esi
2665 dunkaist 470
	add	esi,ecx
471
	lods	byte [esi]
472
	cmp	al,':'
473
	je	preprocess_label
474
	cmp	al,1Ah
475
	jne	not_preprocessor_symbol
476
	lods	byte [esi]
477
	cmp	al,3
478
	jne	not_symbolic_constant
479
	mov	ebx,characters
480
	movzx	eax,byte [esi]
481
	xlat	byte [ebx]
482
	ror	eax,8
483
	mov	al,[esi+1]
484
	xlat	byte [ebx]
485
	ror	eax,8
486
	mov	al,[esi+2]
487
	xlat	byte [ebx]
488
	ror	eax,16
489
	cmp	eax,'equ'
490
	je	define_equ_constant
491
	mov	al,3
492
      not_symbolic_constant:
31 halyavin 493
	mov	ch,1
2665 dunkaist 494
	mov	cl,al
495
	call	get_preprocessor_symbol
496
	jc	not_preprocessor_symbol
497
	push	edx esi
498
	mov	esi,[struc_name]
499
	mov	[struc_label],esi
500
	sub	[struc_label],2
501
	mov	cl,[esi-1]
502
	mov	ch,10b
503
	call	get_preprocessor_symbol
504
	jc	struc_name_ok
505
	mov	ecx,[edx+12]
506
	add	ecx,3
507
	lea	ebx,[edi+ecx]
508
	mov	ecx,edi
509
	sub	ecx,[struc_label]
510
	lea	esi,[edi-1]
511
	lea	edi,[ebx-1]
512
	std
513
	rep	movs byte [edi],[esi]
514
	cld
515
	mov	edi,[struc_label]
516
	mov	esi,[edx+8]
517
	mov	ecx,[edx+12]
518
	add	[struc_name],ecx
519
	add	[struc_name],3
520
	call	move_data
521
	mov	al,3Ah
522
	stos	byte [edi]
523
	mov	ax,3Bh
524
	stos	word [edi]
525
	mov	edi,ebx
526
	pop	esi
527
	add	esi,[edx+12]
528
	add	esi,3
529
	pop	edx
530
	jmp	use_macro
531
      struc_name_ok:
31 halyavin 532
	mov	edx,[struc_name]
2665 dunkaist 533
	movzx	eax,byte [edx-1]
534
	add	edx,eax
535
	push	edi
536
	lea	esi,[edi-1]
537
	mov	ecx,edi
538
	sub	ecx,edx
539
	std
540
	rep	movs byte [edi],[esi]
541
	cld
542
	pop	edi
543
	inc	edi
544
	mov	al,3Ah
545
	mov	[edx],al
546
	inc	al
547
	mov	[edx+1],al
548
	pop	esi edx
549
	inc	esi
550
	jmp	use_macro
551
      preprocess_label:
31 halyavin 552
	dec	esi
2665 dunkaist 553
	sub	esi,ecx
554
	lea	ebp,[esi-2]
555
	mov	ch,10b
556
	call	get_preprocessor_symbol
557
	jnc	symbolic_constant_in_label
558
	lea	esi,[esi+ecx+1]
559
	cmp	byte [esi],':'
4039 heavyiron 560
	jne	preprocess_instruction
561
	inc	esi
562
	jmp	preprocess_instruction
2665 dunkaist 563
      symbolic_constant_in_label:
31 halyavin 564
	mov	ebx,[edx+8]
2665 dunkaist 565
	mov	ecx,[edx+12]
566
	add	ecx,ebx
567
      check_for_broken_label:
31 halyavin 568
	cmp	ebx,ecx
2665 dunkaist 569
	je	label_broken
570
	cmp	byte [ebx],1Ah
571
	jne	label_broken
572
	movzx	eax,byte [ebx+1]
573
	lea	ebx,[ebx+2+eax]
574
	cmp	ebx,ecx
575
	je	label_constant_ok
576
	cmp	byte [ebx],':'
577
	jne	label_broken
578
	inc	ebx
579
	cmp	byte [ebx],':'
4039 heavyiron 580
	jne	check_for_broken_label
581
	inc	ebx
582
	jmp	check_for_broken_label
2665 dunkaist 583
      label_broken:
31 halyavin 584
	push	line_preprocessed
2665 dunkaist 585
	jmp	replace_symbolic_constant
586
      label_constant_ok:
31 halyavin 587
	mov	ecx,edi
2665 dunkaist 588
	sub	ecx,esi
589
	mov	edi,[edx+12]
590
	add	edi,ebp
591
	push	edi
592
	lea	eax,[edi+ecx]
593
	push	eax
594
	cmp	esi,edi
595
	je	replace_label
596
	jb	move_rest_of_line_up
597
	rep	movs byte [edi],[esi]
598
	jmp	replace_label
599
      move_rest_of_line_up:
31 halyavin 600
	lea	esi,[esi+ecx-1]
2665 dunkaist 601
	lea	edi,[edi+ecx-1]
602
	std
603
	rep	movs byte [edi],[esi]
604
	cld
605
      replace_label:
31 halyavin 606
	mov	ecx,[edx+12]
2665 dunkaist 607
	mov	edi,[esp+4]
608
	sub	edi,ecx
609
	mov	esi,[edx+8]
610
	rep	movs byte [edi],[esi]
611
	pop	edi esi
612
	inc	esi
613
	jmp	preprocess_instruction
614
      not_preprocessor_symbol:
31 halyavin 615
	mov	esi,[current_offset]
2665 dunkaist 616
	call	process_equ_constants
617
      line_preprocessed:
31 halyavin 618
	pop	esi ecx
2665 dunkaist 619
	ret
620
31 halyavin 621
 
622
	push	ebp edi esi
2665 dunkaist 623
	mov	ebp,ecx
624
	shl	ebp,22
625
	movzx	ecx,cl
626
	mov	ebx,hash_tree
627
	mov	edi,10
628
      follow_hashes_roots:
31 halyavin 629
	mov	edx,[ebx]
2665 dunkaist 630
	or	edx,edx
631
	jz	preprocessor_symbol_not_found
632
	xor	eax,eax
633
	shl	ebp,1
634
	adc	eax,0
635
	lea	ebx,[edx+eax*4]
636
	dec	edi
637
	jnz	follow_hashes_roots
638
	mov	edi,ebx
639
	call	calculate_hash
640
	mov	ebp,eax
641
	and	ebp,3FFh
642
	shl	ebp,10
643
	xor	ebp,eax
644
	mov	ebx,edi
645
	mov	edi,22
646
      follow_hashes_tree:
31 halyavin 647
	mov	edx,[ebx]
2665 dunkaist 648
	or	edx,edx
649
	jz	preprocessor_symbol_not_found
650
	xor	eax,eax
651
	shl	ebp,1
652
	adc	eax,0
653
	lea	ebx,[edx+eax*4]
654
	dec	edi
655
	jnz	follow_hashes_tree
656
	mov	al,cl
657
	mov	edx,[ebx]
658
	or	edx,edx
659
	jz	preprocessor_symbol_not_found
660
      compare_with_preprocessor_symbol:
31 halyavin 661
	mov	edi,[edx+4]
2665 dunkaist 662
	cmp	edi,1
663
	jbe	next_equal_hash
664
	repe	cmps byte [esi],[edi]
665
	je	preprocessor_symbol_found
666
	mov	cl,al
667
	mov	esi,[esp]
668
      next_equal_hash:
31 halyavin 669
	mov	edx,[edx]
2665 dunkaist 670
	or	edx,edx
671
	jnz	compare_with_preprocessor_symbol
672
      preprocessor_symbol_not_found:
31 halyavin 673
	pop	esi edi ebp
2665 dunkaist 674
	stc
675
	ret
676
      preprocessor_symbol_found:
31 halyavin 677
	pop	ebx edi ebp
2665 dunkaist 678
	clc
679
	ret
680
      calculate_hash:
31 halyavin 681
	xor	ebx,ebx
2665 dunkaist 682
	mov	eax,2166136261
683
	mov	ebp,16777619
684
      fnv1a_hash:
31 halyavin 685
	xor	al,[esi+ebx]
2665 dunkaist 686
	mul	ebp
687
	inc	bl
688
	cmp	bl,cl
689
	jb	fnv1a_hash
690
	ret
691
add_preprocessor_symbol:
31 halyavin 692
	push	edi esi
2665 dunkaist 693
	cmp	ch,11b
694
	je	preprocessor_symbol_name_ok
695
	push	ecx
696
	movzx	ecx,cl
697
	mov	edi,preprocessor_directives
698
	call	get_directive
699
	jnc	reserved_word_used_as_symbol
700
	pop	ecx
701
      preprocessor_symbol_name_ok:
992 heavyiron 702
	call	calculate_hash
2665 dunkaist 703
	mov	ebp,eax
704
	and	ebp,3FFh
705
	shr	eax,10
706
	xor	ebp,eax
707
	shl	ecx,22
708
	or	ebp,ecx
709
	mov	ebx,hash_tree
710
	mov	ecx,32
711
      find_leave_for_symbol:
31 halyavin 712
	mov	edx,[ebx]
2665 dunkaist 713
	or	edx,edx
714
	jz	extend_hashes_tree
715
	xor	eax,eax
716
	rol	ebp,1
717
	adc	eax,0
718
	lea	ebx,[edx+eax*4]
719
	dec	ecx
720
	jnz	find_leave_for_symbol
721
	mov	edx,[ebx]
722
	or	edx,edx
723
	jz	add_symbol_entry
724
	shr	ebp,30
725
	cmp	ebp,11b
726
	je	reuse_symbol_entry
727
	cmp	dword [edx+4],0
728
	jne	add_symbol_entry
729
      find_entry_to_reuse:
31 halyavin 730
	mov	edi,[edx]
2665 dunkaist 731
	or	edi,edi
732
	jz	reuse_symbol_entry
733
	cmp	dword [edi+4],0
734
	jne	reuse_symbol_entry
735
	mov	edx,edi
736
	jmp	find_entry_to_reuse
737
      add_symbol_entry:
31 halyavin 738
	mov	eax,edx
2665 dunkaist 739
	mov	edx,[labels_list]
740
	sub	edx,16
741
	cmp	edx,[free_additional_memory]
742
	jb	out_of_memory
743
	mov	[labels_list],edx
744
	mov	[edx],eax
745
	mov	[ebx],edx
746
      reuse_symbol_entry:
31 halyavin 747
	pop	esi edi
2665 dunkaist 748
	mov	[edx+4],esi
749
	ret
750
      extend_hashes_tree:
31 halyavin 751
	mov	edx,[labels_list]
2665 dunkaist 752
	sub	edx,8
753
	cmp	edx,[free_additional_memory]
754
	jb	out_of_memory
755
	mov	[labels_list],edx
756
	xor	eax,eax
757
	mov	[edx],eax
758
	mov	[edx+4],eax
759
	shl	ebp,1
760
	adc	eax,0
761
	mov	[ebx],edx
762
	lea	ebx,[edx+eax*4]
763
	dec	ecx
764
	jnz	extend_hashes_tree
765
	mov	edx,[labels_list]
766
	sub	edx,16
767
	cmp	edx,[free_additional_memory]
768
	jb	out_of_memory
769
	mov	[labels_list],edx
770
	mov	dword [edx],0
771
	mov	[ebx],edx
772
	pop	esi edi
773
	mov	[edx+4],esi
774
	ret
775
31 halyavin 776
 
777
	add	edx,5
2665 dunkaist 778
	add	esi,2
779
	push	edx
780
	mov	ch,11b
781
	jmp	define_preprocessor_constant
782
define_equ_constant:
31 halyavin 783
	add	esi,3
2665 dunkaist 784
	push	esi
785
	call	process_equ_constants
786
	mov	esi,[struc_name]
787
	mov	ch,10b
788
      define_preprocessor_constant:
109 heavyiron 789
	mov	byte [esi-2],3Bh
2665 dunkaist 790
	mov	cl,[esi-1]
791
	call	add_preprocessor_symbol
792
	pop	ebx
793
	mov	ecx,edi
794
	dec	ecx
795
	sub	ecx,ebx
796
	mov	[edx+8],ebx
797
	mov	[edx+12],ecx
798
	jmp	line_preprocessed
799
define_symbolic_constant:
109 heavyiron 800
	lods	byte [esi]
2665 dunkaist 801
	cmp	al,1Ah
802
	jne	invalid_name
803
	lods	byte [esi]
804
	mov	cl,al
805
	mov	ch,10b
806
	call	add_preprocessor_symbol
807
	movzx	eax,byte [esi-1]
808
	add	esi,eax
809
	lea	ecx,[edi-1]
810
	sub	ecx,esi
811
	mov	[edx+8],esi
812
	mov	[edx+12],ecx
813
	jmp	line_preprocessed
814
109 heavyiron 815
 
31 halyavin 816
	mov	ch,1
2665 dunkaist 817
	jmp	make_macro
818
define_macro:
31 halyavin 819
	xor	ch,ch
2665 dunkaist 820
      make_macro:
31 halyavin 821
	lods	byte [esi]
2665 dunkaist 822
	cmp	al,1Ah
823
	jne	invalid_name
824
	lods	byte [esi]
825
	mov	cl,al
826
	call	add_preprocessor_symbol
827
	mov	eax,[current_line]
828
	mov	[edx+12],eax
829
	movzx	eax,byte [esi-1]
830
	add	esi,eax
831
	mov	[edx+8],esi
832
	mov	al,[macro_status]
833
	and	al,0F0h
834
	or	al,1
835
	mov	[macro_status],al
836
	mov	eax,[current_line]
837
	mov	[error_line],eax
838
	xor	ebp,ebp
839
	lods	byte [esi]
840
	or	al,al
841
	jz	line_preprocessed
842
	cmp	al,'{'
843
	je	found_macro_block
844
	dec	esi
845
      skip_macro_arguments:
31 halyavin 846
	lods	byte [esi]
2665 dunkaist 847
	cmp	al,1Ah
848
	je	skip_macro_argument
849
	cmp	al,'['
850
	jne	invalid_macro_arguments
851
	or	ebp,-1
852
	jz	invalid_macro_arguments
853
	lods	byte [esi]
854
	cmp	al,1Ah
855
	jne	invalid_macro_arguments
856
      skip_macro_argument:
31 halyavin 857
	movzx	eax,byte [esi]
2665 dunkaist 858
	inc	esi
859
	add	esi,eax
860
	lods	byte [esi]
861
	cmp	al,'='
862
	je	macro_argument_with_default_value
863
	cmp	al,'*'
864
	jne	macro_argument_end
865
	lods	byte [esi]
866
      macro_argument_end:
31 halyavin 867
	cmp	al,','
2665 dunkaist 868
	je	skip_macro_arguments
869
	cmp	al,']'
870
	jne	end_macro_arguments
871
	lods	byte [esi]
872
	not	ebp
873
      end_macro_arguments:
31 halyavin 874
	or	ebp,ebp
2665 dunkaist 875
	jnz	invalid_macro_arguments
876
	or	al,al
877
	jz	line_preprocessed
878
	cmp	al,'{'
879
	je	found_macro_block
880
	jmp	invalid_macro_arguments
881
      macro_argument_with_default_value:
2664 dunkaist 882
	or	[default_argument_value],-1
2665 dunkaist 883
	call	skip_macro_argument_value
884
	inc	esi
885
	jmp	macro_argument_end
886
      skip_macro_argument_value:
2664 dunkaist 887
	cmp	byte [esi],'<'
2665 dunkaist 888
	jne	simple_argument
889
	mov	ecx,1
890
	inc	esi
891
      enclosed_argument:
2664 dunkaist 892
	lods	byte [esi]
2665 dunkaist 893
	or	al,al
894
	jz	invalid_macro_arguments
895
	cmp	al,1Ah
896
	je	enclosed_symbol
897
	cmp	al,22h
898
	je	enclosed_string
899
	cmp	al,'>'
900
	je	enclosed_argument_end
901
	cmp	al,'<'
902
	jne	enclosed_argument
903
	inc	ecx
904
	jmp	enclosed_argument
905
      enclosed_symbol:
2664 dunkaist 906
	movzx	eax,byte [esi]
2665 dunkaist 907
	inc	esi
908
	add	esi,eax
909
	jmp	enclosed_argument
910
      enclosed_string:
2664 dunkaist 911
	lods	dword [esi]
2665 dunkaist 912
	add	esi,eax
913
	jmp	enclosed_argument
914
      enclosed_argument_end:
2664 dunkaist 915
	loop	enclosed_argument
2665 dunkaist 916
	lods	byte [esi]
917
	or	al,al
918
	jz	argument_value_end
919
	cmp	al,','
920
	je	argument_value_end
921
	cmp	[default_argument_value],0
922
	je	invalid_macro_arguments
923
	cmp	al,'{'
924
	je	argument_value_end
925
	or	ebp,ebp
926
	jz	invalid_macro_arguments
927
	cmp	al,']'
928
	je	argument_value_end
929
	jmp	invalid_macro_arguments
930
      simple_argument:
2664 dunkaist 931
	lods	byte [esi]
2665 dunkaist 932
	or	al,al
933
	jz	argument_value_end
934
	cmp	al,','
935
	je	argument_value_end
936
	cmp	al,22h
937
	je	argument_string
938
	cmp	al,1Ah
939
	je	argument_symbol
940
	cmp	[default_argument_value],0
941
	je	simple_argument
942
	cmp	al,'{'
943
	je	argument_value_end
944
	or	ebp,ebp
945
	jz	simple_argument
946
	cmp	al,']'
947
	je	argument_value_end
948
      argument_symbol:
2664 dunkaist 949
	movzx	eax,byte [esi]
2665 dunkaist 950
	inc	esi
951
	add	esi,eax
952
	jmp	simple_argument
953
      argument_string:
2664 dunkaist 954
	lods	dword [esi]
2665 dunkaist 955
	add	esi,eax
956
	jmp	simple_argument
957
      argument_value_end:
2664 dunkaist 958
	dec	esi
2665 dunkaist 959
	ret
960
      find_macro_block:
31 halyavin 961
	add	esi,2
2665 dunkaist 962
	lods	byte [esi]
963
	or	al,al
964
	jz	line_preprocessed
965
	cmp	al,'{'
966
	jne	unexpected_characters
967
      found_macro_block:
31 halyavin 968
	or	[macro_status],2
2665 dunkaist 969
      skip_macro_block:
31 halyavin 970
	lods	byte [esi]
2665 dunkaist 971
	cmp	al,1Ah
972
	je	skip_macro_symbol
973
	cmp	al,3Bh
974
	je	skip_macro_symbol
975
	cmp	al,22h
976
	je	skip_macro_string
977
	or	al,al
978
	jz	line_preprocessed
979
	cmp	al,'}'
980
	jne	skip_macro_block
981
	mov	al,[macro_status]
982
	and	[macro_status],0F0h
983
	test	al,8
984
	jnz	use_instant_macro
985
	cmp	byte [esi],0
986
	je	line_preprocessed
987
	mov	ecx,edi
988
	sub	ecx,esi
989
	mov	edx,esi
990
	lea	esi,[esi+ecx-1]
991
	lea	edi,[edi+1+16]
992
	mov	ebx,edi
993
	dec	edi
994
	std
995
	rep	movs byte [edi],[esi]
996
	cld
997
	mov	edi,edx
998
	xor	al,al
999
	stos	byte [edi]
1000
	mov	esi,[current_line]
1001
	mov	[current_line],edi
1002
	mov	ecx,4
1003
	rep	movs dword [edi],[esi]
1004
	mov	edi,ebx
1005
	jmp	initial_preprocessing_ok
1006
      skip_macro_symbol:
31 halyavin 1007
	movzx	eax,byte [esi]
2665 dunkaist 1008
	inc	esi
1009
	add	esi,eax
1010
	jmp	skip_macro_block
1011
      skip_macro_string:
31 halyavin 1012
	lods	dword [esi]
2665 dunkaist 1013
	add	esi,eax
1014
	jmp	skip_macro_block
1015
rept_directive:
31 halyavin 1016
	mov	[base_code],0
2665 dunkaist 1017
	jmp	define_instant_macro
1018
irp_directive:
31 halyavin 1019
	mov	[base_code],1
2665 dunkaist 1020
	jmp	define_instant_macro
1021
irps_directive:
31 halyavin 1022
	mov	[base_code],2
2665 dunkaist 1023
	jmp	define_instant_macro
1024
match_directive:
31 halyavin 1025
	mov	[base_code],10h
2665 dunkaist 1026
define_instant_macro:
31 halyavin 1027
	mov	al,[macro_status]
2665 dunkaist 1028
	and	al,0F0h
1029
	or	al,8+1
1030
	mov	[macro_status],al
1031
	mov	eax,[current_line]
1032
	mov	[error_line],eax
1033
	mov	[instant_macro_start],esi
1034
	cmp	[base_code],10h
1035
	je	prepare_match
1036
      skip_parameters:
1189 heavyiron 1037
	lods	byte [esi]
2665 dunkaist 1038
	or	al,al
1039
	jz	parameters_skipped
1040
	cmp	al,'{'
1041
	je	parameters_skipped
1042
	cmp	al,22h
1043
	je	skip_quoted_parameter
1044
	cmp	al,1Ah
1045
	jne	skip_parameters
1046
	lods	byte [esi]
1047
	movzx	eax,al
1048
	add	esi,eax
1049
	jmp	skip_parameters
1050
      skip_quoted_parameter:
1189 heavyiron 1051
	lods	dword [esi]
2665 dunkaist 1052
	add	esi,eax
1053
	jmp	skip_parameters
1054
      parameters_skipped:
1189 heavyiron 1055
	dec	esi
2665 dunkaist 1056
	mov	[parameters_end],esi
1057
	lods	byte [esi]
1058
	cmp	al,'{'
1059
	je	found_macro_block
1060
	or	al,al
1061
	jnz	invalid_macro_arguments
1062
	jmp	line_preprocessed
1063
prepare_match:
31 halyavin 1064
	call	skip_pattern
2665 dunkaist 1065
	mov	[value_type],80h+10b
1066
	call	process_symbolic_constants
1067
	jmp	parameters_skipped
1068
      skip_pattern:
31 halyavin 1069
	lods	byte [esi]
2665 dunkaist 1070
	or	al,al
1071
	jz	invalid_macro_arguments
1072
	cmp	al,','
1073
	je	pattern_skipped
1074
	cmp	al,22h
1075
	je	skip_quoted_string_in_pattern
1076
	cmp	al,1Ah
1077
	je	skip_symbol_in_pattern
1078
	cmp	al,'='
1079
	jne	skip_pattern
1080
	mov	al,[esi]
1081
	cmp	al,1Ah
1082
	je	skip_pattern
1083
	cmp	al,22h
1084
	je	skip_pattern
1085
	inc	esi
1086
	jmp	skip_pattern
1087
      skip_symbol_in_pattern:
31 halyavin 1088
	lods	byte [esi]
2665 dunkaist 1089
	movzx	eax,al
1090
	add	esi,eax
1091
	jmp	skip_pattern
1092
      skip_quoted_string_in_pattern:
31 halyavin 1093
	lods	dword [esi]
2665 dunkaist 1094
	add	esi,eax
1095
	jmp	skip_pattern
1096
      pattern_skipped:
31 halyavin 1097
	ret
2665 dunkaist 1098
31 halyavin 1099
 
1100
	xor	ch,ch
2665 dunkaist 1101
	jmp	restore_preprocessor_symbol
1102
purge_struc:
31 halyavin 1103
	mov	ch,1
2665 dunkaist 1104
	jmp	restore_preprocessor_symbol
1105
restore_equ_constant:
31 halyavin 1106
	mov	ch,10b
2665 dunkaist 1107
      restore_preprocessor_symbol:
31 halyavin 1108
	push	ecx
2665 dunkaist 1109
	lods	byte [esi]
1110
	cmp	al,1Ah
1111
	jne	invalid_name
1112
	lods	byte [esi]
1113
	mov	cl,al
1114
	call	get_preprocessor_symbol
1115
	jc	no_symbol_to_restore
1116
	mov	dword [edx+4],0
1117
	jmp	symbol_restored
1118
      no_symbol_to_restore:
31 halyavin 1119
	add	esi,ecx
2665 dunkaist 1120
      symbol_restored:
31 halyavin 1121
	pop	ecx
2665 dunkaist 1122
	lods	byte [esi]
1123
	cmp	al,','
1124
	je	restore_preprocessor_symbol
1125
	or	al,al
1126
	jnz	extra_characters_on_line
1127
	jmp	line_preprocessed
1128
31 halyavin 1129
 
1130
	mov	[value_type],11b
2665 dunkaist 1131
	jmp	process_symbolic_constants
1132
process_equ_constants:
31 halyavin 1133
	mov	[value_type],10b
2665 dunkaist 1134
      process_symbolic_constants:
31 halyavin 1135
	mov	ebp,esi
2665 dunkaist 1136
	lods	byte [esi]
1137
	cmp	al,1Ah
1138
	je	check_symbol
1139
	cmp	al,22h
1140
	je	ignore_string
1141
	cmp	al,'{'
1142
	je	check_brace
1143
	or	al,al
1144
	jnz	process_symbolic_constants
1145
	ret
1146
      ignore_string:
31 halyavin 1147
	lods	dword [esi]
2665 dunkaist 1148
	add	esi,eax
1149
	jmp	process_symbolic_constants
1150
      check_brace:
31 halyavin 1151
	test	[value_type],80h
2665 dunkaist 1152
	jz	process_symbolic_constants
1153
	ret
1154
      no_replacing:
31 halyavin 1155
	movzx	ecx,byte [esi-1]
2665 dunkaist 1156
	add	esi,ecx
1157
	jmp	process_symbolic_constants
1158
      check_symbol:
31 halyavin 1159
	mov	cl,[esi]
2665 dunkaist 1160
	inc	esi
1161
	mov	ch,[value_type]
1162
	call	get_preprocessor_symbol
1163
	jc	no_replacing
1164
	mov	[current_section],edi
1165
      replace_symbolic_constant:
31 halyavin 1166
	mov	ecx,[edx+12]
2665 dunkaist 1167
	mov	edx,[edx+8]
1168
	xchg	esi,edx
1169
	call	move_data
1170
	mov	esi,edx
1171
      process_after_replaced:
31 halyavin 1172
	lods	byte [esi]
2665 dunkaist 1173
	cmp	al,1Ah
1174
	je	symbol_after_replaced
1175
	stos	byte [edi]
1176
	cmp	al,22h
1177
	je	string_after_replaced
1178
	cmp	al,'{'
1179
	je	brace_after_replaced
1180
	or	al,al
1181
	jnz	process_after_replaced
1182
	mov	ecx,edi
1183
	sub	ecx,esi
1184
	mov	edi,ebp
1185
	call	move_data
1186
	mov	esi,edi
1187
	ret
1188
      move_data:
31 halyavin 1189
	lea	eax,[edi+ecx]
2665 dunkaist 1190
	cmp	eax,[memory_end]
1191
	jae	out_of_memory
1192
	shr	ecx,1
1193
	jnc	movsb_ok
1194
	movs	byte [edi],[esi]
1195
      movsb_ok:
31 halyavin 1196
	shr	ecx,1
2665 dunkaist 1197
	jnc	movsw_ok
1198
	movs	word [edi],[esi]
1199
      movsw_ok:
31 halyavin 1200
	rep	movs dword [edi],[esi]
2665 dunkaist 1201
	ret
1202
      string_after_replaced:
31 halyavin 1203
	lods	dword [esi]
2665 dunkaist 1204
	stos	dword [edi]
1205
	mov	ecx,eax
1206
	call	move_data
1207
	jmp	process_after_replaced
1208
      brace_after_replaced:
31 halyavin 1209
	test	[value_type],80h
2665 dunkaist 1210
	jz	process_after_replaced
1211
	mov	edx,edi
1212
	mov	ecx,[current_section]
1213
	sub	edx,ecx
1214
	sub	ecx,esi
1215
	rep	movs byte [edi],[esi]
1216
	mov	ecx,edi
1217
	sub	ecx,esi
1218
	mov	edi,ebp
1219
	call	move_data
1220
	lea	esi,[ebp+edx]
1221
	ret
1222
      symbol_after_replaced:
31 halyavin 1223
	mov	cl,[esi]
2665 dunkaist 1224
	inc	esi
1225
	mov	ch,[value_type]
1226
	call	get_preprocessor_symbol
1227
	jnc	replace_symbolic_constant
1228
	movzx	ecx,byte [esi-1]
1229
	mov	al,1Ah
1230
	mov	ah,cl
1231
	stos	word [edi]
1232
	call	move_data
1233
	jmp	process_after_replaced
1234
process_macro_operators:
31 halyavin 1235
	xor	dl,dl
2665 dunkaist 1236
	mov	ebp,edi
1237
      before_macro_operators:
31 halyavin 1238
	mov	edi,esi
2665 dunkaist 1239
	lods	byte [esi]
1240
	cmp	al,'`'
1241
	je	symbol_conversion
1242
	cmp	al,'#'
1243
	je	concatenation
1244
	cmp	al,1Ah
1245
	je	symbol_before_macro_operators
1246
	cmp	al,3Bh
1247
	je	no_more_macro_operators
1248
	cmp	al,22h
1249
	je	string_before_macro_operators
1250
	xor	dl,dl
1251
	or	al,al
1252
	jnz	before_macro_operators
1253
	mov	edi,esi
1254
	ret
1255
      no_more_macro_operators:
31 halyavin 1256
	mov	edi,ebp
2665 dunkaist 1257
	ret
1258
      symbol_before_macro_operators:
31 halyavin 1259
	mov	dl,1Ah
2665 dunkaist 1260
	mov	ebx,esi
1261
	lods	byte [esi]
1262
	movzx	ecx,al
1263
	jecxz	symbol_before_macro_operators_ok
1264
	mov	edi,esi
1265
	cmp	byte [esi],'\'
1266
	je	escaped_symbol
1267
      symbol_before_macro_operators_ok:
31 halyavin 1268
	add	esi,ecx
2665 dunkaist 1269
	jmp	before_macro_operators
1270
      string_before_macro_operators:
31 halyavin 1271
	mov	dl,22h
2665 dunkaist 1272
	mov	ebx,esi
1273
	lods	dword [esi]
1274
	add	esi,eax
1275
	jmp	before_macro_operators
1276
      escaped_symbol:
31 halyavin 1277
	dec	byte [edi-1]
2665 dunkaist 1278
	dec	ecx
1279
	inc	esi
1280
	cmp	ecx,1
1281
	rep	movs byte [edi],[esi]
1282
	jne	after_macro_operators
1283
	mov	al,[esi-1]
1284
	mov	ecx,ebx
1285
	mov	ebx,characters
1286
	xlat	byte [ebx]
1287
	mov	ebx,ecx
1288
	or	al,al
1289
	jnz	after_macro_operators
1290
	sub	edi,3
1291
	mov	al,[esi-1]
1292
	stos	byte [edi]
1293
	xor	dl,dl
1294
	jmp	after_macro_operators
1295
      reduce_symbol_conversion:
109 heavyiron 1296
	inc	esi
2665 dunkaist 1297
      symbol_conversion:
31 halyavin 1298
	mov	edx,esi
2665 dunkaist 1299
	mov	al,[esi]
1300
	cmp	al,1Ah
1301
	jne	symbol_character_conversion
1302
	lods	word [esi]
1303
	movzx	ecx,ah
1304
	lea	ebx,[edi+3]
1305
	jecxz	convert_to_quoted_string
1306
	cmp	byte [esi],'\'
1307
	jne	convert_to_quoted_string
1308
	inc	esi
1309
	dec	ecx
1310
	dec	ebx
1311
	jmp	convert_to_quoted_string
1312
      symbol_character_conversion:
109 heavyiron 1313
	cmp	al,22h
2665 dunkaist 1314
	je	after_macro_operators
1315
	cmp	al,'`'
1316
	je	reduce_symbol_conversion
1317
	lea	ebx,[edi+5]
1318
	xor	ecx,ecx
1319
	or	al,al
1320
	jz	convert_to_quoted_string
1321
	cmp	al,'#'
1322
	je	convert_to_quoted_string
1323
	inc	ecx
1324
      convert_to_quoted_string:
109 heavyiron 1325
	sub	ebx,edx
2665 dunkaist 1326
	ja	shift_line_data
1327
	mov	al,22h
1328
	mov	dl,al
1329
	stos	byte [edi]
1330
	mov	ebx,edi
1331
	mov	eax,ecx
1332
	stos	dword [edi]
1333
	rep	movs byte [edi],[esi]
1334
	cmp	edi,esi
1335
	je	before_macro_operators
1336
	jmp	after_macro_operators
1337
      shift_line_data:
31 halyavin 1338
	push	ecx
2665 dunkaist 1339
	mov	edx,esi
1340
	lea	esi,[ebp-1]
1341
	add	ebp,ebx
1342
	lea	edi,[ebp-1]
1343
	lea	ecx,[esi+1]
1344
	sub	ecx,edx
1345
	std
1346
	rep	movs byte [edi],[esi]
1347
	cld
1348
	pop	eax
1349
	sub	edi,3
1350
	mov	dl,22h
1351
	mov	[edi-1],dl
1352
	mov	ebx,edi
1353
	mov	[edi],eax
1354
	lea	esi,[edi+4+eax]
1355
	jmp	before_macro_operators
1356
      concatenation:
31 halyavin 1357
	cmp	dl,1Ah
2665 dunkaist 1358
	je	symbol_concatenation
1359
	cmp	dl,22h
1360
	je	string_concatenation
1361
      no_concatenation:
31 halyavin 1362
	cmp	esi,edi
2665 dunkaist 1363
	je	before_macro_operators
1364
	jmp	after_macro_operators
1365
      symbol_concatenation:
31 halyavin 1366
	cmp	byte [esi],1Ah
2665 dunkaist 1367
	jne	no_concatenation
1368
	inc	esi
1369
	lods	byte [esi]
1370
	movzx	ecx,al
1371
	jecxz	do_symbol_concatenation
1372
	cmp	byte [esi],'\'
1373
	je	concatenate_escaped_symbol
1374
      do_symbol_concatenation:
31 halyavin 1375
	add	[ebx],cl
2665 dunkaist 1376
	jc	name_too_long
1377
	rep	movs byte [edi],[esi]
1378
	jmp	after_macro_operators
1379
      concatenate_escaped_symbol:
242 heavyiron 1380
	inc	esi
2665 dunkaist 1381
	dec	ecx
1382
	jz	do_symbol_concatenation
1383
	movzx	eax,byte [esi]
1384
	cmp	byte [characters+eax],0
1385
	jne	do_symbol_concatenation
1386
	sub	esi,3
1387
	jmp	no_concatenation
1388
      string_concatenation:
31 halyavin 1389
	cmp	byte [esi],22h
2665 dunkaist 1390
	je	do_string_concatenation
1391
	cmp	byte [esi],'`'
1392
	jne	no_concatenation
1393
      concatenate_converted_symbol:
109 heavyiron 1394
	inc	esi
2665 dunkaist 1395
	mov	al,[esi]
1396
	cmp	al,'`'
1397
	je	concatenate_converted_symbol
1398
	cmp	al,22h
1399
	je	do_string_concatenation
1400
	cmp	al,1Ah
1401
	jne	concatenate_converted_symbol_character
1402
	inc	esi
1403
	lods	byte [esi]
1404
	movzx	ecx,al
1405
	jecxz	finish_concatenating_converted_symbol
1406
	cmp	byte [esi],'\'
1407
	jne	finish_concatenating_converted_symbol
1408
	inc	esi
1409
	dec	ecx
1410
      finish_concatenating_converted_symbol:
242 heavyiron 1411
	add	[ebx],ecx
2665 dunkaist 1412
	rep	movs byte [edi],[esi]
1413
	jmp	after_macro_operators
1414
      concatenate_converted_symbol_character:
109 heavyiron 1415
	or	al,al
2665 dunkaist 1416
	jz	after_macro_operators
1417
	cmp	al,'#'
1418
	je	after_macro_operators
1419
	inc	dword [ebx]
1420
	movs	byte [edi],[esi]
1421
	jmp	after_macro_operators
1422
      do_string_concatenation:
31 halyavin 1423
	inc	esi
2665 dunkaist 1424
	lods	dword [esi]
1425
	mov	ecx,eax
1426
	add	[ebx],eax
1427
	rep	movs byte [edi],[esi]
1428
      after_macro_operators:
31 halyavin 1429
	lods	byte [esi]
2665 dunkaist 1430
	cmp	al,'`'
1431
	je	symbol_conversion
1432
	cmp	al,'#'
1433
	je	concatenation
1434
	stos	byte [edi]
1435
	cmp	al,1Ah
1436
	je	symbol_after_macro_operators
1437
	cmp	al,3Bh
1438
	je	no_more_macro_operators
1439
	cmp	al,22h
1440
	je	string_after_macro_operators
1441
	xor	dl,dl
1442
	or	al,al
1443
	jnz	after_macro_operators
1444
	ret
1445
      symbol_after_macro_operators:
31 halyavin 1446
	mov	dl,1Ah
2665 dunkaist 1447
	mov	ebx,edi
1448
	lods	byte [esi]
1449
	stos	byte [edi]
1450
	movzx	ecx,al
1451
	jecxz	symbol_after_macro_operatorss_ok
1452
	cmp	byte [esi],'\'
1453
	je	escaped_symbol
1454
      symbol_after_macro_operatorss_ok:
31 halyavin 1455
	rep	movs byte [edi],[esi]
2665 dunkaist 1456
	jmp	after_macro_operators
1457
      string_after_macro_operators:
31 halyavin 1458
	mov	dl,22h
2665 dunkaist 1459
	mov	ebx,edi
1460
	lods	dword [esi]
1461
	stos	dword [edi]
1462
	mov	ecx,eax
1463
	rep	movs byte [edi],[esi]
1464
	jmp	after_macro_operators
1465
31 halyavin 1466
 
1467
	push	[free_additional_memory]
2665 dunkaist 1468
	push	[macro_symbols]
1469
	mov	[macro_symbols],0
1470
	push	[counter_limit]
1471
	push	dword [edx+4]
1472
	mov	dword [edx+4],1
1473
	push	edx
1474
	mov	ebx,esi
1475
	mov	esi,[edx+8]
1476
	mov	eax,[edx+12]
1477
	mov	[macro_line],eax
1478
	mov	[counter_limit],0
1479
	xor	ebp,ebp
1480
      process_macro_arguments:
31 halyavin 1481
	mov	al,[esi]
2665 dunkaist 1482
	or	al,al
1483
	jz	arguments_end
1484
	cmp	al,'{'
1485
	je	arguments_end
1486
	inc	esi
1487
	cmp	al,'['
1488
	jne	get_macro_arguments
1489
	mov	ebp,esi
1490
	inc	esi
1491
	inc	[counter_limit]
1492
      get_macro_arguments:
31 halyavin 1493
	call	get_macro_argument
2665 dunkaist 1494
	lods	byte [esi]
1495
	cmp	al,','
1496
	je	next_argument
1497
	cmp	al,']'
1498
	je	next_arguments_group
1499
	dec	esi
1500
	jmp	arguments_end
1501
      next_argument:
31 halyavin 1502
	cmp	byte [ebx],','
2665 dunkaist 1503
	jne	process_macro_arguments
1504
	inc	ebx
1505
	jmp	process_macro_arguments
1506
      next_arguments_group:
31 halyavin 1507
	cmp	byte [ebx],','
2665 dunkaist 1508
	jne	arguments_end
1509
	inc	ebx
1510
	inc	[counter_limit]
1511
	mov	esi,ebp
1512
	jmp	process_macro_arguments
1513
      get_macro_argument:
31 halyavin 1514
	lods	byte [esi]
2665 dunkaist 1515
	movzx	ecx,al
1516
	mov	eax,[counter_limit]
1517
	call	add_macro_symbol
1518
	add	esi,ecx
1519
	xchg	esi,ebx
1520
	mov	[edx+12],esi
1521
	mov	[default_argument_value],0
1522
	call	skip_macro_argument_value
1523
	call	finish_macro_argument
1524
	xchg	esi,ebx
1525
	cmp	byte [esi],'='
1526
	je	argument_with_default_value
1527
	cmp	byte [esi],'*'
1528
	jne	macro_argument_ok
1529
	cmp	dword [edx+8],0
1530
	je	invalid_macro_arguments
1531
	inc	esi
1532
      macro_argument_ok:
31 halyavin 1533
	ret
2665 dunkaist 1534
      finish_macro_argument:
2664 dunkaist 1535
	mov	eax,[edx+12]
2665 dunkaist 1536
	mov	ecx,esi
1537
	sub	ecx,eax
1538
	cmp	byte [eax],'<'
1539
	jne	argument_value_length_ok
1540
	inc	dword [edx+12]
1541
	sub	ecx,2
1542
	or	ecx,80000000h
1543
      argument_value_length_ok:
2664 dunkaist 1544
	mov	[edx+8],ecx
2665 dunkaist 1545
	ret
1546
      argument_with_default_value:
2664 dunkaist 1547
	inc	esi
2665 dunkaist 1548
	push	esi
1549
	or	[default_argument_value],-1
1550
	call	skip_macro_argument_value
1551
	pop	eax
1552
	cmp	dword [edx+8],0
1553
	jne	macro_argument_ok
1554
	mov	[edx+12],eax
1555
	call	finish_macro_argument
1556
	jmp	macro_argument_ok
1557
      arguments_end:
31 halyavin 1558
	cmp	byte [ebx],0
2665 dunkaist 1559
	jne	invalid_macro_arguments
1560
	mov	eax,[esp+4]
1561
	dec	eax
1562
	call	process_macro
1563
	pop	edx
1564
	pop	dword [edx+4]
1565
	pop	[counter_limit]
1566
	pop	[macro_symbols]
1567
	pop	[free_additional_memory]
1568
	jmp	line_preprocessed
1569
use_instant_macro:
31 halyavin 1570
	push	edi [current_line] esi
2665 dunkaist 1571
	mov	eax,[error_line]
1572
	mov	[current_line],eax
1573
	mov	[macro_line],eax
1574
	mov	esi,[instant_macro_start]
1575
	cmp	[base_code],10h
1576
	jae	do_match
1577
	cmp	[base_code],0
1578
	jne	do_irp
1579
	call	precalculate_value
1580
	cmp	eax,0
1581
	jl	value_out_of_range
1582
	push	[free_additional_memory]
1583
	push	[macro_symbols]
1584
	mov	[macro_symbols],0
1585
	push	[counter_limit]
1586
	mov	[struc_name],0
1587
	mov	[counter_limit],eax
1588
	lods	byte [esi]
1589
	or	al,al
1590
	jz	rept_counters_ok
1591
	cmp	al,'{'
1592
	je	rept_counters_ok
1593
	cmp	al,1Ah
1594
	jne	invalid_macro_arguments
1595
      add_rept_counter:
31 halyavin 1596
	lods	byte [esi]
2665 dunkaist 1597
	movzx	ecx,al
1598
	xor	eax,eax
1599
	call	add_macro_symbol
1600
	add	esi,ecx
1601
	xor	eax,eax
1602
	mov	dword [edx+12],eax
1603
	inc	eax
1604
	mov	dword [edx+8],eax
1605
	lods	byte [esi]
1606
	cmp	al,':'
1607
	jne	rept_counter_added
1608
	push	edx
1609
	call	precalculate_value
1610
	mov	edx,eax
1611
	add	edx,[counter_limit]
1612
	jo	value_out_of_range
1613
	pop	edx
1614
	mov	dword [edx+8],eax
1615
	lods	byte [esi]
1616
      rept_counter_added:
31 halyavin 1617
	cmp	al,','
2665 dunkaist 1618
	jne	rept_counters_ok
1619
	lods	byte [esi]
1620
	cmp	al,1Ah
1621
	jne	invalid_macro_arguments
1622
	jmp	add_rept_counter
1623
      rept_counters_ok:
31 halyavin 1624
	dec	esi
2665 dunkaist 1625
	cmp	[counter_limit],0
1626
	je	instant_macro_finish
1627
      instant_macro_parameters_ok:
31 halyavin 1628
	xor	eax,eax
2665 dunkaist 1629
	call	process_macro
1630
      instant_macro_finish:
872 heavyiron 1631
	pop	[counter_limit]
2665 dunkaist 1632
	pop	[macro_symbols]
1633
	pop	[free_additional_memory]
1634
      instant_macro_done:
31 halyavin 1635
	pop	ebx esi edx
2665 dunkaist 1636
	cmp	byte [ebx],0
1637
	je	line_preprocessed
1638
	mov	[current_line],edi
1639
	mov	ecx,4
1640
	rep	movs dword [edi],[esi]
1641
	test	[macro_status],0Fh
1642
	jz	instant_macro_attached_line
1643
	mov	ax,3Bh
1644
	stos	word [edi]
1645
      instant_macro_attached_line:
31 halyavin 1646
	mov	esi,ebx
2665 dunkaist 1647
	sub	edx,ebx
1648
	mov	ecx,edx
1649
	call	move_data
1650
	jmp	initial_preprocessing_ok
1651
      precalculate_value:
1189 heavyiron 1652
	push	edi
2665 dunkaist 1653
	call	convert_expression
1654
	mov	al,')'
1655
	stosb
1656
	push	esi
1657
	mov	esi,[esp+4]
1658
	mov	[error_line],0
1659
	mov	[value_size],0
1660
	call	calculate_expression
1661
	cmp	[error_line],0
1662
	je	value_precalculated
1663
	jmp	[error]
1664
      value_precalculated:
1665
	mov	eax,[edi]
1666
	mov	ecx,[edi+4]
1667
	cdq
1668
	cmp	edx,ecx
1669
	jne	value_out_of_range
1670
	cmp	dl,[edi+13]
1671
	jne	value_out_of_range
1672
	pop	esi edi
1673
	ret
1674
do_irp:
31 halyavin 1675
	cmp	byte [esi],1Ah
2665 dunkaist 1676
	jne	invalid_macro_arguments
1677
	movzx	eax,byte [esi+1]
1678
	lea	esi,[esi+2+eax]
1679
	lods	byte [esi]
1680
	cmp	[base_code],1
1681
	ja	irps_name_ok
1682
	cmp	al,'='
1683
	je	irp_with_default_value
1684
	cmp	al,'*'
1685
	jne	irp_name_ok
1686
	lods	byte [esi]
1687
      irp_name_ok:
31 halyavin 1688
	cmp	al,','
2665 dunkaist 1689
	jne	invalid_macro_arguments
1690
	jmp	irp_parameters_start
1691
      irp_with_default_value:
2664 dunkaist 1692
	xor	ebp,ebp
2665 dunkaist 1693
	or	[default_argument_value],-1
1694
	call	skip_macro_argument_value
1695
	inc	esi
1696
	jmp	irp_parameters_start
4039 heavyiron 1697
      irps_name_ok:
31 halyavin 1698
	cmp	al,','
2665 dunkaist 1699
	jne	invalid_macro_arguments
1700
	mov	al,[esi]
1701
	or	al,al
1702
	jz	instant_macro_done
1703
	cmp	al,'{'
1704
	je	instant_macro_done
1705
      irp_parameters_start:
31 halyavin 1706
	xor	eax,eax
2665 dunkaist 1707
	push	[free_additional_memory]
1708
	push	[macro_symbols]
1709
	mov	[macro_symbols],eax
1710
	push	[counter_limit]
1711
	mov	[counter_limit],eax
1712
	mov	[struc_name],eax
1713
	mov	ebx,esi
1714
	cmp	[base_code],1
1715
	ja	get_irps_parameter
1716
	mov	edx,[parameters_end]
1717
	mov	al,[edx]
1718
	push	eax
1719
	mov	byte [edx],0
1720
      get_irp_parameter:
31 halyavin 1721
	inc	[counter_limit]
2665 dunkaist 1722
	mov	esi,[instant_macro_start]
1723
	inc	esi
1724
	call	get_macro_argument
1725
	cmp	byte [ebx],','
1726
	jne	irp_parameters_end
1727
	inc	ebx
1728
	jmp	get_irp_parameter
1729
      irp_parameters_end:
31 halyavin 1730
	mov	esi,ebx
2665 dunkaist 1731
	pop	eax
1732
	mov	[esi],al
1733
	jmp	instant_macro_parameters_ok
1734
      get_irps_parameter:
31 halyavin 1735
	mov	esi,[instant_macro_start]
2665 dunkaist 1736
	inc	esi
1737
	lods	byte [esi]
1738
	movzx	ecx,al
1739
	inc	[counter_limit]
1740
	mov	eax,[counter_limit]
1741
	call	add_macro_symbol
1742
	mov	[edx+12],ebx
1743
	cmp	byte [ebx],1Ah
1744
	je	irps_symbol
1745
	cmp	byte [ebx],22h
1746
	je	irps_quoted_string
1747
	mov	eax,1
1748
	jmp	irps_parameter_ok
1749
      irps_quoted_string:
31 halyavin 1750
	mov	eax,[ebx+1]
2665 dunkaist 1751
	add	eax,1+4
1752
	jmp	irps_parameter_ok
1753
      irps_symbol:
31 halyavin 1754
	movzx	eax,byte [ebx+1]
2665 dunkaist 1755
	add	eax,1+1
1756
      irps_parameter_ok:
31 halyavin 1757
	mov	[edx+8],eax
2665 dunkaist 1758
	add	ebx,eax
1759
	cmp	byte [ebx],0
1760
	je	irps_parameters_end
1761
	cmp	byte [ebx],'{'
1762
	jne	get_irps_parameter
1763
      irps_parameters_end:
31 halyavin 1764
	mov	esi,ebx
2665 dunkaist 1765
	jmp	instant_macro_parameters_ok
1766
do_match:
31 halyavin 1767
	mov	ebx,esi
2665 dunkaist 1768
	call	skip_pattern
1769
	call	exact_match
1770
	mov	edx,edi
1771
	mov	al,[ebx]
1772
	cmp	al,1Ah
1773
	je	free_match
1774
	cmp	al,','
1775
	jne	instant_macro_done
1776
	cmp	esi,[parameters_end]
1777
	je	matched_pattern
1778
	jmp	instant_macro_done
1779
      free_match:
31 halyavin 1780
	add	edx,12
2665 dunkaist 1781
	cmp	edx,[memory_end]
1782
	ja	out_of_memory
1783
	mov	[edx-12],ebx
1784
	mov	[edx-8],esi
1785
	call	skip_match_element
1786
	jc	try_different_matching
1787
	mov	[edx-4],esi
1788
	movzx	eax,byte [ebx+1]
1789
	lea	ebx,[ebx+2+eax]
1790
	cmp	byte [ebx],1Ah
1791
	je	free_match
1792
      find_exact_match:
31 halyavin 1793
	call	exact_match
2665 dunkaist 1794
	cmp	esi,[parameters_end]
1795
	je	end_matching
1796
	cmp	byte [ebx],1Ah
1797
	je	free_match
1798
	mov	ebx,[edx-12]
1799
	movzx	eax,byte [ebx+1]
1800
	lea	ebx,[ebx+2+eax]
1801
	mov	esi,[edx-4]
1802
	jmp	match_more_elements
1803
      try_different_matching:
31 halyavin 1804
	sub	edx,12
2665 dunkaist 1805
	cmp	edx,edi
1806
	je	instant_macro_done
1807
	mov	ebx,[edx-12]
1808
	movzx	eax,byte [ebx+1]
1809
	lea	ebx,[ebx+2+eax]
1810
	cmp	byte [ebx],1Ah
1811
	je	try_different_matching
1812
	mov	esi,[edx-4]
1813
      match_more_elements:
31 halyavin 1814
	call	skip_match_element
2665 dunkaist 1815
	jc	try_different_matching
1816
	mov	[edx-4],esi
1817
	jmp	find_exact_match
1818
      skip_match_element:
31 halyavin 1819
	cmp	esi,[parameters_end]
2665 dunkaist 1820
	je	cannot_match
1821
	mov	al,[esi]
1822
	cmp	al,1Ah
1823
	je	skip_match_symbol
1824
	cmp	al,22h
1825
	je	skip_match_quoted_string
1826
	add	esi,1
1827
	ret
1828
      skip_match_quoted_string:
31 halyavin 1829
	mov	eax,[esi+1]
2665 dunkaist 1830
	add	esi,5
1831
	jmp	skip_match_ok
1832
      skip_match_symbol:
31 halyavin 1833
	movzx	eax,byte [esi+1]
2665 dunkaist 1834
	add	esi,2
1835
      skip_match_ok:
31 halyavin 1836
	add	esi,eax
2665 dunkaist 1837
	ret
1838
      cannot_match:
31 halyavin 1839
	stc
2665 dunkaist 1840
	ret
1841
      exact_match:
31 halyavin 1842
	cmp	esi,[parameters_end]
2665 dunkaist 1843
	je	exact_match_complete
1844
	mov	ah,[esi]
1845
	mov	al,[ebx]
1846
	cmp	al,','
1847
	je	exact_match_complete
1848
	cmp	al,1Ah
1849
	je	exact_match_complete
1850
	cmp	al,'='
1851
	je	match_verbatim
1852
	call	match_elements
1853
	je	exact_match
1854
      exact_match_complete:
31 halyavin 1855
	ret
2665 dunkaist 1856
      match_verbatim:
31 halyavin 1857
	inc	ebx
2665 dunkaist 1858
	call	match_elements
1859
	je	exact_match
1860
	dec	ebx
1861
	ret
1862
      match_elements:
31 halyavin 1863
	mov	al,[ebx]
2665 dunkaist 1864
	cmp	al,1Ah
1865
	je	match_symbols
1866
	cmp	al,22h
1867
	je	match_quoted_strings
1868
	cmp	al,ah
1869
	je	symbol_characters_matched
1870
	ret
1871
      symbol_characters_matched:
31 halyavin 1872
	lea	ebx,[ebx+1]
2665 dunkaist 1873
	lea	esi,[esi+1]
1874
	ret
1875
      match_quoted_strings:
31 halyavin 1876
	mov	ecx,[ebx+1]
2665 dunkaist 1877
	add	ecx,5
1878
	jmp	compare_elements
1879
      match_symbols:
31 halyavin 1880
	movzx	ecx,byte [ebx+1]
2665 dunkaist 1881
	add	ecx,2
1882
      compare_elements:
31 halyavin 1883
	mov	eax,esi
2665 dunkaist 1884
	mov	ebp,edi
1885
	mov	edi,ebx
1886
	repe	cmps byte [esi],[edi]
1887
	jne	elements_mismatch
1888
	mov	ebx,edi
1889
	mov	edi,ebp
1890
	ret
1891
      elements_mismatch:
31 halyavin 1892
	mov	esi,eax
2665 dunkaist 1893
	mov	edi,ebp
1894
	ret
1895
      end_matching:
31 halyavin 1896
	cmp	byte [ebx],','
2665 dunkaist 1897
	jne	instant_macro_done
1898
      matched_pattern:
31 halyavin 1899
	xor	eax,eax
2665 dunkaist 1900
	push	[free_additional_memory]
1901
	push	[macro_symbols]
1902
	mov	[macro_symbols],eax
1903
	push	[counter_limit]
1904
	mov	[counter_limit],eax
1905
	mov	[struc_name],eax
1906
	push	esi edi edx
1907
      add_matched_symbol:
31 halyavin 1908
	cmp	edi,[esp]
2665 dunkaist 1909
	je	matched_symbols_ok
1910
	mov	esi,[edi]
1911
	inc	esi
1912
	lods	byte [esi]
1913
	movzx	ecx,al
1914
	xor	eax,eax
1915
	call	add_macro_symbol
1916
	mov	eax,[edi+4]
1917
	mov	dword [edx+12],eax
1918
	mov	ecx,[edi+8]
1919
	sub	ecx,eax
1920
	mov	dword [edx+8],ecx
1921
	add	edi,12
1922
	jmp	add_matched_symbol
1923
      matched_symbols_ok:
31 halyavin 1924
	pop	edx edi esi
2665 dunkaist 1925
	jmp	instant_macro_parameters_ok
1926
31 halyavin 1927
 
1928
	push	dword [macro_status]
2665 dunkaist 1929
	or	[macro_status],10h
1930
	push	[counter]
1931
	push	[macro_block]
1932
	push	[macro_block_line]
1933
	push	[macro_block_line_number]
1934
	push	[struc_label]
1935
	push	[struc_name]
1936
	push	eax
1937
	push	[current_line]
1938
	lods	byte [esi]
1939
	cmp	al,'{'
1940
	je	macro_instructions_start
1941
	or	al,al
1942
	jnz	unexpected_characters
1943
      find_macro_instructions:
31 halyavin 1944
	mov	[macro_line],esi
2665 dunkaist 1945
	add	esi,16+2
1946
	lods	byte [esi]
1947
	or	al,al
1948
	jz	find_macro_instructions
1949
	cmp	al,'{'
1950
	je	macro_instructions_start
1951
	cmp	al,3Bh
1952
	jne	unexpected_characters
1953
	call	skip_foreign_symbol
1954
	jmp	find_macro_instructions
1955
      macro_instructions_start:
31 halyavin 1956
	mov	ecx,80000000h
2665 dunkaist 1957
	mov	[macro_block],esi
1958
	mov	eax,[macro_line]
1959
	mov	[macro_block_line],eax
1960
	mov	[macro_block_line_number],ecx
1961
	xor	eax,eax
1962
	mov	[counter],eax
1963
	cmp	[counter_limit],eax
1964
	je	process_macro_line
1965
	inc	[counter]
1966
      process_macro_line:
31 halyavin 1967
	lods	byte [esi]
2665 dunkaist 1968
	or	al,al
1969
	jz	process_next_line
1970
	cmp	al,'}'
1971
	je	macro_block_processed
1972
	dec	esi
1973
	mov	[current_line],edi
1974
	lea	eax,[edi+10h]
1975
	cmp	eax,[memory_end]
1976
	jae	out_of_memory
1977
	mov	eax,[esp+4]
1978
	or	eax,eax
1979
	jz	instant_macro_line_header
1980
	stos	dword [edi]
1981
	mov	eax,ecx
1982
	stos	dword [edi]
1983
	mov	eax,[esp]
1984
	stos	dword [edi]
1985
	mov	eax,[macro_line]
1986
	stos	dword [edi]
1987
	jmp	macro_line_header_ok
1988
      instant_macro_line_header:
31 halyavin 1989
	mov	eax,[macro_line]
2665 dunkaist 1990
	add	eax,16+1
1991
	stos	dword [edi]
1992
	mov	eax,ecx
1993
	stos	dword [edi]
1994
	mov	eax,[macro_line]
1995
	stos	dword [edi]
1996
	stos	dword [edi]
1997
      macro_line_header_ok:
31 halyavin 1998
	or	[macro_status],20h
2665 dunkaist 1999
	push	ebx ecx
2000
	test	[macro_status],0Fh
2001
	jz	process_macro_line_element
2002
	mov	ax,3Bh
2003
	stos	word [edi]
2004
      process_macro_line_element:
31 halyavin 2005
	lea	eax,[edi+100h]
2665 dunkaist 2006
	cmp	eax,[memory_end]
2007
	jae	out_of_memory
2008
	lods	byte [esi]
2009
	cmp	al,'}'
2010
	je	macro_line_processed
2011
	or	al,al
2012
	jz	macro_line_processed
2013
	cmp	al,1Ah
2014
	je	process_macro_symbol
2015
	cmp	al,3Bh
2016
	je	macro_foreign_line
2017
	and	[macro_status],not 20h
2018
	stos	byte [edi]
2019
	cmp	al,22h
2020
	jne	process_macro_line_element
2021
      copy_macro_string:
31 halyavin 2022
	mov	ecx,[esi]
2665 dunkaist 2023
	add	ecx,4
2024
	call	move_data
2025
	jmp	process_macro_line_element
2026
      process_macro_symbol:
31 halyavin 2027
	push	esi edi
2665 dunkaist 2028
	test	[macro_status],20h
2029
	jz	not_macro_directive
2030
	movzx	ecx,byte [esi]
2031
	inc	esi
2032
	mov	edi,macro_directives
2033
	call	get_directive
2034
	jnc	process_macro_directive
2035
	dec	esi
2036
	jmp	not_macro_directive
2037
      process_macro_directive:
31 halyavin 2038
	mov	edx,eax
2665 dunkaist 2039
	pop	edi eax
2040
	mov	byte [edi],0
2041
	inc	edi
2042
	pop	ecx ebx
2043
	jmp	near edx
2044
      not_macro_directive:
31 halyavin 2045
	and	[macro_status],not 20h
2665 dunkaist 2046
	movzx	ecx,byte [esi]
2047
	inc	esi
2048
	mov	eax,[counter]
2049
	call	get_macro_symbol
2050
	jnc	group_macro_symbol
2051
	xor	eax,eax
2052
	cmp	[counter],eax
2053
	je	multiple_macro_symbol_values
2054
	call	get_macro_symbol
2055
	jc	not_macro_symbol
2056
      replace_macro_symbol:
31 halyavin 2057
	pop	edi eax
2665 dunkaist 2058
	mov	ecx,[edx+8]
2059
	mov	edx,[edx+12]
2060
	or	edx,edx
2061
	jz	replace_macro_counter
2062
	and	ecx,not 80000000h
2063
	xchg	esi,edx
2064
	call	move_data
2065
	mov	esi,edx
2066
	jmp	process_macro_line_element
2067
      group_macro_symbol:
31 halyavin 2068
	xor	eax,eax
2665 dunkaist 2069
	cmp	[counter],eax
2070
	je	replace_macro_symbol
2071
	push	esi edx
2072
	sub	esi,ecx
2073
	call	get_macro_symbol
2074
	mov	ebx,edx
2075
	pop	edx esi
2076
	jc	replace_macro_symbol
2077
	cmp	edx,ebx
2078
	ja	replace_macro_symbol
2079
	mov	edx,ebx
2080
	jmp	replace_macro_symbol
2081
      multiple_macro_symbol_values:
31 halyavin 2082
	inc	eax
2665 dunkaist 2083
	push	eax
2084
	call	get_macro_symbol
2085
	pop	eax
2086
	jc	not_macro_symbol
2087
	pop	edi
2088
	push	ecx
2089
	mov	ecx,[edx+8]
2090
	mov	edx,[edx+12]
2091
	xchg	esi,edx
2092
	btr	ecx,31
2093
	jc	enclose_macro_symbol_value
2094
	rep	movs byte [edi],[esi]
2095
	jmp	macro_symbol_value_ok
2096
      enclose_macro_symbol_value:
31 halyavin 2097
	mov	byte [edi],'<'
2665 dunkaist 2098
	inc	edi
2099
	rep	movs byte [edi],[esi]
2100
	mov	byte [edi],'>'
2101
	inc	edi
2102
      macro_symbol_value_ok:
31 halyavin 2103
	cmp	eax,[counter_limit]
2665 dunkaist 2104
	je	multiple_macro_symbol_values_ok
2105
	mov	byte [edi],','
2106
	inc	edi
2107
	mov	esi,edx
2108
	pop	ecx
2109
	push	edi
2110
	sub	esi,ecx
2111
	jmp	multiple_macro_symbol_values
2112
      multiple_macro_symbol_values_ok:
31 halyavin 2113
	pop	ecx eax
2665 dunkaist 2114
	mov	esi,edx
2115
	jmp	process_macro_line_element
2116
      replace_macro_counter:
31 halyavin 2117
	mov	eax,[counter]
2665 dunkaist 2118
	and	eax,not 80000000h
2119
	jz	group_macro_counter
2120
	add	ecx,eax
2121
	dec	ecx
2122
	call	store_number_symbol
2123
	jmp	process_macro_line_element
2124
      group_macro_counter:
31 halyavin 2125
	mov	edx,ecx
2665 dunkaist 2126
	xor	ecx,ecx
2127
      multiple_macro_counter_values:
31 halyavin 2128
	push	ecx edx
2665 dunkaist 2129
	add	ecx,edx
2130
	call	store_number_symbol
2131
	pop	edx ecx
2132
	inc	ecx
2133
	cmp	ecx,[counter_limit]
2134
	je	process_macro_line_element
2135
	mov	byte [edi],','
2136
	inc	edi
2137
	jmp	multiple_macro_counter_values
2138
      store_number_symbol:
31 halyavin 2139
	cmp	ecx,0
2665 dunkaist 2140
	jge	numer_symbol_sign_ok
2141
	neg	ecx
2142
	mov	al,'-'
2143
	stos	byte [edi]
2144
      numer_symbol_sign_ok:
1189 heavyiron 2145
	mov	ax,1Ah
2665 dunkaist 2146
	stos	word [edi]
2147
	push	edi
2148
	mov	eax,ecx
2149
	mov	ecx,1000000000
2150
	xor	edx,edx
2151
	xor	bl,bl
2152
      store_number_digits:
31 halyavin 2153
	div	ecx
2665 dunkaist 2154
	push	edx
2155
	or	bl,bl
2156
	jnz	store_number_digit
2157
	cmp	ecx,1
2158
	je	store_number_digit
2159
	or	al,al
2160
	jz	number_digit_ok
2161
	not	bl
2162
      store_number_digit:
31 halyavin 2163
	add	al,30h
2665 dunkaist 2164
	stos	byte [edi]
2165
      number_digit_ok:
31 halyavin 2166
	mov	eax,ecx
2665 dunkaist 2167
	xor	edx,edx
2168
	mov	ecx,10
2169
	div	ecx
2170
	mov	ecx,eax
2171
	pop	eax
2172
	or	ecx,ecx
2173
	jnz	store_number_digits
2174
	pop	ebx
2175
	mov	eax,edi
2176
	sub	eax,ebx
2177
	mov	[ebx-1],al
2178
	ret
2179
      not_macro_symbol:
31 halyavin 2180
	pop	edi esi
2665 dunkaist 2181
	mov	al,1Ah
2182
	stos	byte [edi]
2183
	mov	al,[esi]
2184
	inc	esi
2185
	stos	byte [edi]
2186
	cmp	byte [esi],'.'
2187
	jne	copy_raw_symbol
2188
	mov	ebx,[esp+8+8]
2189
	or	ebx,ebx
2190
	jz	copy_raw_symbol
2191
	cmp	al,1
2192
	je	copy_struc_name
2193
	xchg	esi,ebx
2194
	movzx	ecx,byte [esi-1]
2195
	add	[edi-1],cl
2196
	jc	name_too_long
2197
	rep	movs byte [edi],[esi]
2198
	xchg	esi,ebx
2199
      copy_raw_symbol:
31 halyavin 2200
	movzx	ecx,al
2665 dunkaist 2201
	rep	movs byte [edi],[esi]
2202
	jmp	process_macro_line_element
2203
      copy_struc_name:
31 halyavin 2204
	inc	esi
2665 dunkaist 2205
	xchg	esi,ebx
2206
	movzx	ecx,byte [esi-1]
2207
	mov	[edi-1],cl
2208
	rep	movs byte [edi],[esi]
2209
	xchg	esi,ebx
2210
	mov	eax,[esp+8+12]
2211
	cmp	byte [eax],3Bh
2212
	je	process_macro_line_element
2213
	cmp	byte [eax],1Ah
2214
	jne	disable_replaced_struc_name
2215
	mov	byte [eax],3Bh
2216
	jmp	process_macro_line_element
2217
      disable_replaced_struc_name:
31 halyavin 2218
	mov	ebx,[esp+8+8]
2665 dunkaist 2219
	push	esi edi
2220
	lea	edi,[ebx-3]
2221
	lea	esi,[edi-2]
2222
	lea	ecx,[esi+1]
2223
	sub	ecx,eax
2224
	std
2225
	rep	movs byte [edi],[esi]
2226
	cld
2227
	mov	word [eax],3Bh
2228
	pop	edi esi
2229
	jmp	process_macro_line_element
2230
      skip_foreign_symbol:
31 halyavin 2231
	lods	byte [esi]
2665 dunkaist 2232
	movzx	eax,al
2233
	add	esi,eax
2234
      skip_foreign_line:
31 halyavin 2235
	lods	byte [esi]
2665 dunkaist 2236
	cmp	al,1Ah
2237
	je	skip_foreign_symbol
2238
	cmp	al,3Bh
2239
	je	skip_foreign_symbol
2240
	cmp	al,22h
2241
	je	skip_foreign_string
2242
	or	al,al
2243
	jnz	skip_foreign_line
2244
	ret
2245
      skip_foreign_string:
31 halyavin 2246
	lods	dword [esi]
2665 dunkaist 2247
	add	esi,eax
2248
	jmp	skip_foreign_line
2249
      macro_foreign_line:
31 halyavin 2250
	call	skip_foreign_symbol
2665 dunkaist 2251
      macro_line_processed:
31 halyavin 2252
	mov	byte [edi],0
2665 dunkaist 2253
	inc	edi
2254
	push	eax
2255
	call	preprocess_line
2256
	pop	eax
2257
	pop	ecx ebx
2258
	cmp	al,'}'
2259
	je	macro_block_processed
2260
      process_next_line:
31 halyavin 2261
	inc	ecx
2665 dunkaist 2262
	mov	[macro_line],esi
2263
	add	esi,16+2
2264
	jmp	process_macro_line
2265
      macro_block_processed:
31 halyavin 2266
	call	close_macro_block
2665 dunkaist 2267
	jc	process_macro_line
2268
	pop	[current_line]
2269
	add	esp,12
2270
	pop	[macro_block_line_number]
2271
	pop	[macro_block_line]
2272
	pop	[macro_block]
2273
	pop	[counter]
2274
	pop	eax
2275
	and	al,0F0h
2276
	and	[macro_status],0Fh
2277
	or	[macro_status],al
2278
	ret
2279
31 halyavin 2280
 
2281
	lods	byte [esi]
2665 dunkaist 2282
	cmp	al,1Ah
2283
	jne	invalid_argument
2284
	mov	byte [edi-1],3Bh
2285
	xor	al,al
2286
	stos	byte [edi]
2287
      make_local_symbol:
31 halyavin 2288
	push	ecx
2665 dunkaist 2289
	lods	byte [esi]
2290
	movzx	ecx,al
2291
	mov	eax,[counter]
2292
	call	add_macro_symbol
2293
	mov	[edx+12],edi
2294
	movzx	eax,[locals_counter]
2295
	add	eax,ecx
2296
	inc	eax
2297
	cmp	eax,100h
2298
	jae	name_too_long
2299
	lea	ebp,[edi+2+eax]
2300
	cmp	ebp,[memory_end]
2301
	jae	out_of_memory
2302
	mov	ah,al
2303
	mov	al,1Ah
2304
	stos	word [edi]
2305
	rep	movs byte [edi],[esi]
2306
	mov	al,'?'
2307
	stos	byte [edi]
2308
	push	esi
2309
	mov	esi,locals_counter+1
2310
	movzx	ecx,[locals_counter]
2311
	rep	movs byte [edi],[esi]
2312
	pop	esi
2313
	mov	eax,edi
2314
	sub	eax,[edx+12]
2315
	mov	[edx+8],eax
2316
	xor	al,al
2317
	stos	byte [edi]
2318
	mov	eax,locals_counter
2319
	movzx	ecx,byte [eax]
2320
      counter_loop:
31 halyavin 2321
	inc	byte [eax+ecx]
2665 dunkaist 2322
	cmp	byte [eax+ecx],'9'+1
2323
	jb	counter_ok
2324
	jne	letter_digit
2325
	mov	byte [eax+ecx],'A'
2326
	jmp	counter_ok
2327
      letter_digit:
31 halyavin 2328
	cmp	byte [eax+ecx],'Z'+1
2665 dunkaist 2329
	jb	counter_ok
2330
	jne	small_letter_digit
2331
	mov	byte [eax+ecx],'a'
2332
	jmp	counter_ok
2333
      small_letter_digit:
692 heavyiron 2334
	cmp	byte [eax+ecx],'z'+1
2665 dunkaist 2335
	jb	counter_ok
2336
	mov	byte [eax+ecx],'0'
2337
	loop	counter_loop
2338
	inc	byte [eax]
2339
	movzx	ecx,byte [eax]
2340
	mov	byte [eax+ecx],'0'
2341
      counter_ok:
31 halyavin 2342
	pop	ecx
2665 dunkaist 2343
	lods	byte [esi]
2344
	cmp	al,'}'
2345
	je	macro_block_processed
2346
	or	al,al
2347
	jz	process_next_line
2348
	cmp	al,','
2349
	jne	extra_characters_on_line
2350
	dec	edi
2351
	lods	byte [esi]
2352
	cmp	al,1Ah
2353
	je	make_local_symbol
2354
	jmp	invalid_argument
2355
common_block:
31 halyavin 2356
	call	close_macro_block
2665 dunkaist 2357
	jc	process_macro_line
2358
	mov	[counter],0
2359
	jmp	new_macro_block
2360
forward_block:
31 halyavin 2361
	cmp	[counter_limit],0
2665 dunkaist 2362
	je	common_block
2363
	call	close_macro_block
2364
	jc	process_macro_line
2365
	mov	[counter],1
2366
	jmp	new_macro_block
2367
reverse_block:
31 halyavin 2368
	cmp	[counter_limit],0
2665 dunkaist 2369
	je	common_block
2370
	call	close_macro_block
2371
	jc	process_macro_line
2372
	mov	eax,[counter_limit]
2373
	or	eax,80000000h
2374
	mov	[counter],eax
2375
      new_macro_block:
31 halyavin 2376
	mov	[macro_block],esi
2665 dunkaist 2377
	mov	eax,[macro_line]
2378
	mov	[macro_block_line],eax
2379
	mov	[macro_block_line_number],ecx
2380
	jmp	process_macro_line
2381
close_macro_block:
31 halyavin 2382
	cmp	[counter],0
2665 dunkaist 2383
	je	block_closed
2384
	jl	reverse_counter
2385
	mov	eax,[counter]
2386
	cmp	eax,[counter_limit]
2387
	je	block_closed
2388
	inc	[counter]
2389
	jmp	continue_block
2390
      reverse_counter:
31 halyavin 2391
	mov	eax,[counter]
2665 dunkaist 2392
	dec	eax
2393
	cmp	eax,80000000h
2394
	je	block_closed
2395
	mov	[counter],eax
2396
      continue_block:
31 halyavin 2397
	mov	esi,[macro_block]
2665 dunkaist 2398
	mov	eax,[macro_block_line]
2399
	mov	[macro_line],eax
2400
	mov	ecx,[macro_block_line_number]
2401
	stc
2402
	ret
2403
      block_closed:
31 halyavin 2404
	clc
2665 dunkaist 2405
	ret
2406
get_macro_symbol:
31 halyavin 2407
	push	ecx
2665 dunkaist 2408
	call	find_macro_symbol_leaf
2409
	jc	macro_symbol_not_found
2410
	mov	edx,[ebx]
2411
	mov	ebx,esi
2412
      try_macro_symbol:
31 halyavin 2413
	or	edx,edx
2665 dunkaist 2414
	jz	macro_symbol_not_found
2415
	mov	ecx,[esp]
2416
	mov	edi,[edx+4]
2417
	repe	cmps byte [esi],[edi]
2418
	je	macro_symbol_found
2419
	mov	esi,ebx
2420
	mov	edx,[edx]
2421
	jmp	try_macro_symbol
2422
      macro_symbol_found:
31 halyavin 2423
	pop	ecx
2665 dunkaist 2424
	clc
2425
	ret
2426
      macro_symbol_not_found:
31 halyavin 2427
	pop	ecx
2665 dunkaist 2428
	stc
2429
	ret
2430
      find_macro_symbol_leaf:
31 halyavin 2431
	shl	eax,8
2665 dunkaist 2432
	mov	al,cl
2433
	mov	ebp,eax
2434
	mov	ebx,macro_symbols
2435
      follow_macro_symbols_tree:
31 halyavin 2436
	mov	edx,[ebx]
2665 dunkaist 2437
	or	edx,edx
2438
	jz	no_such_macro_symbol
2439
	xor	eax,eax
2440
	shr	ebp,1
2441
	adc	eax,0
2442
	lea	ebx,[edx+eax*4]
2443
	or	ebp,ebp
2444
	jnz	follow_macro_symbols_tree
2445
	add	ebx,8
2446
	clc
2447
	ret
2448
      no_such_macro_symbol:
31 halyavin 2449
	stc
2665 dunkaist 2450
	ret
2451
add_macro_symbol:
31 halyavin 2452
	push	ebx ebp
2665 dunkaist 2453
	call	find_macro_symbol_leaf
2454
	jc	extend_macro_symbol_tree
2455
	mov	eax,[ebx]
2456
      make_macro_symbol:
31 halyavin 2457
	mov	edx,[free_additional_memory]
2665 dunkaist 2458
	add	edx,16
2459
	cmp	edx,[labels_list]
2460
	ja	out_of_memory
2461
	xchg	edx,[free_additional_memory]
2462
	mov	[ebx],edx
2463
	mov	[edx],eax
2464
	mov	[edx+4],esi
2465
	pop	ebp ebx
2466
	ret
2467
      extend_macro_symbol_tree:
31 halyavin 2468
	mov	edx,[free_additional_memory]
2665 dunkaist 2469
	add	edx,16
2470
	cmp	edx,[labels_list]
2471
	ja	out_of_memory
2472
	xchg	edx,[free_additional_memory]
2473
	xor	eax,eax
2474
	mov	[edx],eax
2475
	mov	[edx+4],eax
2476
	mov	[edx+8],eax
2477
	mov	[edx+12],eax
2478
	shr	ebp,1
2479
	adc	eax,0
2480
	mov	[ebx],edx
2481
	lea	ebx,[edx+eax*4]
2482
	or	ebp,ebp
2483
	jnz	extend_macro_symbol_tree
2484
	add	ebx,8
2485
	xor	eax,eax
2486
	jmp	make_macro_symbol
2487
31 halyavin 2488
 
2489
	lods	byte [esi]
2665 dunkaist 2490
	cmp	al,22h
2491
	jne	invalid_argument
2492
	lods	dword [esi]
2493
	cmp	byte [esi+eax],0
2494
	jne	extra_characters_on_line
2495
	push	esi
2496
	push	edi
2497
	mov	ebx,[current_line]
2498
      find_current_file_path:
31 halyavin 2499
	mov	esi,[ebx]
2665 dunkaist 2500
	test	byte [ebx+7],80h
2501
	jz	copy_current_file_path
2502
	mov	ebx,[ebx+8]
2503
	jmp	find_current_file_path
2504
      copy_current_file_path:
31 halyavin 2505
	lods	byte [esi]
2665 dunkaist 2506
	stos	byte [edi]
2507
	or	al,al
2508
	jnz	copy_current_file_path
2509
      cut_current_file_name:
31 halyavin 2510
	cmp	edi,[esp]
2665 dunkaist 2511
	je	current_file_path_ok
2512
	cmp	byte [edi-1],'\'
2513
	je	current_file_path_ok
2514
	cmp	byte [edi-1],'/'
2515
	je	current_file_path_ok
2516
	dec	edi
2517
	jmp	cut_current_file_name
2518
      current_file_path_ok:
31 halyavin 2519
	mov	esi,[esp+4]
2665 dunkaist 2520
	call	expand_path
2521
	pop	edx
2522
	mov	esi,edx
2523
	call	open
2524
	jnc	include_path_ok
2525
	mov	ebp,[include_paths]
2526
      try_include_directories:
31 halyavin 2527
	mov	edi,esi
2665 dunkaist 2528
	mov	esi,ebp
2529
	cmp	byte [esi],0
2530
	je	try_in_current_directory
2531
	push	ebp
2532
	push	edi
2533
	call	get_include_directory
2534
	mov	[esp+4],esi
2535
	mov	esi,[esp+8]
2536
	call	expand_path
2537
	pop	edx
2538
	mov	esi,edx
2539
	call	open
2540
	pop	ebp
2541
	jnc	include_path_ok
2542
	jmp	try_include_directories
2543
	mov	edi,esi
2544
      try_in_current_directory:
31 halyavin 2545
	mov	esi,[esp]
2665 dunkaist 2546
	push	edi
2547
	call	expand_path
2548
	pop	edx
2549
	mov	esi,edx
2550
	call	open
2551
	jc	file_not_found
2552
      include_path_ok:
31 halyavin 2553
	mov	edi,[esp]
2665 dunkaist 2554
      copy_preprocessed_path:
31 halyavin 2555
	lods	byte [esi]
2665 dunkaist 2556
	stos	byte [edi]
2557
	or	al,al
2558
	jnz	copy_preprocessed_path
2559
	pop	esi
2560
	lea	ecx,[edi-1]
2561
	sub	ecx,esi
2562
	mov	[esi-4],ecx
2563
	push	dword [macro_status]
2564
	and	[macro_status],0Fh
2565
	call	preprocess_file
2566
	pop	eax
2567
	and	al,0F0h
2568
	and	[macro_status],0Fh
2569
	or	[macro_status],al
2570
	jmp	line_preprocessed
2571
>