Reputation: 660
Ok, to make things as simple as possible, say I have a basic loop that i want to use in order to modify some elements of an array labeled a. In the following sample code I've tried replacing all elements of a with 1, but that doesn't really work.
assume cs:code ,ds:data
data segment
a db 1,2,3,4
i db 0
data ends
code segment
start:
mov ax,data
mov ds,ax
lea si,a
the_loop:
mov cl,i
cmp cl,4
jae the_end
mov ds:si[i],1 ; this is the part that i don't really understand since
inc i ; i'm expecting i=0 and ds:si[i] equiv to ds:si[0] which
loop the_loop ; is apparently not the case here since i actually receives the
; the value 1
the_end:
mov ax,4c00h
int 21h
code ends
end start
I am aware that I could simply do this by modifying the element stored in al
after the lodsb
instruction, and just store that. But I would like to know if it is possible to do something like what I've tried above.
Upvotes: 0
Views: 15439
Reputation: 10580
In x86 assembly you can't use a value stored to a memory to address memory indirectly.
You need to read i
into some register that can be used for memory addressing, and use that instead. You may want to check Wikipedia for 8086 memory addressing modes.
So, replace
mov ds:si[i],1
with (segment ds
is unnecessary here, as it's the default of si
, bx
and bx+si
too):
xor bx,bx
mov bl,[i]
mov [bx+si],byte 1 ; some other assemblers want byte ptr
There are other problems with your code too. The entire loop can be made easier and fixed this way:
lea si,a
xor cx,cx
mov cl,[i]
@fill_loop:
mov [si], byte 1
inc si
dec cx
jnz @fill_loop
Or, if you want to save 1 byte and use loop
instruction.
@fill_loop:
mov [si], byte 1
inc si
loop @fill_loop
Note that in 16-bit mode loop
instruction decrements cx
and jumps to label if cx
is not zero after decrement. However, in 32-bit mode loop
decrements ecx
and in 64-bit mode (x86-64) it decrements rcx
.
Upvotes: 6
Reputation: 36649
I suppose that your code does not even run through the assembler, since
mov ds:si[i],1
is not a valid address mode.
Use something like
mov byte ptr [si],1 ; store value 1 at [SI]
inc si ; point to next array element
instead (used MASM to verify the syntax).
The DS:
prefix is unnecessary for [si]
since this is the default.
See also The 80x86 Addressing Modes.
Upvotes: 1