forked from blau_araujo/pbn
Compare commits
2 commits
Author | SHA1 | Date | |
---|---|---|---|
a853524d46 | |||
a2bdba6e1f |
2 changed files with 88 additions and 1 deletions
|
@ -543,7 +543,7 @@ Quando escrevemos programas em NASM que serão ligados com outros módulos,
|
|||
como bibliotecas externas ou arquivos objeto, nós precisamos informar ao
|
||||
editor de ligações quais símbolos devem ser /exportados/ para esses módulos
|
||||
e quais devem ser /importados/ de outros lugares. No NASM, isso é feito com
|
||||
as diretivas =global= (importação) e =extern= (exportação).
|
||||
as diretivas =global= (exportação) e =extern= (importação).
|
||||
|
||||
No GNU/Linux, especialmente quando não usamos uma linguagem de mais alto
|
||||
nível (como C), nós precisamos especificar manualmente o ponto de entrada
|
||||
|
|
87
docs/prefixo-rex.org
Normal file
87
docs/prefixo-rex.org
Normal file
|
@ -0,0 +1,87 @@
|
|||
* Prefixos REX na arquitetura Intel 64 (x86-64)
|
||||
|
||||
O prefixo REX é um byte opcional usado no modo 64 bits para:
|
||||
|
||||
- Acessar registradores estendidos (~r8–r15~)
|
||||
- Usar operandos de ~64~ bits
|
||||
- Estender campos ~ModR/M~, ~SIB~ ou ~opcode~
|
||||
|
||||
** Formato geral do prefixo REX (1 byte)
|
||||
|
||||
#+begin_example
|
||||
Bits: 7 6 5 4 | 3 | 2 | 1 | 0
|
||||
0 1 0 0 W R X B
|
||||
#+end_example
|
||||
|
||||
| Bit | Nome | Função |
|
||||
|-----+------+--------------------------------------------------------------------|
|
||||
| ~7–4~ | ~0100~ | Identifica o byte como prefixo REX |
|
||||
| ~3~ | ~W~ | ~1~ = operandos de ~64~ bits |
|
||||
| ~2~ | ~R~ | Estende o campo ~Reg~ no byte ~ModR/M~ |
|
||||
| ~1~ | ~X~ | Estende o campo ~Index~ no byte ~SIB~ |
|
||||
| ~0~ | ~B~ | Estende o campo ~Base~ no ~ModR/M~, ~SIB~ ou campo ~reg~ em certos opcodes |
|
||||
|
||||
** Tabela dos 16 prefixos REX possíveis (~0x40–0x4F~)
|
||||
|
||||
| Hex | Binário | ~W~ | ~R~ | ~X~ | ~B~ | Significado resumido |
|
||||
|------+----------+---+---+---+---+-------------------------------------------------|
|
||||
| ~0x40~ | ~01000000~ | ~0~ | ~0~ | ~0~ | ~0~ | Sem extensão nem ~64~-bit |
|
||||
| ~0x41~ | ~01000001~ | ~0~ | ~0~ | ~0~ | ~1~ | ~B = 1~ (extensão do campo Base) |
|
||||
| ~0x42~ | ~01000010~ | ~0~ | ~0~ | ~1~ | ~0~ | ~X = 1~ (extensão do campo Index) |
|
||||
| ~0x43~ | ~01000011~ | ~0~ | ~0~ | ~1~ | ~1~ | ~X = 1~, ~B = 1~ |
|
||||
| ~0x44~ | ~01000100~ | ~0~ | ~1~ | ~0~ | ~0~ | ~R = 1~ (extensão do campo Reg) |
|
||||
| ~0x45~ | ~01000101~ | ~0~ | ~1~ | ~0~ | ~1~ | ~R = 1~, ~B = 1~ |
|
||||
| ~0x46~ | ~01000110~ | ~0~ | ~1~ | ~1~ | ~0~ | ~R = 1~, ~X = 1~ |
|
||||
| ~0x47~ | ~01000111~ | ~0~ | ~1~ | ~1~ | ~1~ | ~R = 1~, ~X = 1~, ~B = 1~ |
|
||||
| ~0x48~ | ~01001000~ | ~1~ | ~0~ | ~0~ | ~0~ | ~W = 1~ (operandos de ~64~ bits) |
|
||||
| ~0x49~ | ~01001001~ | ~1~ | ~0~ | ~0~ | ~1~ | ~W = 1~, ~B = 1~ |
|
||||
| ~0x4A~ | ~01001010~ | ~1~ | ~0~ | ~1~ | ~0~ | ~W = 1~, ~X = 1~ |
|
||||
| ~0x4B~ | ~01001011~ | ~1~ | ~0~ | ~1~ | ~1~ | ~W = 1~, ~X = 1~, ~B = 1~ |
|
||||
| ~0x4C~ | ~01001100~ | ~1~ | ~1~ | ~0~ | ~0~ | ~W = 1~, ~R = 1~ |
|
||||
| ~0x4D~ | ~01001101~ | ~1~ | ~1~ | ~0~ | ~1~ | ~W = 1~, ~R = 1~, ~B = 1~ |
|
||||
| ~0x4E~ | ~01001110~ | ~1~ | ~1~ | ~1~ | ~0~ | ~W = 1~, ~R = 1~, ~X = 1~ |
|
||||
| ~0x4F~ | ~01001111~ | ~1~ | ~1~ | ~1~ | ~1~ | ~W = 1~, ~R = 1~, ~X = 1~, ~B = 1~ (todas as extensões) |
|
||||
|
||||
** Observações
|
||||
|
||||
- O prefixo REX só é válido no modo 64 bits.
|
||||
- Pode ser necessário mesmo com operandos de 32 bits se registradores estendidos
|
||||
forem usados.
|
||||
|
||||
** Exemplo de desmontagem
|
||||
|
||||
#+begin_example
|
||||
48 89 c8 => mov rax, rcx
|
||||
#+end_example
|
||||
|
||||
Nesse caso:
|
||||
- ~48~: É o prefixo REX com ~W = 1~, ~R = 0~, ~X = 0~, ~B = 0~ (operandos de 64 bits).
|
||||
- ~89~: OpCode ~mov r/m, reg~ (como primeiro operando é ~r/m~, temos que ver o byte ModR/M).
|
||||
- ~c8~: Byte ModR/M, onde...
|
||||
|
||||
#+begin_example
|
||||
Bits: 7 8 | 5 4 3 | 2 1 0
|
||||
modo | origem | destino
|
||||
c8 → 11 | 001 | 000
|
||||
regs | rcx | rax
|
||||
#+end_example
|
||||
|
||||
Portanto... ~48 89 c8 => mov rax, rcx~
|
||||
|
||||
** Tabela de registradores no byte ModR/M
|
||||
|
||||
O modo ~11~ indica que os dois operandos estão em registradores. Os 3 bits
|
||||
dos campos ~reg~ e ~r/m~ indicam os registradores, com ou sem extensão via
|
||||
prefixo ~REX~.
|
||||
|
||||
| Código | Reg. | ~REX.R~ ou ~REX.B~ |
|
||||
|--------+------+----------------|
|
||||
| ~000~ | ~rax~ | ~r8~ |
|
||||
| ~001~ | ~rcx~ | ~r9~ |
|
||||
| ~010~ | ~rdx~ | ~r10~ |
|
||||
| ~011~ | ~rbx~ | ~r11~ |
|
||||
| ~100~ | ~rsp~ | ~r12~ |
|
||||
| ~101~ | ~rbp~ | ~r13~ |
|
||||
| ~110~ | ~rsi~ | ~r14~ |
|
||||
| ~111~ | ~rdi~ | ~r15~ |
|
||||
|
Loading…
Add table
Reference in a new issue