YouTip LogoYouTip

Assembly Loop

Assembly Language - Loop Structures

Loops are one of the most common control structures in programming. In assembly language, you can use the LOOP instruction or conditional jumps to implement various loop logic. * * *

The LOOP Instruction

LOOP is an x86 instruction specifically designed for loops, using ECX as a counter: Each time LOOP is executed, ECX is automatically decremented by 1. If ECX is not 0, it jumps to the target label.

Example

; File path: loop_basic.asm

; Basic usage of LOOP instruction: repeat output 5 times

section.data

 msg db'tutorial',0xA

 len equ$- msg

section.text

global _start

_start:

mov ecx,5; Loop counter = 5 (loop 5 times)

repeat:

; Save ecx (system call might modify it)

push ecx

; Output msg

mov eax,4

mov ebx,1

mov ecx, msg

mov edx, len

int 0x80

; Restore ecx

pop ecx

loop repeat ; ecx--; if ecx != 0 jump to repeat

mov eax,1

mov ebx,0

int 0x80
Running result:
$ nasm -f elf32 loop_basic.asm -o loop_basic.o $ ld -m elf_i386 loop_basic.o -o loop_basic $ ./loop_basic tutorial tutorial tutorial tutorial tutorial

loop uses ECX (32-bit) as the counter by default. In 16-bit mode, CX is used; in 64-bit mode, RCX is used. Make sure to set the value of ECX correctly before the loop.

* * *

LOOP Variants

Instruction Jump Condition Description
LOOP ECX != 0 Standard loop, decrements ECX first then checks
LOOPE / LOOPZ ECX != 0 and ZF = 1 Continue loop if equal
LOOPNE / LOOPNZ ECX != 0 and ZF = 0 Continue loop if not equal

Example

; LOOPE example: find the first non-zero value in an array

section.data

 array db 0,0,0,5,0,0; First three are 0, fourth is 5

section.text

global _start

_start:

mov ecx,6; Array length

mov esi, array -1; Point to one position before the array

find_nonzero:

inc esi; Move to the next element

cmp byte,0; Current element == 0 ?

loope find_nonzero ; If it is 0 and ecx > 0, continue looping

; Loop ended: found the first non-zero element, or traversal finished

; esi now points to the address of the first non-zero element

; ecx contains the number of remaining uncompared elements

mov eax,1

mov ebx,0

int 0x80
* * *

Conditional Loops (WHILE Loops)

Implementing a while loop with conditional jumps: check the condition first, then execute the loop body.

Example

; File path: while_loop.asm

; Implementation: while (x < 100) x = x * 2;

section.data

 x dd 1

 limit dd 100

section.text

global _start

_start:

; while loop

 while_start:

mov eax,; Load x

cmp eax,; x < 100 ?

jge while_end ; If x >= 100, end loop

shl eax,1; x = x * 2

mov,eax; Store back to x

jmp while_start ; Go back to the start of the loop, re-check condition

while_end:

; x is now 128 (1->2->4->8->16->32->64->128, 128 >= 100 stop)

mov eax,1

mov ebx,; Return x as exit code

int 0x80
* * *

DO-WHILE Loop

Execute the loop body first, then check the condition:

Example

; DO-WHILE loop: execute at least once

section.data

 counter dd 0

section.text

global _start

_start:

mov dword,0

do_loop:

; Loop body: counter++ (executes at least once)

inc dword

; Check condition

cmp dword,5

jl do_loop ; Continue when counter < 5

; counter finally = 5

mov eax,1

mov ebx,0

int 0x80
* * *

Nested Loops

Nested loops require saving the outer loop counter:

Example

; File path: nested_loop.asm

; Nested loop example: print multiplication table (3Γ—3)

section.data

 space db' '

 newline db 0xA

; Used to store converted number characters (2 digits + space + null)

 num_str db' ',0

section.text

global _start

_start:

mov ecx,3; Outer loop counter (number of rows)

outer_loop:

push ecx; β˜… Save outer counter! (Important)

mov ecx,3; Inner loop counter (number of columns)

inner_loop:

push ecx; Save inner counter

; Calculate product = outer row number(4-current ecx) Γ— inner column number

; Specific number conversion output is omitted here, only demonstrating structure

; Actual output: row number Γ— column number

pop ecx; Restore inner counter

loop inner_loop ; Inner loop

; Output newline

mov eax,4

mov ebx,1

mov ecx, newline

mov edx,1

int 0x80

pop ecx; β˜… Restore outer counter

loop outer_loop ; Outer loop

mov eax,1

mov ebx,0

int 0x80

The most common mistake in nested loops is forgetting to save the outer counter's value on the stack. LOOP modifies ECX; when you reset ECX in the inner loop, the outer count value is lost. The solution is to push ecx before entering the inner loop and pop ecx after leaving it.

* * *

Loop Optimization Tips

Some methods to improve loop efficiency:

Example

; Loop optimization comparison

; Method A: Using LOOP instruction (slower, but not obvious)

mov ecx,1000

 loop_a:

add eax,

add ebx,4

loop loop_a

; Method B: Using conditional jump (manual counting) (usually faster)

mov ecx,1000

 loop_b:

add eax,

add ebx,4

dec ecx

jnz loop_b

; Method C: Loop unrolling (fastest, but larger code size)

; Unroll 1000 iterations into processing 4 elements per iteration

mov ecx,250; 1000 / 4 = 250

 loop_unrolled:

add eax,

add eax,[ebx+4]

add eax,[ebx+8]

add eax,[ebx+12]

add ebx,16

dec ecx

jnz loop_unrolled

; Method D: Counting down (reduces comparison instructions)

mov ecx,1000

lea ebx,[array +1000*4-4]; Start from the end of the array

 loop_reverse:

add eax,

sub ebx,4

dec ecx

jnz loop_reverse
* * *

Complete Example: Calculate the Sum of 1 to 100

Example

; File path: sum_1_to_100.asm

; Calculate 1+2+...+100 = 5050

section.data

 msg db'Sum of 1 to 100 is: '

 msg_len equ$- msg

 newline db 0xA

section.bss

 result_str resb 12; Store the converted number string

section.text

global _start

_start:

; Calculate cumulative sum

mov ecx,100; Loop 100 times

mov eax,0; Initial cumulative sum is 0

mov ebx,1; Current number to add

sum_loop:

add eax,ebx; eax += ebx

inc ebx; Next number

loop sum_loop ; Continue loop

; eax = 5050

; Output prompt text

push eax; Save result

mov eax,4

mov ebx,1

mov ecx, msg

mov edx, msg_len

int 0x80

pop eax; Restore result

; Convert number to string (simple version: output integer value directly)

; Simplified processing here, convert the low byte of eax to character

add al,'0'; Inaccurate, for demonstration only

mov,al

; Output result

mov eax,4

mov ebx,
← Assembly StringAssembly Logic β†’