Subversion Repositories Kolibri OS

Rev

Rev 31 | 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-2006, Tomasz Grysztar.
109 heavyiron 3
; All rights reserved.
31 halyavin 4
5
 
6
        cmp     [output_file],0
109 heavyiron 7
        jne     output_path_ok
8
        push    edi
9
        mov     esi,[input_file]
10
        mov     edi,[free_additional_memory]
11
      copy_output_path:
31 halyavin 12
        lods    byte [esi]
109 heavyiron 13
        cmp     edi,[structures_buffer]
14
        jae     out_of_memory
15
        stos    byte [edi]
16
        or      al,al
17
        jnz     copy_output_path
18
        dec     edi
19
        mov     eax,edi
20
      find_extension:
31 halyavin 21
        dec     eax
109 heavyiron 22
        cmp     eax,[free_additional_memory]
23
        jb      extension_found
24
        cmp     byte [eax],'\'
25
        je      extension_found
26
        cmp     byte [eax],'/'
27
        je      extension_found
28
        cmp     byte [eax],'.'
29
        jne     find_extension
30
        mov     edi,eax
31
      extension_found:
31 halyavin 32
        lea     eax,[edi+9]
109 heavyiron 33
        cmp     eax,[structures_buffer]
34
        jae     out_of_memory
35
        cmp     [output_format],2
36
        je      exe_extension
37
        jb      bin_extension
38
        cmp     [output_format],4
39
        je      obj_extension
40
        cmp     [output_format],5
41
        je      o_extension
42
        cmp     [output_format],3
43
        jne     no_extension
44
        cmp     [subsystem],1
45
        je      sys_extension
46
        bt      [format_flags],8
47
        jnc     exe_extension
48
        mov     eax,'.dll'
49
        jmp     make_extension
50
      sys_extension:
31 halyavin 51
        mov     eax,'.sys'
109 heavyiron 52
        jmp     make_extension
53
      bin_extension:
31 halyavin 54
        mov     eax,'.bin'
109 heavyiron 55
        bt      [format_flags],0
56
        jnc     make_extension
57
        mov     eax,'.com'
58
        jmp     make_extension
59
      obj_extension:
31 halyavin 60
        mov     eax,'.obj'
109 heavyiron 61
        jmp     make_extension
62
      o_extension:
31 halyavin 63
        mov     eax,'.o'
109 heavyiron 64
        bt      [format_flags],0
65
        jnc     make_extension
66
      no_extension:
31 halyavin 67
        xor     eax,eax
109 heavyiron 68
        jmp     make_extension
69
      exe_extension:
31 halyavin 70
        mov     eax,'.exe'
109 heavyiron 71
      make_extension:
31 halyavin 72
        xchg    eax,[edi]
109 heavyiron 73
        scas    dword [edi]
74
        mov     byte [edi],0
75
        scas    byte [edi]
76
        mov     esi,edi
77
        stos    dword [edi]
78
        sub     edi,9
79
        xor     eax,eax
80
        mov     ebx,characters
81
      adapt_case:
31 halyavin 82
        mov     al,[esi]
109 heavyiron 83
        or      al,al
84
        jz      adapt_next
85
        xlat    byte [ebx]
86
        cmp     al,[esi]
87
        je      adapt_ok
88
        sub     byte [edi],20h
89
      adapt_ok:
31 halyavin 90
        inc     esi
109 heavyiron 91
      adapt_next:
31 halyavin 92
        inc     edi
109 heavyiron 93
        cmp     byte [edi],0
94
        jne     adapt_case
95
        mov     esi,edi
96
        lea     ecx,[esi+1]
97
        sub     ecx,[free_additional_memory]
98
        mov     edi,[structures_buffer]
99
        dec     edi
100
        std
101
        rep     movs byte [edi],[esi]
102
        cld
103
        inc     edi
104
        mov     [structures_buffer],edi
105
        mov     [output_file],edi
106
        pop     edi
107
      output_path_ok:
31 halyavin 108
        cmp     [output_format],4
109 heavyiron 109
        je      coff_formatter
110
        cmp     [output_format],5
111
        jne     common_formatter
112
        bt      [format_flags],0
113
        jnc     elf_formatter
114
      common_formatter:
31 halyavin 115
        mov     eax,edi
109 heavyiron 116
        sub     eax,[code_start]
117
        mov     [real_code_size],eax
118
        cmp     edi,[undefined_data_end]
119
        jne     calculate_code_size
120
        mov     edi,[undefined_data_start]
121
      calculate_code_size:
31 halyavin 122
        sub     edi,[code_start]
109 heavyiron 123
        mov     [code_size],edi
124
        mov     [written_size],0
125
        mov     edx,[output_file]
126
        call    create
127
        jc      write_failed
128
        cmp     [output_format],3
129
        jne     stub_written
130
        mov     edx,[code_start]
131
        mov     ecx,[stub_size]
132
        sub     edx,ecx
133
        add     [written_size],ecx
134
        call    write
135
      stub_written:
31 halyavin 136
        cmp     [output_format],2
109 heavyiron 137
        jne     write_output
138
        call    write_mz_header
139
      write_output:
31 halyavin 140
        call    write_code
109 heavyiron 141
      output_written:
31 halyavin 142
        call    close
109 heavyiron 143
        ret
144
      write_code:
31 halyavin 145
        mov     eax,[written_size]
109 heavyiron 146
        mov     [headers_size],eax
147
        mov     edx,[code_start]
148
        mov     ecx,[code_size]
149
        add     [written_size],ecx
150
        call    write
151
        jc      write_failed
152
        ret
153
format_directive:
31 halyavin 154
        cmp     edi,[code_start]
109 heavyiron 155
        jne     unexpected_instruction
156
        cmp     [virtual_data],0
157
        jne     unexpected_instruction
158
        cmp     [output_format],0
159
        jne     unexpected_instruction
160
        lods    byte [esi]
161
        cmp     al,17h
162
        je      format_prefix
163
        cmp     al,18h
164
        jne     invalid_argument
165
        lods    byte [esi]
166
      select_format:
31 halyavin 167
        mov     dl,al
109 heavyiron 168
        shr     al,4
169
        mov     [output_format],al
170
        and     edx,0Fh
171
        or      [format_flags],edx
172
        cmp     al,2
173
        je      format_mz
174
        cmp     al,3
175
        je      format_pe
176
        cmp     al,4
177
        je      format_coff
178
        cmp     al,5
179
        je      format_elf
180
        jmp     instruction_assembled
181
      format_prefix:
31 halyavin 182
        lods    byte [esi]
109 heavyiron 183
        mov     ah,al
184
        lods    byte [esi]
185
        cmp     al,18h
186
        jne     invalid_argument
187
        lods    byte [esi]
188
        mov     edx,eax
189
        shr     dl,4
190
        shr     dh,4
191
        cmp     dl,dh
192
        jne     invalid_argument
193
        or      al,ah
194
        jmp     select_format
195
entry_directive:
31 halyavin 196
        bts     [format_flags],10h
109 heavyiron 197
        jc      setting_already_specified
198
        mov     al,[output_format]
199
        cmp     al,2
200
        je      mz_entry
201
        cmp     al,3
202
        je      pe_entry
203
        cmp     al,5
204
        jne     illegal_instruction
205
        bt      [format_flags],0
206
        jc      elf_entry
207
        jmp     illegal_instruction
208
stack_directive:
31 halyavin 209
        bts     [format_flags],11h
109 heavyiron 210
        jc      setting_already_specified
211
        mov     al,[output_format]
212
        cmp     al,2
213
        je      mz_stack
214
        cmp     al,3
215
        je      pe_stack
216
        jmp     illegal_instruction
217
heap_directive:
31 halyavin 218
        bts     [format_flags],12h
109 heavyiron 219
        jc      setting_already_specified
220
        mov     al,[output_format]
221
        cmp     al,2
222
        je      mz_heap
223
        cmp     al,3
224
        je      pe_heap
225
        jmp     illegal_instruction
226
segment_directive:
227
        cmp     [virtual_data],0
228
        jne     illegal_instruction
229
        mov     al,[output_format]
230
        cmp     al,2
231
        je      mz_segment
232
        cmp     al,5
233
        je      elf_segment
234
        jmp     illegal_instruction
235
section_directive:
31 halyavin 236
        cmp     [virtual_data],0
109 heavyiron 237
        jne     illegal_instruction
238
        mov     al,[output_format]
239
        cmp     al,3
240
        je      pe_section
241
        cmp     al,4
242
        je      coff_section
243
        cmp     al,5
244
        je      elf_section
245
        jmp     illegal_instruction
246
public_directive:
31 halyavin 247
        mov     al,[output_format]
109 heavyiron 248
        cmp     al,4
249
        je      public_allowed
250
        cmp     al,5
251
        jne     illegal_instruction
252
        bt      [format_flags],0
253
        jc      illegal_instruction
254
      public_allowed:
31 halyavin 255
        lods    byte [esi]
109 heavyiron 256
        cmp     al,2
257
        jne     invalid_argument
258
        lods    dword [esi]
259
        cmp     eax,0Fh
260
        jb      invalid_use_of_symbol
261
        je      reserved_word_used_as_symbol
262
        mov     dx,[current_pass]
263
        mov     [eax+18],dx
264
        or      byte [eax+8],8
265
        inc     esi
266
        mov     ebx,[free_additional_memory]
267
        lea     edx,[ebx+10h]
268
        cmp     edx,[structures_buffer]
269
        jae     out_of_memory
270
        mov     [free_additional_memory],edx
271
        mov     [ebx+8],eax
272
        mov     eax,[current_line]
273
        mov     [ebx+0Ch],eax
274
        lods    byte [esi]
275
        cmp     al,86h
276
        jne     invalid_argument
277
        lods    word [esi]
278
        cmp     ax,'('
279
        jne     invalid_argument
280
        mov     [ebx+4],esi
281
        lods    dword [esi]
282
        lea     esi,[esi+eax+1]
283
        mov     byte [ebx],80h
284
        jmp     instruction_assembled
285
extrn_directive:
31 halyavin 286
        mov     al,[output_format]
109 heavyiron 287
        cmp     al,4
288
        je      extrn_allowed
289
        cmp     al,5
290
        jne     illegal_instruction
291
        bt      [format_flags],0
292
        jc      illegal_instruction
293
      extrn_allowed:
31 halyavin 294
        lods    word [esi]
109 heavyiron 295
        cmp     ax,'('
296
        jne     invalid_argument
297
        mov     ebx,esi
298
        lods    dword [esi]
299
        lea     esi,[esi+eax+1]
300
        mov     edx,[free_additional_memory]
301
        lea     eax,[edx+0Ch]
302
        cmp     eax,[structures_buffer]
303
        jae     out_of_memory
304
        mov     [free_additional_memory],eax
305
        mov     byte [edx],81h
306
        mov     [edx+4],ebx
307
        lods    byte [esi]
308
        cmp     al,86h
309
        jne     invalid_argument
310
        lods    byte [esi]
311
        cmp     al,2
312
        jne     invalid_argument
313
        lods    dword [esi]
314
        cmp     eax,0Fh
315
        jb      invalid_use_of_symbol
316
        je      reserved_word_used_as_symbol
317
        inc     esi
318
        mov     ebx,eax
319
        xor     ah,ah
320
        lods    byte [esi]
321
        cmp     al,':'
322
        je      get_extrn_size
323
        dec     esi
324
        cmp     al,11h
325
        jne     extrn_size_ok
326
      get_extrn_size:
31 halyavin 327
        lods    word [esi]
109 heavyiron 328
        cmp     al,11h
329
        jne     invalid_argument
330
      extrn_size_ok:
31 halyavin 331
        mov     [address_symbol],edx
109 heavyiron 332
        movzx   ecx,ah
333
        mov     [edx+8],ecx
334
        xor     eax,eax
335
        xor     edx,edx
336
        xor     ebp,ebp
337
        mov     ch,2
338
        test    [format_flags],8
339
        jz      make_free_label
340
        mov     ch,4
341
        jmp     make_free_label
342
mark_relocation:
31 halyavin 343
        cmp     [value_type],0
109 heavyiron 344
        je      relocation_ok
345
        cmp     [virtual_data],0
346
        jne     relocation_ok
347
        cmp     [output_format],2
348
        je      mark_mz_relocation
349
        cmp     [output_format],3
350
        je      mark_pe_relocation
351
        cmp     [output_format],4
352
        je      mark_coff_relocation
353
        cmp     [output_format],5
354
        je      mark_elf_relocation
355
      relocation_ok:
31 halyavin 356
        ret
109 heavyiron 357
close_pass:
31 halyavin 358
        mov     al,[output_format]
109 heavyiron 359
        cmp     al,3
360
        je      close_pe
361
        cmp     al,4
362
        je      close_coff
363
        cmp     al,5
364
        je      close_elf
365
        ret
366
31 halyavin 367
 
368
        mov     edx,[additional_memory]
109 heavyiron 369
        push    edi
370
        mov     edi,edx
371
        mov     ecx,1Ch shr 2
372
        xor     eax,eax
373
        rep     stos dword [edi]
374
        mov     [free_additional_memory],edi
375
        pop     edi
376
        mov     word [edx+0Ch],0FFFFh
377
        mov     word [edx+10h],1000h
378
        mov     [code_type],16
379
        jmp     instruction_assembled
380
mark_mz_relocation:
31 halyavin 381
        push    eax ebx
109 heavyiron 382
        inc     [number_of_relocations]
383
        mov     ebx,[free_additional_memory]
384
        mov     eax,edi
385
        sub     eax,[code_start]
386
        mov     [ebx],ax
387
        shr     eax,16
388
        shl     ax,12
389
        mov     [ebx+2],ax
390
        cmp     word [ebx],0FFFFh
391
        jne     mz_relocation_ok
392
        inc     word [ebx+2]
393
        sub     word [ebx],10h
394
      mz_relocation_ok:
31 halyavin 395
        add     ebx,4
109 heavyiron 396
        cmp     ebx,[structures_buffer]
397
        jae     out_of_memory
398
        mov     [free_additional_memory],ebx
399
        pop     ebx eax
400
        ret
401
mz_segment:
402
        lods    byte [esi]
403
        cmp     al,2
404
        jne     invalid_argument
405
        lods    dword [esi]
406
        cmp     eax,0Fh
407
        jb      invalid_use_of_symbol
408
        je      reserved_word_used_as_symbol
409
        inc     esi
410
        mov     ebx,eax
411
        mov     eax,edi
412
        sub     eax,[code_start]
413
        mov     ecx,0Fh
414
        add     eax,0Fh
415
        and     eax,1111b
416
        sub     ecx,eax
417
        mov     edx,edi
418
        xor     al,al
419
        rep     stos byte [edi]
420
        mov     dword [org_origin],edi
421
        mov     dword [org_origin+4],0
422
        mov     [org_registers],0
423
        mov     [org_start],edi
424
        mov     eax,edx
425
        call    undefined_data
426
        mov     eax,edi
427
        sub     eax,[code_start]
428
        shr     eax,4
429
        cmp     eax,10000h
430
        jae     value_out_of_range
431
        mov     edx,eax
432
        mov     al,16
433
        cmp     byte [esi],13h
434
        jne     segment_type_ok
435
        inc     esi
436
        lods    byte [esi]
437
      segment_type_ok:
31 halyavin 438
        mov     [code_type],al
109 heavyiron 439
        mov     eax,edx
440
        mov     cx,0100h
441
        xor     edx,edx
442
        xor     ebp,ebp
443
        mov     [address_symbol],edx
444
        jmp     make_free_label
445
mz_entry:
31 halyavin 446
        lods    byte [esi]
109 heavyiron 447
        cmp     al,'('
448
        jne     invalid_argument
449
        call    get_word_value
450
        cmp     [value_type],1
451
        je      initial_cs_ok
452
        cmp     [error_line],0
453
        jne     initial_cs_ok
454
        mov     eax,[current_line]
455
        mov     [error_line],eax
456
        mov     [error],invalid_address
457
      initial_cs_ok:
31 halyavin 458
        mov     edx,[additional_memory]
109 heavyiron 459
        mov     [edx+16h],ax
460
        lods    byte [esi]
461
        cmp     al,':'
462
        jne     invalid_argument
463
        lods    byte [esi]
464
        cmp     al,'('
465
        jne     invalid_argument
466
        ja      invalid_address
467
        call    get_word_value
468
        cmp     [value_type],0
469
        jne     invalid_use_of_symbol
470
        mov     edx,[additional_memory]
471
        mov     [edx+14h],ax
472
        jmp     instruction_assembled
473
mz_stack:
31 halyavin 474
        lods    byte [esi]
109 heavyiron 475
        cmp     al,'('
476
        jne     invalid_argument
477
        call    get_word_value
478
        cmp     byte [esi],':'
479
        je      stack_pointer
480
        cmp     ax,10h
481
        jb      invalid_value
482
        cmp     [value_type],0
483
        jne     invalid_use_of_symbol
484
        mov     edx,[additional_memory]
485
        mov     [edx+10h],ax
486
        jmp     instruction_assembled
487
      stack_pointer:
31 halyavin 488
        cmp     [value_type],1
109 heavyiron 489
        je      initial_ss_ok
490
        cmp     [error_line],0
491
        jne     initial_ss_ok
492
        mov     eax,[current_line]
493
        mov     [error_line],eax
494
        mov     [error],invalid_address
495
      initial_ss_ok:
31 halyavin 496
        mov     edx,[additional_memory]
109 heavyiron 497
        mov     [edx+0Eh],ax
498
        lods    byte [esi]
499
        cmp     al,':'
500
        jne     invalid_argument
501
        lods    byte [esi]
502
        cmp     al,'('
503
        jne     invalid_argument
504
        call    get_word_value
505
        cmp     [value_type],0
506
        jne     invalid_use_of_symbol
507
        mov     edx,[additional_memory]
508
        mov     [edx+10h],ax
509
        bts     [format_flags],4
510
        jmp     instruction_assembled
511
mz_heap:
31 halyavin 512
        cmp     [output_format],2
109 heavyiron 513
        jne     illegal_instruction
514
        lods    byte [esi]
515
        call    get_size_operator
516
        cmp     ah,1
517
        je      invalid_value
518
        cmp     ah,2
519
        ja      invalid_value
520
        cmp     al,'('
521
        jne     invalid_argument
522
        call    get_word_value
523
        cmp     [value_type],0
524
        jne     invalid_use_of_symbol
525
        mov     edx,[additional_memory]
526
        mov     [edx+0Ch],ax
527
        jmp     instruction_assembled
528
write_mz_header:
31 halyavin 529
        mov     edx,[additional_memory]
