简体   繁体   中英

How do I solve the error: Segmentation fault(core dumped) in my code? AT&T syntax

I've been looking for hours, and i can't find the mistake in my code. The program seems to exit at the "opadd" tag. I am using x86_64 on Linux, with AT&T syntax.

The program takes as input a string of characters, for example, "2 3 add 4 mul", and then, for this particular example, should do as follows:

  • adds 2 to the stack
  • adds 3 to the stack
  • computes the sum of 2 and 3 and then adds 5 to the stack
  • multiplies 5 and 4 and adds 20 to the stack, and then prints 20.
.data
    formatPrintf: .asciz "%d"
    sir: .space 1000
    delim: .asciz " "
    formatScanf: .asciz "%1000[^\n]"
    cuvant: .space 100
    primulNumar: .space 4
    atoiCuvant: .long 0
    x: .space 4
    y: .space 4
    eval: .long 0
    op: .space 4
    add: .asciz "add"
    sub: .asciz "sub"
    mul: .asciz "mul"
    div: .asciz "div"
.text

.global main

main:
    pushl $sir
    pushl $formatScanf
    call scanf
    popl %ebx
    popl %ebx
    
    pushl $delim
    pushl $sir
    call strtok
    popl %ebx
    popl %ebx
    
    pushl %eax
    call atoi
    popl primulNumar
    
    movl %eax, primulNumar
    
    pushl primulNumar
    
et_loop:
    pushl $delim
    pushl $0
    call strtok
    popl %ebx
    popl %ebx
    
    cmp $0, %eax
    je exit
    
    mov %eax, cuvant
    
    pushl %eax
    call atoi
    popl %ebx
    
    mov %eax, atoiCuvant
    
    cmp  $0, atoiCuvant
    je operatie
    
    pushl %eax
    
    jmp et_loop
    
operatie:
    
    push $cuvant
    push $add
    call strcmp
    popl %ebx
    popl %ebx
    
    cmp $0, %eax
    je opadd
    
    push $cuvant
    push $sub
    call strcmp
    popl %ebx
    popl %ebx
    
    cmp $0, %eax
    je opsub
    
    push $cuvant
    push $mul
    call strcmp
    popl %ebx
    popl %ebx
    
    cmp $0, %eax
    je opmul
    
    push $cuvant
    push $div
    call strcmp
    popl %ebx
    popl %ebx
    
    cmp $0, %eax
    je opdiv
    
opadd:
    popl %edx
    popl y
    
    add %edx, y
    push y
    
    jmp et_loop
    
opmul:
    popl %eax
    popl %ebx
    mul %ebx
    pushl %eax
    
    jmp et_loop
opdiv:
    popl %eax
    popl %ebx
    div %ebx
    pushl %eax
    
    jmp et_loop

opsub:
    popl %eax
    popl y
    sub %eax,y
    pushl y
    
    jmp et_loop

exit:
    popl eval
    
    pushl eval
    pushl $formatPrintf
    call printf
    popl %ebx
    popl %ebx
    
    pushl $0
    call fflush
    popl %ebx
    
    movl $1, %eax
    xorl %ebx, %ebx
    int $0x80
opadd:
    popl %edx <-- there IS a push without a pop on the first line of code, but...
    popl y <-- now there is nothing left in the stack

It doesn't seem like there is anything left in the stack when you get to opadd . Every push operation in et_loop and operatie has a corresponding pop . I cannot test your example yet, as you didn't include your .data section, but I'm almost sure that this is the problem.

mov %eax, cuvant pushl %eax call atoi popl %ebx

Knowing that atoi espects a pointer, we see that the cuvant variable will hold an address.

 operatie: push $cuvant push $add call strcmp popl %ebx popl %ebx

Knowing that strcmp expects two pointers, we see that this code passes the address of the cuvant variable where in fact it should pass the address that is contained in the cuvant variable (pointing at the current token).
Therefore all comparing in operatie will fail.

 cmp $0, %eax je opdiv opadd:

When all 4 compares fail the code just falls through in opadd: . Nothing good to be expected from that!

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM