Extensible Verification of Untrusted Code BorYuh Evan Chang

  • Slides: 18
Download presentation
Extensible Verification of Untrusted Code Bor-Yuh Evan Chang, Adam Chlipala, Kun Gao, George Necula,

Extensible Verification of Untrusted Code Bor-Yuh Evan Chang, Adam Chlipala, Kun Gao, George Necula, and Robert Schneck May 14, 2004 OSQ Retreat Santa Cruz, California

Type Safety as an Assurance Mechanism OR type checker code untrusted • Type safety

Type Safety as an Assurance Mechanism OR type checker code untrusted • Type safety is an accepted assurance mechanism • Today – Good: Type check source code in a strongly-typed high-level language (e. g. ML, C#, Java) – Better: Type check intermediate code (e. g. , MS-CLI, JVML) 5/14/2004 2

Type Systems Today (JVML, MS-CLI, TAL) • Hard-wired in the verifier • High-level and

Type Systems Today (JVML, MS-CLI, TAL) • Hard-wired in the verifier • High-level and tailored to particular source languages – E. g, built-in object-oriented features • Hard to compile other source languages – Unnatural, loss of performance or expressiveness – E. g, ML ! JVML or Java ! TAL • Under constant pressure to become more complex – To handle more source languages – To be able to check more complex code (e. g. optimizations) 5/14/2004 3

Generality by Customization • MS-CLI is designed for a multiple languages, but – quite

Generality by Customization • MS-CLI is designed for a multiple languages, but – quite complex (e. g. 6 -9 versions of function call) – not complex enough (the ILX project adds more calls) • Still not general enough! – JVML: native code interface – MS-CLI: unverifiable subset of the language • Proposal: Allow multiple type systems and other verification methods (e. g. PCC) to co-exist – Fix only the safety policy (e. g. memory safety) – Not the enforcement mechanism (e. g. a type system) 5/14/2004 4

Design Goals of the Open Verifier • Should be easy to develop “verifier extensions”

Design Goals of the Open Verifier • Should be easy to develop “verifier extensions” – Only incrementally more complicated than a conventional verifier for the same language – Be able to retrofit existing compilers or conventional verifiers • Client should have complete control over the type system or other conventions – Calling conventions, exceptions, stack usage, data layout 5/14/2004 5

Bytecode Verification Example len : list ! int 1 rrv à 0 0 T

Bytecode Verification Example len : list ! int 1 rrv à 0 0 T 2 rarg = 0 t : : = int | list | nelist F 3 rrv à rrv + 1 4 rarg à m[rarg] 5 jump [rra] 5/14/2004 6

Bytecode Verification Example arg : list Why? 1 rrv à 0 arg : list

Bytecode Verification Example arg : list Why? 1 rrv à 0 arg : list Æ rv : int T 2 rarg = 0 F arg : list Æ rv : int arg : nelist Æ rv : int 3 rrv à rrv + 1 4 rarg à m[rarg] arg : nelist Æ rv : int 5 jump [rra] 5/14/2004 7

Bytecode Verifier Correctness • How do we know the verifier didn’t forget any checks?

Bytecode Verifier Correctness • How do we know the verifier didn’t forget any checks? – Should not need to provide proofs involving the model of the machine semantics • Use strongest post-condition generation to eliminate proof obligations about machine transitions – Show at each program point i with next states N, post(Ii) ) Çj 2 N Ij 5/14/2004 8

Verified Bytecode Verification I 1 = arg : list Why? 1 rrv à 0

Verified Bytecode Verification I 1 = arg : list Why? 1 rrv à 0 I 2 = arg : list Æ rv : int T 2 rarg = 0 F 3 rrv à rrv + 1 4 rarg à m[rarg] post(I 1) pc = 2 Æ arg : list Æ rv = 0 post(I 1) ) I 2 new I 2 = post(I 1) with add (rv : int) by imm_int with drop (rv = 0) 5 jump [rra] 5/14/2004 9

Branch arg : list Why? 1 rrv à 0 I 2 = arg :

Branch arg : list Why? 1 rrv à 0 I 2 = arg : list Æ rv : int T 2 rarg = 0 F I 3 = arg : nelist Æ rv : int I 5 = arg : list Æ rv : int 5 jump [rra] 5/14/2004 post(I 2) pc = 3 Æ arg : list Æ rv : int Æ arg 0 Ç pc = 5 Æ arg : list Æ rv : int Æ arg = 0 3 rrv à rrv + 1 4 post(I 2) ) I 3 Ç I 5 case post(I 2) of where ](pc = 3) ) new I 3 = Ifalse with false m[r rarg Ià arg let h, h’ = find (arg : list), find (arg 0) in add (arg : nelist) by (cons h h’) with drop (arg : list) with drop (arg 0) | Itrue where (pc = 5) ) new I 5 = Itrue with drop (arg = 0) 10

Arithmetic arg : list Why? 1 rrv à 0 arg : list Æ rv

Arithmetic arg : list Why? 1 rrv à 0 arg : list Æ rv : int T 2 rarg = 0 F I 3 = arg : nelist Æ rv : int arg : list Æ rv : int 5 jump [rra] 5/14/2004 3 rrv à rrv + 1 post(I 3) 9 rv 3. pc = 4 Æ arg : nelist Æ rv 3 : int Æ rv = rv 3 + 1 I 4 = arg : nelist Æ rv : int 4 rarg à m[rarg] post(I 3) ) I 4 new I 4 = post(I 3) with let h = find (rv 3 : int) in add (rv : int) by (plus h (imm_int)) with drop (rv 3 : int) with drop (rv = rv 3 + 1) 11

Memory Read arg : list F = pc = err Æ ? Why? lem

Memory Read arg : list F = pc = err Æ ? Why? lem 1: If (arg : nelist) then (addr arg) lem 2: If (arg : nelist) then (m[arg] : list) 1 rrv à 0 I 2 = arg : list Æ rv : int T 2 rarg = 0 F arg : list Æ rv : int 5 jump [rra] 5/14/2004 9 arg 4. pc = 2 Æ arg 4 : nelist Æ rv : int Æ addr arg 4 Æ arg = m[arg 4] Ç arg : nelistpcÆ=rverr: int Æ arg : nelist Æ rv : int Æ : (addr arg) 3 rrv à rrv + 1 4 rarg post(I 4) post(I ) ) I Ç F 4 2 I 4 = arg : nelist Æ rv : int case post(I 4) of à m[rarg] Iok where _ ) Iok with let h = find (arg 4 : nelist) in add (arg : list) by (lem 2 h) with … | Ierr where : (addr arg) by bad ) Ierr with let h = … in add ? by (bad (lem 1 h)) with … 12

Customizability Yields Controlled Trust Any Binary (*. exe) Trust Compilers (javac) Trust Specialized Verifiers

Customizability Yields Controlled Trust Any Binary (*. exe) Trust Compilers (javac) Trust Specialized Verifiers (JVM) Trust Typing Rules Trust Model of Machine Semantics Trust Meter 5/14/2004 13

Summary • Provide a “natural” language for the verifier to describe in a checkable

Summary • Provide a “natural” language for the verifier to describe in a checkable form the reasoning it makes – Close to conventional type-based verifiers – Amenable to other safety enforcement mechanisms, such as PCC • PCC – Most of the time, just goes along with post(¢) – When proof is required, give the proof attached with the code – Proof representation can be chosen by the client 5/14/2004 14

Summary post(¢) OR type checker code “preservation and progress” untrusted • Towards practical extensible

Summary post(¢) OR type checker code “preservation and progress” untrusted • Towards practical extensible verification of untrusted code – Ask only for reasoning already done by conventional verifiers 5/14/2004 15

Conclusion • We have verifier extensions for – Cool (“mini-Java”) [Aiken et al. ]

Conclusion • We have verifier extensions for – Cool (“mini-Java”) [Aiken et al. ] • can verify output of existing Cool compilers – TAL (functional typed assembly language) • retrofitted TALx 86 [ Morrisett et al. ] – PCC • Philosophy: – To verify complete software systems, • not a general, super-expressive type system • rather a framework to allow existing ones to work together 5/14/2004 16

Return R = pc = ra 0 Æ rv : int arg : list

Return R = pc = ra 0 Æ rv : int arg : list Why? 1 rrv à 0 arg : list Æ rv : int T 2 rarg = 0 F I 5 = arg : list Æ rv : int post(I 5) arg : nelist Æ rv : int 3 rrv à rrv + 1 4 rarg à m[rarg] pc = ra 0 Æ arg : list Æ rv : int arg : nelist Æ rv : int post(I 5) ) R post(I 5) with drop (arg : list) 5 jump [rra] 5/14/2004 18