hello.asm
section .text
global _start ;must be declared for linker (ld)
_start: ;tell linker entry point
mov edx,len ;message length
mov ecx,msg ;message to write
mov ebx,1 ;file descriptor (stdout)
mov eax,4 ;system call number (sys_write)
int 0x80 ;call kernel
mov eax,1 ;system call number (sys_exit)
int 0x80 ;call kernel
section .data
msg db 'Hello, world!',0xa ;our dear string
len equ $ - msg ;length of our dear string
$ nasm -f elf64 hello.asm # this will produce hello.o ELF object file elf for 32bit
$ ld -s -o hello hello.o # this will produce hello executable
$ xxd hello
00000000: 7f45 4c46 0201 0100 0000 0000 0000 0000 .ELF............
00000010: 0200 3e00 0100 0000 b000 4000 0000 0000 ..>.......@.....
00000020: 4000 0000 0000 0000 f800 0000 0000 0000 @...............
00000030: 0000 0000 4000 3800 0200 4000 0400 0300 ....@.8...@.....
00000040: 0100 0000 0500 0000 0000 0000 0000 0000 ................
00000050: 0000 4000 0000 0000 0000 4000 0000 0000 ..@.......@.....
00000060: cd00 0000 0000 0000 cd00 0000 0000 0000 ................
00000070: 0000 2000 0000 0000 0100 0000 0600 0000 .. .............
00000080: d000 0000 0000 0000 d000 6000 0000 0000 ..........`.....
00000090: d000 6000 0000 0000 0e00 0000 0000 0000 ..`.............
000000a0: 0e00 0000 0000 0000 0000 2000 0000 0000 .......... .....
000000b0: ba0e 0000 00b9 d000 6000 bb01 0000 00b8 ........`.......
000000c0: 0400 0000 cd80 b801 0000 00cd 8000 0000 ................
000000d0: 4865 6c6c 6f2c 2077 6f72 6c64 210a 002e Hello, world!...
000000e0: 7368 7374 7274 6162 002e 7465 7874 002e shstrtab..text..
000000f0: 6461 7461 0000 0000 0000 0000 0000 0000 data............
00000100: 0000 0000 0000 0000 0000 0000 0000 0000 ................
00000110: 0000 0000 0000 0000 0000 0000 0000 0000 ................
00000120: 0000 0000 0000 0000 0000 0000 0000 0000 ................
00000130: 0000 0000 0000 0000 0b00 0000 0100 0000 ................
00000140: 0600 0000 0000 0000 b000 4000 0000 0000 ..........@.....
00000150: b000 0000 0000 0000 1d00 0000 0000 0000 ................
00000160: 0000 0000 0000 0000 1000 0000 0000 0000 ................
00000170: 0000 0000 0000 0000 1100 0000 0100 0000 ................
00000180: 0300 0000 0000 0000 d000 6000 0000 0000 ..........`.....
00000190: d000 0000 0000 0000 0e00 0000 0000 0000 ................
000001a0: 0000 0000 0000 0000 0400 0000 0000 0000 ................
000001b0: 0000 0000 0000 0000 0100 0000 0300 0000 ................
000001c0: 0000 0000 0000 0000 0000 0000 0000 0000 ................
000001d0: de00 0000 0000 0000 1700 0000 0000 0000 ................
000001e0: 0000 0000 0000 0000 0100 0000 0000 0000 ................
000001f0: 0000 0000 0000 0000 ........
0x7F followed by ELF(45 4c 46) in ASCII; these four bytes constitute the magic number.
ascii art elf header
+-------------------+-------------------+-------------------------------------------------------+
| Position (32 bit) | Position (64 bit) | Value |
+-------------------+-------------------+-------------------------------------------------------+
| 0-3 | 0-3 | Magic number - 0x7F, then 'ELF' in ASCII |
| 4 | 4 | 1 = 32 bit, 2 = 64 bit |
| 5 | 5 | 1 = little endian, 2 = big endian |
| 6 | 6 | ELF Version |
| 7 | 7 | OS ABI - usually 0 for System V |
| 8-15 | 8-15 | Unused/padding |
| 16-17 | 16-17 | 1 = relocatable, 2 = executable, 3 = shared, 4 = core |
| 18-19 | 18-19 | Instruction set - see table below |
| 20-23 | 20-23 | ELF Version |
| 24-27 | 24-31 | Program entry position |
| 28-31 | 32-39 | Program header table position |
| 32-35 | 40-47 | Section header table position |
| 36-39 | 48-51 | Flags - architecture dependent; see note below |
| 40-41 | 52-53 | Header size |
| 42-43 | 54-55 | Size of an entry in the program header table |
| 44-45 | 56-57 | Number of entries in the program header table |
| 46-47 | 58-59 | Size of an entry in the section header table |
| 48-49 | 60-61 | Number of entries in the section header table |
| 50-51 | 62-63 | Index in section header table with the section names |
+-------------------+-------------------+-------------------------------------------------------+
$ readelf -h hello
ELF Header:
Magic: 7f 45 4c 46 02 01 01 00 00 00 00 00 00 00 00 00
Class: ELF64
Data: 2's complement, little endian
Version: 1 (current)
OS/ABI: UNIX - System V
ABI Version: 0
Type: EXEC (Executable file)
Machine: Advanced Micro Devices X86-64
Version: 0x1
Entry point address: 0x4000b0
Start of program headers: 64 (bytes into file)
Start of section headers: 248 (bytes into file)
Flags: 0x0
Size of this header: 64 (bytes)
Size of program headers: 56 (bytes)
Number of program headers: 2
Size of section headers: 64 (bytes)
Number of section headers: 4
Section header string table index: 3
New Little Endian Test
#include <stdio.h>
#include <stdlib.h>
int main () {
FILE * pFile;
long lSize;
char * buffer;
size_t result;
pFile = fopen ( "hello" , "rb" );
lSize = 6;
// allocate memory to contain the whole file:
buffer = (char*) malloc (sizeof(char)*lSize);
if (buffer == NULL) {fputs ("Memory error",stderr); exit (2);}
// copy the file into the buffer:
result = fread (buffer,1,lSize,pFile);
if (result != lSize) {fputs ("Reading error",stderr); exit (3);}
if (buffer[5] == 0x01){
printf("%s\n", "Little Endian");
} else {
printf("%s\n", "Big Endian");
}
// terminate
fclose (pFile);
free (buffer);
return 0;
}