Announcement

Collapse
No announcement yet.

Linux: Exec shield overflow protection

Collapse
X
 
  • Filter
  • Time
  • Show
Clear All
new posts

  • Linux: Exec shield overflow protection

    The other day when I read the buffer overflow post by "genjix", I experimented a little with the code and tried to find out what was wrong. I didn't actually found what was wrong, however I came across something else when I tried to compile a sample code from "Hacking: The Art of Exploitation" by Jon Erickson.

    Voulnerable program: http://www.phiral.com/book_code/chap2/vuln.c
    Exploit program: http://www.phiral.com/book_code/chap2/exploit.c

    When I tried to compile and run it, I knew something wasn't right, because I got a segmentation fault when I tried to run it (with kernel 2.6.12.1). Then I remembered I have read an article for a long time ago about Exec shield overflow protection in the 2.4.2x kernels so I thought maybe they had finally get it to work in the late 2.6.x kernels. Then after experimenting a little with the code I tried to compile and run it with kernel 2.4.29 and the exploit program worked.

    Have anyone of experienced any of this? Is it the exec shield overflow protection which causes the segmentation fault in the 2.6.12.1 kernel, or is it some new protection feature in gcc?
    I have not much experience in kernel and compiling security field so I'm hoping any of you guys have some thoughts about this.

    Thanks in advance
    -- dev_zero@

  • #2
    Which one are you having a problem the vul or exploit? The shell code for the exploit will most likely change with a new kernel as things tend to shift around a bit and syscalls will be in new memory locations. You may have to rework the shell code to fit kern 2.6.x this would be a good exerse in flexing what you learned from the book
    "Never Underestimate the Power of Stupid People in Large Groups"

    Comment


    • #3
      Originally posted by hackajar
      Which one are you having a problem the vul or exploit? The shell code for the exploit will most likely change with a new kernel as things tend to shift around a bit and syscalls will be in new memory locations. You may have to rework the shell code to fit kern 2.6.x this would be a good exerse in flexing what you learned from the book
      When I ran exploit through gdb and singel stepped it as far as I know the problem with segmentation fault came in the middle of the strcpy process after execl had executed vuln..

      Well I guess this could be a nice way learning more about the kernels internals, so I will try to experiment with the code.
      -- dev_zero@

      Comment


      • #4
        vul won't change, exploit will with kern versions (most times). Find the Nop sled in that code (probably first or second line) and see where it drops you in memory, if it's no where near eip than that's your problem. Use a standard \x90 or \x41 nop sled, and rediscover the eip that way and compare with the example code. This should give you a good start in the right direction
        "Never Underestimate the Power of Stupid People in Large Groups"

        Comment


        • #5
          I'm waving the white flag, I give up.. I have tried to debug the program under both 2.4 and 2.6, I compiled the 2.4 exploit under kernel 2.4 and the other under 2.6 (I don't know if this has anything to say, but I did it anyway).

          This is how i did it:
          2.4:
          I put break point on execl and execve because I noticed execl called execve.. When I was in execve I single stepped until right after it called int 80.. then I checked the memory where the shellcode was suppose to begin and there it was the entire buffer just waiting to be executed.

          2.6:
          I did the same as I did in the 2.4 version, but at the return address there were lots of 0x00.

          After experiencing this, I will say in the 2.4 kernel the buffer actually gets copied into memory, but in the 2.6 kernel it doesn't..
          I'm throwing in the towel now, unless someone can help me, because this is getting way out of my league.
          -- dev_zero@

          Comment


          • #6
            try throwing the shell code at vul like this:

            perl -e 'print "\x41"x70 . <play with code here>' | vul

            from command line, find what works, then update the exploit.c with new lines from perl statement and recomplie into 2.6.x that's how it's done by hand :)
            "Never Underestimate the Power of Stupid People in Large Groups"

            Comment


            • #7
              Originally posted by hackajar
              try throwing the shell code at vul like this:

              perl -e 'print "\x41"x70 . <play with code here>' | vul

              from command line, find what works, then update the exploit.c with new lines from perl statement and recomplie into 2.6.x that's how it's done by hand :)
              To use that method I have to know the return address, at least that's how he shows it in the book and he uses the output from the exploit program as return address.
              Then here is my problem, exploit prints out the return address etc. on execution and in 2.4 the ret address is the same everytime I run exploit, but when I run exploit in 2.6 I get different return address everytime. And if I'm going to do the "perl method" I think it's quite hard to guess the ret address, at least when the differences of the ret addresses I get from exploit everytime I run it, is very different from eachother..
              -- dev_zero@

              Comment


              • #8
                Originally posted by dev_zero
                To use that method I have to know the return address, at least that's how he shows it in the book and he uses the output from the exploit program as return address.
                Then here is my problem, exploit prints out the return address etc. on execution and in 2.4 the ret address is the same everytime I run exploit, but when I run exploit in 2.6 I get different return address everytime. And if I'm going to do the "perl method" I think it's quite hard to guess the ret address, at least when the differences of the ret addresses I get from exploit everytime I run it, is very different from eachother..
                from command line
                Code:
                ulimit -c unlimited
                Code:
                perl -e 'print <enter shell code here>'
                Code:
                gdb -c core
                This should get you the eip so you can check if it was overwritten

                Get metasploit and run:

                Code:
                ./msfpscan -f vul -s
                That should get you some usable ret addresses to point to in program :)

                Have fun!
                "Never Underestimate the Power of Stupid People in Large Groups"

                Comment


                • #9
                  Originally posted by hackajar
                  from command line
                  Code:
                  ulimit -c unlimited
                  Code:
                  perl -e 'print <enter shell code here>'
                  Code:
                  gdb -c core
                  This should get you the eip so you can check if it was overwritten

                  Get metasploit and run:

                  Code:
                  ./msfpscan -f vul -s
                  That should get you some usable ret addresses to point to in program :)

                  Have fun!
                  msfpscan ruturned 0x00000000... That won't help much :/

                  And I did check something else, I tried making the buffer with the shellcode in an environment variable.. Then I used a little program to find where in the memory the variable was, and it turns out that program also returns different addresses everytime i run it.. It looks like my memory is floating around, but the weird thing is that the 2.4 memory doesn't behave anything like this, I guess they must have rewritten the whole memory management in 2.6.. When that's said, I'm out of ideas, I really thought the environment variable was static and that would work but it didn't.
                  -- dev_zero@

                  Comment


                  • #10
                    Originally posted by dev_zero
                    msfpscan ruturned 0x00000000... That won't help much :/

                    And I did check something else, I tried making the buffer with the shellcode in an environment variable.. Then I used a little program to find where in the memory the variable was, and it turns out that program also returns different addresses everytime i run it.. It looks like my memory is floating around, but the weird thing is that the 2.4 memory doesn't behave anything like this, I guess they must have rewritten the whole memory management in 2.6.. When that's said, I'm out of ideas, I really thought the environment variable was static and that would work but it didn't.
                    This appears to float outside of my knowledge. Anyone else got sometin? Me /got nothing
                    "Never Underestimate the Power of Stupid People in Large Groups"

                    Comment


                    • #11
                      Your mention of a 2.6.12.1 Linux kernel causes me to think that this may be a "stock" kernel, but I still want to ask, is this a pre-ackaged kernel or a stock one from kernel.org?

                      A few distributions of Linux have started including security patches to their pre-packaged kernels.

                      For Example, I think that Owl Security Enhanced Linux comes with a kernel that include security patches for non-executable stack space.

                      RedHat is well known for providing kernels that are far from "stock" and there was a notice that the were going to start including non-executable stack patches in their kernels (maybe not by default) in a new version of RHEL. (I can't find the e-mail sent to me by a peer.)

                      Some patches for Linux kernels will actually log in kern.log or may be available in syslog or dmesg. This is one place I would check after running your buffer overrun and exploit code.

                      There are a few things that I have seen includedin gcc or kernels that could be causing some of what you report:
                      1) (Compiler) Use of "canaries" by gcc in the form of an encrypted copy of the return address that is included on the stack, "above," the return address. Before the return is called, the system or application decrypts the "canary" and compares it to the return address. If not equal, either exception or fault is called an that return is followed.
                      2) (Kernel/OS) OS performs randomization of addresses used by executable at load/run time. This may cause the addresses for the return address to change on each executaion of the application.
                      3) (Kernel/OS) Non-executable Stack enforced by kernel.

                      Because many of these new features are security-based, it is very likely that they were written by security people. As a result, logging of violation attempts to one of the log repositories seems likely. (dmesg/kern.log for kernel-eforced additions and syslog/error/debug for compiler-patched additions.)

                      It looks like my memory is floating around
                      This makes me think that #2 above is being used.

                      Using google provided me with these:
                      link quoted
                      Originally posted by http://kerneltrap.org/node/3070
                      Linux creator Linus Torvalds announced the release of the 2.6.6 stable kernel. A number of notable additions found their way into the mainline 2.6 kernel during this development cycle, including ... support for a non-executable stack on a number of architectures ...
                      On that page scroll down to find a reply "the particular patch in quest" and find more about it.
                      ...

                      After reading the above, I had a few more keywords in future google searches and found that there is support in /proc for enabling/disabling kernel options for this...

                      As for Exec Shield... and for your box, try
                      # cd /proc/sys/kernel
                      # ls *exec*
                      If you see "exec-shield-randomize"
                      Try:
                      # cat exec-shield-randomize
                      Is it non-zero? :-)
                      # echo "0" >> /proc/sys/kernel/exec-shield-randomize
                      Now does the address you notice as changing still change each time it is executed?

                      Do you see other "files" with "exec" or "shield" as part of their name? That is a good hint for what may be included in your kernel.

                      Maybe if you have /proc/sys/kernel/exec-shield
                      # cat /proc/sys/kernel/exec-shield
                      If non-zero, then try
                      # echo "0" >> /proc/sys/kernel/exec-shield

                      If you disable these, does your test on the 2.6.6 (or later) kernel still work as you desire?

                      Sorry, I have not moved to 2.6 yet. I said I would when it got to double-digit sub-version (2.6.X where X >= 10) but I have not had the time as of yet.

                      HTH
                      Last edited by TheCotMan; July 5, 2005, 14:57. Reason: quoting was bad, fixed wording

                      Comment


                      • #12
                        It's CotMan to the rescue! I was running out of idea's there man. Doing the FreeBSD thing, have not taken notice of Linux Kernel since 2.2 first hit the street.
                        "Never Underestimate the Power of Stupid People in Large Groups"

                        Comment


                        • #13
                          Originally posted by hackajar
                          It's CotMan to the rescue! I was running out of idea's there man. Doing the FreeBSD thing, have not taken notice of Linux Kernel since 2.2 first hit the street.
                          I have not built a 2.6 kernel yet, but google helped me to find most of this. This was not a trivial, "just google it," as it took a few queries with intelligent selections of keywords from previously useful searches, until I found was I was looking for.

                          I cheated though... I knew what I wanted; I only needed to know how to get there. ;-)

                          Don't blame me for any answer though, it was google that pointed a finger to help.

                          Comment


                          • #14
                            Originally posted by TheCotMan
                            Don't blame me for any answer though, it was google that pointed a finger to help.
                            Man, no soup kitchen ever made a nickle and a cent giving away the secret sause! sssshhhhhhh, the n00b that keep asking the obvious questions might catch on!
                            "Never Underestimate the Power of Stupid People in Large Groups"

                            Comment


                            • #15
                              Originally posted by TheCotMan
                              Your mention of a 2.6.12.1 Linux kernel causes me to think that this may be a "stock" kernel, but I still want to ask, is this a pre-ackaged kernel or a stock one from kernel.org?
                              I downloaded and configured my own from kernel.org.. And thanks for the help, to both of you.. I will look into it as soon as I turn my laptop on ;)
                              -- dev_zero@

                              Comment

                              Working...
                              X