Sample nasm programs

Specifically: for Intel I-32, e.g. 386, 486, pentium

Specifically: for use with gcc with its libraries and gdb

Specifically: simple nasm syntax using "C" literals

Specifically: showing an equivalent "C" program

Generally, for Linux and possibly other Unix on Intel

Generally, not using 8-bit or 16-bit for anything

The 64-bit samples are here

Contents

  • Makefile for samples shown below
  • hello.asm basic stand alone program
  • printf1.asm basic calling printf
  • printf2.asm more types for printf
  • intarith.asm simple integer arithmetic
  • fltarith.asm simple floating point arithmetic
  • hello.asm basic stand alone program

      The nasm source code is hello.asm
      The result of the assembly is hello.lst
      Running the program produces output hello.out
    
      This program demonstrates basic text output to a screen.
      No "C" library functions are used.
      Calls are made to the operating system directly. (int 80 hex)
    
    ;  hello.asm  a first program for nasm for Linux, Intel, gcc
    ;
    ; assemble:	nasm -f elf -l hello.lst  hello.asm
    ; link:		gcc -o hello  hello.o
    ; run:	        hello 
    ; output is:	Hello World 
    
    	SECTION .data		; data section
    msg:	db "Hello World",10	; the string to print, 10=cr
    len:	equ $-msg		; "$" means "here"
    				; len is a value, not an address
    
    	SECTION .text		; code section
            global main		; make label available to linker 
    main:				; standard  gcc  entry point
    	
    	mov	edx,len		; arg3, length of string to print
    	mov	ecx,msg		; arg2, pointer to string
    	mov	ebx,1		; arg1, where to write, screen
    	mov	eax,4		; write sysout command to int 80 hex
    	int	0x80		; interrupt 80 hex, call kernel
    	
    	mov	ebx,0		; exit code, 0=normal
    	mov	eax,1		; exit command to kernel
    	int	0x80		; interrupt 80 hex, call kernel
       
    

    printf1.asm basic calling printf

      The nasm source code is printf1.asm
      The result of the assembly is printf1.lst
      The equivalent "C" program is printf1.c
      Running the program produces output printf1.out
    
      This program demonstrates basic use of "C" library function  printf.
      The equivalent "C" code is shown as comments in the assembly language.
    
    ; printf1.asm   print an integer from storage and from a register
    ; Assemble:	nasm -f elf -l printf.lst  printf1.asm
    ; Link:		gcc -o printf1  printf1.o
    ; Run:		printf1
    ; Output:	a=5, eax=7
    
    ; Equivalent C code
    ; /* printf1.c  print an int and an expression */
    ; #include 
    ; int main()
    ; {
    ;   int a=5;
    ;   printf("a=%d, eax=%d\n", a, a+2);
    ;   return 0;
    ; }
    
    ; Declare some external functions
    ;
            extern	printf		; the C function, to be called
    
            SECTION .data		; Data section, initialized variables
    
    	a:	dd	5		; int a=5;
    fmt:    db "a=%d, eax=%d", 10, 0 ; The printf format, "\n",'0'
    
    
            SECTION .text                   ; Code section.
    
            global main		; the standard gcc entry point
    main:				; the program label for the entry point
            push    ebp		; set up stack frame
            mov     ebp,esp
    
    	mov	eax, [a]	; put a from store into register
    	add	eax, 2		; a+2
    	push	eax		; value of a+2
            push    dword [a]	; value of variable a
            push    dword fmt	; address of ctrl string
            call    printf		; Call C function
            add     esp, 12		; pop stack 3 push times 4 bytes
    
            mov     esp, ebp	; takedown stack frame
            pop     ebp		; same as "leave" op
    
    	mov	eax,0		;  normal, no error, return value
    	ret			; return
    	
    
    
    

    printf2.asm more types with printf

      The nasm source code is printf2.asm
      The result of the assembly is printf2.lst
      The equivalent "C" program is printf2.c
      Running the program produces output printf2.out
    
      This program demonstrates basic use of "C" library function  printf.
      The equivalent "C" code is shown as comments in the assembly language.
    
    ; printf2.asm  use "C" printf on char, string, int, double
    ; 
    ; Assemble:	nasm -f elf -l printf2.lst  printf2.asm
    ; Link:		gcc -o printf2  printf2.o
    ; Run:		printf2
    ; Output:	
    ;Hello world: a string of length 7 1234567 6789ABCD 5.327000e-30 -1.234568E+302
    ; 
    ; A similar "C" program
    ; #include 
    ; int main()
    ; {
    ;   char   char1='a';         /* sample character */
    ;   char   str1[]="string";   /* sample string */
    ;   int    int1=1234567;      /* sample integer */
    ;   int    hex1=0x6789ABCD;   /* sample hexadecimal */
    ;   float  flt1=5.327e-30;    /* sample float */
    ;   double flt2=-123.4e300;   /* sample double */
    ; 
    ;   printf("Hello world: %c %s %d %X %e %E \n", /* format string for printf */
    ;          char1, str1, int1, hex1, flt1, flt2);
    ;   return 0;
    ; }
    
    
            extern printf                   ; the C function to be called
    
            SECTION .data                   ; Data section
    
    msg:    db "Hello world: %c %s of length %d %d %X %e %E",10,0
    					; format string for printf
    char1:	db	'a'			; a character 
    str1:	db	"string",0	        ; a C string, "string" needs 0
    len:	equ	$-str1			; len has value, not an address
    inta1:	dd	1234567		        ; integer 1234567
    hex1:	dd	0x6789ABCD	        ; hex constant 
    flt1:	dd	5.327e-30		; 32-bit floating point
    flt2:	dq	-123.456789e300	        ; 64-bit floating point
    
    	SECTION .bss
    		
    flttmp:	resq 1			        ; 64-bit temporary for printing flt1
    	
            SECTION .text                   ; Code section.
    
            global	main		        ; "C" main program 
    main:				        ; label, start of main program
    	 
    	fld	dword [flt1]	        ; need to convert 32-bit to 64-bit
    	fstp	qword [flttmp]          ; floating load makes 80-bit,
    	                                ; store as 64-bit
    	                                ; push last argument first
    	push	dword [flt2+4]	        ; 64 bit floating point (bottom)
    	push	dword [flt2]	        ; 64 bit floating point (top)
    	push	dword [flttmp+4]        ; 64 bit floating point (bottom)
    	push	dword [flttmp]	        ; 64 bit floating point (top)
    	push	dword [hex1]	        ; hex constant
    	push	dword [inta1]	        ; integer data pass by value
    	push	dword len	        ; constant pass by value
    	push	dword str1		; "string" pass by reference 
            push    dword [char1]		; 'a'
            push    dword msg		; address of format string
            call    printf			; Call C function
            add     esp, 40			; pop stack 10*4 bytes
    
            mov     eax, 0			; exit code, 0=normal
            ret				; main returns to operating system
    
    
    

    intarith.asm simple integer arithmetic

      The nasm source code is intarith.asm
      The result of the assembly is intarith.lst
      The equivalent "C" program is intarith.c
      Running the program produces output intarith.out
    
      This program demonstrates basic integer arithmetic  add, subtract,
      multiply and divide.
      The equivalent "C" code is shown as comments in the assembly language.
    
    ; intarith.asm    show some simple C code and corresponding nasm code
    ;                 the nasm code is one sample, not unique
    ;
    ; compile:	nasm -f elf -l intarith.lst  intarith.asm
    ; link:		gcc -o intarith  intarith.o
    ; run:		intarith
    ;
    ; the output from running intarith.asm and intarith.c is:	
    ; c=5  , a=3, b=4, c=5
    ; c=a+b, a=3, b=4, c=7
    ; c=a-b, a=3, b=4, c=-1
    ; c=a*b, a=3, b=4, c=12
    ; c=c/a, a=3, b=4, c=4
    ;
    ;The file  intarith.c  is:
    ;  /* intarith.c */
    ;  #include 
    ;  int main()
    ;  { 
    ;    int a=3, b=4, c;
    ;
    ;    c=5;
    ;    printf("%s, a=%d, b=%d, c=%d\n","c=5  ", a, b, c);
    ;    c=a+b;
    ;    printf("%s, a=%d, b=%d, c=%d\n","c=a+b", a, b, c);
    ;    c=a-b;
    ;    printf("%s, a=%d, b=%d, c=%d\n","c=a-b", a, b, c);
    ;    c=a*b;
    ;    printf("%s, a=%d, b=%d, c=%d\n","c=a*b", a, b, c);
    ;    c=c/a;
    ;    printf("%s, a=%d, b=%d, c=%d\n","c=c/a", a, b, c);
    ;    return 0;
    ; }
    
            extern printf		; the C function to be called
    
    %macro	pabc 1			; a "simple" print macro
    	section .data
    .str	db	%1,0		; %1 is first actual in macro call
    	section .text
    				; push onto stack backwards 
    	push	dword [c]	; int c
    	push	dword [b]	; int b 
    	push	dword [a]	; int a
    	push	dword .str 	; users string
            push    dword fmt       ; address of format string
            call    printf          ; Call C function
            add     esp,20          ; pop stack 5*4 bytes
    %endmacro
    	
    	section .data  		; preset constants, writeable
    a:	dd	3		; 32-bit variable a initialized to 3
    b:	dd	4		; 32-bit variable b initializes to 4
    fmt:    db "%s, a=%d, b=%d, c=%d",10,0	; format string for printf
    	
    	section .bss 		; unitialized space
    c:	resd	1		; reserve a 32-bit word
    
    	section .text		; instructions, code segment
    	global	 main		; for gcc standard linking
    main:				; label
    	
    lit5:				; c=5;
    	mov	eax,5	 	; 5 is a literal constant
    	mov	[c],eax		; store into c
    	pabc	"c=5  "		; invoke the print macro
    	
    addb:				; c=a+b;
    	mov	eax,[a]	 	; load a
    	add	eax,[b]		; add b
    	mov	[c],eax		; store into c
    	pabc	"c=a+b"		; invoke the print macro
    	
    subb:				; c=a-b;
    	mov	eax,[a]	 	; load a
    	sub	eax,[b]		; subtract b
    	mov	[c],eax		; store into c
    	pabc	"c=a-b"		; invoke the print macro
    	
    mulb:				; c=a*b;
    	mov	eax,[a]	 	; load a (must be eax for multiply)
    	imul	dword [b]	; signed integer multiply by b
    	mov	[c],eax		; store bottom half of product into c
    	pabc	"c=a*b"		; invoke the print macro
    	
    diva:				; c=c/a;
    	mov	eax,[c]	 	; load c
    	mov	edx,0		; load upper half of dividend with zero
    	idiv	dword [a]	; divide double register edx eax by a
    	mov	[c],eax		; store quotient into c
    	pabc	"c=c/a"		; invoke the print macro
    
            mov     eax,0           ; exit code, 0=normal
    	ret			; main return to operating system
    
    
    
    

    fltarith.asm simple floating point arithmetic

      The nasm source code is fltarith.asm
      The result of the assembly is fltarith.lst
      The equivalent "C" program is fltarith.c
      Running the program produces output fltarith.out
    
      This program demonstrates basic floating point add, subtract,
      multiply and divide.
      The equivalent "C" code is shown as comments in the assembly language.
    
    ; fltarith.asm   show some simple C code and corresponding nasm code
    ;                the nasm code is one sample, not unique
    ;
    ; compile  nasm -f elf -l fltarith.lst  fltarith.asm
    ; link     gcc -o fltarith  fltarith.o
    ; run      fltarith
    ;
    ; the output from running fltarith and fltarithc is:	
    ; c=5.0, a=3.000000e+00, b=4.000000e+00, c=5.000000e+00
    ; c=a+b, a=3.000000e+00, b=4.000000e+00, c=7.000000e+00
    ; c=a-b, a=3.000000e+00, b=4.000000e+00, c=-1.000000e+00
    ; c=a*b, a=3.000000e+00, b=4.000000e+00, c=1.200000e+01
    ; c=c/a, a=3.000000e+00, b=4.000000e+00, c=4.000000e+00
    ;
    ;The file  fltarith.c  is:
    ;  #include 
    ;  int main()
    ;  { 
    ;    double a=3.0, b=4.0, c;
    ;
    ;    c=5.0;
    ;    printf("%s, a=%e, b=%e, c=%e\n","c=5.0", a, b, c);
    ;    c=a+b;
    ;    printf("%s, a=%e, b=%e, c=%e\n","c=a+b", a, b, c);
    ;    c=a-b;
    ;    printf("%s, a=%e, b=%e, c=%e\n","c=a-b", a, b, c);
    ;    c=a*b;
    ;    printf("%s, a=%e, b=%e, c=%e\n","c=a*b", a, b, c);
    ;    c=c/a;
    ;    printf("%s, a=%e, b=%e, c=%e\n","c=c/a", a, b, c);
    ;    return 0;
    ; }
    
            extern printf		; the C function to be called
    
    %macro	pabc 1			; a "simple" print macro
    	section	.data
    .str	db	%1,0		; %1 is macro call first actual parameter
    	section .text
    				; push onto stack backwards 
    	push	dword [c+4]	; double c (bottom)
    	push	dword [c]	; double c
    	push	dword [b+4]	; double b (bottom)
    	push	dword [b]	; double b 
    	push	dword [a+4]	; double a (bottom)
    	push	dword [a]	; double a
    	push	dword .str 	; users string
            push    dword fmt       ; address of format string
            call    printf          ; Call C function
            add     esp,32          ; pop stack 8*4 bytes
    %endmacro
    	
    	section	.data  		; preset constants, writeable
    a:	dq	3.333333333	; 64-bit variable a initialized to 3.0
    b:	dq	4.444444444	; 64-bit variable b initializes to 4.0
    five:	dq	5.0		; constant 5.0
    fmt:    db "%s, a=%e, b=%e, c=%e",10,0	; format string for printf
    	
    	section .bss 		; unitialized space
    c:	resq	1		; reserve a 64-bit word
    
    	section .text		; instructions, code segment
    	global	main		; for gcc standard linking
    main:				; label
    	
    lit5:				; c=5.0;
    	fld	qword [five]	; 5.0 constant
    	fstp	qword [c]	; store into c
    	pabc	"c=5.0"		; invoke the print macro
    	
    addb:				; c=a+b;
    	fld	qword [a] 	; load a (pushed on flt pt stack, st0)
    	fadd	qword [b]	; floating add b (to st0)
    	fstp	qword [c]	; store into c (pop flt pt stack)
    	pabc	"c=a+b"		; invoke the print macro
    	
    subb:				; c=a-b;
    	fld	qword [a] 	; load a (pushed on flt pt stack, st0)
    	fsub	qword [b]	; floating subtract b (to st0)
    	fstp	qword [c]	; store into c (pop flt pt stack)
    	pabc	"c=a-b"		; invoke the print macro
    	
    mulb:				; c=a*b;
    	fld	qword [a]	; load a (pushed on flt pt stack, st0)
    	fmul	qword [b]	; floating multiply by b (to st0)
    	fstp	qword [c]	; store product into c (pop flt pt stack)
    	pabc	"c=a*b"		; invoke the print macro
    	
    diva:				; c=c/a;
    	fld	qword [c] 	; load c (pushed on flt pt stack, st0)
    	fdiv	qword [a]	; floating divide by a (to st0)
    	fstp	qword [c]	; store quotient into c (pop flt pt stack)
    	pabc	"c=c/a"		; invoke the print macro
    
            mov     eax,0           ; exit code, 0=normal
    	ret			; main returns to operating system
    
    
    
    
    

    Now upgrade to 64-bit samples

    Go to top

    Last updated 1/25/2015