109 heavyiron 530
        bt      [format_flags],4
531
        jc      mz_stack_ok
532
        mov     eax,[real_code_size]
533
        dec     eax
534
        shr     eax,4
535
        inc     eax
536
        mov     [edx+0Eh],ax
537
        shl     eax,4
538
        movzx   ecx,word [edx+10h]
539
        add     eax,ecx
540
        mov     [real_code_size],eax
541
      mz_stack_ok:
31 halyavin 542
        mov     edi,[free_additional_memory]
109 heavyiron 543
        mov     eax,[number_of_relocations]
544
        shl     eax,2
545
        add     eax,1Ch
546
        sub     edi,eax
547
        xchg    edi,[free_additional_memory]
548
        mov     ecx,0Fh
549
        add     eax,0Fh
550
        and     eax,1111b
551
        sub     ecx,eax
552
        xor     al,al
553
        rep     stos byte [edi]
554
        sub     edi,[free_additional_memory]
555
        mov     ecx,edi
556
        shr     edi,4
557
        mov     word [edx],'MZ'         ; signature
558
        mov     [edx+8],di              ; header size in paragraphs
559
        mov     eax,[number_of_relocations]
560
        mov     [edx+6],ax              ; number of relocation entries
561
        mov     eax,[code_size]
562
        add     eax,ecx
563
        mov     esi,eax
564
        shr     esi,9
565
        and     eax,1FFh
566
        inc     si
567
        or      ax,ax
568
        jnz     mz_size_ok
569
        mov     ax,200h
570
        dec     si
571
      mz_size_ok:
31 halyavin 572
        mov     [edx+2],ax              ; number of bytes in last page
109 heavyiron 573
        mov     [edx+4],si              ; number of pages
574
        mov     eax,[real_code_size]
575
        dec     eax
576
        shr     eax,4
577
        inc     eax
578
        mov     esi,[code_size]
579
        dec     esi
580
        shr     esi,4
581
        inc     esi
582
        sub     eax,esi
583
        mov     [edx+0Ah],ax            ; minimum memory in addition to code
584
        add     [edx+0Ch],ax            ; maximum memory in addition to code
585
        salc
586
        mov     ah,al
587
        or      [edx+0Ch],ax
588
        mov     word [edx+18h],1Ch      ; offset of relocation table
589
        add     [written_size],ecx
590
        call    write
591
        jc      write_failed
592
        ret
593
31 halyavin 594
 
595
        mov     [stub_file],edx
109 heavyiron 596
        or      edx,edx
597
        jnz     stub_from_file
598
        push    esi
599
        mov     edx,edi
600
        xor     eax,eax
601
        mov     ecx,20h
602
        rep     stos dword [edi]
603
        mov     eax,40h+default_stub_end-default_stub
604
        mov     cx,100h+default_stub_end-default_stub
605
        mov     word [edx],'MZ'
606
        mov     word [edx+4],1
607
        mov     word [edx+2],ax
608
        mov     word [edx+8],4
609
        mov     word [edx+0Ah],10h
610
        mov     word [edx+0Ch],0FFFFh
611
        mov     word [edx+10h],cx
612
        mov     word [edx+3Ch],ax
613
        mov     word [edx+18h],40h
614
        lea     edi,[edx+40h]
615
        mov     esi,default_stub
616
        mov     ecx,default_stub_end-default_stub
617
        rep     movs byte [edi],[esi]
618
        pop     esi
619
        jmp     stub_ok
620
      default_stub:
31 halyavin 621
        use16
109 heavyiron 622
        push    cs
623
        pop     ds
624
        mov     dx,stub_message-default_stub
625
        mov     ah,9
626
        int     21h
627
        mov     ax,4C01h
628
        int     21h
629
      stub_message db 'This program cannot be run in DOS mode.',0Dh,0Ah,24h
31 halyavin 630
        rq      1
109 heavyiron 631
      default_stub_end:
31 halyavin 632
        use32
109 heavyiron 633
      stub_from_file:
31 halyavin 634
        push    esi
109 heavyiron 635
        mov     esi,edx
636
        call    open_binary_file
637
        mov     edx,edi
638
        mov     ecx,1Ch
639
        mov     esi,edx
640
        call    read
641
        jc      binary_stub
642
        cmp     word [esi],'MZ'
643
        jne     binary_stub
644
        add     edi,1Ch
645
        movzx   ecx,word [esi+6]
646
        add     ecx,11b
647
        and     ecx,not 11b
648
        add     ecx,(40h-1Ch) shr 2
649
        lea     eax,[edi+ecx*4]
650
        cmp     edi,[display_buffer]
651
        jae     out_of_memory
652
        xor     eax,eax
653
        rep     stos dword [edi]
654
        mov     edx,40h
655
        xchg    dx,[esi+18h]
656
        xor     al,al
657
        call    lseek
658
        movzx   ecx,word [esi+6]
659
        shl     ecx,2
660
        lea     edx,[esi+40h]
661
        call    read
662
        mov     edx,edi
663
        sub     edx,esi
664
        shr     edx,4
665
        xchg    dx,[esi+8]
666
        shl     edx,4
667
        xor     al,al
668
        call    lseek
669
        movzx   ecx,word [esi+4]
670
        dec     ecx
671
        shl     ecx,9
672
        movzx   edx,word [esi+2]
673
        add     ecx,edx
674
        mov     edx,edi
675
        sub     ecx,eax
676
        je      read_stub_code
677
        jb      stub_code_ok
678
        push    ecx
679
        dec     ecx
680
        shr     ecx,3
681
        inc     ecx
682
        shl     ecx,1
683
        lea     eax,[edi+ecx*4]
684
        cmp     eax,[display_buffer]
685
        jae     out_of_memory
686
        xor     eax,eax
687
        rep     stos dword [edi]
688
        pop     ecx
689
     read_stub_code:
31 halyavin 690
        call    read
109 heavyiron 691
     stub_code_ok:
31 halyavin 692
        call    close
109 heavyiron 693
        mov     edx,edi
694
        sub     edx,esi
695
        mov     ax,dx
696
        and     ax,1FFh
697
        mov     [esi+2],ax
698
        dec     edx
699
        shr     edx,9
700
        inc     edx
701
        mov     [esi+4],dx
702
        mov     eax,edi
703
        sub     eax,esi
704
        mov     [esi+3Ch],eax
705
        pop     esi
706
      stub_ok:
31 halyavin 707
        ret
109 heavyiron 708
      binary_stub:
31 halyavin 709
        mov     esi,edi
109 heavyiron 710
        mov     ecx,40h shr 2
711
        xor     eax,eax
712
        rep     stos dword [edi]
713
        mov     al,2
714
        xor     edx,edx
715
        call    lseek
716
        push    eax
717
        xor     al,al
718
        xor     edx,edx
719
        call    lseek
720
        mov     ecx,[esp]
721
        add     ecx,40h+111b
722
        and     ecx,not 111b
723
        mov     ax,cx
724
        and     ax,1FFh
725
        mov     [esi+2],ax
726
        lea     eax,[ecx+1FFh]
727
        shr     eax,9
728
        mov     [esi+4],ax
729
        mov     [esi+3Ch],ecx
730
        sub     ecx,40h
731
        mov     eax,10000h
732
        sub     eax,ecx
733
        jbe     binary_heap_ok
734
        shr     eax,4
735
        mov     [esi+0Ah],ax
736
      binary_heap_ok:
31 halyavin 737
        mov     word [esi],'MZ'
109 heavyiron 738
        mov     word [esi+8],4
739
        mov     ax,0FFFFh
740
        mov     [esi+0Ch],ax
741
        dec     ax
742
        mov     [esi+10h],ax
743
        sub     ax,0Eh
744
        mov     [esi+0Eh],ax
745
        mov     [esi+16h],ax
746
        mov     word [esi+14h],100h
747
        mov     word [esi+18h],40h
748
        mov     eax,[display_buffer]
749
        sub     eax,ecx
750
        cmp     edi,eax
751
        jae     out_of_memory
752
        mov     edx,edi
753
        shr     ecx,2
754
        xor     eax,eax
755
        rep     stos dword [edi]
756
        pop     ecx
757
        call    read
758
        call    close
759
        pop     esi
760
        ret
761
31 halyavin 762
 
763
        xor     edx,edx
109 heavyiron 764
        mov     [machine],14Ch
765
        mov     [subsystem],3
766
        mov     [subsystem_version],3 + 10 shl 16
767
        mov     [image_base],400000h
768
        test    [format_flags],8
769
        jz      pe_settings
770
        mov     [machine],8664h
771
        mov     [subsystem_version],5 + 0 shl 16
772
        mov     [image_base_high],0
773
      pe_settings:
31 halyavin 774
        cmp     byte [esi],84h
109 heavyiron 775
        je      get_stub_name
776
        cmp     byte [esi],80h
777
        je      get_pe_base
778
        cmp     byte [esi],1Bh
779
        jne     pe_settings_ok
780
        lods    byte [esi]
781
        lods    byte [esi]
782
        test    al,80h+40h
783
        jz      subsystem_setting
784
        cmp     al,80h
785
        je      dll_flag
786
        cmp     al,81h
787
        je      wdm_flag
788
        jmp     pe_settings
789
      dll_flag:
31 halyavin 790
        bts     [format_flags],8
109 heavyiron 791
        jc      setting_already_specified
792
        jmp     pe_settings
793
      wdm_flag:
31 halyavin 794
        bts     [format_flags],9
109 heavyiron 795
        jc      setting_already_specified
796
        jmp     pe_settings
797
      subsystem_setting:
31 halyavin 798
        bts     [format_flags],7
109 heavyiron 799
        jc      setting_already_specified
800
        and     ax,3Fh
801
        mov     [subsystem],ax
802
        cmp     byte [esi],'('
803
        jne     pe_settings
804
        inc     esi
805
        cmp     byte [esi],'.'
806
        jne     invalid_value
807
        inc     esi
808
        push    edx
809
        cmp     byte [esi+11],0
810
        jne     invalid_value
811
        cmp     byte [esi+10],2
812
        ja      invalid_value
813
        mov     dx,[esi+8]
814
        cmp     dx,8000h
815
        je      zero_version
816
        mov     eax,[esi+4]
817
        cmp     dx,7
818
        jg      invalid_value
819
        mov     cx,7
820
        sub     cx,dx
821
        mov     eax,[esi+4]
822
        shr     eax,cl
823
        mov     ebx,eax
824
        shr     ebx,24
825
        cmp     bl,100
826
        jae     invalid_value
827
        and     eax,0FFFFFFh
828
        mov     ecx,100
829
        mul     ecx
830
        shrd    eax,edx,24
831
        jnc     version_value_ok
832
        inc     eax
833
      version_value_ok:
31 halyavin 834
        shl     eax,16
109 heavyiron 835
        mov     ax,bx
836
        jmp     subsystem_version_ok
837
      zero_version:
31 halyavin 838
        xor     eax,eax
109 heavyiron 839
      subsystem_version_ok:
31 halyavin 840
        pop     edx
109 heavyiron 841
        add     esi,13
842
        mov     [subsystem_version],eax
843
        jmp     pe_settings
844
      get_pe_base:
31 halyavin 845
        bts     [format_flags],10
109 heavyiron 846
        jc      setting_already_specified
847
        lods    word [esi]
848
        cmp     ah,'('
849
        jne     invalid_argument
850
        cmp     byte [esi],'.'
851
        je      invalid_value
852
        push    edx edi
853
        add     edi,[stub_size]
854
        test    [format_flags],8
855
        jnz     get_pe64_base
856
        call    get_dword_value
857
        mov     [image_base],eax
858
        jmp     pe_base_ok
859
      get_pe64_base:
31 halyavin 860
        call    get_qword_value
109 heavyiron 861
        mov     [image_base],eax
862
        mov     [image_base_high],edx
863
      pe_base_ok:
31 halyavin 864
        pop     edi edx
109 heavyiron 865
        cmp     [value_type],0
866
        jne     invalid_use_of_symbol
867
        cmp     byte [esi],84h
868
        jne     pe_settings_ok
869
      get_stub_name:
31 halyavin 870
        lods    byte [esi]
109 heavyiron 871
        lods    word [esi]
872
        cmp     ax,'('
873
        jne     invalid_argument
874
        lods    dword [esi]
875
        mov     edx,esi
876
        add     esi,eax
877
        inc     esi
878
      pe_settings_ok:
31 halyavin 879
        mov     ebp,[stub_size]
109 heavyiron 880
        or      ebp,ebp
881
        jz      make_pe_stub
882
        cmp     edx,[stub_file]
883
        je      pe_stub_ok
884
        sub     edi,[stub_size]
885
        mov     [code_start],edi
886
      make_pe_stub:
31 halyavin 887
        call    make_stub
109 heavyiron 888
        mov     eax,edi
889
        sub     eax,[code_start]
890
        mov     [stub_size],eax
891
        mov     [code_start],edi
892
        mov     ebp,eax
893
      pe_stub_ok:
31 halyavin 894
        mov     edx,edi
109 heavyiron 895
        mov     ecx,18h+0E0h
896
        test    [format_flags],8
897
        jz      zero_pe_header
898
        add     ecx,10h
899
      zero_pe_header:
31 halyavin 900
        add     ebp,ecx
109 heavyiron 901
        shr     ecx,2
902
        xor     eax,eax
903
        rep     stos dword [edi]
904
        mov     word [edx],'PE'         ; signature
905
        mov     ax,[machine]
906
        mov     word [edx+4],ax
907
        mov     dword [edx+38h],1000h   ; section alignment
908
        mov     dword [edx+3Ch],200h    ; file alignment
909
        mov     word [edx+40h],1        ; OS version
910
        mov     eax,[subsystem_version]
911
        mov     [edx+48h],eax
912
        mov     ax,[subsystem]
913
        mov     [edx+5Ch],ax
914
        cmp     ax,1
915
        jne     pe_alignment_ok
916
        mov     eax,20h
917
        mov     dword [edx+38h],eax
918
        mov     dword [edx+3Ch],eax
919
      pe_alignment_ok:
31 halyavin 920
        mov     word [edx+1Ah],VERSION_MAJOR + VERSION_MINOR shl 8
109 heavyiron 921
        test    [format_flags],8
922
        jnz     init_pe64_specific
923
        mov     dword [edx+14h],0E0h    ; size of optional header
924
        mov     dword [edx+16h],10B010Eh; flags and magic value
925
        mov     eax,[image_base]
926
        mov     dword [edx+34h],eax
927
        mov     dword [edx+60h],1000h   ; stack reserve
928
        mov     dword [edx+64h],1000h   ; stack commit
929
        mov     dword [edx+68h],10000h  ; heap reserve
930
        mov     dword [edx+6Ch],0       ; heap commit
931
        mov     dword [edx+74h],16      ; number of directories
932
        jmp     pe_header_ok
933
      init_pe64_specific:
31 halyavin 934
        mov     dword [edx+14h],0F0h    ; size of optional header
109 heavyiron 935
        mov     dword [edx+16h],20B002Eh; flags and magic value
936
        mov     eax,[image_base]
937
        mov     dword [edx+30h],eax
938
        mov     eax,[image_base_high]
939
        mov     dword [edx+34h],eax
940
        mov     dword [edx+60h],1000h   ; stack reserve
941
        mov     dword [edx+68h],1000h   ; stack commit
942
        mov     dword [edx+70h],10000h  ; heap reserve
943
        mov     dword [edx+78h],0       ; heap commit
944
        mov     dword [edx+84h],16      ; number of directories
945
      pe_header_ok:
31 halyavin 946
        bsf     ecx,[edx+3Ch]
109 heavyiron 947
        imul    ebx,[number_of_sections],28h
948
        or      ebx,ebx
949
        jnz     reserve_space_for_section_headers
950
        mov     ebx,28h
951
      reserve_space_for_section_headers:
31 halyavin 952
        add     ebx,ebp
109 heavyiron 953
        dec     ebx
954
        shr     ebx,cl
955
        inc     ebx
956
        shl     ebx,cl
957
        sub     ebx,ebp
958
        mov     ecx,ebx
959
        mov     eax,[display_buffer]
960
        sub     eax,ecx
961
        cmp     edi,eax
962
        jae     out_of_memory
963
        shr     ecx,2
964
        xor     eax,eax
965
        rep     stos dword [edi]
966
        mov     eax,edi
967
        sub     eax,[code_start]
968
        add     eax,[stub_size]
969
        mov     [edx+54h],eax           ; size of headers
970
        mov     ecx,[edx+38h]
971
        dec     ecx
972
        add     eax,ecx
973
        not     ecx
974
        and     eax,ecx
975
        bt      [format_flags],8
976
        jc      pe_entry_init_ok
977
        mov     [edx+28h],eax           ; entry point rva
978
      pe_entry_init_ok:
31 halyavin 979
        mov     [number_of_sections],0
109 heavyiron 980
        movzx   ebx,word [edx+14h]
981
        lea     ebx,[edx+18h+ebx]
982
        mov     [current_section],ebx
983
        mov     dword [ebx],'.fla'
984
        mov     dword [ebx+4],'t'
985
        mov     [ebx+14h],edi
986
        mov     [ebx+0Ch],eax
987
        mov     dword [ebx+24h],0E0000060h
988
        xor     ecx,ecx
989
        not     eax
990
        not     ecx
991
        add     eax,1
992
        adc     ecx,0
993
        add     eax,edi
994
        adc     ecx,0
995
        test    [format_flags],8
996
        jnz     pe64_org
997
        sub     eax,[edx+34h]
998
        sbb     ecx,0
999
        mov     bl,2
1000
        mov     [code_type],32
1001
        jmp     pe_org_ok
1002
      pe64_org:
31 halyavin 1003
        sub     eax,[edx+30h]
109 heavyiron 1004
        sbb     ecx,[edx+34h]
1005
        mov     bl,4
1006
        mov     [code_type],64
1007
      pe_org_ok:
31 halyavin 1008
        bt      [resolver_flags],0
109 heavyiron 1009
        jc      pe_labels_type_ok
1010
        xor     bl,bl
1011
      pe_labels_type_ok:
1012
        mov     [labels_type],bl
1013
        mov     dword [org_origin],eax
1014
        mov     dword [org_origin+4],ecx
1015
        mov     [org_registers],0
1016
        mov     [org_start],edi
1017
        bt      [format_flags],8
1018
        jnc     dll_flag_ok
1019
        or      dword [edx+16h],2000h
1020
      dll_flag_ok:
31 halyavin 1021
        bt      [format_flags],9
109 heavyiron 1022
        jnc     wdm_flag_ok
1023
        or      word [edx+5Eh],2000h
