1. ホーム
  2. c

[解決済み] X86アセンブリ - IDIV命令の取り扱い

2022-01-28 13:53:47

質問事項

私は現在、入力として.cファイルを取り、アセンブリコード(X86、AT&T構文)を生成する簡単なCコンパイラを作成しています。 すべてが順調なのですが、IDIVQ命令を実行しようとすると、浮動小数点例外が発生します。以下は私の入力です。

int mymain(int x){
  int d;
  int e;
  d = 3;
  e = 6 / d;
  return e;
}

そして、これが私の生成したコードです。

mymain:
.LFB1:
    .cfi_startproc
    pushq   %rbp
    .cfi_def_cfa_offset 16
    movq    %rsp, %rbp
    .cfi_offset 6, -16
    .cfi_def_cfa_register 6
    movq    %rdi, -40(%rbp)
    movq    $3, -8(%rbp)
    movq    $6, %rax
    movq    -8(%rbp), %rdx
    movq    %rdx, %rbx
    idivq   %rbx
    movq    %rax, -16(%rbp)
    movq    -16(%rbp), %rax
    leave
    .cfi_def_cfa 7, 8
    ret
    .cfi_endproc
.LFE1:
    .size mymain, .-mymain

によると http://www.cs.virginia.edu/~evans/cs216/guides/x86.html , イディブク %rbx で6/d(商)を生成する必要があります。 ラックス . しかし、浮動小数点数の例外が発生し、問題が見つからないようです。

どんなことでもご相談ください。

解決方法は?

Mysticialsの回答の最初の部分は正しいです。 idiv は128/64ビットの除算を行うので、その値は rdx 配当の上位64ビットを保持する「(1)」は、ランダムな値を含んではならない。しかし、拡張子が0というのは、間違っています。

あなたが持っているように サイン 変数を使用する場合は 記号 拡張 raxrdx:rax . これには具体的な指示があります。 cqto ( 4進数から8進数への変換 )をAT&Tで、そして cqo インテル構文では 新しいバージョンのgasは両方の名前を受け付けるようです。

movq    %rdx, %rbx
cqto                  # sign extend rax to rdx:rax
idivq   %rbx