2012-04-18 53 views
0

我正在使用i386:x86_64,並且正在編寫一個簡單的程序來啓動一個shell。貝婁是我的集會。Segmentation fault assembly i386:x86_64

.section .data 
.section .text 
.globl _start 

_start: 
    xor %rax, %rax 
    mov $70, %al 
    xor %rbx, %rbx 
    xor %rcx, %rcx 
    int $0x80 

    jmp ender 

starter: 
    pop %rbx 
    xor %rax, %rax 
    mov %al, 0x07(%rbx) 
    mov %rbx, 0x08(%rbx) 
    mov %rax, 0x0c(%rbx) 
    mov $11, %al 
    lea 0x08(%rbx), %rcx 
    lea 0x0c(%rbx), %rdx 
    int $0x80 

ender: 
    call starter 
    .string "/bin/sh" 

問題是我不斷收到分段錯誤。當我使用objdump的-D my_prog輸出...這

拆卸部分的.text:

0000000000400078 <_start>: 
    400078: 48 31 c0    xor %rax,%rax 
    40007b: b0 46     mov $0x46,%al 
    40007d: 48 31 db    xor %rbx,%rbx 
    400080: 48 31 c9    xor %rcx,%rcx 
    400083: cd 80     int $0x80 
    400085: eb 1b     jmp 4000a2 <ender> 

0000000000400087 <starter>: 
    400087: 5b      pop %rbx 
    400088: 48 31 c0    xor %rax,%rax 
    40008b: 88 43 07    mov %al,0x7(%rbx) 
    40008e: 48 89 5b 08    mov %rbx,0x8(%rbx) 
    400092: 48 89 43 0c    mov %rax,0xc(%rbx) 
    400096: b0 0b     mov $0xb,%al 
    400098: 48 8d 4b 08    lea 0x8(%rbx),%rcx 
    40009c: 48 8d 53 0c    lea 0xc(%rbx),%rdx 
    4000a0: cd 80     int $0x80 

00000000004000a2 <ender>: 
    4000a2: e8 e0 ff ff ff   callq 400087 <starter> 
    4000a7: 2f      (bad) 
    4000a8: 62      (bad) 
    4000a9: 69      .byte 0x69 
    4000aa: 6e      outsb %ds:(%rsi),(%dx) 
    4000ab: 2f      (bad) 
    4000ac: 73 68     jae 400116 <ender+0x74> 

我要採取的猜測,並說,這是被標記地址(壞)這是導致seg故障的原因。我知道這是因爲它希望mem訪問未分配給它的mem。我不確定我應該做什麼。我正在運行Linux。

感謝您的幫助!

+0

你爲什麼把字符串放在文本部分? – 2012-04-18 14:57:07

+0

我正在關注一個教程,並且我複製了粘貼的代碼。這可能是一個問題。 – 2012-04-18 14:58:18

回答

2

這是因爲您試圖將數據寫入內存的代碼(.text)區域而導致的分段錯誤。可執行代碼區域幾乎總是標記爲只讀。

下面是您的代碼和其他一些註釋。

.section .data 
.section .text 
.globl _start 

_start: 
    xor %rax, %rax 
    mov $70, %al 
    xor %rbx, %rbx 
    xor %rcx, %rcx 
    ; call sys_setreuid(0,0) 
    int $0x80 

    jmp ender 

starter: 
    ; take the return address off the stack 
    ; rbx will point to the /bin/sh string after the call instruction 
    pop %rbx 
    ; zero rax 
    xor %rax, %rax 
    ; save a zero byte to the end of the /bin/sh string (it's 7 characters long)... 
    ; (it will segfault here because you're writing to a read-only area) 
    mov %al, 0x07(%rbx) 
    ; ...followed by a pointer to the string... 
    mov %rbx, 0x08(%rbx) 
    ; ...followed by another zero value 
    mov %rax, 0x0c(%rbx) 
    ; setup the parameters for a sys_execve call 
    mov $11, %al 
    lea 0x08(%rbx), %rcx 
    lea 0x0c(%rbx), %rdx 
    int $0x80 

    ; what happens when int 0x80 returns? 
    ; you should do something here or starter will be called again 

ender: 
    call starter 
    .string "/bin/sh" 

該代碼還存在其他問題。考慮:

mov %rbx, 0x08(%rbx) 
mov %rax, 0x0c(%rbx) 

%rbx是一個8字節的值,但代碼只給了它4個字節的空間(0x0c-0x08 = 4)。 如果你想得到它的工作,你需要將字符串移動到一個.data區域(後面有一些額外的空間),並更改代碼以使其對64位友好。

+0

謝謝,我對PC的組裝很新。這有助於。 – 2012-04-19 00:24:43

相關問題