Subversion Repositories Kolibri OS

Rev

Rev 4478 | Go to most recent revision | Blame | Last modification | View Log | Download | RSS feed

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