Unformatted text preview:

EECS 261: Computer Security Fall 2007Lecture 4 — September 6Lecturer: David Wagner Scribe: DK Moon4.1 Required reading materials for this class• Beyond Stack Smashing: Recent Advances in Exploiting Buffer Overruns, Pincus andBaker• Exploiting Format String Vulnerabilities• Basic Integer Overflows4.2 Reasons for vulnerabilities• The lack of security design• Architectural level flaws violating the design principles in Lecture 2• Micro-level implementation bugs (The topic of this lecture)• ...4.3 Buffer Overrun• Morris worm (1988): the first major Internet worm used the technique• State of the art at that time: stack smashing only• But, heap smashing is also possible4.3.1 Stack Smashing• By overwriting a return address stored on stack1 f ( ) {2 char buf [ 8 0 ] , ∗p = buf ;3 while ( ( ∗ p = re ad fr o m net ( ) ) != ’ \0 ’ ) {4 ++p ;5 }6 }4-1EECS 261 Lecture 4 — September 6 Fall 2007Stack Growthpbuf sfp retLow AddressHigh Addressf()’s callerf()Figure 4.1. an example of Stack smashing. Stack grows from high address. A box with rounded cornersrepresents a function frame.The above code is vulnerable as there’s no boundary check in line #3; it will writebeyond buf unless null is given in the first 80 bytes. Figure 4.1 depicts the memory layout.An attacker can jump to wherever she wants by overflowing buf until overwriting the returnaddress; when returning from f(), CPU will see the modified return address, pops the frame,and jumps to the address an attacker specified. In addition, an attacker can also put codeinto memory (i.e. in buf). So, an attacker can inject code and jump to the code.4.3.2 Heap SmashingFor long time, people thought buffer overrun doesn’t work for heap allocated buffer. How-ever..• At least, an attacker can crash a process by corrupting heap.• An attacker can run arbitrary code she wants by keep overflowing heap-allocated bufferuntil overwriting a heap-allocated function pointer. This gives a control to an attackernot immediately, but after the overwritten function pointer is dereferenced. Figure 4.2shows this scenario. Note that it’s possible to calculate how many bytes to overflow ifwe can use some determinism: e.g. a vulnerable code is deterministic.High heap addresstarget bufferLow heap addressfunction pointeroffset...Figure 4.2. an example of Heap smashing. An attack can get a control by overwriting a function pointer onheap. She needs to overflow as many bytes as the offset; it’s possible to calculate the offset when a processbases on determinism.• A more sophisticated attack: an attacker can write any value to any location by over-writing a heap control block used by malloc() and free(); malloc() prepends a heapcontrol block, like Figure 4.3, to maintain doubly-linked memory chunks. On freeingheader, free() adjusts link pointers in a heap control block like this:header → next ptr → prev ptr = header → prev ptr4-2EECS 261 Lecture 4 — September 6 Fall 2007Suppose that an attacker did overflow to fill some value, V , into header → prev ptr andsome address, A, into header → next ptr. Now, calling free() results in ∗(A + C) = V ,where C is the constant offset of prev ptr. This lets an attacker write any value to ar-bitrary location. So, she can change return address, jump to malicious code, overwritefunction pointer, and so on.ptrapp uses this portionnextptrprevptrapp uses this portionnextptrprevptrnextptrapp uses this portionprevFigure 4.3. malloc() prepends header control blocks(shaded in the figure), which contain doubly-linked-list,to maintain memory chunks.Why do we more worry about an attack for full control than a crash?• Whole control gives more options (including crashes).• Crashes are noticeable.• Compromising a superuser-privileged process such as sshd means that a whole host ison an attacker’s hand.Buffer overrun is really common and easy to exploit. Saying like ”it’s very hard to exploitbecause an attacker should know every detail of program’s behavior. So, it will give onlylimited control” is a totally wrong idea. There are tons of clever guys, and even a single-bytebuffer overflow can cause significant impacts like changing frame pointer. We better assumeall buffer overrun vulnerabilities exploitable and fix them right a way.4.4 Format string vulnerabilities1 f ( ) {2 char buf [ 5 1 2 ] ;3 read ( netfd , buf , s i z eo f ( buf ) ) ;4 p r i n t f ( buf ) ; // buggy !5 }This code is buggy. The line #4 should have been printf(”%s”, buf ). If a string suppliedby an attacker contains %d%d%d%d%d..., printf() is going to look for arguments on stack,which don’t exist there.printf() has an internal pointer to look for format arguments on stack. For example, itexpects 4-byte integer pointed by the pointer and increment the pointer by 4 bytes, when it4-3EECS 261 Lecture 4 — September 6 Fall 2007encounters a format specifier %d in a format string. Figure 4.4 shows the call stack of theabove code snippet. The internal pointer, p, reads and moves beyond printf()’s stack framebecause there is no corresponding format argument on the stack. Therefore, we can movethe pointer to the stack location storing f ()’s return address by multiple ’%d’s. (somethinglike ’%100d’ can be used to reduce many %d’s.) And, we can also read the adress value by%x....ret format string buf retinternal pointer,p, for next format argumentprintf()’s stack framef()’s stack framelocal variablesFigure 4.4. printf() has an internal pointer to seek for format arguments. We can move the pointer towardf()’s ret by using format specifiersWorse, an attacker can also write. And she can specify both an address and a value towrite!• Specifying an address: An attacker can also write by ’%n’. Basically, ’%n’ writes thenumber of printed characters so far into a given address. An attacker can supply atarget address in buf , then %n touches the address.• Specifying a value: A returned value by %n is usually small as we do not write suchmany characters. So, 4-byte value is created by concatenating four 1-byte values.For example, we can write 4-byte value into A by using four ’%n’s with overlappingaddresses (A + 0), (A + 1), (A + 2), and (A + 3) (works for little endian machines).4.5 Double free vulnerabilityThis causes heap corruption by calling free() twice with the same argument. Either a crashor taking over a control.4.6 Integer overflowIt occurs when down-casting or up-casting


View Full Document

Berkeley COMPSCI 261N - Lecture 4

Download Lecture 4
Our administrator received your request to download this document. We will send you the file to your email shortly.
Loading Unlocking...
Login

Join to view Lecture 4 and access 3M+ class-specific study document.

or
We will never post anything without your permission.
Don't have an account?
Sign Up

Join to view Lecture 4 2 2 and access 3M+ class-specific study document.

or

By creating an account you agree to our Privacy Policy and Terms Of Use

Already a member?