从NASM多位数输入 [英] Multi-Digit Input from NASM

查看:933
本文介绍了从NASM多位数输入的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

所以,我是相当新的汇编语言我对基本面pretty扎实抓好但用户输入一直把我难倒了。所以现在我有以下的code接收来自用户的一个数字:

So I'm fairly new to Assembly language I have a pretty solid grasp on the fundamentals but user input has always baffled me. So right now I have the following code to receive a single digit from the user:

mov eax, 3
mov ebx, 0
mov ecx, inStrBuf
mov edx, StrLen
int 80h

和则定义如下

SECTION .bss
inStrBuf:  times StrLen resb  ' ' 

Section .data
StrLen: equ 8 

我ECX把值后,该值是数字+ 2608所以,我一直在做的是简单地减去2608和获取数字。现在,当我把在一个以上的数字,如46号,我得到的,当我转换为十进制,669236.目前只是减去2608就像我从前没有简单的方法。

After I put the value in ecx, the value is the digit + 2608. So what I have been doing is simply subtracting 2608 and getting the digit. Now when I put in more than one digit, like the number 46, I get, when I convert to decimal, 669236. There is no simple way of just subtracting 2608 like I was before.

首先,这是怎么回事的2608,是有什么办法只是接受一些像654,把它放在一个寄存器(​​当然在一个十六进制值)。谢谢!

First of all, what's up with the 2608, and is there any way to just accept a number like 654 and put it in a register (in a hex value of course). Thanks!

推荐答案

我不知道在哪里2608,甚至更少669236来了!总的思路是:

I have no idea where 2608 came from, even less 669236! The general idea is:

;zero out someplace to put result
top:
;get a digit/character
;make sure it represents a decimal digit
;(if not - go to done)
;subtract '0' to convert character to number
;multiply "result so far" by 10
;add in the new number
;go to top
done:

这是我平时用...

section .bss
    inStrBuf resb StrLen ; 12+ is good...

section .text
    ...
    push inStrBuf ; pass parameter on stack
    call atoi
    add esp, 4 ; clean up stack
    mov [someplace], eax
    ...

;--------------------
atoi:
    push ebx

    mov edx, [esp + 8]  ; pointer to string
    xor ebx, ebx ; assume not negative

    cmp byte [edx], '-'
    jnz .notneg
    inc ebx ; indicate negative
    inc edx ; move past the '-'
.notneg:

    xor eax, eax        ; clear "result"
.top:
    movzx ecx, byte [edx]
    inc edx
    cmp ecx, byte '0'
    jb .done
    cmp ecx, byte '9'
    ja .done

    ; we have a valid character - multiply
    ; result-so-far by 10, subtract '0'
    ; from the character to convert it to
    ; a number, and add it to result.

    lea eax, [eax + eax * 4]
    lea eax, [eax * 2 + ecx - '0']

    jmp short .top
.done:
    test ebx, ebx
    jz .notminus
    neg eax
.notminus:
    pop ebx
    ret
;------------------------

这使用了两个 LEA S中的聪明的方法,通过十乘,减'0',并添加新的号码。它有没有设置标志的缺点,所以我们不能检查溢出 - 它只是静静地滑过。任何无效字站 - 工程Xero的,换行(这SYS_READ将在那里)...或垃圾。当它返回时,无效字将在ECX(CL只是有趣的是),和EDX指向下一个字符。方便的解析192.168.1.1左右。你可以preFER使用一些更简单。 :) C库的atoi或scanf函数的工作......如果雅想那样做...

This uses the "clever" method of two leas to multiply by ten, subtract '0', and add in the new number. It has the disadvantage of not setting flags, so we can't check for overflow - it just silently rolls over. Any "invalid" character stops - works for xero, linefeed (which sys_read will have there)... or "garbage". When it returns, the "invalid" character will be in ecx (just cl is interesting), and edx points to the next character. Handy for parsing "192.168.1.1" or so. You may prefer to use something more straightforward. :) The C library "atoi" or "scanf" work... if ya wanna do it THAT way...

真的很好奇,其中的2608来了!

Really curious where that 2608 came from!

这篇关于从NASM多位数输入的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