Pelles C forum

Assembly language => Assembly discussions => Topic started by: HellOfMice on December 18, 2024, 08:00:56 PM

Title: Atoi
Post by: HellOfMice on December 18, 2024, 08:00:56 PM
A classic function revisited

;   __________________________________________________________________________________

                            ALIGN   16

;   *****************************************************************
;   *** All the registers are saved except: RAX RCX RDX R8 and R9 ***
;   *****************************************************************

;   Registers used: RDI, RAX, RBX, RCX, RDX, R10 and R11

Atoi                        PROC    USES RBX RDI R10 R11,__lpszNumericString:LPSTR PARMAREA = 4 * QWORD
                            mov     rdi,rcx

                            xor     eax,eax
                            xor     edx,edx                         ; Set initial total to 0
                            xor     ecx,ecx

                            mov     r11d,10                         ; No more than 10 characters: 123 456 789 012
                            mov     r10b,'0'                        ; Stock bounds into registers
                            mov     bl,'9'

                            ALIGN   16
Atoi_convert :
                            mov     al,BYTE PTR [rdi]               ; Get the current character

                            test    al,al                           ; Check for \0
                            jz      Atoi_done

                            cmp     al,r10b                         ; Anything less than 0 is invalid
                            jge     @F                              ; I try to use AL very often to reduce the code

                            jmp     Atoi_error

                            ALIGN   16
@@:
                            cmp     al,bl                           ; Anything greater than 9 is invalid
                            jle     @F

                            jmp     Atoi_error

                            ALIGN   16
@@ :
                            sub     al,r10b                         ; Convert from ASCII to decimal

                            mov     cl,dl
                            shl     edx,3                            ; * 8 ----> No multiplication
                            shl     ecx,1                            ; * 2
                            add     edx,ecx                         ; Multiply total by 10
                            add     edx,eax                         ; Add current digit to total

                            add     edi,1                           ; Get the address of the next character

                            sub     r11d,1                           ; SUB & ADD used rather than INC & DEC
                            jnz     Atoi_convert

                            ALIGN   16
Atoi_error :
                            mov  rax,-1                              ; Return -1 on error in RAX

                            ALIGN   16
Atoi_done :
                            mov     eax,edx  ; CWD more effiscient?

                            ret                                     ; Return total or error code
;   __________________________________________________________________________________
Atoi                        ENDP




If the Input String has more than 10 chacaracters, the function stops.Maybe there is no ending '\0'
Title: Re: Atoi
Post by: Vortex on December 18, 2024, 08:17:19 PM
Here is another version from the Masm64 package :

; ¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤

    .code

; ¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤

atou_ex proc

  ; ------------------------------------------------
  ; Convert decimal string into UNSIGNED QWORD value
  ; ------------------------------------------------
  ; argument in RCX

    xor r11, r11
    movzx rax, BYTE PTR [rcx]
    test rax, rax
    jz quit

    lea r11, [r11+r11*4]
    lea r11, [rax+r11*2-48]
    movzx rax, BYTE PTR [rcx+1]
    test rax, rax
    jz quit

    lea r11, [r11+r11*4]
    lea r11, [rax+r11*2-48]
    movzx rax, BYTE PTR [rcx+2]
    test rax, rax
    jz quit

    lea r11, [r11+r11*4]
    lea r11, [rax+r11*2-48]
    movzx rax, BYTE PTR [rcx+3]
    test rax, rax
    jz quit

    lea r11, [r11+r11*4]
    lea r11, [rax+r11*2-48]
    movzx rax, BYTE PTR [rcx+4]
    test rax, rax
    jz quit

    lea r11, [r11+r11*4]
    lea r11, [rax+r11*2-48]
    movzx rax, BYTE PTR [rcx+5]
    test rax, rax
    jz quit

    lea r11, [r11+r11*4]
    lea r11, [rax+r11*2-48]
    movzx rax, BYTE PTR [rcx+6]
    test rax, rax
    jz quit

    lea r11, [r11+r11*4]
    lea r11, [rax+r11*2-48]
    movzx rax, BYTE PTR [rcx+7]
    test rax, rax
    jz quit

    lea r11, [r11+r11*4]
    lea r11, [rax+r11*2-48]
    movzx rax, BYTE PTR [rcx+8]
    test rax, rax
    jz quit

    lea r11, [r11+r11*4]
    lea r11, [rax+r11*2-48]
    movzx rax, BYTE PTR [rcx+9]
    test rax, rax
    jz quit

    lea r11, [r11+r11*4]
    lea r11, [rax+r11*2-48]
    movzx rax, BYTE PTR [rcx+10]
    test rax, rax
    jz quit

    lea r11, [r11+r11*4]
    lea r11, [rax+r11*2-48]
    movzx rax, BYTE PTR [rcx+11]
    test rax, rax
    jz quit

    lea r11, [r11+r11*4]
    lea r11, [rax+r11*2-48]
    movzx rax, BYTE PTR [rcx+12]
    test rax, rax
    jz quit

    lea r11, [r11+r11*4]
    lea r11, [rax+r11*2-48]
    movzx rax, BYTE PTR [rcx+13]
    test rax, rax
    jz quit

    lea r11, [r11+r11*4]
    lea r11, [rax+r11*2-48]
    movzx rax, BYTE PTR [rcx+14]
    test rax, rax
    jz quit

    lea r11, [r11+r11*4]
    lea r11, [rax+r11*2-48]
    movzx rax, BYTE PTR [rcx+15]
    test rax, rax
    jz quit

    lea r11, [r11+r11*4]
    lea r11, [rax+r11*2-48]
    movzx rax, BYTE PTR [rcx+16]
    test rax, rax
    jz quit

    lea r11, [r11+r11*4]
    lea r11, [rax+r11*2-48]
    movzx rax, BYTE PTR [rcx+17]
    test rax, rax
    jz quit

    lea r11, [r11+r11*4]
    lea r11, [rax+r11*2-48]
    movzx rax, BYTE PTR [rcx+18]
    test rax, rax
    jz quit

    lea r11, [r11+r11*4]
    lea r11, [rax+r11*2-48]
    movzx rax, BYTE PTR [rcx+19]
    test rax, rax
    jz quit

    lea r11, [r11+r11*4]
    lea r11, [rax+r11*2-48]
    movzx rax, BYTE PTR [rcx+20]
    test rax, rax
    jnz out_of_range

  quit:
    lea rax, [r11]      ; return value in EAX
    or rcx, -1          ; non zero in RCX for success
    ret

  out_of_range:
    xor rax, rax        ; zero return value on error
    xor rcx, rcx        ; zero in ECX is out of range error
    ret

atou_ex endp

; ¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤¤

    end
Title: Re: Atoi
Post by: HellOfMice on December 18, 2024, 08:19:54 PM
VORTEX, I should appreciate that you explain it in details


I have changed of keyboard this morning, now it has led every where and they exchanged 2 keys (END and DEL)! So excuse me if words are not well written. Made in China...
Title: Re: Atoi
Post by: John Z on December 19, 2024, 04:18:00 PM
Hi Vortex,

MASM64??  Where to get this package?  I thought MASM32 was all there was...

John Z
Title: Re: Atoi
Post by: HellOfMice on December 19, 2024, 04:33:02 PM
Hi John,


I think that there is a copyright on it. So you will not find it as a free compiler. Try to download windows SDK
I prefer POASM and you can use the debugger with it. The syntax is very close from MASM
Title: Re: Atoi
Post by: John Z on December 19, 2024, 04:34:41 PM
Quote from: HellOfMice on December 19, 2024, 04:33:02 PM
Hi John,


I think that there is a copyright on it. So you will not find it as a free compiler. Try to download windows SDK
I prefer POASM and you can use the debugger with it. The syntax is very close from MASM

Thanks!

John Z
Title: Re: Atoi
Post by: Vortex on December 19, 2024, 07:52:39 PM
Hi John,

You can get the Masm64 SDK from this thread :

https://masm32.com/board/index.php?topic=10880.0

Hi Philippe,

OK, I will try later to post here the explanation of the source code.
Title: Re: Atoi
Post by: HellOfMice on December 19, 2024, 08:31:21 PM
Thank You Vortex, it seems too hard for me
Title: Re: Atoi
Post by: John Z on December 19, 2024, 10:50:34 PM
Quote from: Vortex on December 19, 2024, 07:52:39 PM
Hi John,

You can get the Masm64 SDK from this thread :

https://masm32.com/board/index.php?topic=10880.0

Thanks very much Vortex!!  This might motivate me to take it up again....I'm certainly going to load and look.

