Bugtraq mailing list archives

Re: Buffer overflow prevention


From: Nicholas Weaver <nweaver () CS berkeley edu>
Date: Wed, 13 Aug 2003 12:13:27 -0700

On Wed, Aug 13, 2003 at 02:28:33PM +0400, Eygene A. Ryabinkin composed:

 I have an idea on buffer overflow prevention. I doubt that it's
new, but I haven't seen an implementation of it in any freely
distributable Un*x system.  So, I hardly need your comments on it.

Then why post this to a public list?  Sorry, you are going to get
comments.

 Preliminary: I'm talking about Intel x86 architecture, but maybe it will be
applicable to others as well.

 The idea itself: all (correct me if I'm wrong) buffer overflows are
based on the fact that we're using the stack, referenced by SS:ESP
pair, both for procedure return address and for local variables. It
seems to me, that would we have two stacks -- one for real stack and
one for variables -- it will solve a bunch of problems. So, my
suggestion: let us organise two segments: one for normal stack,
growing downwards, referenced by SS:ESP pair and the second one, for
local variables, referenced by GS:EBP pair, with either upwards or
downwards growing. Now, if we use first segment for passing
variables and procedure return addresses (normal stack usage), and
second segment only for local procedure variables, we will have the
following advantages:

 1) Local variables and return address will be physically (by means
 of CPU) divided and it will not be possible to touch the return
 address by overflowing local buffer.

 2) The procedure introduces only one extra register -- GS, since EBP is
 very often used for the stack frame.

On the x86, introducing ONE extra reserved register into the calling
convention is a performance killer: the ISA is far too register poor
already.

Of course, this two segments can be made non-executable, just in case.

 What we need to implement the idea: first, rewrite kernel to organise two
segments for every process and to place proper values into the segment
registers upon the program startup. Second, rewrite the compiler to support
the new scheme of local variables addresation. So, the changes are minimal,
in some sence.

 As I said, I hardly need your criticism, suggestions, etc. of any type.

This only stops attacks which overwrite the return address pointers on
the stack, it doesn't stop heap overflows or other control-flow
attacks.

As such, it seems like this only stops the same class of attacks which
StackGuard-style checking halts: manipulation of the return address
pointer through data overflows.  

Since stackguard-techniques already exist, are very mature, and is
included as "On By Default" on OpenBSD and potentially on other
platforms (including possibly Windows, it is in Microsoft's latest
compiler and I think that all new code from Microsoft turns on this
compiler flag [1]), there is no sense inventing new structures, which
require substantially more changes to the infrastructure, which don't
offer any more protection.



[1] If microsoft doesn't have this flag turn on on their own products,
this would be a lawsuit waiting to happen.

-- 
Nicholas C. Weaver                                 nweaver () cs berkeley edu


Current thread: