Decker: Attack Surface Reduction
via On-Demand Code Mapping
Chris Porter, Sharjeel Khan, Santosh Pande
ASPLOS 2023
Problem: Code reuse attacks
ROP chain example
0x500000
...
0x5001f9
...
0x52e1fe
...
0x55720a
...
0x600000
pop rcx
ret
mov qword ptr [rcx], rax
ret
pop rax
ret
.text
ROP gadgets within the .text section
ROP chain example
0x55720a
0x2a
0x5001f9
0x800000
0x52e1fe
0x500000
...
0x5001f9
...
0x52e1fe
...
0x55720a
...
0x600000
pop rcx
ret
mov qword ptr [rcx], rax
ret
pop rax
ret
.text
Stack payload
ROP chain example
0x55720a
0x2a
0x5001f9
0x800000
0x52e1fe
0x500000
...
0x5001f9
...
0x52e1fe
...
0x55720a
...
0x600000
pop rcx
ret
mov qword ptr [rcx], rax
ret
pop rax
ret
.text
Stack payload
gadget 1 address -> pop rax; ret;
ROP chain example
0x55720a
0x2a
0x5001f9
0x800000
0x52e1fe
0x500000
...
0x5001f9
...
0x52e1fe
...
0x55720a
...
0x600000
pop rcx
ret
mov qword ptr [rcx], rax
ret
pop rax
ret
.text
Stack payload
ROP chain example
0x55720a
0x2a
0x5001f9
0x800000
0x52e1fe
0x500000
...
0x5001f9
...
0x52e1fe
...
0x55720a
...
0x600000
pop rcx
ret
mov qword ptr [rcx], rax
ret
pop rax
ret
.text
Stack payload
ROP chain example
0x55720a
0x2a
0x5001f9
0x800000
0x52e1fe
0x500000
...
0x5001f9
...
0x52e1fe
...
0x55720a
...
0x600000
pop rcx
ret
mov qword ptr [rcx], rax
ret
pop rax
ret
.text
Stack payload
ROP chain example
0x55720a
0x2a
0x5001f9
0x800000
0x52e1fe
0x500000
...
0x5001f9
...
0x52e1fe
...
0x55720a
...
0x600000
pop rcx
ret
mov qword ptr [rcx], rax
ret
pop rax
ret
.text
Stack payload
ROP chain example
0x55720a
0x2a
0x5001f9
0x800000
0x52e1fe
0x500000
...
0x5001f9
...
0x52e1fe
...
0x55720a
...
0x600000
pop rcx
ret
mov qword ptr [rcx], rax
ret
pop rax
ret
.text
Stack payload
ROP chain example
0x55720a
0x2a
0x5001f9
0x800000
0x52e1fe
0x500000
...
0x5001f9
...
0x52e1fe
...
0x55720a
...
0x600000
pop rcx
ret
mov qword ptr [rcx], rax
ret
pop rax
ret
.text
Stack payload
ROP chain example
Debloating as defense
Soundness and may-use code
Definition
sound transformation: a program transformation that does not change the semantics of a program. Program transformations that induce crashes or cause incorrect output are unsound.
Definition
may-use code: code that may be used by the program under certain inputs or execution conditions.
Properties of debloating frameworks
| Piece-wise | Chisel | Razor | BlankIt |
Works on application | | ✔ | ✔ | |
Works on library | ✔ | | ✔ | ✔ |
Works on binary | | | ✔ | ✔ |
No user input needed | ✔ | | | ✔ |
No training needed | ✔ | | ✔ | |
Is sound | ✔ | | | ✔ |
Can debloat may-use code | | | | ✔ |
Properties of debloating frameworks
| Piece-wise | Chisel | Razor | BlankIt |
Works on application | | ✔ | ✔ | |
Works on library | ✔ | | ✔ | ✔ |
Works on binary | | | ✔ | ✔ |
No user input needed | ✔ | | | ✔ |
No training needed | ✔ | | ✔ | |
Is sound | ✔ | | | ✔ |
Can debloat may-use code | | | | ✔ |
Properties of debloating frameworks
| Piece-wise | Chisel | Razor | BlankIt |
Works on application | | ✔ | ✔ | |
Works on library | ✔ | | ✔ | ✔ |
Works on binary | | | ✔ | ✔ |
No user input needed | ✔ | | | ✔ |
No training needed | ✔ | | ✔ | |
Is sound | ✔ | | | ✔ |
Can debloat may-use code | | | | ✔ |
✗
Motivation
To the best of our knowledge, there is no general technique today that:
Outline
Decker overview
Threat model
Decker Example
Image source: Wikipedia (deck)
Decker Example
A deck
Image source: Wikipedia (deck)
Decker Example
main()
foo()
bar()
Decker Example
main()
...
if(x)
foo()
bar()
foo()
...
bar()
...
main()
foo()
bar()
Decker Example
main()
...
if(x)
foo()
bar()
foo()
...
bar()
...
main()
foo()
bar()
Program counter
Decker Example
main()
...
if(x)
foo()
bar()
foo()
...
bar()
...
main()
foo()
bar()
Decker Example
main()
...
if(x)
foo()
bar()
foo()
...
bar()
...
main()
foo()
bar()
Decker Example
main()
...
if(x)
foo()
bar()
foo()
...
bar()
...
main()
foo()
bar()
Decker Example
main()
...
if(x)
foo()
bar()
foo()
...
bar()
...
main()
foo()
bar()
Decker Example
main()
...
if(x)
foo()
bar()
foo()
...
bar()
...
main()
foo()
bar()
Decker Example
main()
...
if(x)
foo()
bar()
foo()
...
bar()
...
main()
foo()
bar()
Decker Example
main()
...
if(x)
foo()
bar()
foo()
...
bar()
...
main()
foo()
bar()
Decker Example
main()
...
if(x)
foo()
bar()
foo()
...
bar()
...
main()
foo()
bar()
Example (Unprotected Program)
main()
foo()
bar()
✔
Gadget chain components:
Gadget chain possible?
Example (Decker-Protected Program)
main()
foo()
bar()
❌
Gadget chain components:
Gadget chain possible?
✗
✗
✗
✗
Example (Decker-Protected Program)
main()
foo()
bar()
❌
Gadget chain components:
Gadget chain possible?
✗
✗
Example (Decker-Protected Program)
main()
foo()
bar()
❌
Gadget chain components:
Gadget chain possible?
✗
✗
Outline
Program structure and performance
Example
main()
A(func_ptr)
while {
B()
}
A(func_ptr)
B()
func_ptr()
B()
C()
main()
A()
B()
C()
Example
main()
A(func_ptr)
while {
B()
}
A(func_ptr)
B()
func_ptr()
B()
C()
main()
A()
B()
C()
Example
main()
A(func_ptr)
while {
B()
}
A(func_ptr)
B()
func_ptr()
B()
C()
main()
A()
B()
C()
Example
main()
A(func_ptr)
while {
B()
}
A(func_ptr)
B()
func_ptr()
B()
C()
main()
A()
B()
C()
Example
main()
A(func_ptr)
while {
B()
}
A(func_ptr)
B()
func_ptr()
B()
C()
main()
A()
B()
C()
Let’s discuss the 4 deck types!
1. Single deck - Occurs in a non-loop region
main()
A(func_ptr)
while {
B()
}
A(func_ptr)
B()
func_ptr()
B()
C()
main()
A()
B()
DECK-START
DECK-END
C()
map(RX, A)
2. Loop deck - Entrance to loops
main()
A(func_ptr)
while {
B()
}
A(func_ptr)
B()
func_ptr()
B()
C()
main()
A()
B()
DECK-START
DECK-END
C()
map(RX, B, C)
3. Reachable deck - Enter loop region via non-loop
main()
A(func_ptr)
while {
B()
}
A(func_ptr)
B()
func_ptr()
B()
C()
main()
A()
B()
DECK-START
DECK-END
C()
map(RX, B, C)
4. Indirect deck - Occurs at indirect calls
main()
A(func_ptr)
while {
B()
}
A(func_ptr)
B()
func_ptr()
B()
C()
main()
A()
B()
DECK-START
DECK-END
C()
map(RX, ?)
Indirect deck
Linker
Outline
Evaluation goals
Evaluation summary
Evaluation summary
Evaluation details
Conclusion
Thank you!