Como usar o RIP em relação Endereçamento em uma versão de 64 bits do programa assembly?
-
15-09-2020 - |
Pergunta
Como faço para usar o RIP Relativa de Endereçamento em um Linux programa assembly para o AMD64 archtitecture?Eu estou olhando para um exemplo simples (um Hello world programa) que usa o AMD64 RIP em relação adressing modo.
Por exemplo, o seguinte assembly de 64 bits do programa de trabalho normal (endereçamento absoluto):
.text
.global _start
_start:
mov $0xd, %rdx
mov $msg, %rsi
pushq $0x1
pop %rax
mov %rax, %rdi
syscall
xor %rdi, %rdi
pushq $0x3c
pop %rax
syscall
.data
msg:
.ascii "Hello world!\n"
Eu estou supondo que o mesmo programa usando RIP em relação Endereçamento seria algo como:
.text
.global _start
_start:
mov $0xd, %rdx
mov msg(%rip), %rsi
pushq $0x1
pop %rax
mov %rax, %rdi
syscall
xor %rdi, %rdi
pushq $0x3c
pop %rax
syscall
msg:
.ascii "Hello world!\n"
A versão normal é executado correctamente quando compilado com:
as -o hello.o hello.s && ld -s -o hello hello.o && ./hello
Mas eu não posso obter a versão RIP de trabalho.
Qualquer idéias?
--- editar ----
Stephen Canon resposta faz o RIP versão de trabalho.
Agora, quando eu desmontar o executável da versão RIP eu recebo:
o objdump -d olá
0000000000400078 <.text>:
400078: 48 c7 c2 0d 00 00 00 mov $0xd,%rdx
40007f: 48 8d 35 10 00 00 00 lea 0x10(%rip),%rsi # 0x400096
400086: 6a 01 pushq $0x1
400088: 58 pop %rax
400089: 48 89 c7 mov %rax,%rdi
40008c: 0f 05 syscall
40008e: 48 31 ff xor %rdi,%rdi
400091: 6a 3c pushq $0x3c
400093: 58 pop %rax
400094: 0f 05 syscall
400096: 48 rex.W
400097: 65 gs
400098: 6c insb (%dx),%es:(%rdi)
400099: 6c insb (%dx),%es:(%rdi)
40009a: 6f outsl %ds:(%rsi),(%dx)
40009b: 20 77 6f and %dh,0x6f(%rdi)
40009e: 72 6c jb 0x40010c
4000a0: 64 21 0a and %ecx,%fs:(%rdx)
O que mostra que eu estava tentando fazer:lea 0x10(%rip),%rsi carrega o endereço de 17 bytes após a instrução lea, que é o endereço 0x400096 onde o Olá mundo de seqüência de caracteres pode ser encontrado e, portanto, resultando em posição código independente.
Solução
Eu acredito que você deseja carregar o endereço de sua cadeia de caracteres em %rsi
;o código tenta carregar um quadword de que o endereço em vez de o próprio endereço.Você pretende:
lea msg(%rip), %rsi
se não estou enganado.Eu não tenho uma caixa de linux para teste, no entanto.
Outras dicas
Uma vez que você precisa o endereço de erro em %rsi, basta substituir:
mov msg(%rip),%rsi
com:
lea msg(%rip),%rsi