PDA

Bekijk Volledige Versie : Observation on randomization/rebiasing...



Nicholas Weaver
05/02/03, 22:04
I've viewed this general thread with interest. A few comments:


In general, I'm rather skeptical of randomization providing much
prevention after code is injected. There already IS some
randomization in Sapphire's host, and the Sapphire code goes through
the routine to disambiguate things in order to get the function
pointers it needs.

Making it harder to get the API pointers, and the author will directly
call the syscalls (or windows equivelent) needed to find the
infomation it needs. So also the syscal inferface would need to be
randomized.


To prevent code injetion itself, noexec stack&heap works better and is
simpler. True, x86 is horribly broken when it comes to this, but you
can at least do a halfway decent noexec-stack. If one needs
noexec-stack/heap now, you can either get a Sparc or wait for Hammer.


Randomization, combined with code injection prevention, provides more
protection than either alone. Good randomization can prevent
forced-jumps to known code sections which serve an attacker's purpose,
which noexec stack/heap can't. They really address different things,
the Write ^ Exec prevents injection, while randomization prevents
forced jumps.


Randomization is best done with runtime (dynamic) linking. If it is
compile-time, I can plausibly see attackers able to do Over/Under
tests or other smarter searching to get the magic addresses needed,
with the server crashing and restarting each time. Thus the O(2^n)
difficulty/probability of disambiguating becomes O(lg(2^n))->O(n) if
static randomization and the particular bug allows an attacker to tell
if his guess of a magic number is high or low.


Finally, it's been pointed out to me that implementing randomized
dyamic linking, or even randomized static linking, will play havoc with
debuggers and possibly introduce even more Heisenbugs.

--
Nicholas C. Weaver nweaver@cs.berkeley.edu

Jason Coombs
06/02/03, 00:09
Nicholas Weaver wrote:
> There already IS some randomization in Sapphire's host,
> and the Sapphire code goes through the routine to disambiguate

GetProcAddress and similar APIs were not created with security in mind. They
were built for the benefit of programmers, who also were not created with
security in mind.

It is possible to intercept every call to GetProcAddress and determine
whether or not the call should be authorized based on a predetermined list
of known valid callers (runtime call stack analysis). This list of
authorized callers must be constructed through the use of forensic profiling
tools in the case of other people's binaries, but can be constructed with
the help of additional API calls in the case of one's own code. Call a
profiling/tracing API before calling GetProcAddress. After compilation but
before deployment to production boxes you simply execute the code in profile
mode to generate a list of authorized callers. This list is then configured
as a static security setting adhered to by the security layer that sits
between GetProcAddress and the rest of the virtual world.

For programmers doing development one simply instructs such security layer
to allow all callers from the process that is under development.

A properly security-hardened binary DOES NOT require support for arbitrary
relocations, arbitrary dynamic library injection, arbitrary code injection
resulting in new execute paths defined at run-time, and the type of
programmability required by software developers. Once code has been compiled
and linked, even when that code makes use of dynamic libraries, there is no
longer any unknown. With the exception of those very few situations in which
self-modifying code techniques are employed (certain compilers, etc. --
which in general are broken by noexec stack implementations, anyway) all
possible execute paths through the binary and its related libraries are
known at compile-time.

Failing to perform any sort of forensic profiling of these static execute
paths, and failing to restrict use of the microprocessor unless the execute
path attempting to control it conforms to an authorized forensic profile
results in unnecessary run-time programmability that causes the vast
majority of infosec vulnerabilities.

Execute restrictions based on such forensic profiling can be built for
Windows, without access to its source code and without losing binary
backwards compatibility. It is far better to build this countermeasure at
the source level.

This solution brings the essential security benefits of non-programmable
firmware-based embedded systems to our programmable computers and it is long
overdue.

Sincerely,

Jason Coombs
jasonc@science.org

Jason Coombs
06/02/03, 19:48
There are good reasons for extensible architectures. No changes are needed
in this respect, we simply must restrict the scope of that extensibility at
run-time to authorized add-on modules. Other programmers can make it easier
for us to do so by adding some forensic profiling code to their programs,
but this is not necessary to achieve substantially-improved practical
control over the extensible code modules we allow to execute, including the
ability to detect when arbitrary malicious code succeeds in overflowing a
buffer and smashing the stack. Every path through third-party code that we
have not profiled and explicitly authorized is simply denied by default,
including portions of third-party code that are not harmful or of malicious
foreign origin, so that in essence the defense says:

"We will only allow code to execute that we have previously executed during
forensic testing. Everything else is denied by default until we analyze its
origin and intended function."

Jason Coombs
jasonc@science.org

-----Original Message-----
From: Michael Wojcik [mailto:Michael.Wojcik@MicroFocus.com]
Sent: Wednesday, February 05, 2003 10:43 PM
To: BugTraq
Cc: jasonc@science.org; Nicholas Weaver
Subject: RE: Observation on randomization/rebiasing...


> From: Jason Coombs [mailto:jasonc@science.org]
> Sent: Wednesday, February 05, 2003 5:08 PM

> A properly security-hardened binary DOES NOT require support
> for arbitrary relocations, arbitrary dynamic library injection,
> arbitrary code injection resulting in new execute paths defined at
> run-time, and the type of programmability required by software
> developers. Once code has been compiled and linked, even when that
> code makes use of dynamic libraries, there is no longer any unknown.

There are plenty of examples of programs and libraries that by design load
and execute independently-developed code: browser plugins, ISAPI, and so
forth. Leaving aside for the moment the question of whether this is a Good
Thing, or whether it fits someone's definition of "a properly
security-hardened binary", it's certainly a popular approach. The security
community has not to date had much luck convincing users and programmers to
adopt even its uncontroversial recommendations; I doubt you'll get any
traction with this one.

Michael Wojcik
Principal Software Systems Developer, Micro Focus

Michael Wojcik
06/02/03, 21:12
> From: Jason Coombs [mailto:jasonc@science.org]
> Sent: Wednesday, February 05, 2003 5:08 PM

> A properly security-hardened binary DOES NOT require support
> for arbitrary relocations, arbitrary dynamic library injection,
> arbitrary code injection resulting in new execute paths defined at
> run-time, and the type of programmability required by software
> developers. Once code has been compiled and linked, even when that
> code makes use of dynamic libraries, there is no longer any unknown.

There are plenty of examples of programs and libraries that by design load
and execute independently-developed code: browser plugins, ISAPI, and so
forth. Leaving aside for the moment the question of whether this is a Good
Thing, or whether it fits someone's definition of "a properly
security-hardened binary", it's certainly a popular approach. The security
community has not to date had much luck convincing users and programmers to
adopt even its uncontroversial recommendations; I doubt you'll get any
traction with this one.

Michael Wojcik
Principal Software Systems Developer, Micro Focus