Bugs (part 1) CPS210 Spring 2006
Papers Bugs as Deviant Behavior: A General Approach to Inferring Errors in System Code Dawson Engler Eraser: A Dynamic Data Race Detector for Multithreaded Programs Stefan Savage
Take a deep breath One month is over, 2.5 left 15 papers down, 19 to go (the reading schedule lightens) Done with most “core OS” topics Address spaces, page tables, threads, etc
What’s left Various forms of IO e.g. networking and storage Broader system properties e.g. reliability and security Projects!
Dealing with bugs We know how to build systems How do we fix the ones we’re stuck with? What is a buggy program? One that behaves “incorrectly”
What does “correct” look like? At the macro-level this is really hard Need to know user expectations Need to know programmers intentions Easier to look at a micro-level Are variables used as we expect? Are primitives used as we expect?
Consistency example 1.int mxser_write (strcut ttyp_struct *tty) { // B(tty)=unknown 2. struct msxer_sstruct *info = tty>driver_data; // B(tty)=notnull 3. unsigned long flags; if (!tty || !info->xmit_buf) // B(tty)=null,notnull 6. return 0; 7. … Beliefs are MUST beliefs
Example template T = “do not dereference null pntr ” Slote instance p Belief set B p {}, {null}, {notnull}, {null, notnull} Which actions matter? Pointer dereferences, comparisons to null
Statistical analysis example 1.lock l; // lock 2.int a,b; // variables potentially protected by l 3.void foo () { 4. lock (l); // enter critical section 5. a = a + b; // MAY: a, b protected by l 6. unlock (l); // exit critical section 7. b = b + 1; // MUST: b not protected by l 8.} 9.void bar () { 10. lock (l); 11. a = a + 1; // MAY: a protected by l 12. unlock (l); 13.} 14.void baz () { 15. a = a + 1; // MAY: a protected by l 16. unlock (l); 17. b = b – 1; // MUST: b not protected by l 18. a = a / 5; // MUST: a not protected by l 19.} check Slot combination = ( a, l ) T = variable must be protected by lock check check (ERROR)
Statistical analysis example 1.lock l; // lock 2.int a,b; // variables potentially protected by l 3.void foo () { 4. lock (l); // enter critical section 5. a = a + b; // MAY: a, b protected by l 6. unlock (l); // exit critical section 7. b = b + 1; // MUST: b not protected by l 8.} 9.void bar () { 10. lock (l); 11. a = a + 1; // MAY: a protected by l 12. unlock (l); 13.} 14.void baz () { 15. a = a + 1; // MAY: a protected by l 16. unlock (l); 17. b = b – 1; // MUST: b not protected by l 18. a = a / 5; // MUST: a not protected by l 19.} check Slot combination = ( b, l ) T = variable must be protected by lock check (ERROR)
Eraser variable state machine Virgin Exclusive Shared- modified Shared wr, new thread rd/wr, first thread wr rd, new thread rd wr C(v) does not change C(v) changes No errors reported C(v) changes Errors reported
Intentional races 1.if (p->ip_fp == (NI2_XFILE *) 0) { // fpntr set? 2. NI2_LOCKS_LOCK (&p->ip_lock); // acq lock 3. if (p->ip_fp == (NI2_XFILE *) 0) { // fpntr set since we last checked? 4. p->ip_fp = ni2_xfopen (p->ip_name, “rb”); 5. } 6. NI2_LOCKS_UNLOCK (&p->ip_lock); // rel lock 7.} 8.… // no locking overhead if fpntr set