In certain situations when I want to print some string to stdout we need the length for the write syscall in linux. So we can’t always depend on the $-string macro, which is valid for a defined string.
We use the REPNE (REPeat while Not Equal) instruction which will loop as long as CX != 0. Along with REPNE we use SCASB (scan byte string). It compares the content of the accumulator (AL, AX, or EAX) against the current value pointed at by ES:[EDI]. In the end we calculate the difference between offsets of the scanned string (EDI) and the original string (EBX) to find the length.
_strlen:
push ebx
push ecx
mov ebx, edi
xor al, al
mov ecx, 0xffffffff
repne scasb ; REPeat while Not Equal [edi] != al
sub edi, ebx ; length = offset of (edi - ebx)
mov eax, edi
pop ebx
pop ecx
ret
%if 0 | |
* Title: Manual String Length function | |
* Author: Osanda Malith (@OsandaMalith) | |
* Website: https://osandamalith.com | |
%endif | |
global _start | |
section .text | |
_start: | |
mov edi, message | |
call _strlen | |
mov edx, eax | |
mov eax, 0x4 | |
mov ebx, 0x1 | |
mov ecx, message | |
int 0x80 | |
mov eax, 0x1 | |
mov ebx, 0x5 | |
int 0x80 | |
_strlen: | |
push ebx | |
push ecx | |
mov ebx, edi | |
xor al, al | |
mov ecx, 0xffffffff | |
repne scasb ; REPeat while Not Equal [edi] != al | |
sub edi, ebx ; length = offset of (edi – ebx) | |
mov eax, edi | |
pop ebx | |
pop ecx | |
ret | |
section .data | |
message: db "https://osandamalith.com", 0xa |
Interesting, also just find shorter version of it you should look,
\x53\x31\xc9\x4b\x41\x43\x80\x3b\x00\x75\xf9\x49\x5b\xc3
(http://stackoverflow.com/questions/6468480/how-would-i-find-the-length-of-a-string-using-nasm)
This is ours;
\x53\x51\x89\xfb\x30\xc0\xb9\xff\xff\xff\xff\xf2\xae\x29\xdf\x89\xf8\x5b\x59\xc3
Again, good job mate.
Thanks ๐ That is the normal way in assembly and it contains a null byte, but I have tried to save lines plus no null bytes ๐
\x53\x51\x89\xfb\x30\xc0\xb9\xff\xff\xff\xff\xf2\xae\x29\xdf\x89\xf8\x5b\x59\xc3
Furthermore you can make it short to 16 bytes if you remove my registers saving it’s state.
push,pop ebx
push,pop ecx
\x89\xfb\x30\xc0\xb9\xff\xff\xff\xff\xf2\xae\x29\xdf\x89\xf8\xc3