Fog Creek Software
Discussion Board




Blaster - How are buffer overruns actually done?

Re-reading the title I just typed in, it sounds like those messages on CodeGuru you see like, "How can I format the C: drive from a program?", which nobody ever answers, thank goodness.

Actually, I'm curious how buffer overrun "exploits" (I guess that's the word) actually work.  My (extremely vague) understanding is that they send data that contains an address or command they want to execute, it overwrites something in the stack, and it gets executed.  Is that roughly accurate?

My other question is, is this something that could be done to any program that reads data?  I mean, say I have a program that reads in a datafile - could someone play with the datafile, and cause a command to be executed?  (No, I'm not paranoid - just a hypothetical question.)

Assuming the answer is yes, what are the ways to circumvent an attack like this?  I know C++ in .NET places guard variables around buffers (or something like that) to detect if they get trampled, but let's ignore that for the moment.  Wouldn't a big program have a zillion buffers to check?  Or do you only have to check the places where the program accepts data?

Also, a lot of people attack Microsoft for not fixing these problems.  Now, I want to step softly here, because this is an emotional issue.  Let's pretend that everyone currently working at Microsoft were fired, and were replaced by the readers of JoS and SlashDot.  Could we be expected to ever find all the places to fix in a finite period of time?  Or could, say, Windows XP be cleaned up in a few months?  Are there tools and practices that the former MS employees should have used, and didn't?  Is that why the Linux crowd is so upset?

Yeah, I know these sound like trolls, but they're not - they're honest questions.  Frankly, I don't have the background to tell whether the Linux crowd have a pointabout this, or whether they're just automatically anti-MS.  For the record, I've never seen Linux, and have no opinion on it.  (I have lots of opinions about MS, though, depending on which of their tools I'm using...)

Grumpy Old-Timer
Friday, August 15, 2003

Read the cow...

http://www.cultdeadcow.com/cDc_files/cDc-351/

--
ee

eclectic_echidna
Friday, August 15, 2003

Well.

If the buffer is created on the local stack, for instance as an automatic variable in C, and that buffer is created a specific length then if there's no check on the bounds of any input to that buffer you can overwrite that buffer and you're overwriting into the stack space. 

Given sufficient experimentation you can discover the extent of the stack in that routine and where the return instruction is.

If you're moderately smart, well actually if you're just ordinarily intelligent, you can craft a set of op codes such that when that  address is reached in the stack it executes some other code and doesn't return to where it normally should.

Then its just your regular bootstrap mechanism, once you have one known instruction address you can write your code around that and execute it all within the stack space.

If you're reasonably smart you can do all this without breaking the code you just infected, and if you're very very smart you can write the self modifying code so that it only affects a very small address area and is difficult to find.


This isn't the only scenario, but it is the easiest for a buffer overrun exploit.

Simon Lucy
Friday, August 15, 2003

It's roughly like this:

A buffer overflow exploit sends data to a server program.

The data gets processed and passed around in the program's variables.

Many C programs use fixed-length character arrays as strings.

What happens if a function uses such a variable locally? It is stored on the stack, while the function is execute.

And what happens if the variable is 10 characters long, and I pass 20 characters as a parameter?

It's simple - a part of the stack gets overwritten with a part of the passed string.

But, when calling the function, the return address is put on the stack. That is the address the CPU will jump at when the function finishes (usually with a RET instruction).

So, by overwriting part of the stack, I can control the return address.

Now, imagine this:

I write a small program in assembler language, which does what I need to do on the target machine.

Then, I put together the normal string I need to pass to the function, add some more characters in order to overwrite the return address on the stack, and then add the caracters of my small program's machine code.

Then, I send the server the resulting string.

The resulting string gets processed, and, when the target function is executed, the little program is put in the memory (by overwriting the stack), and the return address of the function is overwritten so that, when the function finishes, the control passes to the little program in memory.

So, a buffer overflow exploit allows an attacker to run arbitrary code on the attacked machine.

In order for someone to write a buffer overflow attack, that someone needs to:

- know assembly language very well

- know very well how to use a powerfull debuger such as NuMega SoftIce

- have access to and be able to experiment with the host machine

In order to prevent buffer overflow attacks, several measures can be taken:

- The C programmers must be very careful, have an absolute mistrust of the user input and check the length of all copied strings (for example, by using strncpy instead of strcpy, if I remember correctly)

