[linux-guvenlik] [Fwd: recent security changes in openbsd]

---------

New Message Reply About this list Date view Thread view Subject view Author view

From: Burak DAYIOGLU (dayioglu@metu.edu.tr)
Date: Fri 31 Jan 2003 - 08:40:14 EET


OpenBSD ekibi isletim sistemi duzeyinde guvenligi bir adim daha ileri
tasiyor. Asagida de Raadt'in tech@openbsd'ye gonderdigi bir mesaj var.

Gorundugu kadariyla bu adamlar geleneksel olarak UNIX'lerde eksik kalmis
ne kadar gerekli is varsa tamamlayacaklar.

Ozellikle daha once ELF'te .rodata'nin kullanilmiyor olmasi ve
PROT_EXEC'in gozardi edilmesi bana cok "ilginc" geldi...

selamlar,
-bd

From: Theo de Raadt <deraadt@cvs.openbsd.org>
To: tech@cvs.openbsd.org
Subject: recent security changes in openbsd
Date: 30 Jan 2003 02:11:09 -0700

In the last while, a couple of people in OpenBSD have been putting
some buffer overflow "solutions" into our source tree; under my
continual prodding. I thought I would summarize some of these and how
they fit together, since what I have seen written up so far has been
wildly inaccurate. (Bad reporter, no cookie).

These are, in short form:

1) PROT_* purity
2) W^X
3) .rodata
4) propolice

Let me start at the top then.

1) PROT_* purity

    POSIX systems have three permissions for each page.
        PROT_READ
        PROT_WRITE
        PROT_EXEC
    To control the behaviour of a page, one or's these values together.
    Unfortunately, as you can see from mprotect(2):
     The mprotect() system call changes the specified pages to have protection
     prot. Not all implementations will guarantee protection on a page basis;
     the granularity of protection changes may be as large as an entire re-
     gion.
    This might not be true on a page. All real Unix systems I know of support
    PROT_READ and PROT_WRITE correctly, but PROT_EXEC has largely been implied
    as soon as you ask for PROT_READ.

    This is because the pmap modules have been poorly written, or because the
    mmu's in question are not fully capable. This change makes a best effort
    based on the MMU in question to enforce PROT_EXEC as an independent flag.

                        BEFORE AFTER
           sparc nope fully correct
           sparc64 nope fully correct
           alpha nope fully correct
           vax nope impossible
           m68k nope impossible
           hppa nope fully correct
           i386 nope see Note 1
           powerpc nope see Note 2

    Oh oh. i386 and powerpc, two very common architecures, have ominous
    notes. Now you guys know why I want fast sparc64 machines to run.

    Note 1)
        The i386 is not capable of doing per-page execute permission.
        At most it is only capable of drawing a line through the address
        space, by limiting the code segment length (using the code segment
        register). So we can say, "from 0 to this point is executable"
        and "from that point on to the end of userland is not executable".
        This sucks, but it is the best we can currently do. We can protect
        the stack, and not much else.

        There are a lot of other i386 details that are interesting to some
        of us, but you don't want to know them. Anyways we are investigating
        some possible changes that might help us protect more.

        By the way, hammer will not have this problem...

     Note 2)
        The powerpc has a slightly more flexible mechanism than the i386,
        but let me just say it still totally sucks. We can protect
        the stack, and not much else.

    So what we did here is to make a best effort solution at making the
    stack non-executable on most architectures. On many others, we have
    also made the data and bss segments non-executable.

    In other words, the VM system needed slight tracks to correct the
    tracking of PROT_EXEC more carefully, and then the pmap modules in
    each architecture was modified to take a `best effort' approach
    towards making PROT_EXEC an independent flag.

2) W^X.

    W^X is a short form for "PROT_WRITE XOR PROT_EXEC". The basic
    idea here is that most buffer overflow "eggs" rely on a particular
    feature: That there is memory which they can write to, and then jump
    to.

    What if there was no such memory? Does a normal Unix process have
    memory that is both writeable and executable? Turns out they do: In
    particular, (ELF) shared library programs have these two segments
    called GOT and PLT that are (depending on which architecture) normally
    part of the text or data segment. They are overwritten at times.

    But do they need it? The change that has been made is to put the
    GOT and PLT into their own segments. The main goal of course, is to
    try to ensure that at any time, no page in the system is both writeable
    and executable.

    We managed to get it working. The attackers just lost a place to put
    their buffer overflow egg. On architectures where goal (1) is fully
    working, that is...

3) .rodata

    Now there is another problem. The code segment of a program, called
    the text segment, has two parts in it on most systems: real code,
    and read-only data. Historically a.out only had text, data and bss
    segments, and it appears that when people moved to ELF they basically
    just didn't use any new features that ELF has. We've finally now
    moved to a seperate .rodata segment. Unlike the real text segment
    which is PROT_READ|PROT_EXEC, this new segment is only PROT_READ.

    What difference does this make? Well, if you manage to find some
    data in a program that looks like instructions you might want to
    run from your exploit, you can no longer do that. This may sound like
    a minor chance (but there are also cache and performance reasons
    too ;-)

4) Propolice

    Propolice is, as I like say describe it, "Stackgaurd on steriods".
    Stackgaurd uses a random canary (random value constant per run)
    placed by the function prologue and checked by the function epilogues
    to ensure the return address has not been moved. It was i386 only
    code. Propolice is machine independent, running on most of our
    architectures. As well, Propolice rearranges variables inside a
    stack frame so that the ones most likely to overflow (ie buffers) are
    closest to the canary, thereby making it hard to overwrite pointers or
    regular integers (which it moves down).

We feel that these 4 technologies together will be a a royal pain in
the ass for the typical buffer overflow attacker.

We'll be writing a real paper about all of this later, but perhaps now
people will understand why we are excited about 3.4.

-- 
Burak DAYIOGLU
Phone: +90 312 2103379      Fax: +90 312 2103333
http://www.dayioglu.net        ICQ UIN: 72276975

----------------------------------------------------------------------- Liste üyeliğiniz ile ilgili her türlü işlem için http://liste.linux.org.tr adresindeki web arayüzünü kullanabilirsiniz.

Listeden çıkmak için: 'linux-guvenlik-request@linux.org.tr' adresine, "Konu" kısmında "unsubscribe" yazan bir e-posta gönderiniz. -----------------------------------------------------------------------


New Message Reply About this list Date view Thread view Subject view Author view

---------

Bu arsiv hypermail 2b29 tarafindan uretilmistir.