2017-12-23 4 views
2

대학 프로젝트로 컴파일러를 쓰고 있습니다. 나는 코드 생성 단계에있다. 그리고 이것은 (항상 0 인쇄) 작동하지 않는 이유를 궁금하네요 :어셈블리에서 부동 값 인쇄 및 인쇄

.extern printf 
.section .data 
hello: 
    .string "Hello %f!\n" 
.section .text 
.globl main 
main: 
    pushl %ebp 
    movl %esp, %ebp 

    pushl $3214514586 // or pushl $0xbf99999a 
    pushl $hello 
    call printf 

    leave 
    ret 

을하지만이 제대로 작동 :

(printf와 같은) 가변 인자 함수에 C 플로트 argments에서
.extern printf 
.section .data 
hello: 
    .string "Hello %f!\n" 
.section .text 
.globl main 
main: 
    pushl %ebp 
    movl %esp, %ebp 

    pushl $3214514586 // or pushl $0xbf99999a 

    flds (%esp) 
    fstpl (%esp) 

    pushl $hello 
    call printf 
    leave 
    ret 

답변

3

은 두 배로 승진했다. 두 번째 코드는 4 바이트 float을 8 바이트 double로 변환하여 printf에 올바른 값을 전달하지만 저장된 값 ebp을 덮어 쓰므로 충돌 할 수 있습니다.

+0

답변의 첫 번째 부분에 자리가 있지만 두 번째 부분을 얻지 못합니다 - 저장된 ebp를 손상시키는 부분은 어디입니까? –

+0

이제 알았어.하지만 두 단편 모두에 공통적이라고 지적 했어. –

+1

@Matteo, No, 첫 번째 예제는 스택의 모든 것을 덮어 쓰지 않습니다. 그것은 단지 밀기 만합니다. 두 번째 예제는 4 바이트를 푸시 한 다음 8 바이트로 덮어 쓰며 스택에서 스택 위에있는 값을 덮어 쓰며 ebp의 저장된 값입니다. – prl