1024
      wdm_flag_ok:
31 halyavin 1025
        jmp     instruction_assembled
109 heavyiron 1026
pe_section:
31 halyavin 1027
        call    close_pe_section
109 heavyiron 1028
        bts     [format_flags],5
1029
        lea     ecx,[ebx+28h]
1030
        add     edx,[edx+54h]
1031
        sub     edx,[stub_size]
1032
        cmp     ecx,edx
1033
        jbe     new_section
1034
        lea     ebx,[edx-28h]
1035
        or      [next_pass_needed],-1
1036
        push    edi
1037
        mov     edi,ebx
1038
        mov     ecx,28h shr 4
1039
        xor     eax,eax
1040
        rep     stos dword [edi]
1041
        pop     edi
1042
      new_section:
31 halyavin 1043
        mov     [ebx+0Ch],eax
109 heavyiron 1044
        lods    word [esi]
1045
        cmp     ax,'('
1046
        jne     invalid_argument
1047
        lea     edx,[esi+4]
1048
        mov     ecx,[esi]
1049
        lea     esi,[esi+4+ecx+1]
1050
        cmp     ecx,8
1051
        ja      name_too_long
1052
        xor     eax,eax
1053
        mov     [ebx],eax
1054
        mov     [ebx+4],eax
1055
        push    esi edi
1056
        mov     edi,ebx
1057
        mov     esi,edx
1058
        rep     movs byte [edi],[esi]
1059
        pop     edi esi
1060
        mov     dword [ebx+24h],0
1061
        mov     [ebx+14h],edi
1062
        mov     edx,[code_start]
1063
        mov     eax,edi
1064
        xor     ecx,ecx
1065
        sub     eax,[ebx+0Ch]
1066
        sbb     ecx,0
1067
        test    [format_flags],8
1068
        jnz     pe64_section_org
1069
        sub     eax,[edx+34h]
1070
        sbb     ecx,0
1071
        mov     [labels_type],2
1072
        mov     [code_type],32
1073
        bt      [resolver_flags],0
1074
        jc      pe_section_org_ok
1075
        mov     [labels_type],0
1076
        jmp     pe_section_org_ok
1077
      pe64_section_org:
31 halyavin 1078
        sub     eax,[edx+30h]
109 heavyiron 1079
        sbb     ecx,[edx+34h]
1080
        mov     [labels_type],4
1081
        mov     [code_type],64
1082
        bt      [resolver_flags],0
1083
        jc      pe_section_org_ok
1084
        mov     [labels_type],0
1085
      pe_section_org_ok:
31 halyavin 1086
        mov     dword [org_origin],eax
109 heavyiron 1087
        mov     dword [org_origin+4],ecx
1088
        mov     [org_registers],0
1089
        mov     [org_start],edi
1090
      get_section_flags:
31 halyavin 1091
        lods    byte [esi]
109 heavyiron 1092
        cmp     al,1Ah
1093
        je      set_directory
1094
        cmp     al,19h
1095
        je      section_flag
1096
        dec     esi
1097
        jmp     instruction_assembled
1098
      set_directory:
31 halyavin 1099
        movzx   eax,byte [esi]
109 heavyiron 1100
        inc     esi
1101
        mov     ecx,ebx
1102
        test    [format_flags],8
1103
        jnz     pe64_directory
1104
        xchg    ecx,[edx+78h+eax*8]
1105
        mov     dword [edx+78h+eax*8+4],-1
1106
        jmp     pe_directory_set
1107
      pe64_directory:
31 halyavin 1108
        xchg    ecx,[edx+88h+eax*8]
109 heavyiron 1109
        mov     dword [edx+88h+eax*8+4],-1
1110
      pe_directory_set:
31 halyavin 1111
        or      ecx,ecx
109 heavyiron 1112
        jnz     data_already_defined
1113
        push    ebx edx
1114
        call    generate_pe_data
1115
        pop     edx ebx
1116
        jmp     get_section_flags
1117
      section_flag:
31 halyavin 1118
        lods    byte [esi]
109 heavyiron 1119
        cmp     al,9
1120
        je      invalid_argument
1121
        cmp     al,11
1122
        je      invalid_argument
1123
        mov     cl,al
1124
        mov     eax,1
1125
        shl     eax,cl
1126
        test    dword [ebx+24h],eax
1127
        jnz     setting_already_specified
1128
        or      dword [ebx+24h],eax
1129
        jmp     get_section_flags
1130
      close_pe_section:
31 halyavin 1131
        mov     ebx,[current_section]
109 heavyiron 1132
        mov     edx,[code_start]
1133
        mov     eax,edi
1134
        sub     eax,[ebx+14h]
1135
        jnz     finish_section
1136
        bt      [format_flags],5
1137
        jc      finish_section
1138
        mov     eax,[ebx+0Ch]
1139
        ret
1140
      finish_section:
31 halyavin 1141
        mov     [ebx+8],eax
109 heavyiron 1142
        cmp     edi,[undefined_data_end]
1143
        jne     align_section
1144
        cmp     dword [edx+38h],1000h
1145
        jb      align_section
1146
        mov     edi,[undefined_data_start]
1147
      align_section:
31 halyavin 1148
        mov     [undefined_data_end],0
109 heavyiron 1149
        mov     ebp,edi
1150
        sub     ebp,[ebx+14h]
1151
        mov     ecx,[edx+3Ch]
1152
        dec     ecx
1153
        lea     eax,[ebp+ecx]
1154
        not     ecx
1155
        and     eax,ecx
1156
        mov     [ebx+10h],eax
1157
        sub     eax,ebp
1158
        mov     ecx,eax
1159
        xor     al,al
1160
        rep     stos byte [edi]
1161
        mov     eax,[code_start]
1162
        sub     eax,[stub_size]
1163
        sub     [ebx+14h],eax
1164
        mov     eax,[ebx+8]
1165
        or      eax,eax
1166
        jz      udata_ok
1167
        cmp     dword [ebx+10h],0
1168
        jne     udata_ok
1169
        or      byte [ebx+24h],80h
1170
      udata_ok:
31 halyavin 1171
        mov     ecx,[edx+38h]
109 heavyiron 1172
        dec     ecx
1173
        add     eax,ecx
1174
        not     ecx
1175
        and     eax,ecx
1176
        add     eax,[ebx+0Ch]
1177
        add     ebx,28h
1178
        mov     [current_section],ebx
1179
        inc     word [number_of_sections]
1180
        jz      format_limitations_exceeded
1181
        ret
1182
data_directive:
31 halyavin 1183
        cmp     [output_format],3
109 heavyiron 1184
        jne     illegal_instruction
1185
        lods    byte [esi]
1186
        cmp     al,1Ah
1187
        je      predefined_data_type
1188
        cmp     al,'('
1189
        jne     invalid_argument
1190
        call    get_byte_value
1191
        cmp     al,16
1192
        jb      data_type_ok
1193
        jmp     invalid_value
1194
      predefined_data_type:
31 halyavin 1195
        movzx   eax,byte [esi]
109 heavyiron 1196
        inc     esi
1197
      data_type_ok:
31 halyavin 1198
        mov     ebx,[current_section]
109 heavyiron 1199
        mov     ecx,edi
1200
        sub     ecx,[ebx+14h]
1201
        add     ecx,[ebx+0Ch]
1202
        mov     edx,[code_start]
1203
        test    [format_flags],8
1204
        jnz     pe64_data
1205
        xchg    ecx,[edx+78h+eax*8]
1206
        jmp     init_pe_data
1207
      pe64_data:
31 halyavin 1208
        xchg    ecx,[edx+88h+eax*8]
109 heavyiron 1209
      init_pe_data:
31 halyavin 1210
        or      ecx,ecx
109 heavyiron 1211
        jnz     data_already_defined
1212
        call    allocate_structure_data
1213
        mov     word [ebx],data_directive-assembler
1214
        mov     [ebx+2],al
1215
        mov     edx,[current_line]
1216
        mov     [ebx+4],edx
1217
        call    generate_pe_data
1218
        jmp     instruction_assembled
1219
      end_data:
31 halyavin 1220
        cmp     [output_format],3
109 heavyiron 1221
        jne     illegal_instruction
1222
        call    find_structure_data
1223
        jc      unexpected_instruction
1224
        movzx   eax,byte [ebx+2]
1225
        mov     edx,[current_section]
1226
        mov     ecx,edi
1227
        sub     ecx,[edx+14h]
1228
        add     ecx,[edx+0Ch]
1229
        mov     edx,[code_start]
1230
        test    [format_flags],8
1231
        jnz     end_pe64_data
1232
        sub     ecx,[edx+78h+eax*8]
1233
        mov     [edx+78h+eax*8+4],ecx
1234
        jmp     remove_structure_data
1235
      end_pe64_data:
31 halyavin 1236
        sub     ecx,[edx+88h+eax*8]
109 heavyiron 1237
        mov     [edx+88h+eax*8+4],ecx
1238
        jmp     remove_structure_data
1239
pe_entry:
31 halyavin 1240
        lods    byte [esi]
109 heavyiron 1241
        cmp     al,'('
1242
        jne     invalid_argument
1243
        cmp     byte [esi],'.'
1244
        je      invalid_value
1245
        test    [format_flags],8
1246
        jnz     pe64_entry
1247
        call    get_dword_value
1248
        mov     bl,2
1249
        bt      [resolver_flags],0
1250
        jc      check_pe_entry_label_type
1251
        xor     bl,bl
1252
      check_pe_entry_label_type:
1253
        cmp     [value_type],bl
1254
        je      pe_entry_ok
1255
        cmp     [error_line],0
1256
        jne     pe_entry_ok
1257
        mov     edx,[current_line]
1258
        mov     [error_line],edx
1259
        mov     [error],invalid_address
1260
      pe_entry_ok:
31 halyavin 1261
        mov     edx,[code_start]
109 heavyiron 1262
        sub     eax,[edx+34h]
1263
        mov     [edx+28h],eax
1264
        jmp     instruction_assembled
1265
      pe64_entry:
31 halyavin 1266
        call    get_qword_value
109 heavyiron 1267
        mov     bl,4
1268
        bt      [resolver_flags],0
1269
        jc      check_pe64_entry_label_type
1270
        xor     bl,bl
1271
      check_pe64_entry_label_type:
1272
        cmp     [value_type],bl
1273
        je      pe64_entry_type_ok
1274
        cmp     [error_line],0
1275
        jne     pe64_entry_type_ok
1276
        mov     edx,[current_line]
1277
        mov     [error_line],edx
1278
        mov     [error],invalid_address
1279
      pe64_entry_type_ok:
1280
        mov     ecx,[code_start]
1281
        sub     eax,[ecx+30h]
1282
        sbb     edx,[ecx+34h]
1283
        jz      pe64_entry_range_ok
1284
        mov     edx,[current_line]
1285
        mov     [error_line],edx
1286
        mov     [error],value_out_of_range
1287
      pe64_entry_range_ok:
1288
        mov     [ecx+28h],eax
1289
        jmp     instruction_assembled
1290
pe_stack:
31 halyavin 1291
        lods    byte [esi]
109 heavyiron 1292
        cmp     al,'('
1293
        jne     invalid_argument
1294
        cmp     byte [esi],'.'
1295
        je      invalid_value
1296
        test    [format_flags],8
1297
        jnz     pe64_stack
1298
        call    get_dword_value
1299
        cmp     [value_type],0
1300
        jne     invalid_use_of_symbol
1301
        mov     edx,[code_start]
1302
        mov     [edx+60h],eax
1303
        cmp     byte [esi],','
1304
        jne     default_stack_commit
1305
        lods    byte [esi]
1306
        lods    byte [esi]
1307
        cmp     al,'('
1308
        jne     invalid_argument
1309
        cmp     byte [esi],'.'
1310
        je      invalid_value
1311
        call    get_dword_value
1312
        cmp     [value_type],0
1313
        jne     invalid_use_of_symbol
1314
        mov     edx,[code_start]
1315
        mov     [edx+64h],eax
1316
        cmp     eax,[edx+60h]
1317
        ja      value_out_of_range
1318
        jmp     instruction_assembled
1319
      default_stack_commit:
31 halyavin 1320
        mov     dword [edx+64h],1000h
109 heavyiron 1321
        mov     eax,[edx+60h]
1322
        cmp     eax,1000h
1323
        ja      instruction_assembled
1324
        mov     dword [edx+64h],eax
1325
        jmp     instruction_assembled
1326
      pe64_stack:
31 halyavin 1327
        call    get_qword_value
109 heavyiron 1328
        cmp     [value_type],0
1329
        jne     invalid_use_of_symbol
1330
        mov     ecx,[code_start]
1331
        mov     [ecx+60h],eax
1332
        mov     [ecx+64h],edx
1333
        cmp     byte [esi],','
1334
        jne     default_pe64_stack_commit
1335
        lods    byte [esi]
1336
        lods    byte [esi]
1337
        cmp     al,'('
1338
        jne     invalid_argument
1339
        cmp     byte [esi],'.'
1340
        je      invalid_value
1341
        call    get_qword_value
1342
        cmp     [value_type],0
1343
        jne     invalid_use_of_symbol
1344
        mov     ecx,[code_start]
1345
        mov     [ecx+68h],eax
1346
        mov     [ecx+6Ch],edx
1347
        cmp     edx,[ecx+64h]
1348
        ja      value_out_of_range
1349
        jb      instruction_assembled
1350
        cmp     eax,[edx+60h]
1351
        ja      value_out_of_range
1352
        jmp     instruction_assembled
1353
      default_pe64_stack_commit:
31 halyavin 1354
        mov     dword [edx+68h],1000h
109 heavyiron 1355
        cmp     dword [edx+64h],0
1356
        jne     instruction_assembled
1357
        mov     eax,[edx+60h]
1358
        cmp     eax,1000h
1359
        ja      instruction_assembled
1360
        mov     dword [edx+68h],eax
1361
        jmp     instruction_assembled
1362
pe_heap:
31 halyavin 1363
        lods    byte [esi]
109 heavyiron 1364
        cmp     al,'('
1365
        jne     invalid_argument
1366
        cmp     byte [esi],'.'
1367
        je      invalid_value
1368
        test    [format_flags],8
1369
        jnz     pe64_heap
1370
        call    get_dword_value
1371
        cmp     [value_type],0
1372
        jne     invalid_use_of_symbol
1373
        mov     edx,[code_start]
1374
        mov     [edx+68h],eax
1375
        cmp     byte [esi],','
1376
        jne     instruction_assembled
1377
        lods    byte [esi]
1378
        lods    byte [esi]
1379
        cmp     al,'('
1380
        jne     invalid_argument
1381
        cmp     byte [esi],'.'
1382
        je      invalid_value
1383
        call    get_dword_value
1384
        cmp     [value_type],0
1385
        jne     invalid_use_of_symbol
1386
        mov     edx,[code_start]
1387
        mov     [edx+6Ch],eax
1388
        cmp     eax,[edx+68h]
1389
        ja      value_out_of_range
1390
        jmp     instruction_assembled
1391
      pe64_heap:
31 halyavin 1392
        call    get_qword_value
109 heavyiron 1393
        cmp     [value_type],0
1394
        jne     invalid_use_of_symbol
1395
        mov     ecx,[code_start]
1396
        mov     [ecx+70h],eax
1397
        mov     [ecx+74h],edx
1398
        cmp     byte [esi],','
1399
        jne     instruction_assembled
1400
        lods    byte [esi]
1401
        lods    byte [esi]
1402
        cmp     al,'('
1403
        jne     invalid_argument
1404
        cmp     byte [esi],'.'
1405
        je      invalid_value
1406
        call    get_qword_value
1407
        cmp     [value_type],0
1408
        jne     invalid_use_of_symbol
1409
        mov     ecx,[code_start]
1410
        mov     [ecx+78h],eax
1411
        mov     [ecx+7Ch],edx
1412
        cmp     edx,[ecx+74h]
1413
        ja      value_out_of_range
1414
        jb      instruction_assembled
1415
        cmp     eax,[edx+70h]
1416
        ja      value_out_of_range
1417
        jmp     instruction_assembled
1418
mark_pe_relocation:
31 halyavin 1419
        push    eax ebx
109 heavyiron 1420
        mov     al,2
1421
        test    [format_flags],8
1422
        jz      check_pe_relocation_type
1423
        mov     al,4
1424
      check_pe_relocation_type:
1425
        cmp     [value_type],al
1426
        je      pe_relocation_type_ok
1427
        cmp     [error_line],0
1428
        jne     pe_relocation_type_ok
1429
        mov     eax,[current_line]
1430
        mov     [error_line],eax
1431
        mov     [error],invalid_use_of_symbol
1432
      pe_relocation_type_ok:
1433
        mov     ebx,[current_section]
1434
        mov     eax,edi
1435
        sub     eax,[ebx+14h]
1436
        add     eax,[ebx+0Ch]
1437
        mov     ebx,[free_additional_memory]
1438
        inc     [number_of_relocations]
1439
        jz      invalid_use_of_symbol
1440
        mov     [ebx],eax
1441
        add     ebx,4
1442
        cmp     ebx,[structures_buffer]
1443
        jae     out_of_memory
1444
        mov     [free_additional_memory],ebx
1445
        pop     ebx eax
1446
        ret
1447
generate_pe_data:
31 halyavin 1448
        cmp     al,2
109 heavyiron 1449
        je      make_pe_resource
1450
        cmp     al,5
1451
        je      make_pe_fixups
1452
        ret
1453
make_pe_resource:
31 halyavin 1454
        cmp     byte [esi],82h
109 heavyiron 1455
        jne     resource_done
1456
        inc     esi
1457
        lods    word [esi]
1458
        cmp     ax,'('
1459
        jne     invalid_argument
1460
        lods    dword [esi]
1461
        mov     edx,esi
1462
        lea     esi,[esi+eax+1]
1463
        cmp     [next_pass_needed],0
1464
        je      resource_from_file
1465
        cmp     [current_pass],0
1466
        jne     reserve_space_for_resource
1467
        mov     [resource_size],0
1468
      reserve_space_for_resource:
31 halyavin 1469
        add     edi,[resource_size]
109 heavyiron 1470
        cmp     edi,[display_buffer]
1471
        ja      out_of_memory
1472
        jmp     resource_done
1473
      resource_from_file:
31 halyavin 1474
        push    esi
109 heavyiron 1475
        mov     esi,edx
1476
        call    open_binary_file
1477
        push    ebx
1478
        mov     esi,[free_additional_memory]
1479
        lea     eax,[esi+20h]
1480
        cmp     eax,[structures_buffer]
1481
        ja      out_of_memory
1482
        mov     edx,esi
1483
        mov     ecx,20h
1484
        call    read
1485
        jc      invalid_file_format
1486
        xor     eax,eax
1487
        cmp     [esi],eax
1488
        jne     invalid_file_format
1489
        mov     ax,0FFFFh
1490
        cmp     [esi+8],eax
1491
        jne     invalid_file_format
1492
        cmp     [esi+12],eax
1493
        jne     invalid_file_format
1494
        mov     eax,20h
1495
        cmp     [esi+4],eax
1496
        jne     invalid_file_format
1497
      read_resource_headers:
31 halyavin 1498
        test    eax,11b
109 heavyiron 1499
        jz      resource_file_alignment_ok
1500
        mov     edx,4
1501
        and     eax,11b
1502
        sub     edx,eax
1503
        mov     al,1
1504
        call    lseek
1505
      resource_file_alignment_ok:
31 halyavin 1506
        mov     [esi],eax
109 heavyiron 1507
        lea     edx,[esi+12]
1508
        mov     ecx,8
1509
        call    read
1510
        jc      resource_headers_ok
1511
        mov     ecx,[esi+16]
1512
        add     [esi],ecx
1513
        lea     edx,[esi+20]
1514
        sub     ecx,8
1515
        mov     [esi+16],ecx
1516
        lea     eax,[edx+ecx]
1517
        cmp     eax,[structures_buffer]
1518
        ja      out_of_memory
1519
        call    read
1520
        jc      invalid_file_format
1521
        mov     edx,[esi]
1522
        add     edx,[esi+12]
1523
        mov     eax,[esi+16]
1524
        lea     ecx,[esi+20]
1525
        lea     esi,[ecx+eax]
1526
        add     ecx,2
1527
        cmp     word [ecx-2],0FFFFh
1528
        je      resource_header_type_ok
1529
      check_resource_header_type:
31 halyavin 1530
        cmp     ecx,esi
109 heavyiron 1531
        jae     invalid_file_format
1532
        cmp     word [ecx],0
1533
        je      resource_header_type_ok
1534
        add     ecx,2
1535
        jmp     check_resource_header_type
1536
      resource_header_type_ok:
31 halyavin 1537
        add     ecx,2
109 heavyiron 1538
        cmp     word [ecx],0FFFFh
1539
        je      resource_header_name_ok
1540
      check_resource_header_name:
31 halyavin 1541
        cmp     ecx,esi
109 heavyiron 1542
        jae     invalid_file_format
1543
        cmp     word [ecx],0
1544
        je      resource_header_name_ok
1545
        add     ecx,2
1546
        jmp     check_resource_header_name
1547
      resource_header_name_ok:
31 halyavin 1548
        xor     al,al
109 heavyiron 1549
        call    lseek
1550
        jmp     read_resource_headers
1551
      resource_headers_ok:
31 halyavin 1552
        xor     eax,eax
109 heavyiron 1553
        mov     [esi],eax
1554
        mov     [resource_data],edi
1555
        lea     eax,[edi+16]
1556
        cmp     eax,[display_buffer]
1557
        jae     out_of_memory
1558
        xor     eax,eax
1559
        stos    dword [edi]
1560
        call    make_timestamp
1561
        stos    dword [edi]
1562
        xor     eax,eax
1563
        stos    dword [edi]
1564
        stos    dword [edi]
1565
        xor     ebx,ebx
1566
      make_type_name_directory:
31 halyavin 1567
        mov     esi,[free_additional_memory]
109 heavyiron 1568
        xor     edx,edx
1569
      find_type_name:
31 halyavin 1570
        cmp     dword [esi],0
109 heavyiron 1571
        je      type_name_ok
1572
        add     esi,20
1573
        cmp     word [esi],0FFFFh
1574
        je      check_next_type_name
1575
        or      ebx,ebx
1576
        jz      check_this_type_name
1577
        xor     ecx,ecx
1578
      compare_with_previous_type_name:
31 halyavin 1579
        mov     ax,[esi+ecx]
109 heavyiron 1580
        cmp     ax,[ebx+ecx]
1581
        ja      check_this_type_name
1582
        jb      check_next_type_name
1583
        add     ecx,2
1584
        mov     ax,[esi+ecx]
1585
        or      ax,[ebx+ecx]
1586
        jnz     compare_with_previous_type_name
1587
        jmp     check_next_type_name
1588
      check_this_type_name:
31 halyavin 1589
        or      edx,edx
109 heavyiron 1590
        jz      type_name_found
1591
        xor     ecx,ecx
1592
      compare_with_current_type_name:
31 halyavin 1593
        mov     ax,[esi+ecx]
109 heavyiron 1594
        cmp     ax,[edx+ecx]
1595
        ja      check_next_type_name
1596
        jb      type_name_found
1597
        add     ecx,2
1598
        mov     ax,[esi+ecx]
1599
        or      ax,[edx+ecx]
1600
        jnz     compare_with_current_type_name
1601
        jmp     same_type_name
1602
      type_name_found:
31 halyavin 1603
        mov     edx,esi
109 heavyiron 1604
      same_type_name:
31 halyavin 1605
        mov     [esi-16],edi
109 heavyiron 1606
      check_next_type_name:
31 halyavin 1607
        mov     eax,[esi-4]
109 heavyiron 1608
        add     esi,eax
1609
        jmp     find_type_name
1610
      type_name_ok:
31 halyavin 1611
        or      edx,edx
109 heavyiron 1612
        jz      type_name_directory_done
1613
        mov     ebx,edx
1614
      make_type_name_entry:
31 halyavin 1615
        mov     eax,[resource_data]
109 heavyiron 1616
        inc     word [eax+12]
1617
        lea     eax,[edi+8]
1618
        cmp     eax,[display_buffer]
1619
        jae     out_of_memory
1620
        mov     eax,ebx
1621
        stos    dword [edi]
1622
        xor     eax,eax
1623
        stos    dword [edi]
1624
        jmp     make_type_name_directory
1625
      type_name_directory_done:
31 halyavin 1626
        mov     ebx,-1
109 heavyiron 1627
      make_type_id_directory:
31 halyavin 1628
        mov     esi,[free_additional_memory]
109 heavyiron 1629
        mov     edx,10000h
1630
      find_type_id:
31 halyavin 1631
        cmp     dword [esi],0
109 heavyiron 1632
        je      type_id_ok
1633
        add     esi,20
1634
        cmp     word [esi],0FFFFh
1635
        jne     check_next_type_id
1636
        movzx   eax,word [esi+2]
1637
        cmp     eax,ebx
1638
        jle     check_next_type_id
1639
        cmp     eax,edx
1640
        jg      check_next_type_id
1641
        mov     edx,eax
1642
        mov     [esi-16],edi
1643
      check_next_type_id:
31 halyavin 1644
        mov     eax,[esi-4]
109 heavyiron 1645
        add     esi,eax
1646
        jmp     find_type_id
1647
      type_id_ok:
31 halyavin 1648
        cmp     edx,10000h
109 heavyiron 1649
        je      type_id_directory_done
1650
        mov     ebx,edx
1651
      make_type_id_entry:
31 halyavin 1652
        mov     eax,[resource_data]
109 heavyiron 1653
        inc     word [eax+14]
1654
        lea     eax,[edi+8]
1655
        cmp     eax,[display_buffer]
1656
        jae     out_of_memory
1657
        mov     eax,ebx
1658
        stos    dword [edi]
1659
        xor     eax,eax
1660
        stos    dword [edi]
1661
        jmp     make_type_id_directory
1662
      type_id_directory_done:
31 halyavin 1663
        mov     esi,[resource_data]
109 heavyiron 1664
        add     esi,10h
1665
        mov     ecx,[esi-4]
1666
        or      cx,cx
1667
        jz      resource_directories_ok
1668
      make_resource_directories:
31 halyavin 1669
        push    ecx
109 heavyiron 1670
        push    edi
1671
        mov     edx,edi
1672
        sub     edx,[resource_data]
1673
        bts     edx,31
1674
        mov     [esi+4],edx
1675
        lea     eax,[edi+16]
1676
        cmp     eax,[display_buffer]
1677
        jae     out_of_memory
1678
        xor     eax,eax
1679
        stos    dword [edi]
1680
        call    make_timestamp
1681
        stos    dword [edi]
1682
        xor     eax,eax
1683
        stos    dword [edi]
1684
        stos    dword [edi]
1685
        mov     ebp,esi
1686
        xor     ebx,ebx
1687
      make_resource_name_directory:
31 halyavin 1688
        mov     esi,[free_additional_memory]
109 heavyiron 1689
        xor     edx,edx
1690
      find_resource_name:
31 halyavin 1691
        cmp     dword [esi],0
109 heavyiron 1692
        je      resource_name_ok
1693
        push    esi
1694
        cmp     [esi+4],ebp
1695
        jne     check_next_resource_name
1696
        add     esi,20
1697
        call    skip_resource_name
1698
        cmp     word [esi],0FFFFh
1699
        je      check_next_resource_name
1700
        or      ebx,ebx
1701
        jz      check_this_resource_name
1702
        xor     ecx,ecx
1703
      compare_with_previous_resource_name:
31 halyavin 1704
        mov     ax,[esi+ecx]
109 heavyiron 1705
        cmp     ax,[ebx+ecx]
1706
        ja      check_this_resource_name
1707
        jb      check_next_resource_name
1708
        add     ecx,2
1709
        mov     ax,[esi+ecx]
1710
        or      ax,[ebx+ecx]
1711
        jnz     compare_with_previous_resource_name
1712
        jmp     check_next_resource_name
1713
      skip_resource_name:
31 halyavin 1714
        cmp     word [esi],0FFFFh
109 heavyiron 1715
        jne     skip_unicode_string
1716
        add     esi,4
1717
        ret
1718
      skip_unicode_string:
31 halyavin 1719
        add     esi,2
109 heavyiron 1720
        cmp     word [esi-2],0
1721
        jne     skip_unicode_string
1722
        ret
1723
      check_this_resource_name:
31 halyavin 1724
        or      edx,edx
109 heavyiron 1725
        jz      resource_name_found
1726
        xor     ecx,ecx
1727
      compare_with_current_resource_name:
31 halyavin 1728
        mov     ax,[esi+ecx]
109 heavyiron 1729
        cmp     ax,[edx+ecx]
1730
        ja      check_next_resource_name
1731
        jb      resource_name_found
1732
        add     ecx,2
1733
        mov     ax,[esi+ecx]
1734
        or      ax,[edx+ecx]
1735
        jnz     compare_with_current_resource_name
1736
        jmp     same_resource_name
1737
      resource_name_found:
31 halyavin 1738
        mov     edx,esi
109 heavyiron 1739
      same_resource_name:
31 halyavin 1740
        mov     eax,[esp]
109 heavyiron 1741
        mov     [eax+8],edi
1742
      check_next_resource_name:
31 halyavin 1743
        pop     esi
109 heavyiron 1744
        mov     eax,[esi+16]
1745
        lea     esi,[esi+20+eax]
1746
        jmp     find_resource_name
1747
      resource_name_ok:
31 halyavin 1748
        or      edx,edx
109 heavyiron 1749
        jz      resource_name_directory_done
1750
        mov     ebx,edx
1751
      make_resource_name_entry:
31 halyavin 1752
        mov     eax,[esp]
109 heavyiron 1753
        inc     word [eax+12]
1754
        lea     eax,[edi+8]
1755
        cmp     eax,[display_buffer]
1756
        jae     out_of_memory
1757
        mov     eax,ebx
1758
        stos    dword [edi]
1759
        xor     eax,eax
1760
        stos    dword [edi]
1761
        jmp     make_resource_name_directory
1762
      resource_name_directory_done:
31 halyavin 1763
        mov     ebx,-1
109 heavyiron 1764
      make_resource_id_directory:
31 halyavin 1765
        mov     esi,[free_additional_memory]
109 heavyiron 1766
        mov     edx,10000h
1767
      find_resource_id:
31 halyavin 1768
        cmp     dword [esi],0
109 heavyiron 1769
        je      resource_id_ok
1770
        push    esi
1771
        cmp     [esi+4],ebp
1772
        jne     check_next_resource_id
1773
        add     esi,20
1774
        call    skip_resource_name
1775
        cmp     word [esi],0FFFFh
1776
        jne     check_next_resource_id
1777
        movzx   eax,word [esi+2]
1778
        cmp     eax,ebx
1779
        jle     check_next_resource_id
1780
        cmp     eax,edx
1781
        jg      check_next_resource_id
1782
        mov     edx,eax
1783
        mov     eax,[esp]
1784
        mov     [eax+8],edi
1785
      check_next_resource_id:
31 halyavin 1786
        pop     esi
109 heavyiron 1787
        mov     eax,[esi+16]
1788
        lea     esi,[esi+20+eax]
1789
        jmp     find_resource_id
1790
      resource_id_ok:
31 halyavin 1791
        cmp     edx,10000h
109 heavyiron 1792
        je      resource_id_directory_done
1793
        mov     ebx,edx
1794
      make_resource_id_entry:
31 halyavin 1795
        mov     eax,[esp]
109 heavyiron 1796
        inc     word [eax+14]
1797
        lea     eax,[edi+8]
1798
        cmp     eax,[display_buffer]
1799
        jae     out_of_memory
1800
        mov     eax,ebx
1801
        stos    dword [edi]
1802
        xor     eax,eax
1803
        stos    dword [edi]
1804
        jmp     make_resource_id_directory
1805
      resource_id_directory_done:
31 halyavin 1806
        pop     eax
109 heavyiron 1807
        mov     esi,ebp
1808
        pop     ecx
1809
        add     esi,8
1810
        dec     cx
1811
        jnz     make_resource_directories
1812
      resource_directories_ok:
31 halyavin 1813
        shr     ecx,16
109 heavyiron 1814
        jnz     make_resource_directories
1815
        mov     esi,[resource_data]
1816
        add     esi,10h
1817
        movzx   eax,word [esi-4]
1818
        movzx   edx,word [esi-2]
1819
        add     eax,edx
1820
        lea     esi,[esi+eax*8]
1821
        push    edi                     ; address of language directories
1822
      update_resource_directories:
31 halyavin 1823
        cmp     esi,[esp]
109 heavyiron 1824
        je      resource_directories_updated
1825
        add     esi,10h
1826
        mov     ecx,[esi-4]
1827
        or      cx,cx
1828
        jz      language_directories_ok
1829
      make_language_directories:
31 halyavin 1830
        push    ecx
109 heavyiron 1831
        push    edi
1832
        mov     edx,edi
1833
        sub     edx,[resource_data]
1834
        bts     edx,31
1835
        mov     [esi+4],edx
1836
        lea     eax,[edi+16]
1837
        cmp     eax,[display_buffer]
1838
        jae     out_of_memory
1839
        xor     eax,eax
1840
        stos    dword [edi]
1841
        call    make_timestamp
1842
        stos    dword [edi]
1843
        xor     eax,eax
1844
        stos    dword [edi]
1845
        stos    dword [edi]
1846
        mov     ebp,esi
1847
        mov     ebx,-1
1848
      make_language_id_directory:
31 halyavin 1849
        mov     esi,[free_additional_memory]
109 heavyiron 1850
        mov     edx,10000h
1851
      find_language_id:
31 halyavin 1852
        cmp     dword [esi],0
109 heavyiron 1853
        je      language_id_ok
1854
        push    esi
1855
        cmp     [esi+8],ebp
1856
        jne     check_next_language_id
1857
        add     esi,20
1858
        mov     eax,esi
1859
        call    skip_resource_name
1860
        call    skip_resource_name
1861
        neg     eax
1862
        add     eax,esi
1863
        and     eax,11b
1864
        add     esi,eax
1865
      get_language_id:
31 halyavin 1866
        movzx   eax,word [esi+6]
109 heavyiron 1867
        cmp     eax,ebx
1868
        jle     check_next_language_id
1869
        cmp     eax,edx
1870
        jge     check_next_language_id
1871
        mov     edx,eax
1872
        mov     eax,[esp]
1873
        mov     [current_offset],eax
1874
      check_next_language_id:
31 halyavin 1875
        pop     esi
109 heavyiron 1876
        mov     eax,[esi+16]
1877
        lea     esi,[esi+20+eax]
1878
        jmp     find_language_id
1879
      language_id_ok:
31 halyavin 1880
        cmp     edx,10000h
109 heavyiron 1881
        je      language_id_directory_done
1882
        mov     ebx,edx
1883
      make_language_id_entry:
31 halyavin 1884
        mov     eax,[esp]
109 heavyiron 1885
        inc     word [eax+14]
1886
        lea     eax,[edi+8]
1887
        cmp     eax,[display_buffer]
1888
        jae     out_of_memory
1889
        mov     eax,ebx
1890
        stos    dword [edi]
1891
        mov     eax,[current_offset]
1892
        stos    dword [edi]
1893
        jmp     make_language_id_directory
1894
      language_id_directory_done:
31 halyavin 1895
        pop     eax
109 heavyiron 1896
        mov     esi,ebp
1897
        pop     ecx
1898
        add     esi,8
1899
        dec     cx
1900
        jnz     make_language_directories
1901
      language_directories_ok:
31 halyavin 1902
        shr     ecx,16
109 heavyiron 1903
        jnz     make_language_directories
1904
        jmp     update_resource_directories
1905
      resource_directories_updated:
31 halyavin 1906
        mov     esi,[resource_data]
109 heavyiron 1907
        push    edi
1908
      make_name_strings:
31 halyavin 1909
        add     esi,10h
109 heavyiron 1910
        movzx   eax,word [esi-2]
1911
        movzx   ecx,word [esi-4]
1912
        add     eax,ecx
1913
        lea     eax,[esi+eax*8]
1914
        push    eax
1915
        or      ecx,ecx
1916
        jz      string_entries_processed
1917
      process_string_entries:
31 halyavin 1918
        push    ecx
109 heavyiron 1919
        mov     edx,edi
1920
        sub     edx,[resource_data]
1921
        bts     edx,31
1922
        xchg    [esi],edx
1923
        mov     ebx,edi
1924
        xor     ax,ax
1925
        stos    word [edi]
1926
      copy_string_data:
31 halyavin 1927
        lea     eax,[edi+2]
109 heavyiron 1928
        cmp     eax,[display_buffer]
1929
        jae     out_of_memory
1930
        mov     ax,[edx]
1931
        or      ax,ax
1932
        jz      string_data_copied
1933
        stos    word [edi]
1934
        inc     word [ebx]
1935
        add     edx,2
1936
        jmp     copy_string_data
1937
      string_data_copied:
31 halyavin 1938
        add     esi,8
