13 label . : sizeof.name
\r
76 ELFOSABI_SOLARIS = 6
\r
79 ELFOSABI_FREEBSD = 9
\r
81 ELFOSABI_MODESTO = 11
\r
82 ELFOSABI_OPENBSD = 12
\r
83 ELFOSABI_OPENVMS = 13
\r
86 ELFOSABI_FENIXOS = 16
\r
87 ELFOSABI_CLOUDABI = 17
\r
88 ELFOSABI_OPENVOS = 18
\r
106 SHN_LORESERVE = 0xff00
\r
107 SHN_LOPROC = 0xff00
\r
108 SHN_HIPROC = 0xff1f
\r
110 SHN_COMMON = 0xfff2
\r
111 SHN_HIRESERVE = 0xffff
\r
125 SHT_LOPROC = 0x70000000
\r
126 SHT_HIPROC = 0x7fffffff
\r
127 SHT_LOUSER = 0x80000000
\r
128 SHT_HIUSER = 0xffffffff
\r
132 SHF_EXECINSTR = 0x4
\r
133 SHF_MASKPROC = 0xf0000000
\r
155 R_X86_64_GLOB_DAT = 6
\r
156 R_X86_64_JUMP_SLOT = 7
\r
157 R_X86_64_RELATIVE = 8
\r
158 R_X86_64_GOTPCREL = 9
\r
165 R_X86_64_DPTMOD64 = 16
\r
166 R_X86_64_DTPOFF64 = 17
\r
167 R_X86_64_TPOFF64 = 18
\r
168 R_X86_64_TLSGD = 19
\r
169 R_X86_64_TLSLD = 20
\r
170 R_X86_64_DTPOFF32 = 21
\r
171 R_X86_64_GOTTPOFF = 22
\r
172 R_X86_64_TPOFF32 = 23
\r
174 R_X86_64_GOTOFF64 = 25
\r
175 R_X86_64_GOTPC32 = 26
\r
181 if defined Settings.Machine
\r
182 MACHINE := Settings.Machine
\r
184 MACHINE := EM_X86_64
\r
187 if defined Settings.ABI
\r
188 ABI := Settings.ABI
\r
190 ABI := ELFOSABI_NONE
\r
193 if MACHINE = EM_X86_64
\r
195 R_32 = R_X86_64_32S
\r
196 R_PC32 = R_X86_64_PC32
\r
197 R_PLT32 = R_X86_64_PLT32
\r
202 e_ident db 0x7F,'ELF',ELFCLASS64,ELFDATA2LSB,EV_CURRENT,ABI,(16-$) dup 0
\r
204 e_machine dw MACHINE
\r
205 e_version dd EV_CURRENT
\r
208 e_shoff dq SECTION_TABLE_OFFSET
\r
210 e_ehsize dw Content
\r
213 e_shentsize dw sizeof Elf64_Shdr
\r
214 e_shnum dw NUMBER_OF_SECTIONS
\r
215 e_shstrndx dw STRING_TABLE_SECTION_INDEX
\r
220 section_table:: rb NUMBER_OF_SECTIONS * sizeof Elf64_Shdr
\r
224 symbol_table:: rb NUMBER_OF_SYMBOLS * sizeof Elf64_Sym
\r
230 _symtab db '.symtab',0
\r
231 _strtab db '.strtab',0
\r
232 SECTION_NAME_POSITION = $
\r
233 rb SECTION_NAME_TABLE_SIZE - $
\r
234 STRING_POSITION = $
\r
235 rb STRING_TABLE_SIZE - $
\r
239 relocations:: rb NUMBER_OF_RELOCATIONS * sizeof Elf64_Rela
\r
242 element relocatable?
\r
246 element sym : relocatable * SECTION_INDEX + SECTION_SYMBOL_INDEX
\r
251 RELOCATION_INDEX = 0
\r
253 SECTION_SYMBOL_INDEX = SECTION_INDEX
\r
254 SECTION_RELOCATION_INDEX = RELOCATION_INDEX
\r
255 SYMBOL_INDEX = NUMBER_OF_SECTION_SYMBOLS
\r
257 SECTION_OFFSET = $%
\r
259 SECTION_NAME = '.flat'
\r
260 SECTION_FLAGS = SHF_ALLOC + SHF_WRITE + SHF_EXECINSTR
\r
261 DEFINED_SECTION = 0
\r
269 SECTION_SIZE = $% - SECTION_OFFSET
\r
271 if DEFINED_SECTION | SECTION_SIZE > 0
\r
273 store SECTION_OFFSET at section_table : Elf64_Shdr.sh_offset + SECTION_INDEX * sizeof Elf64_Shdr
\r
274 store SECTION_SIZE at section_table : Elf64_Shdr.sh_size + SECTION_INDEX * sizeof Elf64_Shdr
\r
275 store SECTION_ALIGN at section_table : Elf64_Shdr.sh_addralign + SECTION_INDEX * sizeof Elf64_Shdr
\r
276 store SECTION_FLAGS at section_table : Elf64_Shdr.sh_flags + SECTION_INDEX * sizeof Elf64_Shdr
\r
278 if $%% = SECTION_OFFSET
\r
279 store SHT_NOBITS at section_table : Elf64_Shdr.sh_type + SECTION_INDEX * sizeof Elf64_Shdr
\r
282 store SHT_PROGBITS at section_table : Elf64_Shdr.sh_type + SECTION_INDEX * sizeof Elf64_Shdr
\r
283 UNINITIALIZED_LENGTH = $% - $%%
\r
285 db UNINITIALIZED_LENGTH dup 0
\r
288 store SECTION_INDEX at symbol_table : Elf64_Sym.st_shndx + SECTION_SYMBOL_INDEX * sizeof Elf64_Sym
\r
289 store STT_SECTION + STB_LOCAL shl 4 at symbol_table : Elf64_Sym.st_info + SECTION_SYMBOL_INDEX * sizeof Elf64_Sym
\r
291 if RELOCATION_INDEX > SECTION_RELOCATION_INDEX
\r
293 store RELOCATIONS_OFFSET + SECTION_RELOCATION_INDEX * sizeof Elf64_Rela at section_table : Elf64_Shdr.sh_offset + (SECTION_INDEX+1) * sizeof Elf64_Shdr
\r
294 store (RELOCATION_INDEX - SECTION_RELOCATION_INDEX) * sizeof Elf64_Rela at section_table : Elf64_Shdr.sh_size + (SECTION_INDEX+1) * sizeof Elf64_Shdr
\r
295 store SHT_RELA at section_table : Elf64_Shdr.sh_type + (SECTION_INDEX+1) * sizeof Elf64_Shdr
\r
296 store SYMBOL_TABLE_SECTION_INDEX at section_table : Elf64_Shdr.sh_link + (SECTION_INDEX+1) * sizeof Elf64_Shdr
\r
297 store SECTION_INDEX at section_table : Elf64_Shdr.sh_info + (SECTION_INDEX+1) * sizeof Elf64_Shdr
\r
298 store sizeof Elf64_Rela at section_table : Elf64_Shdr.sh_entsize + (SECTION_INDEX+1) * sizeof Elf64_Shdr
\r
299 store 8 at section_table : Elf64_Shdr.sh_addralign + (SECTION_INDEX+1) * sizeof Elf64_Shdr
\r
301 store SECTION_NAME_POSITION at section_table : Elf64_Shdr.sh_name + (SECTION_INDEX+1) * sizeof Elf64_Shdr
\r
302 store SECTION_NAME_POSITION + 5 at section_table : Elf64_Shdr.sh_name + SECTION_INDEX * sizeof Elf64_Shdr
\r
303 store SECTION_NAME_POSITION + 5 at symbol_table : Elf64_Sym.st_name + SECTION_SYMBOL_INDEX * sizeof Elf64_Sym
\r
304 store '.rela' + SECTION_NAME shl (5*8) : 5 + lengthof (string SECTION_NAME) at string_table:SECTION_NAME_POSITION
\r
305 SECTION_NAME_POSITION = SECTION_NAME_POSITION + 5 + lengthof (string SECTION_NAME) + 1
\r
307 SECTION_INDEX = SECTION_INDEX + 2
\r
308 SECTION_SYMBOL_INDEX = SECTION_SYMBOL_INDEX + 1
\r
311 store SECTION_NAME_POSITION at section_table : Elf64_Shdr.sh_name + SECTION_INDEX * sizeof Elf64_Shdr
\r
312 store SECTION_NAME_POSITION at symbol_table : Elf64_Sym.st_name + SECTION_SYMBOL_INDEX * sizeof Elf64_Sym
\r
313 store SECTION_NAME : lengthof (string SECTION_NAME) at string_table:SECTION_NAME_POSITION
\r
314 SECTION_NAME_POSITION = SECTION_NAME_POSITION + lengthof (string SECTION_NAME) + 1
\r
316 SECTION_INDEX = SECTION_INDEX + 1
\r
317 SECTION_SYMBOL_INDEX = SECTION_SYMBOL_INDEX + 1
\r
326 macro section? declaration*
\r
331 DEFINED_SECTION = 1
\r
332 SECTION_FLAGS = SHF_ALLOC
\r
333 SECTION_OFFSET = $%
\r
336 match name attributes, declaration
\r
338 SECTION_NAME = name
\r
341 match flags =align? boundary, attributes
\r
342 SECTION_ALIGN = boundary
\r
344 else match =align? boundary, attributes
\r
345 SECTION_ALIGN = boundary
\r
348 define seq attributes
\r
361 irpv attribute, list
\r
362 match =writeable?, attribute
\r
363 SECTION_FLAGS = SECTION_FLAGS or SHF_WRITE
\r
364 else match =executable?, attribute
\r
365 SECTION_FLAGS = SECTION_FLAGS or SHF_EXECINSTR
\r
367 err 'unknown attribute "',`attribute,'"'
\r
373 SECTION_NAME = declaration
\r
379 SECTION_RELOCATION_INDEX = RELOCATION_INDEX
\r
384 calminstruction align? boundary,value:?
\r
385 check ELF.SECTION_ALIGN mod (boundary) = 0
\r
387 arrange value, =err 'section not aligned enough'
\r
391 compute boundary, (boundary-1)-($-ELF.SECTION_BASE+boundary-1) mod boundary
\r
392 arrange value, =db boundary =dup value
\r
394 end calminstruction
\r
396 macro public? declaration*
\r
398 match value =as? str, declaration
\r
399 SYMBOL_VALUE = value
\r
400 SYMBOL_SIZE = sizeof value
\r
401 SYMBOL_NAME = string str
\r
403 SYMBOL_VALUE = declaration
\r
404 SYMBOL_SIZE = sizeof declaration
\r
405 SYMBOL_NAME = `declaration
\r
407 if SYMBOL_VALUE relativeto 1 elementof SYMBOL_VALUE & 1 elementof (1 metadataof SYMBOL_VALUE) relativeto relocatable & 1 scaleof (1 metadataof SYMBOL_VALUE) > 0
\r
408 SYMBOL_SECTION_INDEX = 1 scaleof (1 metadataof SYMBOL_VALUE)
\r
409 SYMBOL_VALUE = SYMBOL_VALUE - 1 elementof SYMBOL_VALUE
\r
411 SYMBOL_SECTION_INDEX = SHN_ABS
\r
413 store STRING_POSITION at symbol_table : Elf64_Sym.st_name + SYMBOL_INDEX * sizeof Elf64_Sym
\r
414 store SYMBOL_NAME : lengthof SYMBOL_NAME at string_table:STRING_POSITION
\r
415 STRING_POSITION = STRING_POSITION + lengthof SYMBOL_NAME + 1
\r
416 store SYMBOL_VALUE at symbol_table : Elf64_Sym.st_value + SYMBOL_INDEX * sizeof Elf64_Sym
\r
417 store SYMBOL_SIZE at symbol_table : Elf64_Sym.st_size + SYMBOL_INDEX * sizeof Elf64_Sym
\r
418 store SYMBOL_SECTION_INDEX at symbol_table : Elf64_Sym.st_shndx + SYMBOL_INDEX * sizeof Elf64_Sym
\r
420 store STT_OBJECT + STB_GLOBAL shl 4 at symbol_table : Elf64_Sym.st_info + SYMBOL_INDEX * sizeof Elf64_Sym
\r
422 store STT_FUNC + STB_GLOBAL shl 4 at symbol_table : Elf64_Sym.st_info + SYMBOL_INDEX * sizeof Elf64_Sym
\r
424 SYMBOL_INDEX = SYMBOL_INDEX + 1
\r
428 macro extrn? declaration*
\r
431 element sym : relocatable * (-1) + SYMBOL_INDEX
\r
432 element psym : PLT + SYMBOL_INDEX
\r
433 match str =as? name:size, declaration
\r
434 label name:size at sym
\r
435 label PLT.name at psym
\r
436 SYMBOL_NAME = string str
\r
438 else match name:size, declaration
\r
439 label name:size at sym
\r
440 label PLT.name at psym
\r
441 SYMBOL_NAME = `name
\r
443 else match str =as? name, declaration
\r
445 label PLT.name at psym
\r
446 SYMBOL_NAME = string str
\r
449 label declaration at sym
\r
450 label PLT.declaration at psym
\r
451 SYMBOL_NAME = `declaration
\r
454 store STRING_POSITION at symbol_table : Elf64_Sym.st_name + SYMBOL_INDEX * sizeof Elf64_Sym
\r
455 store SYMBOL_NAME : lengthof SYMBOL_NAME at string_table:STRING_POSITION
\r
456 STRING_POSITION = STRING_POSITION + lengthof SYMBOL_NAME + 1
\r
457 store SYMBOL_SIZE at symbol_table : Elf64_Sym.st_size + SYMBOL_INDEX * sizeof Elf64_Sym
\r
458 store STT_NOTYPE + STB_GLOBAL shl 4 at symbol_table : Elf64_Sym.st_info + SYMBOL_INDEX * sizeof Elf64_Sym
\r
459 SYMBOL_INDEX = SYMBOL_INDEX + 1
\r
465 calminstruction calminstruction?.init? var*, val:0
\r
468 end calminstruction
\r
470 calminstruction calminstruction?.initsym? var*, val&
\r
472 end calminstruction
\r
474 calminstruction calminstruction?.unique? name
\r
475 local counter, buffer
\r
477 compute counter, counter + 1
\r
478 arrange buffer, name#counter
\r
479 publish name, buffer
\r
480 end calminstruction
\r
482 calminstruction calminstruction?.asm? line&
\r
483 local tmp, ln, buffer
\r
484 initsym tmp, unique ln
\r
487 arrange buffer, =assemble ln
\r
489 end calminstruction
\r
491 calminstruction dword? value
\r
492 compute value, value
\r
493 check ~ value relativeto 0 & value relativeto 1 elementof value & 1 elementof (1 metadataof value) relativeto ELF.relocatable
\r
495 check ~ value relativeto 0 & (value + ELF.SECTION_BASE) relativeto 1 elementof (value + ELF.SECTION_BASE)
\r
497 check 1 elementof (1 metadataof (value + ELF.SECTION_BASE)) relativeto ELF.relocatable
\r
499 check 1 elementof (1 metadataof (value + ELF.SECTION_BASE)) relativeto PLT
\r
504 local offset, addend, info
\r
510 compute offset, offset - ELF.SECTION_OFFSET
\r
511 compute addend, 0 scaleof value
\r
512 compute info, ELF.R_32 + (0 scaleof (1 metadataof value)) shl 32
\r
513 jump add_relocation
\r
519 compute offset, offset - ELF.SECTION_OFFSET
\r
520 compute addend, 0 scaleof (value + ELF.SECTION_BASE + offset)
\r
521 compute info, ELF.R_PC32 + (0 scaleof (1 metadataof value)) shl 32
\r
522 jump add_relocation
\r
528 compute offset, offset - ELF.SECTION_OFFSET
\r
529 compute addend, 0 scaleof (value + ELF.SECTION_BASE + offset)
\r
530 compute info, ELF.R_PLT32 + (0 scaleof (1 metadataof value)) shl 32
\r
531 jump add_relocation
\r
534 compute Rela, ELF.RELOCATION_INDEX * sizeof Elf64_Rela
\r
535 asm store offset at ELF.relocations : Rela + Elf64_Rela.r_offset
\r
536 asm store addend at ELF.relocations : Rela + Elf64_Rela.r_addend
\r
537 asm store info at ELF.relocations : Rela + Elf64_Rela.r_info
\r
538 compute ELF.RELOCATION_INDEX, ELF.RELOCATION_INDEX + 1
\r
540 end calminstruction
\r
542 calminstruction qword? value
\r
543 compute value, value
\r
544 check ~ value relativeto 0 & value relativeto 1 elementof value & 1 elementof (1 metadataof value) relativeto ELF.relocatable
\r
549 local offset, addend, info
\r
555 compute offset, offset - ELF.SECTION_OFFSET
\r
556 compute addend, 0 scaleof value
\r
557 compute info, ELF.R_64 + (0 scaleof (1 metadataof value)) shl 32
\r
560 compute Rela, ELF.RELOCATION_INDEX * sizeof Elf64_Rela
\r
561 asm store offset at ELF.relocations : Rela + Elf64_Rela.r_offset
\r
562 asm store addend at ELF.relocations : Rela + Elf64_Rela.r_addend
\r
563 asm store info at ELF.relocations : Rela + Elf64_Rela.r_info
\r
564 compute ELF.RELOCATION_INDEX, ELF.RELOCATION_INDEX + 1
\r
566 end calminstruction
\r
568 iterate <dd,dword>, dd,dword, dq,qword
\r
570 calminstruction dd? definitions&
\r
573 match value=,definitions, definitions, ()
\r
575 match value, definitions
\r
576 arrange definitions,
\r
578 match n =dup? value, value, ()
\r
582 arrange value, =dword value
\r
585 match , definitions
\r
588 take definitions, definitions
\r
592 arrange value, =dd ?
\r
596 match (value), value
\r
600 take definitions, value
\r
601 arrange value, definitions
\r
604 end calminstruction
\r
606 calminstruction (label) dd? definitions&
\r
608 arrange cmd, =label label : =dword
\r
610 arrange cmd, =dd definitions
\r
612 end calminstruction
\r
621 SECTION_NAME_TABLE_SIZE := SECTION_NAME_POSITION
\r
622 STRING_TABLE_SIZE := STRING_POSITION
\r
624 NUMBER_OF_SECTION_SYMBOLS := SECTION_SYMBOL_INDEX
\r
625 NUMBER_OF_SYMBOLS := SYMBOL_INDEX
\r
626 SYMBOL_TABLE_SIZE := NUMBER_OF_SYMBOLS * sizeof Elf64_Sym
\r
628 NUMBER_OF_RELOCATIONS := RELOCATION_INDEX
\r
630 RELOCATIONS_OFFSET = $%
\r
631 load byte_sequence : NUMBER_OF_RELOCATIONS * sizeof Elf64_Rela from relocations:0
\r
634 store _symtab at section_table : Elf64_Shdr.sh_name + SECTION_INDEX * sizeof Elf64_Shdr
\r
635 store $% at section_table : Elf64_Shdr.sh_offset + SECTION_INDEX * sizeof Elf64_Shdr
\r
636 store SYMBOL_TABLE_SIZE at section_table : Elf64_Shdr.sh_size + SECTION_INDEX * sizeof Elf64_Shdr
\r
637 store sizeof Elf64_Sym at section_table : Elf64_Shdr.sh_entsize + SECTION_INDEX * sizeof Elf64_Shdr
\r
638 store 8 at section_table : Elf64_Shdr.sh_addralign + SECTION_INDEX * sizeof Elf64_Shdr
\r
639 store SHT_SYMTAB at section_table : Elf64_Shdr.sh_type + SECTION_INDEX * sizeof Elf64_Shdr
\r
640 store STRING_TABLE_SECTION_INDEX at section_table : Elf64_Shdr.sh_link + SECTION_INDEX * sizeof Elf64_Shdr
\r
641 store NUMBER_OF_SECTION_SYMBOLS at section_table : Elf64_Shdr.sh_info + SECTION_INDEX * sizeof Elf64_Shdr
\r
642 SYMBOL_TABLE_SECTION_INDEX := SECTION_INDEX
\r
643 load byte_sequence : SYMBOL_TABLE_SIZE from symbol_table:0
\r
645 SECTION_INDEX = SECTION_INDEX + 1
\r
647 store _strtab at section_table : Elf64_Shdr.sh_name + SECTION_INDEX * sizeof Elf64_Shdr
\r
648 store $% at section_table : Elf64_Shdr.sh_offset + SECTION_INDEX * sizeof Elf64_Shdr
\r
649 store STRING_TABLE_SIZE at section_table : Elf64_Shdr.sh_size + SECTION_INDEX * sizeof Elf64_Shdr
\r
650 store 1 at section_table : Elf64_Shdr.sh_addralign + SECTION_INDEX * sizeof Elf64_Shdr
\r
651 store SHT_STRTAB at section_table : Elf64_Shdr.sh_type + SECTION_INDEX * sizeof Elf64_Shdr
\r
652 STRING_TABLE_SECTION_INDEX := SECTION_INDEX
\r
653 load byte_sequence : STRING_TABLE_SIZE from string_table:0
\r
655 SECTION_INDEX = SECTION_INDEX + 1
\r
657 assert SECTION_INDEX <= SHN_LORESERVE
\r
659 NUMBER_OF_SECTIONS := SECTION_INDEX
\r
661 SECTION_TABLE_OFFSET := $%
\r
662 load byte_sequence : NUMBER_OF_SECTIONS * sizeof Elf64_Shdr from section_table:0
\r