Kirk: Difference between revisions
No edit summary |
(→Table) |
||
Line 103: | Line 103: | ||
! scope="col"| Input size | ! scope="col"| Input size | ||
! scope="col"| Output size | ! scope="col"| Output size | ||
! scope="col"| Used in | ! scope="col"| Used in | ||
|- | |- | ||
Line 117: | Line 116: | ||
| KIRK_CMD_2 | | KIRK_CMD_2 | ||
| Encrypt Operation (inverse of cmd 3) | | Encrypt Operation (inverse of cmd 3) | ||
| | | | ||
| | | | ||
Line 125: | Line 123: | ||
| KIRK_CMD_3 | | KIRK_CMD_3 | ||
| Decrypt Operation (inverse of cmd 2) | | Decrypt Operation (inverse of cmd 2) | ||
| | | | ||
| | | | ||
Line 135: | Line 132: | ||
| buf_size+0x14 | | buf_size+0x14 | ||
| buf_size+0x14 | | buf_size+0x14 | ||
| chnnlsv, memab | | chnnlsv, memab | ||
|- | |- | ||
Line 143: | Line 139: | ||
| buf_size+0x14 | | buf_size+0x14 | ||
| buf_size+0x14 | | buf_size+0x14 | ||
| chnnlsv, psheet since PSP FW 2.81 for PGD, ?openpsid for IDS Certificates? | | chnnlsv, psheet since PSP FW 2.81 for PGD, ?openpsid for IDS Certificates? | ||
|- | |- | ||
Line 149: | Line 144: | ||
| KIRK_CMD_ENCRYPT_IV_USER | | KIRK_CMD_ENCRYPT_IV_USER | ||
| Encrypt Operation (inverse of cmd 9) (IV=UserDefined) | | Encrypt Operation (inverse of cmd 9) (IV=UserDefined) | ||
| | | | ||
| | | | ||
Line 159: | Line 153: | ||
| buf_size+0x14 | | buf_size+0x14 | ||
| buf_size+0x14 | | buf_size+0x14 | ||
| memlmd, mesg_led,chnnlsv, memab | | memlmd, mesg_led,chnnlsv, memab | ||
|- | |- | ||
Line 167: | Line 160: | ||
| buf_size+0x14 | | buf_size+0x14 | ||
| buf_size+0x14 | | buf_size+0x14 | ||
| chnnlsv, psheet since PSP FW 2.81 for PGD | | chnnlsv, psheet since PSP FW 2.81 for PGD | ||
|- | |- | ||
Line 173: | Line 165: | ||
| KIRK_CMD_DECRYPT_IV_USER | | KIRK_CMD_DECRYPT_IV_USER | ||
| Decrypt Operation (inverse of cmd 6) (IV=UserDefined) | | Decrypt Operation (inverse of cmd 6) (IV=UserDefined) | ||
| | | | ||
| | | | ||
Line 181: | Line 172: | ||
| KIRK_CMD_PRIV_SIGVRY | | KIRK_CMD_PRIV_SIGVRY | ||
| Private Signature Verify (checks for private SCE sig) | | Private Signature Verify (checks for private SCE sig) | ||
| | | | ||
| | | | ||
Line 191: | Line 181: | ||
| buf_size >= 0x14 | | buf_size >= 0x14 | ||
| ?0x14? | | ?0x14? | ||
| memlmd, mesg_led, memab | | memlmd, mesg_led, memab | ||
|- | |- | ||
Line 199: | Line 188: | ||
| 0 | | 0 | ||
| 0x3C | | 0x3C | ||
| memab | | memab | ||
|- | |- | ||
Line 207: | Line 195: | ||
| 0x3C | | 0x3C | ||
| 0x3C | | 0x3C | ||
| | | | ||
|- | |- | ||
Line 215: | Line 202: | ||
| 0 | | 0 | ||
| 0x14 | | 0x14 | ||
| mesg_led, chnnlsv, memab, semawm | | mesg_led, chnnlsv, memab, semawm | ||
|- | |- | ||
Line 221: | Line 207: | ||
| KIRK_CMD_15 | | KIRK_CMD_15 | ||
| (absolutely no idea – could be KIRK initialization) | | (absolutely no idea – could be KIRK initialization) | ||
| | | | ||
| | | | ||
Line 231: | Line 216: | ||
| 0x34 | | 0x34 | ||
| 0x28 | | 0x28 | ||
| memab | | memab | ||
|- | |- | ||
Line 239: | Line 223: | ||
| 0x64 | | 0x64 | ||
| 0 | | 0 | ||
| memab | | memab | ||
|- | |- | ||
Line 247: | Line 230: | ||
| 0xB8 | | 0xB8 | ||
| 0 | | 0 | ||
| openpsid, memab | | openpsid, memab | ||
|} | |} |
Revision as of 12:47, 4 February 2023
The PSP KIRK Crypto Engine is a security hardware device that is embedded into the TACHYON main IC chip. It is a bus master and can DMA to/from main DDR RAM memory, operating independantly of the CPU. It is intefaced via memory mapped registers at base of 0xBDE00000 (SPOCK Crypto Engine on the other hand is mapped to 0xBDF00000). It is capable of performing AES encryption, decryption, SHA1 Hash, pseudo random number generation, and signature generation and verifications (ECDSA) and CMAC.
Invocation
All of the Kirk commands can be used using the function sceUtilsBufferCopyWithRange, which takes five arguments:
- the output buffer
- the output buffer size
- the input buffer (if there is one, NULL otherwise)
- the input buffer size (if there is one, 0 otherwise)
- the index of the command (as detailed below).
Elliptic curves
The PSP uses ECDSA for public-key cryptography. Elliptic curves are known for being fast and only requiring small keys, contrary to other public-key cryptography algorithms. They are still considered to be very secure, even for the 160-bit curves used by the PSP, unless a mistake is made when using them.
These curves have been designed by Sony only for the console. They are not vulnerable to any known attack.
Both use the usual Weierstrass form.
Elliptic curve for CMD1
This curve is used for the ECDSA verification of CMD1.
p = 0xFFFFFFFFFFFFFFFF0001B5C617F290EAE1DBAD8F G = (0x2259ACEE15489CB096A882F0AE1CF9FD8EE5F8FA, 0x604358456D0A1CB2908DE90F27D75C82BEC108C0) n = 0xFFFFFFFFFFFFFFFF00000001FFFFFFFFFFFFFFFF a = -3 b = 0x65D1488C0359E234ADC95BD3908014BD91A525F9
The public key is hardcoded, and is equal to: (0xED9CE58234E61A53C685D64D51D0236BC3B5D4B9, 0x049DF1A075C0E04FB344858B61B79B69A63D2C39).
Elliptic curve for the other commands
This curved is used for Kirk commands 0xC, 0xD, 0x10, 0x11, and likely 0x12.
p = 0xFFFFFFFFFFFFFFFEFFFFB5AE3C523E63944F2127 G = (0x128EC4256487FD8FDF64E2437BC0A1F6D5AFDE2C, 0x5958557EB1DB001260425524DBC379D5AC5F4ADF) n = 0xFFFFFFFFFFFFFFFF00000001FFFFFFFFFFFFFFFF a = -3 b = 0xA68BEDC33418029C1D3CE33B9A321FCCBB9E0F0B
The public key is variable. For the latest Pre-IPL version which add an additional ECDSA verification of the XOR of the block hashes, the public key is (0xBC660611A70BD7F2D140A48215C096D11D2D4112, 0xF0E9379AC4E0D387C542D091349DD15169DD5A87).
Code sample
Below is an example of how to manipulate these curves using the ecpy python library.
import ecpy.curves psp_curve_cmd1 = { 'name': "psp_curve_cmd1", 'type': "weierstrass", 'size': 160, 'field': 0xFFFFFFFFFFFFFFFF00000001FFFFFFFFFFFFFFFF, 'generator': (0x2259ACEE15489CB096A882F0AE1CF9FD8EE5F8FA, 0x604358456D0A1CB2908DE90F27D75C82BEC108C0), 'order': 0xFFFFFFFFFFFFFFFF0001B5C617F290EAE1DBAD8F, 'cofactor': 1, 'a': -3, 'b': 0x65D1488C0359E234ADC95BD3908014BD91A525F9, } psp_curve_cmd17 = { 'name': "psp_curve_cmd17", 'type': "weierstrass", 'size': 160, 'field': 0xFFFFFFFFFFFFFFFF00000001FFFFFFFFFFFFFFFF, 'generator': (0x128EC4256487FD8FDF64E2437BC0A1F6D5AFDE2C, 0x5958557EB1DB001260425524DBC379D5AC5F4ADF), 'order': 0xFFFFFFFFFFFFFFFEFFFFB5AE3C523E63944F2127, 'cofactor': 1, 'a': -3, 'b': 0xA68BEDC33418029C1D3CE33B9A321FCCBB9E0F0B, } crv1 = ecpy.curves.WeierstrassCurve(psp_curve_cmd1) crv17 = ecpy.curves.WeierstrassCurve(psp_curve_cmd17) pt1 = ecpy.curves.Point(0xED9CE58234E61A53C685D64D51D0236BC3B5D4B9, 0x049DF1A075C0E04FB344858B61B79B69A63D2C39, crv1) pt17 = ecpy.curves.Point(0xbc660611a70bd7f2d140a48215c096d11d2d4112, 0xf0e9379ac4e0d387c542d091349dd15169dd5a87, crv17) # verify the KIRK1 ECDSA private key crv1_g = ecpy.curves.Point(0x2259ACEE15489CB096A882F0AE1CF9FD8EE5F8FA, 0x604358456D0A1CB2908DE90F27D75C82BEC108C0, crv1) assert(crv1.mul_point(crv1.generator, 0xF392E26490B80FD889F2D9722C1F34D7274F983D) == pt1)
Commands
On PSP there are 18 KIRK commands. On PSVita, there are these 18 commands plus some new commands to support bigger keys (192 bits for example). See F00D commands.
KIRK functions are called with the same 5 arguments (outbuf, outbuf_size, inbuf, inbuf_size, service_number (which is the command ID)). Depending on the service number used, the expectations of the inbuf or outbuf vary and are detailed below.
Table
Command ID | Name | Short description | Input size | Output size | Used in | |
---|---|---|---|---|---|---|
1 | KIRK_CMD_DECRYPT_PRIVATE | Super-Duper decryption (no inverse) | buf_size+0x40 | buf_size | memlmd, mesg_led | |
2 | KIRK_CMD_2 | Encrypt Operation (inverse of cmd 3) | ||||
3 | KIRK_CMD_3 | Decrypt Operation (inverse of cmd 2) | ||||
4 | KIRK_CMD_ENCRYPT_IV_0 | Encrypt Operation (inverse of cmd 7) (IV=0) | buf_size+0x14 | buf_size+0x14 | chnnlsv, memab | |
5 | KIRK_CMD_ENCRYPT_IV_FUSE | Encrypt Operation (inverse of cmd 8) (IV=FuseID) | buf_size+0x14 | buf_size+0x14 | chnnlsv, psheet since PSP FW 2.81 for PGD, ?openpsid for IDS Certificates? | |
6 | KIRK_CMD_ENCRYPT_IV_USER | Encrypt Operation (inverse of cmd 9) (IV=UserDefined) | ||||
7 | KIRK_CMD_DECRYPT_IV_0 | Decrypt Operation (inverse of cmd 4) (IV=0) | buf_size+0x14 | buf_size+0x14 | memlmd, mesg_led,chnnlsv, memab | |
8 | KIRK_CMD_DECRYPT_IV_FUSE | Decrypt Operation (inverse of cmd 5) (IV=FuseID) | buf_size+0x14 | buf_size+0x14 | chnnlsv, psheet since PSP FW 2.81 for PGD | |
9 | KIRK_CMD_DECRYPT_IV_USER | Decrypt Operation (inverse of cmd 6) (IV=UserDefined) | ||||
10 (0xA) | KIRK_CMD_PRIV_SIGVRY | Private Signature Verify (checks for private SCE sig) | ||||
11 (0xB) | KIRK_CMD_HASH | SHA1 Hash | buf_size >= 0x14 | ?0x14? | memlmd, mesg_led, memab | |
12 (0xC) | KIRK_CMD_MUL1 | ECDSA Generate Keys | 0 | 0x3C | memab | |
13 (0xD) | KIRK_CMD_MUL2 | ECDSA Multiply Point | 0x3C | 0x3C | ||
14 (0xE) | KIRK_CMD_PRNGEN | Pseudo Random Number Generation | 0 | 0x14 | mesg_led, chnnlsv, memab, semawm | |
15 (0xF) | KIRK_CMD_15 | (absolutely no idea – could be KIRK initialization) | IPL | |||
16 (0x10) | KIRK_CMD_SIGGEN | ECDSA Signature Generation | 0x34 | 0x28 | memab | |
17 (0x11) | KIRK_CMD_SIGVRY | Signature Verification (checks for generated signatures) | 0x64 | 0 | memab | |
18 (0x12) | KIRK_CMD_CERTVRY | Certificate Verification (IDStorage Certificates CMAC) | 0xB8 | 0 | openpsid, memab |
Command 1: decryption and authentication
Overview
This function is used to both decrypt and verify the signature of the IPL blocks.
There are two versions of this service: AES CMAC Verification, and ECDSA Verification. They use the header section of the input buffer slightly differently.
In both cases, the total header length is 0x90. The first 0x60 bytes depend on the version. The last 0x30 bytes are the same in both cases:
Metadata Header Structure (Length 0x30):
Address | Size | Description |
---|---|---|
0x60 | 4 | Set to 1 |
0x64 | 4 | 0 indicates AES CMAC version, 1 indicates ECDSA version |
0x68 | 4 | 0 |
0x6C | 4 | 0 for retail version and 0xFFFFFFFF for dev versions |
0x70 | 4 | Length of decrypted data |
0x74 | 4 | Length of the padding after the header and before the real data |
0x78 | 8 | 0 |
AES CMAC Version
Key Header Structure (Length 0x60):
Address | Size | Description |
---|---|---|
0x00 | 16 | Decryption key, encrypted with the KIRK1 AES master key |
0x10 | 16 | CMAC key, encrypted with the KIRK1 AES master key |
0x20 | 16 | Header hash (CMAC) |
0x30 | 16 | Data hash (CMAC) |
0x40 | 32 | 0 |
Decryption process
The first 0x20 bytes of the Key Header are decrypted with the KIRK 1 Stored AES Key. This was allegedly discovered by Datel by decapping the chip and reversing engineering the algorithms and keys. This was also recovered through the failure in PS3 cryptography by decrypting the isolated module in the PSP emulator on the PS3.
The first block is the AES Key used for decrypting the main data. The second block is used to decrypt the next two blocks (0x20 bytes at offset 0x20). These represent the Metadata Header CMAC and the Data CMAC. They are checked against the AES CMAC of the header section and the AES CMAC of the data section.
ECDSA Version
Key Header Structure (Length 0x60):
Address | Size | Description |
---|---|---|
0x00 | 16 | Decryption key, encrypted with the KIRK1 AES master key |
0x10 | 16 | Header ECDSA signature r |
0x24 | 16 | Header ECDSA signature s |
0x38 | 16 | Data ECDSA signature r |
0x4C | 16 | Data ECDSA signature s |
Decryption process
The ECDSA version is slightly different. Only the first block (0x10 bytes) is decrypted with the Kirk 1 AES Key. It is used to decrypt the main data section just as in the AES CMAC version. Rather than a CMAC, the Metadata header is checked by SHA1 hashing its 0x30 bytes and checking the signature components through a ECDSA Verify call. The encrypted Data section is also checked via SHA1 of the entire data through a ECDSA Verify call.
The ECDSA curve parameters are indicated above.
Command 2 & 3: DRM encrypt & decrypt
These commands are mostly unknown. In command 2, the input data passed to KIRK is first checked (presumably CMAC), then decrypted, and re-encrypted with the console unique private key. Having that common key would allow legit creation of DRM BB install packages.
Command 3 is the decryption counterpart of command 2.
Commands 4 & 7: AES encrypt & decrypt, IV=0
These commands are used for encryption & decryption using a set of keys, all of which are available on the Keys page.
In both cases, data is prefixed with a 0x14-byte long header:
Address | Size | Description |
---|---|---|
0x00 | 4 | Mode: must be 4 for encryption, 5 for decryption |
0x04 | 8 | Unknown (maybe used for commands 5/6/8/9?) |
0x0C | 4 | Keyseed: index of the key to use, between 0x00 and 0x7F included |
0x10 | 4 | Size of the following data |
A simple AES128-CBC encryption/decryption with an IV equal to 0 is applied on the rest of the data.
Commands 5 & 6 & 8 & 9: AES encrypt & decrypt, IV!=0
These commands are supposed to be similar to commands 4 & 7, but with different IVs. They might use the same header. The keys might also be different. Commands 5/8 use a key based off the fuseID making all operations unique per PSP, while commands 6/9 use a user-defined 128-bit key.
This needs testing!
Command 10
Command 11
Command 12: ECDSA key pair generation
This command generates a random private key and computes the associated public key. See above for the parameters of the elliptic curve.
This returns the following into the keypair buffer, of size 0x3C (each value is 0x14 bytes long):
- 0x00 - randomly generated private key
- 0x14 - Public Key point x value
- 0x28 - Public Key point y value
Command 13: point multiplication
This command multiplies an elliptic curve point by a scalar. See above for the parameters of the elliptic curve.
Input (size 0x3c):
- 0x00 - scalar k
- 0x14 - point x value P.x
- 0x28 - point y value P.y
Output (size 0x28):
- 0x00 - point x value (kP).x
- 0x14 - point y value (kP).y
The result is a new point(x and y are each 0x14 bytes long).