109 heavyiron 1939
        pop     ecx
1940
        loop    process_string_entries
1941
      string_entries_processed:
31 halyavin 1942
        pop     esi
109 heavyiron 1943
        cmp     esi,[esp]
1944
        jb      make_name_strings
1945
        mov     eax,edi
1946
        sub     eax,[resource_data]
1947
        test    al,11b
1948
        jz      resource_strings_alignment_ok
1949
        xor     ax,ax
1950
        stos    word [edi]
1951
      resource_strings_alignment_ok:
31 halyavin 1952
        pop     edx
109 heavyiron 1953
        pop     ebx                     ; address of language directories
1954
        mov     ebp,edi
1955
      update_language_directories:
31 halyavin 1956
        add     ebx,10h
109 heavyiron 1957
        movzx   eax,word [ebx-2]
1958
        movzx   ecx,word [ebx-4]
1959
        add     ecx,eax
1960
      make_data_records:
31 halyavin 1961
        push    ecx
109 heavyiron 1962
        mov     esi,edi
1963
        sub     esi,[resource_data]
1964
        xchg    esi,[ebx+4]
1965
        lea     eax,[edi+16]
1966
        cmp     eax,[display_buffer]
1967
        jae     out_of_memory
1968
        mov     eax,esi
1969
        stos    dword [edi]
1970
        mov     eax,[esi+12]
1971
        stos    dword [edi]
1972
        xor     eax,eax
1973
        stos    dword [edi]
1974
        stos    dword [edi]
1975
        pop     ecx
1976
        add     ebx,8
1977
        loop    make_data_records
1978
        cmp     ebx,edx
1979
        jb      update_language_directories
1980
        pop     ebx                     ; file handle
1981
        mov     esi,ebp
1982
        mov     ebp,edi
1983
      update_data_records:
31 halyavin 1984
        push    ebp
109 heavyiron 1985
        mov     ecx,edi
1986
        mov     eax,[current_section]
1987
        sub     ecx,[eax+14h]
1988
        add     ecx,[eax+0Ch]
1989
        xchg    ecx,[esi]
1990
        mov     edx,[ecx]
1991
        xor     al,al
1992
        call    lseek
1993
        mov     edx,edi
1994
        mov     ecx,[esi+4]
1995
        add     edi,ecx
1996
        cmp     edi,[display_buffer]
1997
        ja      out_of_memory
1998
        call    read
1999
        mov     eax,edi
2000
        sub     eax,[resource_data]
2001
        and     eax,11b
2002
        jz      resource_data_alignment_ok
2003
        mov     ecx,4
2004
        sub     ecx,eax
2005
        xor     al,al
2006
        rep     stos byte [edi]
2007
      resource_data_alignment_ok:
31 halyavin 2008
        pop     ebp
109 heavyiron 2009
        add     esi,16
2010
        cmp     esi,ebp
2011
        jb      update_data_records
2012
        pop     esi
2013
        call    close
2014
        mov     eax,edi
2015
        sub     eax,[resource_data]
2016
        mov     [resource_size],eax
2017
      resource_done:
31 halyavin 2018
        ret
109 heavyiron 2019
make_pe_fixups:
31 halyavin 2020
        bts     [resolver_flags],0
109 heavyiron 2021
        jc      pe_relocatable_ok
2022
        or      [next_pass_needed],-1
2023
     pe_relocatable_ok:
2024
        push    esi
2025
        mov     ecx,[number_of_relocations]
2026
        mov     esi,[free_additional_memory]
2027
        mov     eax,ecx
2028
        shl     eax,2
2029
        sub     esi,eax
2030
        mov     [free_additional_memory],esi
2031
        or      [number_of_relocations],-1
2032
        xor     edx,edx
2033
        mov     ebp,edi
2034
      make_fixups:
31 halyavin 2035
        cmp     [esi],edx
109 heavyiron 2036
        jb      store_fixup
2037
        mov     eax,edi
2038
        sub     eax,ebp
2039
        test    eax,11b
2040
        jz      fixups_block
2041
        xor     ax,ax
2042
        stos    word [edi]
2043
        add     dword [ebx],2
2044
      fixups_block:
31 halyavin 2045
        mov     eax,edx
109 heavyiron 2046
        add     edx,1000h
2047
        cmp     [esi],edx
2048
        jae     fixups_block
2049
        stos    dword [edi]
2050
        mov     ebx,edi
2051
        mov     eax,8
2052
        stos    dword [edi]
2053
      store_fixup:
31 halyavin 2054
        jecxz   fixups_done
109 heavyiron 2055
        add     dword [ebx],2
2056
        mov     eax,[esi]
2057
        and     ax,0FFFh
2058
        test    [format_flags],8
2059
        jnz     fixup_64bit
2060
        or      ax,3000h
2061
        jmp     fixup_ok
2062
      fixup_64bit:
31 halyavin 2063
        or      ax,0A000h
109 heavyiron 2064
      fixup_ok:
31 halyavin 2065
        stos    word [edi]
109 heavyiron 2066
        add     esi,4
2067
        loop    make_fixups
2068
      fixups_done:
31 halyavin 2069
        pop     esi
109 heavyiron 2070
        ret
2071
close_pe:
31 halyavin 2072
        call    close_pe_section
109 heavyiron 2073
        mov     edx,[code_start]
2074
        mov     [edx+50h],eax
2075
        call    make_timestamp
2076
        mov     edx,[code_start]
2077
        mov     [edx+8],eax
2078
        mov     eax,[number_of_relocations]
2079
        cmp     eax,-1
2080
        je      pe_relocations_ok
2081
        shl     eax,2
2082
        sub     [free_additional_memory],eax
2083
        btr     [resolver_flags],0
2084
        jnc     pe_relocations_ok
2085
        or      [next_pass_needed],-1
2086
      pe_relocations_ok:
2087
        mov     eax,[number_of_sections]
2088
        mov     [edx+6],ax
2089
        imul    eax,28h
2090
        movzx   ecx,word [edx+14h]
2091
        lea     eax,[eax+18h+ecx]
2092
        add     eax,[stub_size]
2093
        mov     ecx,[edx+3Ch]
2094
        dec     ecx
2095
        add     eax,ecx
2096
        not     ecx
2097
        and     eax,ecx
2098
        cmp     eax,[edx+54h]
2099
        je      pe_sections_ok
2100
        or      [next_pass_needed],-1
2101
      pe_sections_ok:
31 halyavin 2102
        xor     ecx,ecx
109 heavyiron 2103
        add     edx,78h
2104
        test    [format_flags],8
2105
        jz      process_directories
2106
        add     edx,10h
2107
      process_directories:
31 halyavin 2108
        mov     eax,[edx+ecx*8]
109 heavyiron 2109
        or      eax,eax
2110
        jz      directory_ok
2111
        cmp     dword [edx+ecx*8+4],-1
2112
        jne     directory_ok
2113
      section_data:
31 halyavin 2114
        mov     ebx,[edx+ecx*8]
109 heavyiron 2115
        mov     eax,[ebx+0Ch]
2116
        mov     [edx+ecx*8],eax         ; directory rva
2117
        mov     eax,[ebx+8]
2118
        mov     [edx+ecx*8+4],eax       ; directory size
2119
      directory_ok:
31 halyavin 2120
        inc     cl
109 heavyiron 2121
        cmp     cl,10h
2122
        jb      process_directories
2123
        mov     ebx,[code_start]
2124
        sub     ebx,[stub_size]
2125
        mov     ecx,edi
2126
        sub     ecx,ebx
2127
        mov     ebp,ecx
2128
        shr     ecx,1
2129
        xor     eax,eax
2130
        cdq
2131
      calculate_checksum:
31 halyavin 2132
        mov     dx,[ebx]
109 heavyiron 2133
        add     eax,edx
2134
        mov     dx,ax
2135
        shr     eax,16
2136
        add     eax,edx
2137
        add     ebx,2
2138
        loop    calculate_checksum
2139
        add     eax,ebp
2140
        mov     ebx,[code_start]
2141
        mov     [ebx+58h],eax
2142
        ret
2143
31 halyavin 2144
 
2145
        mov     eax,[additional_memory]
109 heavyiron 2146
        mov     [symbols_stream],eax
2147
        mov     ebx,eax
2148
        add     eax,20h
2149
        cmp     eax,[structures_buffer]
2150
        jae     out_of_memory
2151
        mov     [free_additional_memory],eax
2152
        xor     eax,eax
2153
        mov     [ebx],al
2154
        mov     [ebx+4],eax
2155
        mov     [ebx+8],edi
2156
        mov     al,4
2157
        mov     [ebx+10h],eax
2158
        mov     al,60h
2159
        bt      [format_flags],0
2160
        jnc     flat_section_flags_ok
2161
        or      eax,0E0000000h
2162
      flat_section_flags_ok:
31 halyavin 2163
        mov     dword [ebx+14h],eax
109 heavyiron 2164
        mov     [current_section],ebx
2165
        mov     [number_of_sections],0
2166
        mov     dword [org_origin],edi
2167
        mov     dword [org_origin+4],0
2168
        mov     [org_registers],0
2169
        mov     [org_start],edi
2170
        mov     [org_symbol],ebx
2171
        mov     [labels_type],2
2172
        mov     [code_type],32
2173
        test    [format_flags],8
2174
        jz      instruction_assembled
2175
        mov     [labels_type],4
2176
        mov     [code_type],64
2177
        jmp     instruction_assembled
2178
coff_section:
31 halyavin 2179
        call    close_coff_section
109 heavyiron 2180
        mov     ebx,[free_additional_memory]
2181
        lea     eax,[ebx+20h]
2182
        cmp     eax,[structures_buffer]
2183
        jae     out_of_memory
2184
        mov     [free_additional_memory],eax
2185
        mov     [current_section],ebx
2186
        inc     [number_of_sections]
2187
        xor     eax,eax
2188
        mov     [ebx],al
2189
        mov     [ebx+8],edi
2190
        mov     dword [org_origin],edi
2191
        mov     dword [org_origin+4],0
2192
        mov     [org_registers],0
2193
        mov     [org_start],edi
2194
        mov     [org_symbol],ebx
2195
        mov     [labels_type],2
2196
        test    [format_flags],8
2197
        jz      coff_labels_type_ok
2198
        mov     [labels_type],4
2199
      coff_labels_type_ok:
31 halyavin 2200
        mov     [ebx+10h],eax
109 heavyiron 2201
        mov     [ebx+14h],eax
2202
        lods    word [esi]
2203
        cmp     ax,'('
2204
        jne     invalid_argument
2205
        mov     [ebx+4],esi
2206
        mov     ecx,[esi]
2207
        lea     esi,[esi+4+ecx+1]
2208
        cmp     ecx,8
2209
        ja      name_too_long
2210
      coff_section_flags:
31 halyavin 2211
        cmp     byte [esi],1Ch
109 heavyiron 2212
        je      coff_section_alignment
2213
        cmp     byte [esi],19h
2214
        jne     coff_section_settings_ok
2215
        inc     esi
2216
        lods    byte [esi]
2217
        bt      [format_flags],0
2218
        jc      coff_section_flag_ok
2219
        cmp     al,7
2220
        ja      invalid_argument
2221
      coff_section_flag_ok:
31 halyavin 2222
        mov     cl,al
109 heavyiron 2223
        mov     eax,1
2224
        shl     eax,cl
2225
        test    dword [ebx+14h],eax
2226
        jnz     setting_already_specified
2227
        or      dword [ebx+14h],eax
2228
        jmp     coff_section_flags
2229
      coff_section_alignment:
31 halyavin 2230
        bt      [format_flags],0
109 heavyiron 2231
        jnc     invalid_argument
2232
        inc     esi
2233
        lods    byte [esi]
2234
        or      al,al
2235
        jnz     invalid_argument
2236
        lods    byte [esi]
2237
        cmp     al,'('
2238
        jne     invalid_argument
2239
        cmp     byte [esi],'.'
2240
        je      invalid_value
2241
        push    ebx
2242
        call    get_dword_value
2243
        pop     ebx
2244
        cmp     [value_type],0
2245
        jne     invalid_use_of_symbol
2246
        mov     edx,eax
2247
        dec     edx
2248
        test    eax,edx
2249
        jnz     invalid_value
2250
        or      eax,eax
2251
        jz      invalid_value
2252
        cmp     eax,2000h
2253
        ja      invalid_value
2254
        bsf     edx,eax
2255
        inc     edx
2256
        shl     edx,20
2257
        or      [ebx+14h],edx
2258
        xchg    [ebx+10h],eax
2259
        or      eax,eax
2260
        jnz     setting_already_specified
2261
        jmp     coff_section_flags
2262
      coff_section_settings_ok:
31 halyavin 2263
        cmp     dword [ebx+10h],0
109 heavyiron 2264
        jne     instruction_assembled
2265
        mov     dword [ebx+10h],4
2266
        bt      [format_flags],0
2267
        jnc     instruction_assembled
2268
        or      dword [ebx+14h],300000h
2269
        jmp     instruction_assembled
2270
      close_coff_section:
31 halyavin 2271
        mov     ebx,[current_section]
109 heavyiron 2272
        mov     eax,edi
2273
        mov     edx,[ebx+8]
2274
        sub     eax,edx
2275
        mov     [ebx+0Ch],eax
2276
        xor     eax,eax
2277
        xchg    [undefined_data_end],eax
2278
        cmp     eax,edi
2279
        jne     coff_section_ok
2280
        cmp     edx,[undefined_data_start]
2281
        jne     coff_section_ok
2282
        mov     edi,edx
2283
        or      byte [ebx+14h],80h
2284
      coff_section_ok:
31 halyavin 2285
        ret
109 heavyiron 2286
mark_coff_relocation:
31 halyavin 2287
        cmp     [value_type],3
109 heavyiron 2288
        je      coff_relocation_relative
2289
        push    ebx eax
2290
        test    [format_flags],8
2291
        jnz     coff_64bit_relocation
2292
        mov     al,6
2293
        jmp     coff_relocation
2294
      coff_64bit_relocation:
31 halyavin 2295
        mov     al,1
109 heavyiron 2296
        cmp     [value_type],4
2297
        je      coff_relocation
2298
        mov     al,2
2299
        jmp     coff_relocation
2300
      coff_relocation_relative:
31 halyavin 2301
        push    ebx
109 heavyiron 2302
        bt      [format_flags],0
2303
        jnc     relative_ok
2304
        mov     ebx,[current_section]
2305
        mov     ebx,[ebx+8]
2306
        sub     ebx,edi
2307
        sub     eax,ebx
2308
        add     eax,4
2309
      relative_ok:
31 halyavin 2310
        push    eax
109 heavyiron 2311
        mov     al,20
2312
        test    [format_flags],8
2313
        jnz     relative_coff_64bit_relocation
2314
        cmp     [labels_type],2
2315
        jne     invalid_use_of_symbol
2316
        jmp     coff_relocation
2317
      relative_coff_64bit_relocation:
31 halyavin 2318
        mov     al,4
109 heavyiron 2319
        cmp     [labels_type],4
2320
        jne     invalid_use_of_symbol
2321
      coff_relocation:
31 halyavin 2322
        mov     ebx,[free_additional_memory]
109 heavyiron 2323
        add     ebx,0Ch
2324
        cmp     ebx,[structures_buffer]
2325
        jae     out_of_memory
2326
        mov     [free_additional_memory],ebx
2327
        mov     byte [ebx-0Ch],al
2328
        mov     eax,[current_section]
2329
        mov     eax,[eax+8]
2330
        neg     eax
2331
        add     eax,edi
2332
        mov     [ebx-0Ch+4],eax
2333
        mov     eax,[symbol_identifier]
2334
        mov     [ebx-0Ch+8],eax
2335
        pop     eax ebx
2336
        ret
2337
close_coff:
31 halyavin 2338
        call    close_coff_section
109 heavyiron 2339
        cmp     [next_pass_needed],0
2340
        je      coff_closed
2341
        mov     eax,[symbols_stream]
2342
        mov     [free_additional_memory],eax
2343
      coff_closed:
31 halyavin 2344
        ret
109 heavyiron 2345
coff_formatter:
31 halyavin 2346
        sub     edi,[code_start]
109 heavyiron 2347
        mov     [code_size],edi
2348
        call    prepare_default_section
2349
        mov     edi,[free_additional_memory]
2350
        mov     ebx,edi
2351
        mov     ecx,28h shr 2
2352
        imul    ecx,[number_of_sections]
2353
        add     ecx,14h shr 2
2354
        lea     eax,[edi+ecx*4]
2355
        cmp     eax,[structures_buffer]
2356
        jae     out_of_memory
2357
        xor     eax,eax
2358
        rep     stos dword [edi]
2359
        mov     word [ebx],14Ch
2360
        test    [format_flags],8
2361
        jz      coff_magic_ok
2362
        mov     word [ebx],8664h
2363
      coff_magic_ok:
31 halyavin 2364
        mov     word [ebx+12h],104h
109 heavyiron 2365
        bt      [format_flags],0
2366
        jnc     coff_flags_ok
2367
        or      byte [ebx+12h],80h
2368
      coff_flags_ok:
31 halyavin 2369
        push    ebx
109 heavyiron 2370
        call    make_timestamp
2371
        pop     ebx
2372
        mov     [ebx+4],eax
2373
        mov     eax,[number_of_sections]
2374
        mov     [ebx+2],ax
2375
        mov     esi,[symbols_stream]
2376
        xor     eax,eax
2377
        xor     ecx,ecx
2378
      enumerate_symbols:
31 halyavin 2379
        cmp     esi,[free_additional_memory]
109 heavyiron 2380
        je      symbols_enumerated
2381
        mov     dl,[esi]
2382
        or      dl,dl
2383
        jz      enumerate_section
2384
        cmp     dl,80h
2385
        je      enumerate_public
2386
        ja      enumerate_extrn
2387
        add     esi,0Ch
2388
        jmp     enumerate_symbols
2389
      enumerate_section:
31 halyavin 2390
        mov     edx,eax
109 heavyiron 2391
        shl     edx,8
2392
        mov     [esi],edx
2393
        inc     eax
2394
        inc     ecx
2395
        mov     [esi+1Eh],cx
2396
        add     esi,20h
2397
        jmp     enumerate_symbols
2398
      enumerate_public:
31 halyavin 2399
        mov     edx,eax
109 heavyiron 2400
        shl     edx,8
2401
        mov     dl,80h
2402
        mov     [esi],edx
2403
        mov     edx,[esi+8]
2404
        add     esi,10h
2405
        inc     eax
2406
        cmp     byte [edx+11],2
2407
        jne     enumerate_symbols
2408
        mov     edx,[edx+20]
2409
        cmp     byte [edx],81h
2410
        jne     enumerate_symbols
2411
        inc     eax
2412
        jmp     enumerate_symbols
2413
      enumerate_extrn:
31 halyavin 2414
        mov     edx,eax
109 heavyiron 2415
        shl     edx,8
2416
        mov     dl,81h
2417
        mov     [esi],edx
2418
        add     esi,0Ch
2419
        inc     eax
2420
        jmp     enumerate_symbols
2421
      prepare_default_section:
31 halyavin 2422
        mov     ebx,[symbols_stream]
109 heavyiron 2423
        cmp     dword [ebx+0Ch],0
2424
        jne     default_section_ok
2425
        cmp     [number_of_sections],0
2426
        je      default_section_ok
2427
        mov     edx,ebx
2428
      find_references_to_default_section:
31 halyavin 2429
        cmp     ebx,[free_additional_memory]
109 heavyiron 2430
        jne     check_reference
2431
        add     [symbols_stream],20h
2432
        ret
2433
      check_reference:
31 halyavin 2434
        mov     al,[ebx]
109 heavyiron 2435
        or      al,al
2436
        jz      skip_other_section
2437
        cmp     al,80h
2438
        je      check_public_reference
2439
        ja      next_reference
2440
        cmp     edx,[ebx+8]
2441
        je      default_section_ok
2442
      next_reference:
31 halyavin 2443
        add     ebx,0Ch
109 heavyiron 2444
        jmp     find_references_to_default_section
2445
      check_public_reference:
31 halyavin 2446
        mov     eax,[ebx+8]
109 heavyiron 2447
        add     ebx,10h
2448
        test    byte [eax+8],1
2449
        jz      find_references_to_default_section
2450
        mov     cx,[current_pass]
2451
        cmp     cx,[eax+16]
2452
        jne     find_references_to_default_section
2453
        cmp     edx,[eax+20]
2454
        je      default_section_ok
2455
        jmp     find_references_to_default_section
2456
      skip_other_section:
31 halyavin 2457
        add     ebx,20h
109 heavyiron 2458
        jmp     find_references_to_default_section
2459
      default_section_ok:
31 halyavin 2460
        inc     [number_of_sections]
109 heavyiron 2461
        ret
2462
      symbols_enumerated:
31 halyavin 2463
        mov     [ebx+0Ch],eax
109 heavyiron 2464
        mov     ebp,edi
2465
        sub     ebp,ebx
2466
        push    ebp
2467
        lea     edi,[ebx+14h]
2468
        mov     esi,[symbols_stream]
2469
      find_section:
31 halyavin 2470
        cmp     esi,[free_additional_memory]
109 heavyiron 2471
        je      sections_finished
2472
        mov     al,[esi]
2473
        or      al,al
2474
        jz      section_found
2475
        add     esi,0Ch
2476
        cmp     al,80h
2477
        jne     find_section
2478
        add     esi,4
2479
        jmp     find_section
2480
      section_found:
31 halyavin 2481
        push    esi edi
109 heavyiron 2482
        mov     esi,[esi+4]
2483
        or      esi,esi
2484
        jz      default_section
2485
        mov     ecx,[esi]
2486
        add     esi,4
2487
        rep     movs byte [edi],[esi]
2488
        jmp     section_name_ok
2489
      default_section:
31 halyavin 2490
        mov     al,'.'
109 heavyiron 2491
        stos    byte [edi]
2492
        mov     eax,'flat'
2493
        stos    dword [edi]
2494
      section_name_ok:
31 halyavin 2495
        pop     edi esi
109 heavyiron 2496
        mov     eax,[esi+0Ch]
2497
        mov     [edi+10h],eax
2498
        mov     eax,[esi+14h]
2499
        mov     [edi+24h],eax
2500
        test    al,80h
2501
        jnz     section_ptr_ok
2502
        mov     eax,[esi+8]
2503
        sub     eax,[code_start]
2504
        add     eax,ebp
2505
        mov     [edi+14h],eax
2506
      section_ptr_ok:
31 halyavin 2507
        mov     ebx,[code_start]
109 heavyiron 2508
        mov     edx,[code_size]
2509
        add     ebx,edx
2510
        add     edx,ebp
2511
        xor     ecx,ecx
2512
        add     esi,20h
2513
      find_relocations:
31 halyavin 2514
        cmp     esi,[free_additional_memory]
109 heavyiron 2515
        je      section_relocations_done
2516
        mov     al,[esi]
2517
        or      al,al
2518
        jz      section_relocations_done
2519
        cmp     al,80h
2520
        jb      add_relocation
2521
        ja      next_relocation
2522
        add     esi,10h
2523
        jmp     find_relocations
2524
      add_relocation:
31 halyavin 2525
        lea     eax,[ebx+0Ah]
109 heavyiron 2526
        cmp     eax,[display_buffer]
2527
        ja      out_of_memory
2528
        mov     eax,[esi+4]
2529
        mov     [ebx],eax
2530
        mov     eax,[esi+8]
2531
        mov     eax,[eax]
2532
        shr     eax,8
2533
        mov     [ebx+4],eax
2534
        movzx   ax,byte [esi]
2535
        mov     [ebx+8],ax
2536
        add     ebx,0Ah
2537
        inc     ecx
2538
      next_relocation:
31 halyavin 2539
        add     esi,0Ch
109 heavyiron 2540
        jmp     find_relocations
2541
      section_relocations_done:
31 halyavin 2542
        cmp     ecx,10000h
109 heavyiron 2543
        jb      section_relocations_count_16bit
2544
        bt      [format_flags],0
2545
        jnc     format_limitations_exceeded
2546
        mov     word [edi+20h],0FFFFh
2547
        or      dword [edi+24h],1000000h
2548
        mov     [edi+18h],edx
2549
        push    esi edi
2550
        push    ecx
2551
        lea     esi,[ebx-1]
2552
        add     ebx,0Ah
2553
        lea     edi,[ebx-1]
2554
        imul    ecx,0Ah
2555
        std
2556
        rep     movs byte [edi],[esi]
2557
        cld
2558
        pop     ecx
2559
        inc     esi
2560
        inc     ecx
2561
        mov     [esi],ecx
2562
        xor     eax,eax
2563
        mov     [esi+4],eax
2564
        mov     [esi+8],ax
2565
        pop     edi esi
2566
        jmp     section_relocations_ok
2567
      section_relocations_count_16bit:
31 halyavin 2568
        mov     [edi+20h],cx
109 heavyiron 2569
        jcxz    section_relocations_ok
2570
        mov     [edi+18h],edx
2571
      section_relocations_ok:
31 halyavin 2572
        sub     ebx,[code_start]
109 heavyiron 2573
        mov     [code_size],ebx
2574
        add     edi,28h
2575
        jmp     find_section
2576
      sections_finished:
31 halyavin 2577
        mov     edx,[free_additional_memory]
109 heavyiron 2578
        mov     ebx,[code_size]
2579
        add     ebp,ebx
2580
        mov     [edx+8],ebp
2581
        add     ebx,[code_start]
2582
        mov     edi,ebx
2583
        mov     ecx,[edx+0Ch]
2584
        imul    ecx,12h shr 1
2585
        xor     eax,eax
2586
        shr     ecx,1
2587
        jnc     zero_symbols_table
2588
        stos    word [edi]
2589
      zero_symbols_table:
31 halyavin 2590
        rep     stos dword [edi]
109 heavyiron 2591
        mov     edx,edi
2592
        stos    dword [edi]
2593
        mov     esi,[symbols_stream]
2594
      make_symbols_table:
2595
        cmp     esi,[free_additional_memory]
2596
        je      symbols_table_ok
2597
        mov     al,[esi]
2598
        cmp     al,80h
2599
        je      add_public_symbol
2600
        ja      add_extrn_symbol
2601
        or      al,al
2602
        jz      add_section_symbol
2603
        add     esi,0Ch
2604
        jmp     make_symbols_table
2605
      add_section_symbol:
31 halyavin 2606
        call    store_symbol_name
109 heavyiron 2607
        movzx   eax,word [esi+1Eh]
2608
        mov     [ebx+0Ch],ax
2609
        mov     byte [ebx+10h],3
2610
        add     esi,20h
2611
        add     ebx,12h
2612
        jmp     make_symbols_table
2613
      add_extrn_symbol:
31 halyavin 2614
        call    store_symbol_name
109 heavyiron 2615
        mov     byte [ebx+10h],2
2616
        add     esi,0Ch
2617
        add     ebx,12h
2618
        jmp     make_symbols_table
2619
      add_public_symbol:
31 halyavin 2620
        call    store_symbol_name
109 heavyiron 2621
        mov     eax,[esi+0Ch]
2622
        mov     [current_line],eax
2623
        mov     eax,[esi+8]
2624
        test    byte [eax+8],1
2625
        jz      undefined_symbol
2626
        mov     cx,[current_pass]
2627
        cmp     cx,[eax+16]
2628
        jne     undefined_symbol
2629
        mov     cl,[eax+11]
2630
        or      cl,cl
2631
        jz      public_constant
2632
        test    [format_flags],8
2633
        jnz     check_64bit_public_symbol
2634
        cmp     cl,2
2635
        je      public_symbol_type_ok
2636
        jmp     invalid_use_of_symbol
2637
      check_64bit_public_symbol:
31 halyavin 2638
        cmp     cl,4
109 heavyiron 2639
        jne     invalid_use_of_symbol
2640
      public_symbol_type_ok:
31 halyavin 2641
        mov     ecx,[eax+20]
109 heavyiron 2642
        cmp     byte [ecx],81h
2643
        je      alias_symbol
2644
        cmp     byte [ecx],0
2645
        jne     invalid_use_of_symbol
2646
        mov     cx,[ecx+1Eh]
2647
        mov     [ebx+0Ch],cx
2648
      public_symbol_section_ok:
31 halyavin 2649
        cmp     dword [eax+4],0
109 heavyiron 2650
        je      store_public_symbol
2651
        cmp     dword [eax+4],-1
2652
        jne     value_out_of_range
2653
        bt      dword [eax],31
2654
        jnc     value_out_of_range
2655
      store_public_symbol:
31 halyavin 2656
        mov     eax,[eax]
109 heavyiron 2657
        mov     [ebx+8],eax
2658
        mov     byte [ebx+10h],2
2659
        add     esi,10h
2660
        add     ebx,12h
2661
        jmp     make_symbols_table
2662
      alias_symbol:
31 halyavin 2663
        bt      [format_flags],0
109 heavyiron 2664
        jnc     invalid_use_of_symbol
2665
        mov     ecx,[eax]
2666
        or      ecx,[eax+4]
2667
        jnz     invalid_use_of_symbol
2668
        mov     byte [ebx+10h],69h
2669
        mov     byte [ebx+11h],1
2670
        add     ebx,12h
2671
        mov     ecx,[eax+20]
2672
        mov     ecx,[ecx]
2673
        shr     ecx,8
2674
        mov     [ebx],ecx
2675
        mov     byte [ebx+4],3
2676
        add     esi,10h
2677
        add     ebx,12h
2678
        jmp     make_symbols_table
2679
      public_constant:
31 halyavin 2680
        mov     word [ebx+0Ch],0FFFFh
109 heavyiron 2681
        jmp     public_symbol_section_ok
2682
      symbols_table_ok:
31 halyavin 2683
        mov     eax,edi
109 heavyiron 2684
        sub     eax,edx
2685
        mov     [edx],eax
2686
        sub     edi,[code_start]
2687
        mov     [code_size],edi
2688
        mov     [written_size],0
2689
        mov     edx,[output_file]
2690
        call    create
2691
        jc      write_failed
2692
        mov     edx,[free_additional_memory]
2693
        pop     ecx
2694
        add     [written_size],ecx
2695
        call    write
2696
        jc      write_failed
2697
        jmp     write_output
2698
      store_symbol_name:
31 halyavin 2699
        push    esi
109 heavyiron 2700
        mov     esi,[esi+4]
2701
        or      esi,esi
2702
        jz      default_name
2703
        lods    dword [esi]
2704
        mov     ecx,eax
2705
        cmp     ecx,8
2706
        ja      add_string
2707
        push    edi
2708
        mov     edi,ebx
2709
        rep     movs byte [edi],[esi]
2710
        pop     edi esi
2711
        ret
2712
      default_name:
31 halyavin 2713
        mov     dword [ebx],'.fla'
109 heavyiron 2714
        mov     dword [ebx+4],'t'
2715
        pop     esi
2716
        ret
2717
      add_string:
31 halyavin 2718
        mov     eax,edi
109 heavyiron 2719
        sub     eax,edx
2720
        mov     [ebx+4],eax
2721
        inc     ecx
2722
        rep     movs byte [edi],[esi]
2723
        pop     esi
2724
        ret
2725
31 halyavin 2726
 
2727
        test    [format_flags],8
109 heavyiron 2728
        jnz     format_elf64
2729
        mov     edx,edi
2730
        mov     ecx,34h shr 2
2731
        lea     eax,[edi+ecx*4]
2732
        cmp     eax,[display_buffer]
2733
        jae     out_of_memory
2734
        xor     eax,eax
2735
        rep     stos dword [edi]
2736
        mov     dword [edx],7Fh + 'ELF' shl 8
2737
        mov     al,1
2738
        mov     [edx+4],al
2739
        mov     [edx+5],al
2740
        mov     [edx+6],al
2741
        mov     [edx+14h],al
2742
        mov     byte [edx+12h],3
2743
        mov     byte [edx+28h],34h
2744
        mov     byte [edx+2Eh],28h
2745
        mov     [code_type],32
2746
        cmp     word [esi],1D19h
2747
        je      format_elf_exe
2748
        mov     [labels_type],2
2749
      elf_header_ok:
31 halyavin 2750
        mov     byte [edx+10h],1
109 heavyiron 2751
        mov     eax,[additional_memory]
2752
        mov     [symbols_stream],eax
2753
        mov     ebx,eax
2754
        add     eax,20h
2755
        cmp     eax,[structures_buffer]
2756
        jae     out_of_memory
2757
        mov     [free_additional_memory],eax
2758
        xor     eax,eax
2759
        mov     [current_section],ebx
2760
        mov     [number_of_sections],eax
2761
        mov     dword [org_origin],edi
2762
        mov     dword [org_origin+4],eax
2763
        mov     [org_registers],eax
2764
        mov     [org_start],edi
2765
        mov     [org_symbol],ebx
2766
        mov     [ebx],al
2767
        mov     [ebx+4],eax
2768
        mov     [ebx+8],edi
2769
        mov     al,111b
2770
        mov     [ebx+14h],eax
2771
        mov     al,4
2772
        mov     [ebx+10h],eax
2773
        test    [format_flags],8
2774
        jz      instruction_assembled
2775
        mov     byte [ebx+10h],8
2776
        jmp     instruction_assembled
2777
      format_elf64:
31 halyavin 2778
        mov     edx,edi
109 heavyiron 2779
        mov     ecx,40h shr 2
2780
        lea     eax,[edi+ecx*4]
2781
        cmp     eax,[display_buffer]
2782
        jae     out_of_memory
2783
        xor     eax,eax
2784
        rep     stos dword [edi]
2785
        mov     dword [edx],7Fh + 'ELF' shl 8
2786
        mov     al,1
2787
        mov     [edx+5],al
2788
        mov     [edx+6],al
2789
        mov     [edx+14h],al
2790
        mov     byte [edx+4],2
2791
        mov     byte [edx+12h],62
2792
        mov     byte [edx+34h],40h
2793
        mov     byte [edx+3Ah],40h
2794
        mov     [code_type],64
2795
        cmp     word [esi],1D19h
2796
        je      format_elf64_exe
2797
        mov     [labels_type],4
2798
        jmp     elf_header_ok
2799
elf_section:
31 halyavin 2800
        bt      [format_flags],0
109 heavyiron 2801
        jc      illegal_instruction
2802
        call    close_coff_section
2803
        mov     ebx,[free_additional_memory]
2804
        lea     eax,[ebx+20h]
2805
        cmp     eax,[structures_buffer]
2806
        jae     out_of_memory
2807
        mov     [free_additional_memory],eax
2808
        mov     [current_section],ebx
2809
        inc     word [number_of_sections]
2810
        jz      format_limitations_exceeded
2811
        xor     eax,eax
2812
        mov     [ebx],al
2813
        mov     [ebx+8],edi
2814
        mov     dword [org_origin],edi
2815
        mov     dword [org_origin+4],0
2816
        mov     [org_registers],0
2817
        mov     [org_start],edi
2818
        mov     [org_symbol],ebx
2819
        test    [format_flags],8
2820
        jnz     elf64_labels_type
2821
        mov     [labels_type],2
2822
        jmp     elf_labels_type_ok
2823
      elf64_labels_type:
31 halyavin 2824
        mov     [labels_type],4
109 heavyiron 2825
      elf_labels_type_ok:
31 halyavin 2826
        mov     [ebx+10h],eax
109 heavyiron 2827
        mov     al,10b
2828
        mov     [ebx+14h],eax
2829
        lods    word [esi]
2830
        cmp     ax,'('
2831
        jne     invalid_argument
2832
        mov     [ebx+4],esi
2833
        mov     ecx,[esi]
2834
        lea     esi,[esi+4+ecx+1]
2835
      elf_section_flags:
31 halyavin 2836
        cmp     byte [esi],1Ch
109 heavyiron 2837
        je      elf_section_alignment
2838
        cmp     byte [esi],19h
2839
        jne     elf_section_settings_ok
2840
        inc     esi
2841
        lods    byte [esi]
2842
        sub     al,28
2843
        xor     al,11b
2844
        test    al,not 10b
2845
        jnz     invalid_argument
2846
        mov     cl,al
2847
        mov     al,1
2848
        shl     al,cl
2849
        test    byte [ebx+14h],al
2850
        jnz     setting_already_specified
2851
        or      byte [ebx+14h],al
2852
        jmp     elf_section_flags
2853
      elf_section_alignment:
31 halyavin 2854
        inc     esi
109 heavyiron 2855
        lods    byte [esi]
2856
        or      al,al
2857
        jnz     invalid_argument
2858
        lods    byte [esi]
2859
        cmp     al,'('
2860
        jne     invalid_argument
2861
        cmp     byte [esi],'.'
2862
        je      invalid_value
2863
        push    ebx
2864
        call    get_dword_value
2865
        pop     ebx
2866
        cmp     [value_type],0
2867
        jne     invalid_use_of_symbol
2868
        mov     edx,eax
2869
        dec     edx
2870
        test    eax,edx
2871
        jnz     invalid_value
2872
        or      eax,eax
