diff --git a/Makefile b/Makefile index 4d4d98c..5b55a2d 100644 --- a/Makefile +++ b/Makefile @@ -1,12 +1,24 @@ +help: ## Print this help message + @M=$$(perl -ne 'm/^((\w|-)*):.*##/ && print length($$1)."\n"' Makefile | \ + sort -nr | head -1) && \ + perl -ne "m/^((\w|-)*):.*##\s*(.*)/ && print(sprintf(\"%s: %s\t%s\n\", \$$1, \" \"x($$M-length(\$$1)), \$$3))" Makefile -hello32: +hello32: hello32.s ## Build the 32 bit version of Project 1 nasm -f elf hello32.s ld -m elf_i386 -o hello32 hello32.o -hello64: +hello64: hello64.s ## Build the 32 bit version of Project 1 nasm -f elf64 hello64.s ld -o hello64 hello64.o -clean: - rm -f hello32 hello64 *.o +hello-strlen32: hello-strlen32.s ## Build the 32 bit version of Project 1 + nasm -f elf hello-strlen32.s + ld -m elf_i386 -o hello-strlen32 hello-strlen32.o + +hello-strlen64: hello-strlen64.s ## Build the 32 bit version of Project 1 + nasm -f elf64 hello-strlen64.s + ld -o hello-strlen64 hello-strlen64.o + +clean: ## Delete all built and intermediate features + rm -f hello32 hello64 hello-strlen32 hello-strlen64 *.o diff --git a/hello-strlen32.s b/hello-strlen32.s new file mode 100755 index 0000000..e01d116 --- /dev/null +++ b/hello-strlen32.s @@ -0,0 +1,47 @@ + ;; Hello World Program #1 + ;; Compile with: nasm -f elf hello.s + ;; Link with: ld -m elf_i386 -o hello hello.o + ;; Run with: ./hello + + ;; sys/unistd_32.h +%define SYS_write 4 +%define SYS_exit 1 + + ;; unistd.h +%define STDOUT 1 + +section .data + msg db "Hello You Beautiful Human, You're Looking Fine Today!", 0Ah, 00h + +section .text + global _start + +_start: + mov ebx, msg ; Move the address of the message into ebx + mov eax, ebx ; Move the address of the message into eax (Register-to-register copying is faster that a constant!) + +nextchar: + cmp byte [eax], 0 ; Compare the byte pointed to by eax with zero. + + ;; Small detail: cmp and sub use the same internal architecture, + ;; except cmp doesn't copy the results into the first operand and + ;; sub does. cmp sets flags; does sub? This is why 'jz' works, + ;; because if they're equal the result of subtraction is zero. + jz counted ; Jump if the zero flag set + inc eax + jmp nextchar + +counted: + sub eax, ebx ; Subtract the end from the start, and the result goes into the start + + mov edx, eax ; syswrite needs that register for something else! Man, picking registers is hard. + mov ecx, msg ; Address of the message (not the content) + mov ebx, STDOUT ; using STDOUT (see definition above) + mov eax, SYS_write ; Using WRITE in 32-bit mode? + int 80h ; Interrupt target. The 'h' means 'hexidecimal' + + mov ebx, 0 + mov eax, SYS_exit + int 80h + + diff --git a/hello-strlen64.s b/hello-strlen64.s new file mode 100644 index 0000000..98f1daa --- /dev/null +++ b/hello-strlen64.s @@ -0,0 +1,47 @@ + ;; Hello World Program #1 + ;; Compile with: nasm -f elf64 hello.s + ;; Link with: ld -o hello hello.o + ;; Run with: ./hello + + ;; sys/unistd_64.h +%define SYS_write 1 +%define SYS_exit 60 + + ;; unistd.h +%define STDOUT 1 + +section .data + msg db "Hello You Beautiful Human, You're Looking Mighty Fine!", 0Ah, 00h + +section .text + global _start + +_start: + mov rsi, msg ; Move the address of the message into rsi + mov rax, rsi ; Move the address of the message into rax + ; (Register-to-register copying is faster that a constant!) + +nextchar: + cmp byte [rax], 0 ; Compare the byte pointed to by eax with zero + + + ;; Small detail: cmp and sub use the same internal architecture, + ;; except cmp doesn't copy the results into the first operand and + ;; sub does. cmp sets flags; does sub? This is why 'jz' works, + ;; because if they're equal the result of subtraction is zero. + jz counted ; Jump if the zero flag set + inc rax + jmp nextchar + +counted: + sub rax, rsi ; Substract source from endpointer, leaving counter + mov rdx, rax ; Length of the message + mov rsi, msg ; Address of the message + mov rdi, STDOUT ; using STDOUT (see definition above) + mov rax, SYS_write ; Using WRITE in 32-bit mode? + syscall + + mov rdi, 0 + mov rax, SYS_exit + syscall + diff --git a/hello32.s b/hello32.s index f9d5a30..63aad58 100755 --- a/hello32.s +++ b/hello32.s @@ -1,5 +1,5 @@ ;; Hello World Program #1 - ;; Compile with: nasm -f elf32 hello.s + ;; Compile with: nasm -f elf hello.s ;; Link with: ld -m elf_i386 -o hello hello.o ;; Run with: ./hello @@ -12,12 +12,13 @@ section .data msg db "Hello You Beautiful Human", 0Ah - + len equ $-msg ; NASM-supplied macro + section .text global _start _start: - mov edx, 26d ; Length of the message. The 'd' means 'decimal' + mov edx, len mov ecx, msg ; Address of the message (not the content) mov ebx, STDOUT ; using STDOUT (see definition above) mov eax, SYS_write ; Using WRITE in 32-bit mode? diff --git a/hello64.s b/hello64.s index 04d0195..1b8ae3a 100644 --- a/hello64.s +++ b/hello64.s @@ -1,6 +1,6 @@ ;; Hello World Program #1 - ;; Compile with: nasm -f elf32 hello.s - ;; Link with: ld -m elf_i386 -o hello hello.o + ;; Compile with: nasm -f elf64 hello.s + ;; Link with: ld -o hello hello.o ;; Run with: ./hello ;; sys/unistd_64.h @@ -12,12 +12,13 @@ section .data msg db "Hello You Beautiful Human", 0Ah + len equ $-msg ; NASM-supplied macro section .text global _start _start: - mov rdx, 26d ; Length of the message + mov rdx, len ; Length of the message mov rsi, msg ; Address of the message mov rdi, STDOUT ; using STDOUT (see definition above) mov rax, SYS_write ; Using WRITE in 32-bit mode?