See the assignment's PDF available on BrightSpace for task descriptions and submission requirements.
Level 3
1. The vulnerability in this program is that the C file runs a command using system("python3 /levels/level3/script.py"); and It runs this with elevated privileges, namely the privileges of the file. Now the problem here is that the command uses our PATH variable from our environment vars, to fetch the aliases for the binaries. So it doesn't specify the filepath of the binary python3 . it only uses the alias Python3 and the way that it fetches the alias is using the PATH variable of of the user who is running the terminal session in which the C file is run. But the system function inside the C program uses the permissions of the file itself. because it's our environment variable we can override python3 to point to some other program.
2. We can do this by change the path variable with export. In the home dir, i write a simple bash script that runs 'escalate'. I simply call this is called python3 and then I make sure it overwrites python3 by simply putting the location of this binary that we defined ourselves before the actual Python3. We can also change the .profile, or make an alias, what matters is: python3 should point to the script, not to python binary.
students177@appsec2026:/levels/level9$ cat /levels/level3/script.py
#!/usr/bin/env python3
import sys
global input_str
global input_offset
def is_whitespace(val):
return val == ' ' or val == '\t'
def is_number(val):
return val >= '0' and val <= '9'
def next_token():
global input_offset
global input_str
while input_offset < len(input_str):
if not is_whitespace(input_str[input_offset]):
input_offset += 1
return input_str[input_offset-1]
input_offset += 1
return ''
def unread_token():
global input_offset
global input_str
while input_offset > 0:
input_offset -= 1
if not is_whitespace(input_str[input_offset]):
break
def calc_number():
result = 0
lookahead = next_token()
while is_number(lookahead):
result *= 10
result += int(lookahead)
lookahead = next_token()
unread_token()
return result
def calc_mul():
result = calc_number()
lookahead = next_token()
while lookahead == '*' or lookahead == '/':
if lookahead == '*':
result *= calc_number()
else:
result /= calc_number()
lookahead = next_token()
unread_token()
return result
def calc_add():
result = calc_mul()
lookahead = next_token()
while lookahead == '+' or lookahead == '-':
if lookahead == '+':
result += calc_mul()
else:
result -= calc_mul()
lookahead = next_token()
unread_token()
return result
def calc():
global input_offset
input_offset = 0
return calc_add()
print('HOLY PYTHON CALCULATOR v42.B')
print('Enter calculation')
for line in sys.stdin:
try:
input_str = line.strip()
print(calc())
except:
print('ERR')
