$
AT&T アセンブリ構文では、リテラル値の前に記号を付ける必要があります
$
ただし、メモリ アドレッシングでは、リテラル値には符号がありません。
例えば:
mov %eax, -100(%eax)
と
jmp 100
jmp $100, $100
異なっています。
私の質問は、なぜ$
接頭辞がとても混乱するのですか?
$
AT&T アセンブリ構文では、リテラル値の前に記号を付ける必要があります
$
ただし、メモリ アドレッシングでは、リテラル値には符号がありません。
例えば:
mov %eax, -100(%eax)
と
jmp 100
jmp $100, $100
異なっています。
私の質問は、なぜ$
接頭辞がとても混乱するのですか?
jmp 100
jmp my_label
のコードへのジャンプと同様に、絶対アドレス 100 へのジャンプmy_label
です。EIP = 100 または EIP = のアドレスmy_label
。
(再配置を伴う にjmp 100
アセンブルし、リンカに、命令自身のアドレスから絶対ターゲットまでの右側の相対オフセットを埋めるように要求します。)jmp rel32
R_386_PC32
jmp
jmp x
したがって、AT&T の構文では、LEA から EIP への変換のようなものと考えることができます。
または、別の考え方として、コード フェッチは指定されたメモリ位置から開始されます。$
直接近くのジャンプのマシン エンコーディングでは、絶対ではなく相対変位が使用されるため、即時にa を要求することは実際には意味がありません。( http://felixcloutier.com/x86/JMP.html )。
また、間接ジャンプは異なる構文 (jmp *%eax
レジスタ間接またはjmp *(%edi, %ecx, 4)
メモリ間接) を使用するため、即時とメモリを区別する必要はありません。
しかし、ファージャンプは別の話です。
jmp ptr16:32
とjmp m16:32
はどちらも 32 ビット モードで使用できるため、 と を区別する必要がありljmp *(%edi)
ますljmp $100, $100
。
Direct far jump ( ) は、命令にエンコードされたイミディエイトを使用するのjmp far ptr16:32
と同様に、命令にエンコードされた絶対セグメント:オフセットを使用します。add $123, %eax
質問: 私の質問は、プレフィックス付きの $ がなぜ混乱しているのかということです。
$ プレフィックスは、値をそのままロード/使用するために使用されます。
例:
movl $5, %eax #copy value 5 to eax
addl $10,%eax # add 10 + 5 and store result in eax
$5、$10 は値 (定数) であり、レジスタやメモリなどの外部ソースからは取得されません。
メモリアドレッシングでは、具体的には「ダイレクトアドレッシングモード」で、特定のメモリ位置に格納された値を使用したいと考えています。
例:
movl 20, %eax
上記は、メモリ位置 20 に格納されている値を取得します。
実際には、メモリ位置は 16 進数 (0x00000000 ~ 0xfffffffff) で番号付けされているため、命令でメモリ位置を 16 進数で指定することは困難です。そのため、場所にシンボルを割り当てます
例:
.section .data
mydata:
long 4
.section .text
.globl _start
_start
movl mydata, %eax
上記のコードでは、 mydata は、値「4」が格納されている特定のメモリ位置を指定したシンボリック表現です。
上記で混乱が解消されることを願っています。