2873
        jz      invalid_value
2874
        xchg    [ebx+10h],eax
2875
        or      eax,eax
2876
        jnz     setting_already_specified
2877
        jmp     elf_section_flags
2878
      elf_section_settings_ok:
31 halyavin 2879
        cmp     dword [ebx+10h],0
109 heavyiron 2880
        jne     instruction_assembled
2881
        mov     dword [ebx+10h],4
2882
        test    [format_flags],8
2883
        jz      instruction_assembled
2884
        mov     byte [ebx+10h],8
2885
        jmp     instruction_assembled
2886
mark_elf_relocation:
31 halyavin 2887
        cmp     [value_type],3
109 heavyiron 2888
        je      elf_relocation_relative
2889
        push    ebx eax
2890
        cmp     [value_type],3
2891
        je      elf_gotoff_relocation
2892
        mov     al,1
2893
        test    [format_flags],8
2894
        jz      coff_relocation
2895
        cmp     [value_type],4
2896
        je      coff_relocation
2897
        mov     al,11
2898
        jmp     coff_relocation
2899
      elf_gotoff_relocation:
2900
        mov     al,9
2901
        jmp     coff_relocation
2902
      elf_relocation_relative:
31 halyavin 2903
        cmp     [labels_type],0
109 heavyiron 2904
        je      invalid_use_of_symbol
2905
        push    ebx
2906
        mov     ebx,[current_section]
2907
        mov     ebx,[ebx+8]
2908
        sub     ebx,edi
2909
        sub     eax,ebx
2910
        push    eax
2911
        mov     al,2
2912
        jmp     coff_relocation
2913
close_elf:
31 halyavin 2914
        bt      [format_flags],0
109 heavyiron 2915
        jc      close_elf_exe
2916
        call    close_coff_section
2917
        cmp     [next_pass_needed],0
2918
        je      elf_closed
2919
        mov     eax,[symbols_stream]
2920
        mov     [free_additional_memory],eax
2921
      elf_closed:
31 halyavin 2922
        ret
109 heavyiron 2923
elf_formatter:
31 halyavin 2924
        push    edi
109 heavyiron 2925
        call    prepare_default_section
2926
        mov     esi,[symbols_stream]
2927
        mov     edi,[free_additional_memory]
2928
        xor     eax,eax
2929
        mov     ecx,4
2930
        rep     stos dword [edi]
2931
        test    [format_flags],8
2932
        jz      find_first_section
2933
        mov     ecx,2
2934
        rep     stos dword [edi]
2935
      find_first_section:
31 halyavin 2936
        mov     al,[esi]
109 heavyiron 2937
        or      al,al
2938
        jz      first_section_found
2939
        cmp     al,80h
2940
        jne     skip_other_symbol
2941
        add     esi,4
2942
      skip_other_symbol:
31 halyavin 2943
        add     esi,0Ch
109 heavyiron 2944
        jmp     find_first_section
2945
      first_section_found:
31 halyavin 2946
        mov     ebx,esi
109 heavyiron 2947
        mov     ebp,esi
2948
        add     esi,20h
2949
        xor     ecx,ecx
2950
        xor     edx,edx
2951
      find_next_section:
31 halyavin 2952
        cmp     esi,[free_additional_memory]
109 heavyiron 2953
        je      make_section_symbol
2954
        mov     al,[esi]
2955
        or      al,al
2956
        jz      make_section_symbol
2957
        cmp     al,80h
2958
        je      skip_public
2959
        ja      skip_extrn
2960
        or      byte [ebx+14h],40h
2961
      skip_extrn:
31 halyavin 2962
        add     esi,0Ch
109 heavyiron 2963
        jmp     find_next_section
2964
      skip_public:
31 halyavin 2965
        add     esi,10h
109 heavyiron 2966
        jmp     find_next_section
2967
      make_section_symbol:
31 halyavin 2968
        mov     eax,edi
109 heavyiron 2969
        xchg    eax,[ebx+4]
2970
        stos    dword [edi]
2971
        test    [format_flags],8
2972
        jnz     elf64_section_symbol
2973
        xor     eax,eax
2974
        stos    dword [edi]
2975
        stos    dword [edi]
2976
        call    store_section_index
2977
        jmp     section_symbol_ok
2978
      store_section_index:
31 halyavin 2979
        inc     ecx
109 heavyiron 2980
        mov     eax,ecx
2981
        shl     eax,8
2982
        mov     [ebx],eax
2983
        inc     dx
2984
        jz      format_limitations_exceeded
2985
        mov     eax,edx
2986
        shl     eax,16
2987
        mov     al,3
2988
        test    byte [ebx+14h],40h
2989
        jz      section_index_ok
2990
        or      ah,-1
2991
        inc     dx
2992
        jz      format_limitations_exceeded
2993
      section_index_ok:
31 halyavin 2994
        stos    dword [edi]
109 heavyiron 2995
        ret
2996
      elf64_section_symbol:
31 halyavin 2997
        call    store_section_index
109 heavyiron 2998
        xor     eax,eax
2999
        stos    dword [edi]
3000
        stos    dword [edi]
3001
        stos    dword [edi]
3002
        stos    dword [edi]
3003
      section_symbol_ok:
31 halyavin 3004
        mov     ebx,esi
109 heavyiron 3005
        add     esi,20h
3006
        cmp     ebx,[free_additional_memory]
3007
        jne     find_next_section
3008
        inc     dx
3009
        jz      format_limitations_exceeded
3010
        mov     [current_section],edx
3011
        mov     esi,[symbols_stream]
3012
      find_other_symbols:
31 halyavin 3013
        cmp     esi,[free_additional_memory]
109 heavyiron 3014
        je      elf_symbol_table_ok
3015
        mov     al,[esi]
3016
        or      al,al
3017
        jz      skip_section
3018
        cmp     al,80h
3019
        je      make_public_symbol
3020
        ja      make_extrn_symbol
3021
        add     esi,0Ch
3022
        jmp     find_other_symbols
3023
      skip_section:
31 halyavin 3024
        add     esi,20h
109 heavyiron 3025
        jmp     find_other_symbols
3026
      make_public_symbol:
31 halyavin 3027
        mov     eax,[esi+0Ch]
109 heavyiron 3028
        mov     [current_line],eax
3029
        mov     ebx,[esi+8]
3030
        test    byte [ebx+8],1
3031
        jz      undefined_symbol
3032
        mov     ax,[current_pass]
3033
        cmp     ax,[ebx+16]
3034
        jne     undefined_symbol
3035
        mov     dl,[ebx+11]
3036
        or      dl,dl
3037
        jz      public_absolute
3038
        mov     eax,[ebx+20]
3039
        cmp     byte [eax],0
3040
        jne     invalid_use_of_symbol
3041
        mov     eax,[eax+4]
3042
        test    [format_flags],8
3043
        jnz     elf64_public
3044
        cmp     dl,2
3045
        jne     invalid_use_of_symbol
3046
        mov     dx,[eax+0Eh]
3047
        jmp     section_for_public_ok
3048
      elf64_public:
31 halyavin 3049
        cmp     dl,4
109 heavyiron 3050
        jne     invalid_use_of_symbol
3051
        mov     dx,[eax+6]
3052
        jmp     section_for_public_ok
3053
      public_absolute:
31 halyavin 3054
        mov     dx,0FFF1h
109 heavyiron 3055
      section_for_public_ok:
31 halyavin 3056
        mov     eax,[esi+4]
109 heavyiron 3057
        stos    dword [edi]
3058
        test    [format_flags],8
3059
        jnz     elf64_public_symbol
3060
        call    get_public_value
3061
        stos    dword [edi]
3062
        xor     eax,eax
3063
        mov     al,[ebx+10]
3064
        stos    dword [edi]
3065
        mov     eax,edx
3066
        shl     eax,16
3067
        mov     al,10h
3068
        cmp     byte [ebx+10],0
3069
        je      elf_public_function
3070
        or      al,1
3071
        jmp     store_elf_public_info
3072
      elf_public_function:
3073
        or      al,2
3074
      store_elf_public_info:
3075
        stos    dword [edi]
3076
        jmp     public_symbol_ok
3077
      elf64_public_symbol:
31 halyavin 3078
        mov     eax,edx
109 heavyiron 3079
        shl     eax,16
3080
        mov     al,10h
3081
        cmp     byte [ebx+10],0
3082
        je      elf64_public_function
3083
        or      al,1
3084
        jmp     store_elf64_public_info
3085
      elf64_public_function:
3086
        or      al,2
3087
      store_elf64_public_info:
3088
        stos    dword [edi]
3089
        call    get_public_value
3090
        stos    dword [edi]
3091
        xor     eax,eax
3092
        stos    dword [edi]
3093
        mov     al,[ebx+10]
3094
        stos    dword [edi]
3095
        xor     al,al
3096
        stos    dword [edi]
3097
      public_symbol_ok:
31 halyavin 3098
        inc     ecx
109 heavyiron 3099
        mov     eax,ecx
3100
        shl     eax,8
3101
        mov     al,80h
3102
        mov     [esi],eax
3103
        add     esi,10h
3104
        jmp     find_other_symbols
3105
      get_public_value:
31 halyavin 3106
        mov     eax,[ebx]
109 heavyiron 3107
        cmp     dword [ebx+4],0
3108
        je      public_value_ok
3109
        cmp     dword [ebx+4],-1
3110
        jne     value_out_of_range
3111
        bt      eax,31
3112
        jnc     value_out_of_range
3113
      public_value_ok:
31 halyavin 3114
        ret
109 heavyiron 3115
      make_extrn_symbol:
31 halyavin 3116
        mov     eax,[esi+4]
109 heavyiron 3117
        stos    dword [edi]
3118
        test    [format_flags],8
3119
        jnz     elf64_extrn_symbol
3120
        xor     eax,eax
3121
        stos    dword [edi]
3122
        mov     eax,[esi+8]
3123
        stos    dword [edi]
3124
        mov     eax,10h
3125
        stos    dword [edi]
3126
        jmp     extrn_symbol_ok
3127
      elf64_extrn_symbol:
31 halyavin 3128
        mov     eax,10h
109 heavyiron 3129
        stos    dword [edi]
3130
        xor     al,al
3131
        stos    dword [edi]
3132
        stos    dword [edi]
3133
        mov     eax,[esi+8]
3134
        stos    dword [edi]
3135
        xor     eax,eax
3136
        stos    dword [edi]
3137
      extrn_symbol_ok:
31 halyavin 3138
        inc     ecx
109 heavyiron 3139
        mov     eax,ecx
3140
        shl     eax,8
3141
        mov     al,81h
3142
        mov     [esi],eax
3143
        add     esi,0Ch
3144
        jmp     find_other_symbols
3145
      elf_symbol_table_ok:
31 halyavin 3146
        mov     edx,edi
109 heavyiron 3147
        mov     ebx,[free_additional_memory]
3148
        xor     al,al
3149
        stos    byte [edi]
3150
        add     edi,16
3151
        mov     [edx+1],edx
3152
        add     ebx,10h
3153
        test    [format_flags],8
3154
        jz      make_string_table
3155
        add     ebx,8
3156
      make_string_table:
31 halyavin 3157
        cmp     ebx,edx
109 heavyiron 3158
        je      elf_string_table_ok
3159
        test    [format_flags],8
3160
        jnz     make_elf64_string
3161
        cmp     byte [ebx+0Dh],0
3162
        je      rel_prefix_ok
3163
        mov     byte [ebx+0Dh],0
3164
        mov     eax,'.rel'
3165
        stos    dword [edi]
3166
      rel_prefix_ok:
31 halyavin 3167
        mov     esi,edi
109 heavyiron 3168
        sub     esi,edx
3169
        xchg    esi,[ebx]
3170
        add     ebx,10h
3171
      make_elf_string:
31 halyavin 3172
        or      esi,esi
109 heavyiron 3173
        jz      default_string
3174
        lods    dword [esi]
3175
        mov     ecx,eax
3176
        rep     movs byte [edi],[esi]
3177
        xor     al,al
3178
        stos    byte [edi]
3179
        jmp     make_string_table
3180
      make_elf64_string:
31 halyavin 3181
        cmp     byte [ebx+5],0
109 heavyiron 3182
        je      elf64_rel_prefix_ok
3183
        mov     byte [ebx+5],0
3184
        mov     eax,'.rel'
3185
        stos    dword [edi]
3186
        mov     al,'a'
3187
        stos    byte [edi]
3188
      elf64_rel_prefix_ok:
31 halyavin 3189
        mov     esi,edi
109 heavyiron 3190
        sub     esi,edx
3191
        xchg    esi,[ebx]
3192
        add     ebx,18h
3193
        jmp     make_elf_string
3194
      default_string:
31 halyavin 3195
        mov     eax,'.fla'
109 heavyiron 3196
        stos    dword [edi]
3197
        mov     ax,'t'
3198
        stos    word [edi]
3199
        jmp     make_string_table
3200
      elf_string_table_ok:
31 halyavin 3201
        mov     [edx+1+8],edi
109 heavyiron 3202
        mov     ebx,[code_start]
3203
        mov     eax,edi
3204
        sub     eax,[free_additional_memory]
3205
        test    [format_flags],8
3206
        jnz     finish_elf64_header
3207
        mov     [ebx+20h],eax
3208
        mov     eax,[current_section]
3209
        inc     ax
3210
        jz      format_limitations_exceeded
3211
        mov     [ebx+32h],ax
3212
        inc     ax
3213
        jz      format_limitations_exceeded
3214
        mov     [ebx+30h],ax
3215
        jmp     elf_header_finished
3216
      finish_elf64_header:
31 halyavin 3217
        mov     [ebx+28h],eax
109 heavyiron 3218
        mov     eax,[current_section]
3219
        inc     ax
3220
        jz      format_limitations_exceeded
3221
        mov     [ebx+3Eh],ax
3222
        inc     ax
3223
        jz      format_limitations_exceeded
3224
        mov     [ebx+3Ch],ax
3225
      elf_header_finished:
31 halyavin 3226
        xor     eax,eax
109 heavyiron 3227
        mov     ecx,10
3228
        rep     stos dword [edi]
3229
        test    [format_flags],8
3230
        jz      elf_null_section_ok
3231
        mov     ecx,6
3232
        rep     stos dword [edi]
3233
      elf_null_section_ok:
31 halyavin 3234
        mov     esi,ebp
109 heavyiron 3235
        xor     ecx,ecx
3236
      make_section_entry:
31 halyavin 3237
        mov     ebx,edi
109 heavyiron 3238
        mov     eax,[esi+4]
3239
        mov     eax,[eax]
3240
        stos    dword [edi]
3241
        mov     eax,1
3242
        cmp     dword [esi+0Ch],0
3243
        je      bss_section
3244
        test    byte [esi+14h],80h
3245
        jz      section_type_ok
3246
      bss_section:
31 halyavin 3247
        mov     al,8
109 heavyiron 3248
      section_type_ok:
31 halyavin 3249
        stos    dword [edi]
109 heavyiron 3250
        mov     eax,[esi+14h]
3251
        and     al,3Fh
3252
        call    store_elf_machine_word
3253
        xor     eax,eax
3254
        call    store_elf_machine_word
3255
        mov     eax,[esi+8]
3256
        mov     [image_base],eax
3257
        sub     eax,[code_start]
3258
        call    store_elf_machine_word
3259
        mov     eax,[esi+0Ch]
3260
        call    store_elf_machine_word
3261
        xor     eax,eax
3262
        stos    dword [edi]
3263
        stos    dword [edi]
3264
        mov     eax,[esi+10h]
3265
        call    store_elf_machine_word
3266
        xor     eax,eax
3267
        call    store_elf_machine_word
3268
        inc     ecx
3269
        add     esi,20h
3270
        xchg    edi,[esp]
3271
        mov     ebp,edi
3272
      convert_relocations:
31 halyavin 3273
        cmp     esi,[free_additional_memory]
109 heavyiron 3274
        je      relocations_converted
3275
        mov     al,[esi]
3276
        or      al,al
3277
        jz      relocations_converted
3278
        cmp     al,80h
3279
        jb      make_relocation_entry
3280
        ja      relocation_entry_ok
3281
        add     esi,10h
3282
        jmp     convert_relocations
3283
      make_relocation_entry:
31 halyavin 3284
        test    [format_flags],8
109 heavyiron 3285
        jnz     make_elf64_relocation_entry
3286
        mov     eax,[esi+4]
3287
        stos    dword [edi]
3288
        mov     eax,[esi+8]
3289
        mov     eax,[eax]
3290
        mov     al,[esi]
3291
        stos    dword [edi]
3292
        jmp     relocation_entry_ok
3293
      make_elf64_relocation_entry:
31 halyavin 3294
        mov     eax,[esi+4]
109 heavyiron 3295
        stos    dword [edi]
3296
        xor     eax,eax
3297
        stos    dword [edi]
3298
        movzx   eax,byte [esi]
3299
        stos    dword [edi]
3300
        mov     eax,[esi+8]
3301
        mov     eax,[eax]
3302
        shr     eax,8
3303
        stos    dword [edi]
3304
        xor     eax,eax
3305
        stos    dword [edi]
3306
        stos    dword [edi]
3307
      relocation_entry_ok:
31 halyavin 3308
        add     esi,0Ch
109 heavyiron 3309
        jmp     convert_relocations
3310
      store_elf_machine_word:
31 halyavin 3311
        stos    dword [edi]
109 heavyiron 3312
        test    [format_flags],8
3313
        jz      elf_machine_word_ok
3314
        mov     dword [edi],0
3315
        add     edi,4
3316
      elf_machine_word_ok:
31 halyavin 3317
        ret
109 heavyiron 3318
      relocations_converted:
31 halyavin 3319
        cmp     edi,ebp
109 heavyiron 3320
        xchg    edi,[esp]
3321
        je      rel_section_ok
3322
        mov     eax,[ebx]
3323
        sub     eax,4
3324
        test    [format_flags],8
3325
        jz      store_relocations_name_offset
3326
        dec     eax
3327
      store_relocations_name_offset:
31 halyavin 3328
        stos    dword [edi]
109 heavyiron 3329
        test    [format_flags],8
3330
        jnz     rela_section
3331
        mov     eax,9
3332
        jmp     store_relocations_type
3333
      rela_section:
31 halyavin 3334
        mov     eax,4
109 heavyiron 3335
      store_relocations_type:
31 halyavin 3336
        stos    dword [edi]
109 heavyiron 3337
        xor     al,al
3338
        call    store_elf_machine_word
3339
        call    store_elf_machine_word
3340
        mov     eax,ebp
3341
        sub     eax,[code_start]
