Home page logo

basics logo Security Basics mailing list archives

RE: Regarding Aleph's "Smashing the Stack for fun and Profit"
From: R A <ra_in_2003 () yahoo com>
Date: Wed, 5 Oct 2005 02:52:03 -0700 (PDT)

Hey Bryan,

Little correction here, in your mail my code and
Aleph's have been marked wrongly. 

At one level I wasn't able to understand the logic
behind (*ret) += 8 even in Aleph's article. I think it
should be 10. But then I've tried all that and more.
Found about GCC bug 9624
which results in more buffer space being allocated
than is needed even after accomodating 4byte
boundaries. I tried adding 20 to each word from
buffer1 to buffer1+80 which should include return
address in between somewhere. and this addition on 20
should result in a crash atleast and x=1 or for that
matter printf should not execute. But then also the
program printed "1". I am really confused.

Here's the C code:
void function(int a, int b, int c) {
   char buffer1[5];
   char buffer2[10];
   int *ret;
   ret = (int*)buffer1+12;
   (*ret) += 10;

int main() {
  int x;
  x = 0;
  return 0;

Here's the diassembly of main:
0x080481ee <main+0>:    push   %ebp
0x080481ef <main+1>:    mov    %esp,%ebp
0x080481f1 <main+3>:    sub    $0x8,%esp
0x080481f4 <main+6>:    and    $0xfffffff0,%esp
0x080481f7 <main+9>:    mov    $0x0,%eax
0x080481fc <main+14>:   sub    %eax,%esp
0x080481fe <main+16>:   movl   $0x0,0xfffffffc(%ebp)
0x08048205 <main+23>:   sub    $0x4,%esp
0x08048208 <main+26>:   push   $0x3
0x0804820a <main+28>:   push   $0x2
0x0804820c <main+30>:   push   $0x1
0x0804820e <main+32>:   call   0x80481d0 <function>
0x08048213 <main+37>:   add    $0x10,%esp
0x08048216 <main+40>:   movl   $0x1,0xfffffffc(%ebp)
0x0804821d <main+47>:   sub    $0x8,%esp
0x08048220 <main+50>:   pushl  0xfffffffc(%ebp)
0x08048223 <main+53>:   push   $0x808efa8
0x08048228 <main+58>:   call   0x80488e8 <printf>
0x0804822d <main+63>:   add    $0x10,%esp
0x08048230 <main+66>:   mov    $0x0,%eax
0x08048235 <main+71>:   leave
0x08048236 <main+72>:   ret

And here's the disassembly of function:
0x080481d0 <function+0>:        push   %ebp
0x080481d1 <function+1>:        mov    %esp,%ebp
0x080481d3 <function+3>:        sub    $0x38,%esp
0x080481d6 <function+6>:        lea   
0x080481d9 <function+9>:        add    $0x30,%eax
0x080481dc <function+12>:       mov   
0x080481df <function+15>:       mov   
0x080481e2 <function+18>:       mov   
0x080481e5 <function+21>:       mov    (%eax),%eax
0x080481e7 <function+23>:       add    $0xa,%eax
0x080481ea <function+26>:       mov    %eax,(%edx)
0x080481ec <function+28>:       leave
0x080481ed <function+29>:       ret

What am I missing out?


--- Bryan McAninch <BMcAninch () PENSON COM> wrote:

I recall encountering a few differences between my
gdb output and the
output provided in Aleph's article (perhaps even a
few typos). Obviously
the addresses will differ, but I can't recall the
reason why the
assembly code itself differs. AFAIK, compilers
compile code differently
on different distros; maybe someone else on the list
can queue in and
answer. From what you're describing, it sounds as if
your return address
is not correct, your 'ret' pointer is not actually
pointing to the
return address, or both. 

In Aleph's code below, the return address pushed
onto the stack when
calling <function> should be that of the next
instruction, 0x0804836b
<main+37>. The assignment of 'x=1' occurs at
0x0804836e <main+40>, which
means you'll need to change the value used in
<function> to change the
return address to an instruction after 0x0804836e
<main+40>, perhaps
0x08048375 <main+47>. If my calculations are
correct, the value used in
<function> should be (0x0804836b - 0x0804836e) = 8,
which is what Aleph
has used in his document, "*ret += 8".

For your code, simply follow the same methodology as
above, but first
ensure 'ret = buffer1 + 12' is actually pointing to
your return address
on the stack. Perhaps you can include your gdb
output for <function> if
the following suggestions don't work. When
<function> is called, the
return address pushed onto the stack should be
0x80004a8 <main+24>, the
assignment of 'x=1' occurs at 0x80004ab <main+27>,
meaning you'll want
to skip that instruction and return to the next one
instead, 0x80004b2
<main+34>. Thus, your return address should be
(0x80004b2 - 0x80004a8) =
10. So, try using *ret += 10 in function. 


Aleph's code:

0x08048346 <main+0>:  push %ebp
0x08048347 <main+1>:  mov %esp,%ebp
0x08048349 <main+3>:  sub $0x8,%esp
0x0804834c <main+6>:  and $0xfffffff0,%esp 
0x0804834f <main+9>:  mov $0x0,%eax
0x08048354 <main+14>: sub %eax,%esp
0x08048356 <main+16>: movl $0x0,0xfffffffc(%ebp)
0x0804835d <main+23>: sub $0x4,%esp
0x08048360 <main+26>: push $0x3
0x08048362 <main+28>: push $0x2
0x08048364 <main+30>: push $0x1
0x08048366 <main+32>: call 0x8048328 <function>
0x0804836b <main+37>: add $0x10,%esp 
0x0804836e <main+40>: movl $0x1,0xfffffffc(%ebp)
0x08048375 <main+47>: sub $0x8,%esp
0x08048378 <main+50>: pushl 0xfffffffc(%ebp)
0x0804837b <main+53>: push $0x8048438
0x08048380 <main+58>: call 0x8048268 <printf>
0x08048385 <main+63>: add $0x10,%esp
0x08048388 <main+66>: leave
0x08048389 <main+67>: ret

Your code:

0x8000490 <main>:    pushl %ebp
0x8000491 <main+1>:  movl %esp,%ebp
0x8000493 <main+3>:  subl $0x4,%esp
0x8000496 <main+6>:  movl $0x0,0xfffffffc(%ebp)
0x800049d <main+13>: pushl $0x3
0x800049f <main+15>: pushl $0x2
0x80004a1 <main+17>: pushl $0x1
0x80004a3 <main+19>: call 0x8000470 <function>
0x80004a8 <main+24>: addl $0xc,%esp
0x80004ab <main+27>: movl $0x1,0xfffffffc(%ebp)
0x80004b2 <main+34>: movl 0xfffffffc(%ebp),%eax
0x80004b5 <main+37>: pushl %eax
0x80004b6 <main+38>: pushl $0x80004f8
0x80004bb <main+43>: call 0x8000378 <printf>
0x80004c0 <main+48>: addl $0x8,%esp
0x80004c3 <main+51>: movl %ebp,%esp
0x80004c5 <main+53>: popl %ebp
0x80004c6 <main+54>: ret
0x80004c7 <main+55>: nop

Yahoo! for Good 
Donate to the Hurricane Katrina relief effort. 

  By Date           By Thread  

Current thread:
[ Nmap | Sec Tools | Mailing Lists | Site News | About/Contact | Advertising | Privacy ]