我试图在程序集中反转一个字符串.但是我的代码似乎无法正常工作.我添加了换行符字符串以提高可读性.
我使用linux和nasm作为编译器.
我认为如果我采用地址指针的值并将它们切换到正确的位置,字符串最终会被反转然后恢复正常.
这是我的代码:
section .data
hello db 'Hello world!'
helloLen equ $-hello
derp db '=========',10
derplen equ $-derp
section .text
global main
main:
mov eax,0
mov ecx,helloLen
reverse:
;move pointer
mov ebx,hello
add ebx,eax
push eax
;move pointer
mov eax,hello
add eax,ecx
push ecx
;switch bytes
push ebx
mov ebx,[ebx]
mov [eax],ebx
pop ebx
mov eax,[eax]
mov [ebx],eax
;print text
mov eax,4
mov ebx,1
mov ecx,hello
mov edx,helloLen
int 80h
;Print newline
mov eax,4
mov ebx,1
mov ecx,derp
mov edx,derplen
int 80h
;increment and decrement
pop ecx
dec ecx
pop eax
inc eax
cmp eax,helloLen
jne reverse
end:
mov eax,1
mov ebx,0
int 80h
Run Code Online (Sandbox Code Playgroud)
这是我得到的输出:
Hello world!Hell=====
Hello worldellol=====
Hello worlllo ol=====
Hello worlo w ol=====
Hello woo wow ol=====
Hello wooooow ol=====
Hello wooooow ol=====
Helloooooooow ol=====
Helloooooooow ol=====
Helooowooooow ol=====
Heoow wooooow ol=====
How o wooooow ol=====
Run Code Online (Sandbox Code Playgroud)
通过交换字符来反转字符串的方法是交换第一个和最后一个,然后是第二个和倒数第二个,等等.在C中,你会写:
for (i = 0; i < len/2; ++i)
{
c = s[i];
s[i] = s[len-i-1];
s[len-i-1] = c;
}
Run Code Online (Sandbox Code Playgroud)
在汇编语言中,最简单的方法是将ESI和EDI寄存器设置为指向字符串的开头和结尾,然后循环.在每次迭代时,您都会增加ESI并减少EDI.结果看起来像这样:
mov ecx, helloLen
mov eax, hello
mov esi, eax ; esi points to start of string
add eax, ecx
mov edi, eax
dec edi ; edi points to end of string
shr ecx, 1 ; ecx is count (length/2)
jz done ; if string is 0 or 1 characters long, done
reverseLoop:
mov al, [esi] ; load characters
mov bl, [edi]
mov [esi], bl ; and swap
mov [edi], al
inc esi ; adjust pointers
dec edi
dec ecx ; and loop
jnz reverseLoop
Run Code Online (Sandbox Code Playgroud)