0% found this document useful (0 votes)
248 views

'Hello World' in 32-Bit Linux Assembly

This document provides instructions for writing a "Hello World" program in 32-bit Linux Assembly using NASM. It includes the source code, explains how to compile and link it into an executable, and run the program. It notes that while the code is short, the resulting ELF binary is larger than necessary due to linkage requirements, but can be optimized smaller. Background information on Linux system calls and NASM is provided for further reading.
Copyright
© © All Rights Reserved
Available Formats
Download as DOCX, PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
248 views

'Hello World' in 32-Bit Linux Assembly

This document provides instructions for writing a "Hello World" program in 32-bit Linux Assembly using NASM. It includes the source code, explains how to compile and link it into an executable, and run the program. It notes that while the code is short, the resulting ELF binary is larger than necessary due to linkage requirements, but can be optimized smaller. Background information on Linux system calls and NASM is provided for further reading.
Copyright
© © All Rights Reserved
Available Formats
Download as DOCX, PDF, TXT or read online on Scribd
You are on page 1/ 5

Hello World in 32-bit Linux Assembly (NASM)

Posted on April 30, 2012

Writing a 32 bit Hello World program in NASM is a good first step for anyone that wants to learn Linux assembly. Whether youre a programmer who wants to try some assembly optimization or an aspiring shellcoder, theres no avoiding Hello World (unless you luck out and find an assembly quine tutorial). In-depth Linux assembly guides with complete background information are available all over the place, beginning with Sourceforges NASM manual. The Hello World routine below could serve as a good quickstart for Linux NASM, or Linux assembly in general. It includes NASM source code and brief compilation instructions. How to write, compile and run a Hello World program in 32 bit Linux assembly (NASM): 1. Install NASM. 2. Write or copy/paste your assembly source file 3. Compile the assembly into machine code with NASM. 4. Link the compiled code with ld or gcc. 5. Run the resulting ELF executable. Update: You can download the commented source code and a convenient Makefile for the 32-bit and 64-bit NASM Hello World programs here (tarball). Its all automated.

1. Install NASM and build-essential


I used apt-get to install NASM on my computer. Its important to note that I did this on a 64 bit version of Ubuntu 11.10. System calls and tools can be very different between distributions. This process may not work at all on other versions or distributions. I cant vouch.

1 2 $ sudo apt-get install nasm build-essential 3

2. Create the assembly source

Download the source code or copy and paste from here:

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28

; "Hello World!" in 32 bit Linux NASM ; adapted from http://asm.sourceforge.net/intro/hello.html by Mark Loiseau ; referenced in http://blog.markloiseau.com/2012/04/hello-world-NASM-Linux global _start section .text _start: ; sys_write(stdout, message, length) mov eax, 4 ; sys_write syscall mov ebx, 1 ; stdout mov ecx, message ; message address mov edx, length ; message string length int 80h ; sys_exit(return_code) mov eax, 1 mov ebx, 0 int 80h ; sys_exit syscall ; return 0 (success) ; global entry point export for ld

section .data message: db 'Hello, world!',0x0A ; message and newline length: equ $-message ; NASM definition pseudo-instruction

If you find the assembly code confusing, there is a more detailed explanation here.

Brief Explanation:
The number in EAX refers to a system function. In this case, the system is Linux and the system call in EAX is 4. Linux system call 4 refers to the sys_write function, which writes a given amount of data from memory to a file descriptor. We want to write the data at address message to stdout, so we put 1 in EBX because 1 refers to stdout. Then we put the address of our message in ECX and the message length in EDX. Were telling the system to take length bytes of data from the message address and write them tostdout. In C, sys_write is a function with three arguments that has a prototype like this:

1 2 sys_write(unsigned int file_descriptor, const char * message, size_t length); 3

Once weve placed our syscall and its arguments in the right registers, we trigger interrupt 80h. The int 80h code tells the system to do it! The sys_exit routine has a similar setup. We put the sys_exit system call (1) in EAX and its only argument (0) in EBX. Then we call interrupt 80h and the code in address 80h of the Interrupt Vector Table runs sys_exit, cleanly ending our program. If the short summary isnt enough for you, consider checking some of the background links.

3. Compile the Assembly program into machine code


Save your assembly code as hello32.nasm and issue the following command: 64 bit system: $ nasm -f elf64 -o hello32.o hello32.nasm 32 bit system: $ nasm -f elf -o hello32.o hello32.nasm This will translate your assembly program into x86 machine code that your processor can understand. NASM supports a variety of architectures. You can see the list by typing $ nasm -hf Unfortunately, raw machine code cant be run by itself. It needs to be presented to the operating system in a standardized format with a few pieces or relevant metadata. Linux uses the Executable and Linkable Format (ELF) for executables. To run our compiled code, we need to link it into an ELF binary.

4. Link the machine code into an ELF binary


The following command will use ld, the dynamic linker and loader, to link our NASM-compiled machine code into an ELF binary.

1 2 $ ld -o hello32 hello32.o 3

5. Run the executable


The newly linked ELF binary can be run like any other program:

1 2 $ ./hello32 3 Hello World! 4

If your code segfaulted before or after displaying Hello World, there is something different between your system and mine. Either your OS and syscalls arent like mine, your architecture isnt like mine, or you have a typo in your code. Its possible that something e ven stranger happened, like an incompatibility in ld or NASM. Any debugging is left as an exercise to the reader. If your code didnt segfault, congratulations! If youre like me, you may have typed $wc hello32 and noticed that your ELF binary is around a kilobyte in size. Youre probably thinking, The original code is so short! Is all that space really necessary? I thought the same thing, and the answer is no. With a little bit of streamlining, we can compile our code into a much smaller ELF executable.

Further Reading
Introduction to UNIX assembly programming NASM Manual / Linux Assembly Tutorial Linux 2.2 System Call Table / Linux 2.6.35 System Call Table Linux System Calls for HLA Programmers by Randall Hyde (This is the best paper on Linux system calls in assembly Ive encountered) Incoming search terms:

NASM LINUX

NASM TUTORIAL

NASM HELLO WORLD

LINUX NASM

HELLO WORLD NASM

NASM FOR LINUX

NASM TUTORIAL LINUX

NASM UBUNTU

NASM ON LINUX

NASM 32 BIT

This entry was filed under Programming and tagged Assembly, hello world, linux, NASM, system calls, tutorial by mark. Bookmark the permalink.

You might also like