3342
        call    store_elf_machine_word
3343
        mov     eax,[esp]
3344
        sub     eax,ebp
3345
        call    store_elf_machine_word
3346
        mov     eax,[current_section]
3347
        stos    dword [edi]
3348
        mov     eax,ecx
3349
        stos    dword [edi]
3350
        inc     ecx
3351
        test    [format_flags],8
3352
        jnz     finish_elf64_rela_section
3353
        mov     eax,4
3354
        stos    dword [edi]
3355
        mov     al,8
3356
        stos    dword [edi]
3357
        jmp     rel_section_ok
3358
      finish_elf64_rela_section:
31 halyavin 3359
        mov     eax,8
109 heavyiron 3360
        stos    dword [edi]
3361
        xor     al,al
3362
        stos    dword [edi]
3363
        mov     al,24
3364
        stos    dword [edi]
3365
        xor     al,al
3366
        stos    dword [edi]
3367
      rel_section_ok:
31 halyavin 3368
        cmp     esi,[free_additional_memory]
109 heavyiron 3369
        jne     make_section_entry
3370
        pop     eax
3371
        mov     ebx,[code_start]
3372
        sub     eax,ebx
3373
        mov     [code_size],eax
3374
        mov     ecx,20h
3375
        test    [format_flags],8
3376
        jz      adjust_elf_section_headers_offset
3377
        mov     ecx,28h
3378
      adjust_elf_section_headers_offset:
31 halyavin 3379
        add     [ebx+ecx],eax
109 heavyiron 3380
        mov     eax,1
3381
        stos    dword [edi]
3382
        mov     al,2
3383
        stos    dword [edi]
3384
        xor     al,al
3385
        call    store_elf_machine_word
3386
        call    store_elf_machine_word
3387
        mov     eax,[code_size]
3388
        call    store_elf_machine_word
3389
        mov     eax,[edx+1]
3390
        sub     eax,[free_additional_memory]
3391
        call    store_elf_machine_word
3392
        mov     eax,[current_section]
3393
        inc     eax
3394
        stos    dword [edi]
3395
        mov     eax,[number_of_sections]
3396
        inc     eax
3397
        stos    dword [edi]
3398
        test    [format_flags],8
3399
        jnz     finish_elf64_sym_section
3400
        mov     eax,4
3401
        stos    dword [edi]
3402
        mov     al,10h
3403
        stos    dword [edi]
3404
        jmp     sym_section_ok
3405
      finish_elf64_sym_section:
31 halyavin 3406
        mov     eax,8
109 heavyiron 3407
        stos    dword [edi]
3408
        xor     al,al
3409
        stos    dword [edi]
3410
        mov     al,18h
3411
        stos    dword [edi]
3412
        xor     al,al
3413
        stos    dword [edi]
3414
      sym_section_ok:
31 halyavin 3415
        mov     al,1+8
109 heavyiron 3416
        stos    dword [edi]
3417
        mov     al,3
3418
        stos    dword [edi]
3419
        xor     al,al
3420
        call    store_elf_machine_word
3421
        call    store_elf_machine_word
3422
        mov     eax,[edx+1]
3423
        sub     eax,[free_additional_memory]
3424
        add     eax,[code_size]
3425
        call    store_elf_machine_word
3426
        mov     eax,[edx+1+8]
3427
        sub     eax,[edx+1]
3428
        call    store_elf_machine_word
3429
        xor     eax,eax
3430
        stos    dword [edi]
3431
        stos    dword [edi]
3432
        mov     al,1
3433
        call    store_elf_machine_word
3434
        xor     eax,eax
3435
        call    store_elf_machine_word
3436
        mov     eax,'tab'
3437
        mov     dword [edx+1],'.sym'
3438
        mov     [edx+1+4],eax
3439
        mov     dword [edx+1+8],'.str'
3440
        mov     [edx+1+8+4],eax
3441
        mov     [written_size],0
3442
        mov     edx,[output_file]
3443
        call    create
3444
        jc      write_failed
3445
        call    write_code
3446
        mov     ecx,edi
3447
        mov     edx,[free_additional_memory]
3448
        sub     ecx,edx
3449
        add     [written_size],ecx
3450
        call    write
3451
        jc      write_failed
3452
        jmp     output_written
3453
31 halyavin 3454
 
3455
        add     esi,2
109 heavyiron 3456
        or      [format_flags],1
3457
        mov     [image_base],8048000h
3458
        cmp     byte [esi],80h
3459
        jne     elf_exe_base_ok
3460
        lods    word [esi]
3461
        cmp     ah,'('
3462
        jne     invalid_argument
3463
        cmp     byte [esi],'.'
3464
        je      invalid_value
3465
        push    edx
3466
        call    get_dword_value
3467
        cmp     [value_type],0
3468
        jne     invalid_use_of_symbol
3469
        mov     [image_base],eax
3470
        pop     edx
3471
      elf_exe_base_ok:
31 halyavin 3472
        mov     byte [edx+10h],2
109 heavyiron 3473
        mov     byte [edx+2Ah],20h
3474
        mov     ebx,edi
3475
        mov     ecx,20h shr 2
3476
        cmp     [current_pass],0
3477
        je      init_elf_segments
3478
        imul    ecx,[number_of_sections]
3479
      init_elf_segments:
3480
        xor     eax,eax
3481
        rep     stos dword [edi]
3482
        mov     [number_of_sections],0
3483
        mov     byte [ebx],1
3484
        mov     word [ebx+1Ch],1000h
3485
        mov     byte [ebx+18h],111b
3486
        mov     eax,edi
3487
        sub     eax,[code_start]
3488
        mov     [ebx+4],eax
3489
        add     eax,[image_base]
3490
        mov     [ebx+8],eax
3491
        mov     [ebx+0Ch],eax
3492
        mov     [edx+18h],eax
3493
        xor     edx,edx
3494
        not     eax
3495
        not     edx
3496
        add     eax,1
3497
        adc     edx,0
3498
        add     eax,edi
3499
        adc     edx,0
3500
        mov     dword [org_origin],eax
3501
        mov     dword [org_origin+4],edx
3502
        mov     [org_registers],0
3503
        mov     [org_start],edi
3504
        mov     [symbols_stream],edi
3505
        jmp     instruction_assembled
3506
      format_elf64_exe:
31 halyavin 3507
        add     esi,2
109 heavyiron 3508
        or      [format_flags],1
3509
        mov     [image_base],400000h
3510
        mov     [image_base_high],0
3511
        cmp     byte [esi],80h
3512
        jne     elf64_exe_base_ok
3513
        lods    word [esi]
3514
        cmp     ah,'('
3515
        jne     invalid_argument
3516
        cmp     byte [esi],'.'
3517
        je      invalid_value
3518
        push    edx
3519
        call    get_qword_value
3520
        cmp     [value_type],0
3521
        jne     invalid_use_of_symbol
3522
        mov     [image_base],eax
3523
        mov     [image_base_high],edx
3524
        pop     edx
3525
      elf64_exe_base_ok:
31 halyavin 3526
        mov     byte [edx+10h],2
109 heavyiron 3527
        mov     byte [edx+36h],38h
3528
        mov     ebx,edi
3529
        mov     ecx,38h shr 2
3530
        cmp     [current_pass],0
3531
        je      init_elf64_segments
3532
        imul    ecx,[number_of_sections]
3533
      init_elf64_segments:
3534
        xor     eax,eax
3535
        rep     stos dword [edi]
3536
        mov     [number_of_sections],0
3537
        mov     byte [ebx],1
3538
        mov     word [ebx+30h],1000h
3539
        mov     byte [ebx+4],111b
3540
        push    edx
3541
        mov     eax,edi
3542
        sub     eax,[code_start]
3543
        mov     [ebx+8],eax
3544
        xor     edx,edx
3545
        add     eax,[image_base]
3546
        adc     edx,[image_base_high]
3547
        mov     [ebx+10h],eax
3548
        mov     [ebx+10h+4],edx
3549
        mov     [ebx+18h],eax
3550
        mov     [ebx+18h+4],edx
3551
        pop     ebx
3552
        mov     [ebx+18h],eax
3553
        mov     [ebx+18h+4],edx
3554
        not     eax
3555
        not     edx
3556
        add     eax,1
3557
        adc     edx,0
3558
        add     eax,edi
3559
        adc     edx,0
3560
        mov     dword [org_origin],eax
3561
        mov     dword [org_origin+4],edx
3562
        mov     [org_registers],0
3563
        mov     [org_start],edi
3564
        mov     [symbols_stream],edi
3565
        jmp     instruction_assembled
3566
elf_entry:
31 halyavin 3567
        lods    byte [esi]
109 heavyiron 3568
        cmp     al,'('
3569
        jne     invalid_argument
3570
        cmp     byte [esi],'.'
3571
        je      invalid_value
3572
        test    [format_flags],8
3573
        jnz     elf64_entry
3574
        call    get_dword_value
3575
        cmp     [value_type],0
3576
        jne     invalid_use_of_symbol
3577
        mov     edx,[code_start]
3578
        mov     [edx+18h],eax
3579
        jmp     instruction_assembled
3580
      elf64_entry:
31 halyavin 3581
        call    get_qword_value
109 heavyiron 3582
        cmp     [value_type],0
3583
        jne     invalid_use_of_symbol
3584
        mov     ebx,[code_start]
3585
        mov     [ebx+18h],eax
3586
        mov     [ebx+1Ch],edx
3587
        jmp     instruction_assembled
3588
elf_segment:
3589
        bt      [format_flags],0
3590
        jnc     illegal_instruction
3591
        test    [format_flags],8
3592
        jnz     elf64_segment
3593
        call    close_elf_segment
3594
        push    eax
3595
        mov     ebx,[number_of_sections]
3596
        shl     ebx,5
3597
        add     ebx,[code_start]
3598
        add     ebx,34h
3599
        cmp     ebx,[symbols_stream]
3600
        jb      new_elf_segment
3601
        mov     ebx,[symbols_stream]
3602
        sub     ebx,20h
3603
        push    edi
3604
        mov     edi,ebx
3605
        mov     ecx,20h shr 2
3606
        xor     eax,eax
3607
        rep     stos dword [edi]
3608
        pop     edi
3609
        or      [next_pass_needed],-1
3610
      new_elf_segment:
3611
        mov     byte [ebx],1
3612
        mov     word [ebx+1Ch],1000h
3613
      elf_segment_flags:
3614
        cmp     byte [esi],19h
3615
        jne     elf_segment_flags_ok
3616
        lods    word [esi]
3617
        sub     ah,28
3618
        jbe     invalid_argument
3619
        cmp     ah,1
3620
        je      mark_elf_segment_flag
3621
        cmp     ah,3
3622
        ja      invalid_argument
3623
        xor     ah,1
3624
        cmp     ah,2
3625
        je      mark_elf_segment_flag
3626
        inc     ah
3627
      mark_elf_segment_flag:
3628
        test    [ebx+18h],ah
3629
        jnz     setting_already_specified
3630
        or      [ebx+18h],ah
3631
        jmp     elf_segment_flags
3632
      elf_segment_flags_ok:
3633
        mov     eax,edi
3634
        sub     eax,[code_start]
3635
        mov     [ebx+4],eax
3636
        pop     edx
3637
        and     eax,0FFFh
3638
        add     edx,eax
3639
        mov     [ebx+8],edx
3640
        mov     [ebx+0Ch],edx
3641
        mov     eax,edx
3642
        xor     edx,edx
3643
        not     eax
3644
        not     edx
3645
        add     eax,1
3646
        adc     edx,0
3647
        add     eax,edi
3648
        adc     edx,0
3649
        mov     dword [org_origin],eax
3650
        mov     dword [org_origin+4],edx
3651
        mov     [org_registers],0
3652
        mov     [org_start],edi
3653
        inc     [number_of_sections]
3654
        jmp     instruction_assembled
3655
      close_elf_segment:
3656
        cmp     [number_of_sections],0
3657
        jne     finish_elf_segment
3658
        cmp     edi,[symbols_stream]
3659
        jne     first_elf_segment_ok
3660
        push    edi
3661
        mov     edi,[code_start]
3662
        add     edi,34h
3663
        mov     ecx,20h shr 2
3664
        xor     eax,eax
3665
        rep     stos dword [edi]
3666
        pop     edi
3667
        mov     eax,[image_base]
3668
        ret
3669
      first_elf_segment_ok:
3670
        inc     [number_of_sections]
3671
      finish_elf_segment:
3672
        mov     ebx,[number_of_sections]
3673
        dec     ebx
3674
        shl     ebx,5
3675
        add     ebx,[code_start]
3676
        add     ebx,34h
3677
        mov     eax,edi
3678
        sub     eax,[code_start]
3679
        sub     eax,[ebx+4]
3680
        mov     edx,edi
3681
        cmp     edi,[undefined_data_end]
3682
        jne     elf_segment_size_ok
3683
        mov     edi,[undefined_data_start]
3684
      elf_segment_size_ok:
3685
        mov     [ebx+14h],eax
3686
        add     eax,edi
3687
        sub     eax,edx
3688
        mov     [ebx+10h],eax
3689
        mov     eax,[ebx+8]
3690
        add     eax,[ebx+14h]
3691
        add     eax,0FFFh
3692
        and     eax,not 0FFFh
3693
        ret
3694
      elf64_segment:
3695
        call    close_elf64_segment
3696
        push    eax edx
3697
        mov     ebx,[number_of_sections]
3698
        imul    ebx,38h
3699
        add     ebx,[code_start]
3700
        add     ebx,40h
3701
        cmp     ebx,[symbols_stream]
3702
        jb      new_elf64_segment
3703
        mov     ebx,[symbols_stream]
3704
        sub     ebx,38h
3705
        push    edi
3706
        mov     edi,ebx
3707
        mov     ecx,38h shr 2
3708
        xor     eax,eax
3709
        rep     stos dword [edi]
3710
        pop     edi
3711
        or      [next_pass_needed],-1
3712
      new_elf64_segment:
3713
        mov     byte [ebx],1
3714
        mov     word [ebx+30h],1000h
3715
      elf64_segment_flags:
3716
        cmp     byte [esi],19h
3717
        jne     elf64_segment_flags_ok
3718
        lods    word [esi]
3719
        sub     ah,28
3720
        jbe     invalid_argument
3721
        cmp     ah,1
3722
        je      mark_elf64_segment_flag
3723
        cmp     ah,3
3724
        ja      invalid_argument
3725
        xor     ah,1
3726
        cmp     ah,2
3727
        je      mark_elf64_segment_flag
3728
        inc     ah
3729
      mark_elf64_segment_flag:
3730
        test    [ebx+4],ah
3731
        jnz     setting_already_specified
3732
        or      [ebx+4],ah
3733
        jmp     elf64_segment_flags
3734
      elf64_segment_flags_ok:
3735
        mov     ecx,edi
3736
        sub     ecx,[code_start]
3737
        mov     [ebx+8],ecx
3738
        pop     edx eax
3739
        and     ecx,0FFFh
3740
        add     eax,ecx
3741
        adc     edx,0
3742
        mov     [ebx+10h],eax
3743
        mov     [ebx+10h+4],edx
3744
        mov     [ebx+18h],eax
3745
        mov     [ebx+18h+4],edx
3746
        not     eax
3747
        not     edx
3748
        add     eax,1
3749
        adc     edx,0
3750
        add     eax,edi
3751
        adc     edx,0
3752
        mov     dword [org_origin],eax
3753
        mov     dword [org_origin+4],edx
3754
        mov     [org_registers],0
3755
        mov     [org_start],edi
3756
        inc     [number_of_sections]
3757
        jmp     instruction_assembled
3758
      close_elf64_segment:
3759
        cmp     [number_of_sections],0
3760
        jne     finish_elf64_segment
3761
        cmp     edi,[symbols_stream]
3762
        jne     first_elf64_segment_ok
3763
        push    edi
3764
        mov     edi,[code_start]
3765
        add     edi,40h
3766
        mov     ecx,38h shr 2
3767
        xor     eax,eax
3768
        rep     stos dword [edi]
3769
        pop     edi
3770
        mov     eax,[image_base]
3771
        mov     edx,[image_base_high]
3772
        ret
3773
      first_elf64_segment_ok:
3774
        inc     [number_of_sections]
3775
      finish_elf64_segment:
3776
        mov     ebx,[number_of_sections]
3777
        dec     ebx
3778
        imul    ebx,38h
3779
        add     ebx,[code_start]
3780
        add     ebx,40h
3781
        mov     eax,edi
3782
        sub     eax,[code_start]
3783
        sub     eax,[ebx+8]
3784
        mov     edx,edi
3785
        cmp     edi,[undefined_data_end]
3786
        jne     elf64_segment_size_ok
3787
        mov     edi,[undefined_data_start]
3788
      elf64_segment_size_ok:
3789
        mov     [ebx+28h],eax
3790
        add     eax,edi
3791
        sub     eax,edx
3792
        mov     [ebx+20h],eax
3793
        mov     eax,[ebx+10h]
3794
        mov     edx,[ebx+10h+4]
3795
        add     eax,[ebx+28h]
3796
        adc     edx,0
3797
        sub     eax,1
3798
        sbb     edx,0
3799
        shrd    eax,edx,12
3800
        shr     edx,12
3801
        add     eax,1
3802
        adc     edx,0
3803
        shld    edx,eax,12
3804
        shl     eax,12
3805
        ret
3806
close_elf_exe:
31 halyavin 3807
        test    [format_flags],8
109 heavyiron 3808
        jnz     close_elf64_exe
3809
        call    close_elf_segment
3810
        mov     edx,[code_start]
3811
        mov     eax,[number_of_sections]
3812
        mov     byte [edx+1Ch],34h
3813
        mov     [edx+2Ch],ax
3814
        shl     eax,5
3815
        add     eax,edx
3816
        add     eax,34h
3817
        cmp     eax,[symbols_stream]
3818
        je      elf_exe_ok
3819
        or      [next_pass_needed],-1
3820
      elf_exe_ok:
31 halyavin 3821
        ret
109 heavyiron 3822
      close_elf64_exe:
31 halyavin 3823
        call    close_elf64_segment
109 heavyiron 3824
        mov     edx,[code_start]
3825
        mov     eax,[number_of_sections]
3826
        mov     byte [edx+20h],40h
3827
        mov     [edx+38h],ax
3828
        imul    eax,38h
3829
        add     eax,edx
3830
        add     eax,40h
3831
        cmp     eax,[symbols_stream]
3832
        je      elf64_exe_ok
3833
        or      [next_pass_needed],-1
3834
      elf64_exe_ok:
31 halyavin 3835
        ret
109 heavyiron 3836