【问题标题】:Using syscall with FASM to read numbers with suffix使用带有 FASM 的 syscall 读取带后缀的数字
【发布时间】:2014-11-15 14:53:42
【问题描述】:

我正在尝试在程序集中模拟一个带有不同后缀(h-hex、b-bin 等)的 scanf。这对于无符号值效果很好,但是在添加了这 5 行(在下面注释,以启用有符号值)之后,如果我输入无符号值,我会遇到缺少前位数字的问题,但对于有符号值却可以正常工作。

;Linux Mint 17 (64-bit)
;./fasm scanf.asm
;./scanf
format elf64 executable
include 'PROC64.INC'
include 'IF.INC'

    push    tstValue    
    call    SCANF

    push    1           ;sign
    push    [tstValue]  ;No problem here
    call    DISP_INT

    call    EXIT
    tstValue dq 0

proc SCANF,value
    locals
        flag db 0
        key rb 1
    endl
    push    rsi rdi rax rcx rdx
    push    rbx r8 r9 r10

    xor     r10,r10
    xor     r8,r8           ;loop index
    lea     rsi,[key]   
    mov     edx,1       
    xor     edi,edi     
    xor     eax,eax         ;Problem starts after I     
    syscall                 ;added these
    cmp     byte[key],'-'   ;5 new lines to allow signess   
    jne     .begin          ;
    mov     byte[flag],1    ;
.begin: 
    xor     rax,rax
    syscall
    mov     r10b,byte[rsi]
    cmp     r10b,0ah
    jz      .select
    push    r10
    inc     r8
    jmp     .begin
.select:
    pop     rax
    cmp     al,'h'
    je      .hexadecimal
    cmp     al,'H'
    je      .hexadecimal
    cmp     al,'b'
    je      .binary
    cmp     al,'B'
    je      .binary
    cmp     al,'o'
    je      .octal
    cmp     al,'O'
    je      .octal
    cmp     al,'d'
    je      .decimal
    cmp     al,'D'
    je      .decimal
    push    rax     ;if no suffix, defaults to decimal
    inc     r8      ;re-adjust index
.decimal:   
    xor     r9,r9
    pop     rax
    sub     rax,30h
    add     r9,rax
    mov     rcx,10
    mov     rbx,10
    dec     r8
    jmp     .translate
.hexadecimal:
    xor     r9,r9
    pop     rax
    .if al >= 'a' & al <= 'f'
        sub rax,27h
    .elseif al >= 'A' & al <= 'F'
        sub rax,7h
    .endif
    sub     rax,30h
    add     r9,rax
    mov     rcx,16
    mov     rbx,16
    dec     r8
    jmp     .translate
.octal:
    xor     r9,r9
    pop     rax
    sub     rax,30h
    add     r9,rax
    mov     rcx,8
    mov     rbx,8
    dec     r8
    jmp     .translate
.binary:    
    xor     r9,r9
    pop     rax
    sub     rax,30h
    add     r9,rax
    mov     rcx,2
    mov     rbx,2
    dec     r8
    jmp     .translate
.translate:
    dec     r8
    jz      .exit
    pop     rax
   .if al >= 'a' & al <= 'f'
        sub rax,27h
   .elseif al >= 'A' & al <= 'F'
        sub rax,7h
   .endif
    sub     rax,30h 
    mul     rcx
    add     r9,rax
    mov     rax,rbx
    mul     rcx
    mov     rcx,rax
    jmp     .translate
.exit:      
    mov     rax,[value]
    .if [flag] = 1
        neg r9
    .endif
    mov     [rax],r9
    pop     r10 r9 r8 rbx
    pop     rdx rcx rax rdi rsi
    ret
endp

我检查了 .begin 标签之前的所有寄存器,它们都按预期工作(因此系统调用应该具有读取单个字符的正确参数,eax=0,edx=1,edi=0,rsi 指向特点)。如果我删除了所有有问题的 5 行,程序可以正常工作,但我只剩下未签名的程序。

谁能帮我指出可能是什么问题?我似乎没有主意了。在调用 .begin 之前,我没有进行任何推送或增加我的索引 (r8)。这应该可以消除堆栈或索引问题。

这是无符号的输出

3455    ;keyboard input
455

这个作品(签名)

-3455
-3455

提前谢谢你

【问题讨论】:

  • 为了帮助您放大问题,该程序在多个过程(DISP_HEX、DISP_BIN、DISP_OCT 和 DISP_INT)上按预期工作。所以问题不在于外部。唯一的问题是在我将符号处理添加到程序中之后处理无符号值时。
  • 有人吗?我必须发布更多代码吗?但我认为没有必要。
  • 我可以通过在 .translate 标签下插入其他代码来轻松解决它,但这不是我的问题的重点。我怀疑系统调用有问题。好吧,我希望我错了。

标签: 64-bit system-calls fasm


【解决方案1】:

您评论的第四行必须再跳两行。这就是您丢失无符号值的第一位的原因!

xor     eax,eax         ;Problem starts after I     
syscall                 ;added these
cmp     byte[key],'-'   ;5 new lines to allow signess   
jne     .beginEx        ;
mov     byte[flag],1    ;
.begin: 
xor     rax,rax
syscall
.beginEx:
mov     r10b,byte[rsi]

【讨论】:

  • 谢谢。我总是这么粗心。
猜你喜欢
  • 1970-01-01
  • 2019-07-19
  • 2012-07-03
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-10-18
  • 1970-01-01
  • 2013-06-12
相关资源
最近更新 更多