- The OS may have a non-executable stack. Indeed, if the current instruction pointer is set somewhere on the stack, but the stack is not executable, the CPU will just issue an exception and the app will be terminated - no attack code will get executed.

- Programmers can use languages such as Delphi or Python, which don't use fixed length character arrays as strings.


> My other question is, is this something that
> could be done to any program that reads data?
> I mean, say I have a program that reads in a
> datafile - could someone play with the datafile,
> and cause a command to be executed?

Yes, this is unfortunately possible.


> Let's pretend that everyone currently working
> at Microsoft were fired, and were replaced by
> the readers of JoS and SlashDot.  Could we be
> expected to ever find all the places to fix in a
> finite period of time?  Or could, say, Windows XP
> be cleaned up in a few months?

In my opinion, Windows XP is already clean. There are very, very few vulnerabilities.


> Are there tools and practices that the former
> MS employees should have used, and didn't?

Such practices do exist, and I am sure they already use lots of them.

The proof is the fact that Windows XP has very few vulnerabilities.

If they didn't use such practices, WinXP would be a swiss cheese of security holes and vulnerabilities. But, it isn't.


> Is that why the Linux crowd is so upset?

Many distributions of Linux also had problems with Linux worms.

The real offender among Microsoft's software is Outlook Express.

In my opinion, it was an e-mail program quickly put together. Their goal was to get something to the market very fast, sacrificing everything else, so they could gain market share.

You know, when you hurry a lot to release a program, it may have a lot of bugs and security problems.

But, they are fixing it by ceasing development on Outlook Express and offering some other solution.

B.J. Thunderstone
Friday, August 15, 2003

Another link:

http://www.cse.ogi.edu/DISC/projects/immunix/StackGuard/profit.html

Actually that was suggested reading in my Computer Security class at UC Davis.  They walked us through writing a buffer overflow to get a root shell.  Pretty interesting.

Andrew Hurst
Friday, August 15, 2003

GOT,

I'm suprised that this question is coming from you, given your position on both C++ knowledge and the need to understand both C and basic computer science.

I'm not a genious programmer, but most of the basics have been listed already. First, assume that any source of input is potentially corrupt, even if you don't think the user has been able to get at it. Second, good memory management practices will stop a lot of the problems.

Good security practices also tend to make for stable software. That's because good security practices mean making sure that everything is fine with your memory management, which at least seems to be what causes my software to fall down and go boom.

Clay Dowling
Friday, August 15, 2003

"In my opinion, Windows XP is already clean. There are very, very few vulnerabilities."

This week might tend to give the lie to this.  The problem of course is that an OS is more than a kernel, a file system and some means of loading programs and executing them.  They're made up of components some of which belong to the OS supplier but quite a lot will be written by some third party.

Depending on the OS these components will have access to system and kernel functions to a greater or a lesser degree and any buffer overrun exploit in one component can give access to the whole OS.

Now, it might seem that hosted applications, Java, .NET and so on, are isolated from such problems they live in their own sandbox. 

This is true only if the runtime doesn't itself have a possible buffer overrun exploit.  And there is the rub.  You can exploit any known memory address given sufficient patience.

Load images of applications with their associated runtimes, DLLs and such tend to have the same profile regardless of wherever they get loaded in an individual machine.  From that profile you can decide how best to find an exploit.

You can reduce the likelihood of leaving a possible exploit but you'll never be able to eliminate them.

Simon Lucy
Saturday, August 16, 2003

The Microsoft Press book _Writing Secure Code_ seems to have good explanations on such exploits.  Too bad they don't normally distribute it in .chm files, as they probably do within MSFT.

Tayssir John Gabbour
Saturday, August 16, 2003

Get a safari 14 days free trial account and read it for free at http://safari.oreilly.com

Just me (Sir to you)
Monday, August 18, 2003

"I'm suprised that this question is coming from you, given your position on both C++ knowledge and the need to understand both C and basic computer science."

I don't know everything.  I'm not ashamed to reveal my ignorance.  This is how I learn.  Having posted this question, and read the informative answers, I am now smarter than I was before.

Grumpy Old-Timer
Monday, August 18, 2003

If you're intersted in a detailed explanation of how buffer overflow exploits work, check out Alpeh One's now (in)famous piece. http://www.phrack.org/show.php?p=49&a=14 

Anonymous
Wednesday, August 20, 2003

*  Recent Topics

*  Fog Creek Home