Dependent types for assembly code safety

When proving that programs adhere to various safety and security properties, it is often useful to work with binary code instead of the high-level source code from which it was compiled. Proving safety for binary code means that we need not trust the compiler and that end users can check the safety property without access to the source code. But most of today's safety tools operate only on source code, where analysis and program transformation are easier. We need a way to take safety results that have been established for source code and propagate them to the binary level. This dissertation proposes such a system for certified assembly code, and shows how it can be used with three source-code safety tools that operate on existing C programs: CCured, Deputy, and Cqual. A key feature of this system is a novel dependent type system suitable for assembly code. It is difficult to use dependent types safely in languages where heap values can be modified, because modifying a value can change the type of some other memory location. We address this problem by limiting in-memory dependent types so that they only refer to other fields of the same object. We show that it is possible to safely update such an object by allowing memory to temporarily be in a "bad" state until enough fields have been written so that the object is again internally consistent. And we show examples from CCured and Deputy where such a type system is necessary. The second key contribution of this dissertation is a type inference system for assembly code that has been generated by a "black box" compiler. This algorithm discovers the (possibly dependent) types of registers at each program point, and therefore reconstructs the invariants that were shown to hold during source-code verification. We use abstract interpretation of symbolic expressions for this inference, and discuss how to deal with pointer arithmetic. Finally, we have an implementation of our verifier for CCured and Cqual. This verifier parses x86 assembly code generated by GCC and ensures that the program was correctly analyzed and instrumented by CCured or Cqual prior to being compiled, and that the object code has not been tampered with in a way that would affect type safety. We present experimental results for our verifier which show that verification can be done in an efficient manner, but certain C constructs such as complicated array index expressions are difficult to analyze.

[1]  Úlfar Erlingsson,et al.  SASI enforcement of security policies: a retrospective , 1999, Proceedings DARPA Information Survivability Conference and Exposition. DISCEX'00.

[2]  Karl Crary,et al.  An expressive, scalable type theory for certified code , 2002, ICFP '02.

[3]  George C. Necula,et al.  Translation validation for an optimizing compiler , 2000, PLDI '00.

[4]  Andrew C. Myers,et al.  Language-based information-flow security , 2003, IEEE J. Sel. Areas Commun..

[5]  Shane Markstrum,et al.  Semantic type qualifiers , 2005, PLDI '05.

[6]  Hugo Herbelin,et al.  The Coq proof assistant : reference manual, version 6.1 , 1997 .

[7]  Bernhard Steffen,et al.  Detecting Equalities of Variables: Combining Efficiency with Precision , 1999, SAS.

[8]  Mark N. Wegman,et al.  Efficiently computing static single assignment form and the control dependence graph , 1991, TOPL.

[9]  Dan Grossman,et al.  TALx86: A Realistic Typed Assembly Language∗ , 1999 .

[10]  Vitaly Osipov,et al.  Format String Attacks , 2005 .

[11]  Robert O. Hastings,et al.  Fast detection of memory leaks and access errors , 1991 .

[12]  Jason Hickey,et al.  Formal Objects in Type Theory Using Very Dependent Types , 1996 .

[13]  Alexander Aiken,et al.  A theory of type qualifiers , 1999, PLDI '99.

[14]  Ken Kennedy,et al.  An algorithm for reduction of operator strength , 1977, Commun. ACM.

[15]  Daniel Kästner,et al.  Generic control flow reconstruction from assembly code , 2002, LCTES/SCOPES '02.

[16]  Hans-Juergen Boehm,et al.  Garbage collection in an uncooperative environment , 1988, Softw. Pract. Exp..

[17]  George C. Necula,et al.  Dependent Types for Low-Level Programming , 2007, ESOP.

[18]  Amir Pnueli,et al.  Translation Validation , 1998, TACAS.

[19]  David Walker,et al.  A type system for expressive security policies , 2000, POPL '00.

[20]  Doug Simon,et al.  Assembly to high-level language translation , 1998, Proceedings. International Conference on Software Maintenance (Cat. No. 98CB36272).

[21]  George C. Necula,et al.  Extensible untrusted code verification , 2004 .

[22]  George C. Necula,et al.  A certifying compiler for Java , 2000, PLDI '00.

[23]  Sumit Gulwani,et al.  Path-Sensitive Analysis for Linear Arithmetic and Uninterpreted Functions , 2004, SAS.

[24]  Robert Harper,et al.  A dependently typed assembly language , 2001, ICFP '01.

[25]  David Detlefs,et al.  Simplify: a theorem prover for program checking , 2005, JACM.

[26]  Dan Grossman,et al.  Type-safe multithreading in cyclone , 2003, TLDI '03.

[27]  Thomas W. Reps,et al.  WYSINWYX: What You See Is Not What You eXecute , 2005, VSTTE.

[28]  Antoine Miné,et al.  The octagon abstract domain , 2001, High. Order Symb. Comput..

[29]  George C. Necula,et al.  The design and implementation of a certifying compiler , 1998, PLDI.

[30]  George C. Necula,et al.  CCured: type-safe retrofitting of legacy software , 2005, TOPL.

[31]  David A. Wagner,et al.  Finding User/Kernel Pointer Bugs with Type Inference , 2004, USENIX Security Symposium.

[32]  Hongwei Xi,et al.  Imperative programming with dependent types , 2000, Proceedings Fifteenth Annual IEEE Symposium on Logic in Computer Science (Cat. No.99CB36332).

[33]  David Walker,et al.  Stack-based typed assembly language , 1998, Journal of Functional Programming.

[34]  Frank Yellin,et al.  The Java Virtual Machine Specification , 1996 .

[35]  Steven S. Muchnick,et al.  Advanced Compiler Design and Implementation , 1997 .

[36]  Martín Abadi,et al.  A type system for Java bytecode subroutines , 1999, TOPL.

[37]  David A. Wagner,et al.  This copyright notice must be included in the reproduced paper. USENIX acknowledges all trademarks herein. Detecting Format String Vulnerabilities with Type Qualifiers , 2001 .

[38]  Andrew D. Gordon,et al.  Typing a multi-language intermediate code , 2001, POPL '01.

[39]  Thomas W. Reps,et al.  Analyzing Memory Accesses in x86 Executables , 2004, CC.

[40]  George C. Necula,et al.  Analysis of Low-Level Code Using Cooperating Decompilers , 2006, SAS.

[41]  Dan Grossman Existential Types for Imperative Languages , 2002, ESOP.

[42]  James Cheney,et al.  Cyclone: A Safe Dialect of C , 2002, USENIX Annual Technical Conference, General Track.

[43]  Alan Mycroft,et al.  Type-Based Decompilation (or Program Reconstruction via Type Reconstruction) , 1999, ESOP.

[44]  Bor-Yuh Evan Chang Type-Based Verification of Assembly Language , 2008 .

[45]  Peter Lee,et al.  Automated techniques for provably safe mobile code , 2003, Theor. Comput. Sci..

[46]  Join Algorithms for the Theory of Uninterpreted Functions , 2004, FSTTCS.

[47]  Bor-Yuh Evan Chang,et al.  Abstract Interpretation with Alien Expressions and Heap Structures , 2005, VMCAI.

[48]  Nicholas Nethercote,et al.  Valgrind: a framework for heavyweight dynamic binary instrumentation , 2007, PLDI '07.

[49]  Patrick Cousot,et al.  Systematic design of program analysis frameworks , 1979, POPL.