-
Notifications
You must be signed in to change notification settings - Fork 2
/
decrypt.sh
executable file
·306 lines (274 loc) · 8.52 KB
/
decrypt.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
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
#!/bin/bash
WDIR=`pwd`
KEYCHAIN_FILE="${WDIR}/FileVaultMaster.keychain"
PASS_FILE="${WDIR}/pass.txt"
INFODIR="${WDIR}/diskutil_outputs"
if [ -d "$INFODIR" ]; then
LOGDIR="${INFODIR}/`sw_vers -productVersion`"
mkdir -p "${LOGDIR}"
sw_vers | awk -v T="`date +%F" "%T" "%Z`" '{print T":"$0}' >> "${LOGDIR}/sw_vers.txt"
gatherlog=YES
fi
message(){
TYPE=$1
shift
echo "`date +%F" "%T" "%Z` [$TYPE] $@" >&2
}
unlock_KeyChain(){
KC="$1"
PASS="$2"
if [ ! -f "$KC" ]; then message ERROR "Not found $KC" ; exit 1 ; fi
if [ ! -f "$PASS" ]; then message ERROR "Not found $PASS" ; exit 1 ; fi
KCPASS=`head -1 "$PASS" | tr -d '\n\r'`
security unlock-keychain -p "$KCPASS" "$KC"
if [ $? -eq 0 ]; then
message INFO $KC unlocked.
else
message ERROR Failed to unlock ${KC}.
exit 1
fi
}
isEncryptCS(){
encryptionType=`diskutil cs list | grep "Encryption Type" | awk '{print $3}'`
if [ ${encryptionType:-unknown} = None ]; then
message INFO This Mac has a coreStorage logical volume.
message INFO But the coreStorage logical volume is not encrypted.
message INFO Please check it.
diskutil cs list
exit 0
fi
convertStatus=`diskutil cs list | grep "Conversion Status" | awk '{print $3}'`
if [ ${convertStatus:=Null} != Complete ]; then
conversionDirection=`diskutil cs list| grep "Conversion Direction" | awk '{print $3}'`
diskutil cs list
message INFO File Vault conversion is now working.
message INFO You DO NOT touch this volume until conversion finished.
message INFO Conversion Status: $convertStatus
message INFO Conversion Direction: ${conversionDirection:-unknown}
exit 1
fi
}
isEncryptAPFS(){
miner_ver=`sw_vers -productVersion| awk -F. '{print $3}'`
if [ ${miner_ver:-0} -le 1 ]; then
# from 10.13 to 10.13.1
flag="Encrypted:"
else
# 10.13.2 or later
flag="FileVault:"
fi
encryptionStatus=`diskutil ap list | awk -v F=$flag '$2 == F {print $3}' | grep -c "Yes"`
if [ ${encryptionStatus:-0} -ne 1 ]; then
message INFO This Mac has an AppleFileSystem volume.
message INFO But the AppleFileSystem volume is not encrypted.
message INFO Or multipule encrypted volumes.
message INFO Please check it.
diskutil ap list
exit 0
fi
echo `diskutil ap list | awk '$NF == "role)" {print $6}'`
}
unlockCS(){
FILE="$1"
CSUUID=`diskutil cs list | grep Logical | tail -1 | awk '{print $NF}'`
encryptionStatus=`diskutil cs list | grep "Encryption Status" | awk '{print $3}'`
if [ ${encryptionStatus:-Unlocked} = Locked ]; then
diskutil cs unlockVolume "$CSUUID" -recoveryKeychain "$FILE"
if [ $? -eq 0 ]; then
message INFO OK I unlock it.
else
diskuti cs list
message ERROR Failed to unlock volume with ${FILE}.
exit 1
fi
else
FVdisk=`diskutil cs list | grep Disk | grep -v disk0s2 | awk '{print $2}'`
message INFO Volume \(${FVdisk}\) is already unlocked.
fi
isRevertible=`diskutil cs list | awk '$1 == "Revertible:" {print $2}'`
if [ ${isRevertible:-No} = Yes ]; then
message INFO This storage can be revertible.
else
diskutil cs list
message ERROR I could not revert encypted volume due to limitation of recovery system.
message ERROR But you can copy itmes from unlocked volume to another storage.
exit 1
fi
if [ ${gatherlog:-NO} = YES ]; then
diskutil cs list > ${LOGDIR}/filevault_unlocked_`date +%F"-"%T"-"%Z`.txt
fi
}
watchConversion(){
sleep 10
if [ ${gatherlog:-NO} = YES ]; then
diskutil cs list > ${LOGDIR}/filevault_convertion_inprogress_`date +%F"-"%T"-"%Z`.txt
fi
while true
do
PROGRESS=`diskutil cs list | grep "Conversion Progress:" | awk '{print $3}'`
if [ ${PROGRESS:-X} = X ]; then
diskutil cs list
message ERROR Something wong. Abort.
exit 1
fi
echo "Conversion: $PROGRESS done."
if [ $PROGRESS = "100%" ]; then
if [ ${gatherlog:-NO} = YES ]; then
diskutil cs list > ${LOGDIR}/filevault_convertion_done_`date +%F"-"%T"-"%Z`.txt
fi
sleep 10
break
fi
done
}
askreboot(){
message INFO OK. You can reboot now.
message INFO Do you want to reboot now? [y/n]
while true
do
read ANS
R=`echo $ANS | tr [:upper:] [:lower:]`
case ${R:-n} in
y | yes )
macOSversion=`sw_vers -productVersion| awk -F. '{print $2}'`
if [ $macOSversion -lt 11 ]; then
/usr/sbin/systemsetup -setstartupdisk \
"`/usr/sbin/systemsetup -liststartupdisks | tail -1`"
fi
sync; sync; sync; /sbin/reboot
;;
n | no )
exit 0
;;
* )
message INFO Do you want to reboot now? [y/n]
;;
esac
done
}
decryptCS(){
FILE="$1"
CSUUID=`diskutil cs list | grep Logical | tail -1 | awk '{print $NF}'`
macOSversion=`sw_vers -productVersion| awk -F. '{print $2}'`
RevertibleDescription="`diskutil cs list | awk '$1 == "Revertible:" {print $0}'| tr '()' ':' | awk -F: '{print $(NF -1)}'`"
# "unlock and decryption required"
#
diskutil cs revert "$CSUUID" -recoveryKeychain "$FILE"
if [ $? -eq 0 ]; then
message INFO Start to revert.
else
diskutil cs list
message ERROR Failed to revert storage.
exit 1
fi
if [ ${gatherlog:-NO} = YES ]; then
diskutil cs list > ${LOGDIR}/filevault_reverted_1st_`date +%F"-"%T"-"%Z`.txt
fi
case $macOSversion in
9)
watchConversion
diskutil cs revert "$CSUUID" -recoveryKeychain "$FILE"
if [ $? -eq 0 ]; then
message INFO Complete reverted.
else
diskutil cs list
message ERROR Failed to revert storage.
exit 1
fi
if [ ${gatherlog:-NO} = YES ]; then
diskutil cs list > ${LOGDIR}/filevault_reverted_2nd_`date +%F"-"%T"-"%Z`.txt
fi
askreboot
;;
*)
: `sw_vers -productVersion`
askreboot
;;
esac
}
unlockAPFS(){
devfile=$1
FILE="$2"
diskutil ap unlockvolume $devfile -recoverykeychain "$FILE"
if [ $? -ne 0 ]; then
message ERROR "diskutil ap unlockvolume $devfile -recoverykeychain $FILE got error."
exit 1
fi
}
decryptAPFS(){
devfile=$1
diskutil ap decryptVolume $devfile -user xxxx
}
################################
# M A I N
################################
# Check Kind of FileSystem
diskutil cs list > /dev/null 2>&1
if [ $? -eq 0 ]; then
if [ "`diskutil cs list | awk 'NR == 1 {print $1}'`" = "No" ]; then
isCoreStorage=NO
else
isCoreStorage=YES
message INFO Found CoreStorage.
fi
else
isCoreStorage=NO
fi
diskutil ap list > /dev/null 2>&1
if [ $? -eq 0 ]; then
if [ "`diskutil ap list | awk 'NR == 1 {print $1}'`" = "No" ]; then
isAppleFileSystem=NO
else
isAppleFileSystem=YES
message INFO Found AppleFileSystem.
fi
else
isAppleFileSystem=NO
fi
if [ "${isCoreStorage}${isAppleFileSystem}" = "NONO" ];then
message INFO Unexpected File System type.
message INFO Maybe no need decript.
diskutil list
exit 1
fi
if [ "${isCoreStorage}${isAppleFileSystem}" = "YESYES" ];then
message WARN There are both APFS and CoreStorage Volume.
message WARN Unmount volumes which is not startup disk.
exit 1
fi
# Unlock and decrypt
if [ $isCoreStorage = YES ]; then
isEncryptCS
unlock_KeyChain "$KEYCHAIN_FILE" "$PASS_FILE"
unlockCS "$KEYCHAIN_FILE"
decryptCS "$KEYCHAIN_FILE"
fi
if [ $isAppleFileSystem = YES ]; then
OS_VERS=`sw_vers -productVersion`
case $OS_VERS in
'10.13' )
: Not work.
message ERROR "This version of macOS, $OS_VERS, could not decrypt with Insutitute master key."
message INFO "Version 10.13.1 or later of macOS is required."
exit 1
;;
*)
: OK.
;;
esac
target=`isEncryptAPFS`
unlock_KeyChain "$KEYCHAIN_FILE" "$PASS_FILE"
unlockAPFS $target "$KEYCHAIN_FILE"
#decryptAPFS $target
fi
exit 0
# for Emacsen
# Local Variables:
# mode: sh
# sh-dasic-offset: 4
# sh-indentation: 4
# tab-width: 4
# indent-tabs-mode: nil
# coding: utf-8
# End:
# vi: set ts=4 sw=4 sts=4 et ft=sh fenc=utf-8 ff=unix :