Iterate through string in memory in Assembly

11,816

Many, many years ago, someone put it this way:
Do you want the box, or what is in the [box]?

I've also tried the following:

mov al, [bx] ; Move the dereferenced address to `al` (so `al` has `H`) 
add al, 1 ; Increment `al`, but of course I'm getting the ASCII value of `H` + 1

The CPU is doing exactly what you told it to do!

mov al, [bx]

Moves the value pointed to by bx into al (in your case, H)

add al, 1

adds 1 to H.

add bx, 1
mov al, [bx]

Now, al will contain E

Or you could do:

mov al, [bx + 1]

to get E

In your other code, bx is a word sized register (16 bits) and cl is a byte sized register (8 bits) you truncated the address hence the invalid address (what do you expect to happed when you try to put 16 bits into an 8 bit register?)

Here is an example:

 HELLO_MSG db 'Hello, World!', 0
 HELLO_LEN equ  $ - HELLO_MSG
...
...
...
    mov     si, HELLO_MSG
    xor     bx, bx
Next:
    mov     al, byte [si + bx]
    mov     ah, 0x0e
    int     0x10

    mov     al, 10
    mov     ah, 0x0e
    int     0x10

    inc     bx
    cmp     bx, HELLO_LEN
    jne     Next

Output:

enter image description here

Share:
11,816
jviotti
Author by

jviotti

Software Engineer at Balena.io.

Updated on June 04, 2022

Comments

  • jviotti
    jviotti almost 2 years

    I'm having some troubles accessing each character of a string in turn in Assembly. I have the following code that calls the print_string routine, before declaring 'Hello World!', 0 into the bx registry:

    mov bx, HELLO_MSG
    call print_string
    
    HELLO_MSG:
      db 'Hello, World!', 0
    

    Within print_string, I'm able to print the first character of the string by doing this:

    mov al, [bx]
    
    ; Trigger a single character print
    mov ah, 0x0e
    int 0x10
    

    In my basic understanding of assembly, the address of the first character (H) got saved into bx, so by doing mov al, [bx] I'm dereferencing the pointer and assigning the real value of H into al.

    Based on that understanding (please correct me if I'm wrong) I've tried the following approaches:

    mov cl, bx ; Move the pointer to `cl`
    add cl, 1 ; Do pointer arithmetic to add one byte to the address (hopefully referencing the next character)
    mov al, [cl] ; Dereference the address
    

    But I got this error pointing to the mov al, [cl] line:

    error: invalid effective address
    

    I've also tried the following:

    mov al, [bx] ; Move the dereferenced address to `al` (so `al` has `H`)
    add al, 1 ; Increment `al`, but of course I'm getting the ASCII value of `H` + 1, which is not the next character in the string.