Following fail0verflow's PS4 Crashdumps / Kernel Dumping and PS4 Aux Hax Documentation alongside his recent PS4 Sflash0 Pack Tool, PlayStation 4 developer @SocraticBliss made available a PS4 Crash Dump Decryptor Python Script for scene devs on Twitter today.
Download: ps4_crash_dump_decryptor.py / ps4_mono_to_il.py (PS4 MONO binaries to IL MONO binaries - updated script to work with the PS4's .dll.sprx and .exe.sprx files to turn them into .dll and .exe to be inspected with something like dnSpy)
From the Tweets below, here's what he had to say on it: "Still tweaking this somewhat, but decided to take a swing at fail0verflow's PS4 Crash Dump Decryptor script (since at this point its fairly outdated), enjoy!
Thanks goes out to notzecoxao, CelesteBlue123, and most of all fail0verflow! "
ps4_crash_dump_decryptor.py
Crash Dump KeySeed
Sealed Key Values
Keyset 1
AES-CBC-128
Key = B5DAEFFF39E6D90ECA7DC5B029A8153E
SHA-256-HMAC
Hash = 8707960A53468D6C843B3DC9624E22AF
Keyset 2
AES-CBC-128
Key = EC0D347E2A7657471F1FC33E9E916FD4
SHA-256-HMAC
Hash = A6D6583D3217E87D9BE9BCFC4436BE4F
Keyset 3
AES-CBC-128
Key = 51D8BFB4E387FB4120F081FE33E4BE9A
SHA-256-HMAC
Hash = FFF9BDEA803B14824C61850EBB084EE9
Keyset 4
AES-CBC-128
Key = 346B5D231332AC428A44A708B1138F6D
SHA-256-HMAC
Hash = 5DC6B8D1A3A0741852A7D44268714824
Dumped with getSealedKeySecret on 5.05
Download: ps4_crash_dump_decryptor.py / ps4_mono_to_il.py (PS4 MONO binaries to IL MONO binaries - updated script to work with the PS4's .dll.sprx and .exe.sprx files to turn them into .dll and .exe to be inspected with something like dnSpy)
From the Tweets below, here's what he had to say on it: "Still tweaking this somewhat, but decided to take a swing at fail0verflow's PS4 Crash Dump Decryptor script (since at this point its fairly outdated), enjoy!
Thanks goes out to notzecoxao, CelesteBlue123, and most of all fail0verflow! "
ps4_crash_dump_decryptor.py
Code:
#!/usr/bin/env python
'''
Crash Dump Decryptor by SocraticBliss (R)
Thanks to...
# Team FailOverflow
# CelesteBlue
# zecoxao
1) Replace AES KEY # with the actual key
2) Replace HMAC KEY # with the actual key
3) Have orbiscore-systemcrash.orbisstate in the same directory
4) python ps4_crash_dump_decryptor.py
'''
from binascii import unhexlify as uhx, hexlify as hx
from Crypto.Cipher import AES
from Crypto.Hash import HMAC, SHA256
import struct
import sys
class Header:
def __init__(self, f):
__slots__ = ('VERSION', 'OPEN_PSID', 'PADDING_1', 'PADDING_2',
'UNKNOWN', 'STATE', 'DATA_LEN', 'PADDING_3', 'DATA_HMAC')
# Secure Header
self.VERSION = struct.unpack('<I', f.read(4))[0]
self.PSID_ENC = struct.unpack('<16s', f.read(16))[0]
self.PADDING_1 = struct.unpack('<I13Q', f.read(108))[0]
# Padding
self.PADDING_2 = struct.unpack('<4Q', f.read(32))[0]
# Final Header
self.UNKNOWN = struct.unpack('<2Q', f.read(16))[0]
self.STATE = struct.unpack('<Q', f.read(8))[0]
self.DATA_LEN = struct.unpack('<Q', f.read(8))[0]
self.PADDING_3 = struct.unpack('<2Q', f.read(16))[0]
self.DATA_HMAC = struct.unpack('<4Q', f.read(32))[0]
KEYS = [
['',''],
['AES KEY 1','HMAC KEY 1'], # 1.01
['AES KEY 2','HMAC KEY 2'], # 3.55
['AES KEY 3','HMAC KEY 3'], # 4.05
['AES KEY 4','HMAC KEY 4'], # 4.07
]
def aes_ecb_encrypt(key, data):
return AES.new(uhx(key), AES.MODE_ECB).encrypt(data)
def aes_ecb_decrypt(key, data):
return AES.new(uhx(key), AES.MODE_ECB).decrypt(data)
def hmac_sha256(key, data):
return HMAC.new(uhx(key), msg = data, digestmod = SHA256).digest()
# PROGRAM START
def main (argc, argv):
# 1) Read the Header
with open('orbiscore-systemcrash.orbisstate', 'rb') as f:
ps = Header(f)
KD = KEYS[ps.VERSION][0]
KC = KEYS[ps.VERSION][1]
print('\nEncrypted PSID: %s' % hx(ps.PSID_ENC).upper())
PSID_DEC = aes_ecb_decrypt(KD, ps.PSID_ENC)
print('\nPSID: %s' % hx(PSID_DEC).upper())
# HMAC DIGEST
DIGEST = hmac_sha256(KC, ps.PSID_ENC)
print('HASH: %s' % hx(DIGEST).upper())
KD = DIGEST[0x10:]
KC = DIGEST[:0x10]
print('\nAES : %s' % hx(KC).upper())
print('HMAC: %s' % hx(KD).upper())
# 2) Dump Starts Here
f.seek(0x4000)
DATA_ENC = f.read()
# 3) Utilize the proper key set to decrypt the data
IV = '0000000000000000'
DATA = AES.new(KD, AES.MODE_CBC, IV).decrypt(DATA_ENC)
# 4) Save the decrypted data
with open('debug.bin', 'wb') as f:
f.write(DATA)
print('\nSaved to debug.bin')
if __name__=='__main__':
sys.exit(main(len(sys.argv), sys.argv))
Code:
kd, kc
KEYS = [
['',''],
[b'8F86DDEDCBF24A44EB6C30607AA26F76', b'4125715AAB8B78E569F512E65CA62DD3'], # 1.01-3.15
[b'63AEF79DC49969FD8997B2F60DB65F81', b'1800A5DE2D0F0652FA5602FFADD440AA'], # 3.50-3.70
[b'05205507B7A154E08A7A38B1897563FB', b'AD334D142EAF8B9438DB00D1D0BFF357'], # 4.00-4.05
[b'04C1A0961BBB0CB2140361B0956AAABA', b'052D2FF3014FB38CAAF6898CB899982A'], # 4.06-4.07 (to test)
]
Keyset 1
AES-CBC-128
Key = B5DAEFFF39E6D90ECA7DC5B029A8153E
SHA-256-HMAC
Hash = 8707960A53468D6C843B3DC9624E22AF
Keyset 2
AES-CBC-128
Key = EC0D347E2A7657471F1FC33E9E916FD4
SHA-256-HMAC
Hash = A6D6583D3217E87D9BE9BCFC4436BE4F
Keyset 3
AES-CBC-128
Key = 51D8BFB4E387FB4120F081FE33E4BE9A
SHA-256-HMAC
Hash = FFF9BDEA803B14824C61850EBB084EE9
Keyset 4
AES-CBC-128
Key = 346B5D231332AC428A44A708B1138F6D
SHA-256-HMAC
Hash = 5DC6B8D1A3A0741852A7D44268714824
Dumped with getSealedKeySecret on 5.05