NASM没有打印出我的所有指示;跳过一段代码

时间:2013-03-15 20:27:34

标签: assembly nasm

我正在开发一个玩具NASM程序,它将在特定程序中添加所有值。 我现在正在玩NASM,因为我构建我的程序以了解一切是如何工作的。

在我的程序中,我已经放置了一系列输出,说“工作”,所以我可以缩小错误的位置。

目前我希望看到五个“工作”的打印输出,但我只看到四个。显然,Output:下的代码无法打印,但我不能为我的生活找出原因。

segment .data
    ;studentInfo: db 10,'Program by Raphael Stein', 10, '6079652', 10, 10 ;
    ;infoLen: equ $-studentInfo

    NUM_ROWS: equ 5
    NUM_COLUMNS: equ 5
    NUM_ROW_BYTES: equ 10

    ;Default matrix
    matrix: dw  5, 4, 9, 7, 2
        dw  1, 4, 6, 8, 7
        dw  9, 9, 2, 3, 7
        dw  6, 5, 8, 3, 4
        dw  1, 2, 8, 2, 6   
    matrixLen: equ $-matrix

    sum:    db "The sum of the last column is: ", 10

    ;FOR TESTING
    works: db 'Works!', 10
    worksLen: equ $-works

segment .bss
    counter resb 1

segment .text
    global main

main:
;------------------------------------------------------------------------
    mov eax, 4      ; system call 4
    mov ebx, 1      ; standard output 
    mov ecx, works      ; Works!            1
    mov edx, worksLen
    int 0x80
;-------------------------------------------------------------------------
    ;mov CX, NUM_ROWS           ;Works!
    mov ECX, counter
    sub AX, AX
    sub EBX, EBX
    mov ESI, NUM_COLUMNS-1


;------------------------------------------------------------------------
    mov eax, 4      ; system call 4
    mov ebx, 1      ; standard output 
    mov ecx, works      ; Works!            2
    mov edx, worksLen
    int 0x80
;------------------------------------------------------------------------


sum_loop:               
    add EAX, [matrix + EBX + ESI*2]
    add EBX, NUM_ROW_BYTES
    add ECX, 1
    cmp EAX,ECX
    mov esi, eax
    jge Output
    LOOP sum_loop

;------------------------------------------------------------------------
    mov eax, 4      ; system call 4
    mov ebx, 1      ; standard output 
    mov ecx, works      ; Works!            3
    mov edx, worksLen
    int 0x80
;-------------------------------------------------------------------------

Output:
    mov eax, 4  
    mov ebx, 1
    mov ecx, works
    mov edx, worksLen
    int 0x80


;------------------------------------------------------------------------
    mov eax, 4      ; system call 4
    mov ebx, 1      ; standard output 
    mov ecx, works      ; Works!            4
    mov edx, worksLen
    int 0x80
;-------------------------------------------------------------------------

EXIT:
    mov eax, 1
    xor ebx, ebx
    int 0x80

1 个答案:

答案 0 :(得分:1)

我在这里看到一些问题。没有特别的顺序:

  • 您真的想要将ad-hoc调试打印指令序列抽象为单独的函数。这将是一次练习的好机会。这样做可以消除代码重复,并可能消除一些错误。比如...
  • 在sum_loop标签下,第一条指令添加到EAX。根据最近的修改(看起来像打印副本/粘贴),EAX是4。
  • 因此,在第一个ADD指令之后,EAX = 4 + address_of(矩阵)+ EBX + ESI * 2。这将是......一个相当大的数量(地址将使它变大)。代码将它与ECX进行比较,ECX包含...'works'字符串的偏移量。同样,由于复制/粘贴,这看起来像是一个错误。 ECX可能应该是计数器,在上一个块中定义。
  • 'jge Output'指令获取前一个CMP指令的结果,即“CMP EAX,ECX”。这样的净效果是:“if(EAX> = ECX)然后转到输出”。指针在.data部分中的排列方式与(有时是偶然的)数学相结合意味着这是正确的。这意味着......
  • 正在执行输出标签下的代码。至少,我的阅读表明了这一点。您的各种调试打印并不能真正提供任何触发的数据。我希望在输出标签之前的调试打印块没有被执行。
  • sum_loop无意中被短路可能是一件幸事。否则,它永远不会终止。读取x86 LOOP指令 - 在递减ECX中,如果ECX不为0,则跳转。请注意,每次迭代都要向ECX添加1。所以,它正在做:“ECX + = 1; if(--ECX!= 0)然后循环”。这永远不会终止。

良好的开端和主动性。继续练习。