John Z
Title: Re: Atoi
Post by: HellOfMice on December 20, 2024, 08:50:40 AM
I cannot install the VLSX file. I stopped the antivirus but no result the file crash. I open the file with 7zip and extracted the X64 folder
Title: Re: Atoi
Post by: TimoVJL on December 20, 2024, 04:11:36 PM
Quote from: HellOfMice on December 20, 2024, 08:50:40 AM
I cannot install the VLSX file..... I open the file with 7zip and extracted the X64 folder
A that packed file is just part of installation and update system, not something like msi.
Title: Re: Atoi
Post by: HellOfMice on December 20, 2024, 04:16:44 PM
It has been extracted with 7zip
Title: Re: Atoi
Post by: TimoVJL on December 20, 2024, 04:43:00 PM
And what you think, that i have missed ?
Just stay in in this actual topic about asm atoi  ;)
Title: Re: Atoi
Post by: HellOfMice on December 20, 2024, 05:04:41 PM
In four days it is Christmas
for thank you for the work made in this forum
I made you this (see below)


It is a sad year, Pelle has gone. I like what he did and found him very strong.
I hope he has no personal problem and a good health.
I will wish the same thing for the next year.


When I look at the biathlon on TV I often think to you.


A+


Philippe
Title: Re: Atoi
Post by: Vortex on December 20, 2024, 09:05:30 PM
Hello,

With thanks to jj2007, member of the Masm Forum, you can try the new Masm64 package downloading also the Microsoft Masm 64-bit assembler :

QuoteMasm64 SDK installer: betatesters please

https://masm32.com/board/index.php?topic=12051.0

Direct link :

https://masm32.com/files/MASM64-SDKdev/Working/Installer/Masm64Sdk21set24.zip
Title: Re: Atoi
Post by: HellOfMice on December 20, 2024, 09:10:10 PM
I kow him, he is is a nice italian programmer
Title: Re: Atoi
Post by: Vortex on December 24, 2024, 05:25:15 PM
Hi Philippe,

Converting the atou_ex function from Masm64 to Poasm64 is very easy. The two versions are almost identical.

The method to convert a string to A number is handling correctly the Base-10 number system. To get the numerical value of a simple ASCII digit, one must extract 48 from this ASCII code. For example, the ASCII code of 5 is 53. 53-48=5
To shift each digit to the left, you multiply it by 10 :

    lea     r11, [r11+r11*4]       ;  r11=5*r11
    lea     r11, [rax+r11*2-48]  ;  r11=2*r11 + rax - 48


r11+r11*4 means multiplying r11 by 5. In the second line, after multiplying r11 by 2 , r11 becomes 10*r11 compared to the initial value of this register. The rest is easy, rax holds the ASCII digit and subtracting 48 from rax provides the numerical value.

The largest value of an unsigned 64-bit integer is 2^20 = 18446744073709551616. This means that a maxinum of 20 steps is necessary to convert correctly an ASCII string to integer.

Attached is a simple example, you can examine it with x64dbg to see how the algorithm works.
Title: Re: Atoi
Post by: HellOfMice on December 24, 2024, 05:55:52 PM
Hi Vortex

Thank you for your comments I learnt something:

Quotelea     r11, [rax+r11*2-48]  ;  r11=2*r11 + rax - 48
I did not know this was possible!


Thank you professor and Happy, merry christmas.


Philippe
Title: Re: Atoi
Post by: HellOfMice on December 24, 2024, 06:00:24 PM
Surprising!


It is like this function only know to do one thing!


If you have others like this I take


Merci


Philippe
Title: Re: Atoi
Post by: Vortex on December 24, 2024, 06:09:53 PM
Hi Philippe,

The Masm32 and Masm64 packages are providing a lot of useful funcrions. You can download the installers and study the help files shipped with them.
Title: Re: Atoi
Post by: HellOfMice on December 24, 2024, 06:16:32 PM
Yes that's right, I already downloaded it but the functions I looked at where not as much interesting than the atou_ex. I am looking at its code, not finished since you sent the post.
A gift for my 65 years birthday.


I wanted to answer to your MS-DOS header message, but you did not let me the time to do it. I answer into this one.
I think I saw interesting things into CCleaner header.


I will write a small program for using atou_ex and seeing how it works under the debugger.
Very good and thanks again Vortex


Philippe