key_manager.cpp 48 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323
  1. // SPDX-FileCopyrightText: Copyright 2018 yuzu Emulator Project
  2. // SPDX-License-Identifier: GPL-2.0-or-later
  3. #include <algorithm>
  4. #include <array>
  5. #include <bitset>
  6. #include <cctype>
  7. #include <fstream>
  8. #include <locale>
  9. #include <map>
  10. #include <sstream>
  11. #include <tuple>
  12. #include <vector>
  13. #include <mbedtls/bignum.h>
  14. #include <mbedtls/cipher.h>
  15. #include <mbedtls/cmac.h>
  16. #include <mbedtls/sha256.h>
  17. #include "common/fs/file.h"
  18. #include "common/fs/fs.h"
  19. #include "common/fs/path_util.h"
  20. #include "common/hex_util.h"
  21. #include "common/logging/log.h"
  22. #include "common/settings.h"
  23. #include "common/string_util.h"
  24. #include "core/crypto/aes_util.h"
  25. #include "core/crypto/key_manager.h"
  26. #include "core/crypto/partition_data_manager.h"
  27. #include "core/file_sys/content_archive.h"
  28. #include "core/file_sys/nca_metadata.h"
  29. #include "core/file_sys/registered_cache.h"
  30. #include "core/hle/service/filesystem/filesystem.h"
  31. #include "core/loader/loader.h"
  32. namespace Core::Crypto {
  33. namespace {
  34. constexpr u64 CURRENT_CRYPTO_REVISION = 0x5;
  35. constexpr u64 FULL_TICKET_SIZE = 0x400;
  36. using Common::AsArray;
  37. // clang-format off
  38. constexpr std::array eticket_source_hashes{
  39. AsArray("B71DB271DC338DF380AA2C4335EF8873B1AFD408E80B3582D8719FC81C5E511C"), // eticket_rsa_kek_source
  40. AsArray("E8965A187D30E57869F562D04383C996DE487BBA5761363D2D4D32391866A85C"), // eticket_rsa_kekek_source
  41. };
  42. // clang-format on
  43. constexpr std::array<std::pair<std::string_view, KeyIndex<S128KeyType>>, 30> s128_file_id{{
  44. {"eticket_rsa_kek", {S128KeyType::ETicketRSAKek, 0, 0}},
  45. {"eticket_rsa_kek_source",
  46. {S128KeyType::Source, static_cast<u64>(SourceKeyType::ETicketKek), 0}},
  47. {"eticket_rsa_kekek_source",
  48. {S128KeyType::Source, static_cast<u64>(SourceKeyType::ETicketKekek), 0}},
  49. {"rsa_kek_mask_0", {S128KeyType::RSAKek, static_cast<u64>(RSAKekType::Mask0), 0}},
  50. {"rsa_kek_seed_3", {S128KeyType::RSAKek, static_cast<u64>(RSAKekType::Seed3), 0}},
  51. {"rsa_oaep_kek_generation_source",
  52. {S128KeyType::Source, static_cast<u64>(SourceKeyType::RSAOaepKekGeneration), 0}},
  53. {"sd_card_kek_source", {S128KeyType::Source, static_cast<u64>(SourceKeyType::SDKek), 0}},
  54. {"aes_kek_generation_source",
  55. {S128KeyType::Source, static_cast<u64>(SourceKeyType::AESKekGeneration), 0}},
  56. {"aes_key_generation_source",
  57. {S128KeyType::Source, static_cast<u64>(SourceKeyType::AESKeyGeneration), 0}},
  58. {"package2_key_source", {S128KeyType::Source, static_cast<u64>(SourceKeyType::Package2), 0}},
  59. {"master_key_source", {S128KeyType::Source, static_cast<u64>(SourceKeyType::Master), 0}},
  60. {"header_kek_source", {S128KeyType::Source, static_cast<u64>(SourceKeyType::HeaderKek), 0}},
  61. {"key_area_key_application_source",
  62. {S128KeyType::Source, static_cast<u64>(SourceKeyType::KeyAreaKey),
  63. static_cast<u64>(KeyAreaKeyType::Application)}},
  64. {"key_area_key_ocean_source",
  65. {S128KeyType::Source, static_cast<u64>(SourceKeyType::KeyAreaKey),
  66. static_cast<u64>(KeyAreaKeyType::Ocean)}},
  67. {"key_area_key_system_source",
  68. {S128KeyType::Source, static_cast<u64>(SourceKeyType::KeyAreaKey),
  69. static_cast<u64>(KeyAreaKeyType::System)}},
  70. {"titlekek_source", {S128KeyType::Source, static_cast<u64>(SourceKeyType::Titlekek), 0}},
  71. {"keyblob_mac_key_source",
  72. {S128KeyType::Source, static_cast<u64>(SourceKeyType::KeyblobMAC), 0}},
  73. {"tsec_key", {S128KeyType::TSEC, 0, 0}},
  74. {"secure_boot_key", {S128KeyType::SecureBoot, 0, 0}},
  75. {"sd_seed", {S128KeyType::SDSeed, 0, 0}},
  76. {"bis_key_0_crypt", {S128KeyType::BIS, 0, static_cast<u64>(BISKeyType::Crypto)}},
  77. {"bis_key_0_tweak", {S128KeyType::BIS, 0, static_cast<u64>(BISKeyType::Tweak)}},
  78. {"bis_key_1_crypt", {S128KeyType::BIS, 1, static_cast<u64>(BISKeyType::Crypto)}},
  79. {"bis_key_1_tweak", {S128KeyType::BIS, 1, static_cast<u64>(BISKeyType::Tweak)}},
  80. {"bis_key_2_crypt", {S128KeyType::BIS, 2, static_cast<u64>(BISKeyType::Crypto)}},
  81. {"bis_key_2_tweak", {S128KeyType::BIS, 2, static_cast<u64>(BISKeyType::Tweak)}},
  82. {"bis_key_3_crypt", {S128KeyType::BIS, 3, static_cast<u64>(BISKeyType::Crypto)}},
  83. {"bis_key_3_tweak", {S128KeyType::BIS, 3, static_cast<u64>(BISKeyType::Tweak)}},
  84. {"header_kek", {S128KeyType::HeaderKek, 0, 0}},
  85. {"sd_card_kek", {S128KeyType::SDKek, 0, 0}},
  86. }};
  87. auto Find128ByName(std::string_view name) {
  88. return std::find_if(s128_file_id.begin(), s128_file_id.end(),
  89. [&name](const auto& pair) { return pair.first == name; });
  90. }
  91. constexpr std::array<std::pair<std::string_view, KeyIndex<S256KeyType>>, 6> s256_file_id{{
  92. {"header_key", {S256KeyType::Header, 0, 0}},
  93. {"sd_card_save_key_source", {S256KeyType::SDKeySource, static_cast<u64>(SDKeyType::Save), 0}},
  94. {"sd_card_nca_key_source", {S256KeyType::SDKeySource, static_cast<u64>(SDKeyType::NCA), 0}},
  95. {"header_key_source", {S256KeyType::HeaderSource, 0, 0}},
  96. {"sd_card_save_key", {S256KeyType::SDKey, static_cast<u64>(SDKeyType::Save), 0}},
  97. {"sd_card_nca_key", {S256KeyType::SDKey, static_cast<u64>(SDKeyType::NCA), 0}},
  98. }};
  99. auto Find256ByName(std::string_view name) {
  100. return std::find_if(s256_file_id.begin(), s256_file_id.end(),
  101. [&name](const auto& pair) { return pair.first == name; });
  102. }
  103. using KeyArray = std::array<std::pair<std::pair<S128KeyType, u64>, std::string_view>, 7>;
  104. constexpr KeyArray KEYS_VARIABLE_LENGTH{{
  105. {{S128KeyType::Master, 0}, "master_key_"},
  106. {{S128KeyType::Package1, 0}, "package1_key_"},
  107. {{S128KeyType::Package2, 0}, "package2_key_"},
  108. {{S128KeyType::Titlekek, 0}, "titlekek_"},
  109. {{S128KeyType::Source, static_cast<u64>(SourceKeyType::Keyblob)}, "keyblob_key_source_"},
  110. {{S128KeyType::Keyblob, 0}, "keyblob_key_"},
  111. {{S128KeyType::KeyblobMAC, 0}, "keyblob_mac_key_"},
  112. }};
  113. template <std::size_t Size>
  114. bool IsAllZeroArray(const std::array<u8, Size>& array) {
  115. return std::all_of(array.begin(), array.end(), [](const auto& elem) { return elem == 0; });
  116. }
  117. } // Anonymous namespace
  118. u64 GetSignatureTypeDataSize(SignatureType type) {
  119. switch (type) {
  120. case SignatureType::RSA_4096_SHA1:
  121. case SignatureType::RSA_4096_SHA256:
  122. return 0x200;
  123. case SignatureType::RSA_2048_SHA1:
  124. case SignatureType::RSA_2048_SHA256:
  125. return 0x100;
  126. case SignatureType::ECDSA_SHA1:
  127. case SignatureType::ECDSA_SHA256:
  128. return 0x3C;
  129. }
  130. UNREACHABLE();
  131. }
  132. u64 GetSignatureTypePaddingSize(SignatureType type) {
  133. switch (type) {
  134. case SignatureType::RSA_4096_SHA1:
  135. case SignatureType::RSA_4096_SHA256:
  136. case SignatureType::RSA_2048_SHA1:
  137. case SignatureType::RSA_2048_SHA256:
  138. return 0x3C;
  139. case SignatureType::ECDSA_SHA1:
  140. case SignatureType::ECDSA_SHA256:
  141. return 0x40;
  142. }
  143. UNREACHABLE();
  144. }
  145. SignatureType Ticket::GetSignatureType() const {
  146. if (const auto* ticket = std::get_if<RSA4096Ticket>(&data)) {
  147. return ticket->sig_type;
  148. }
  149. if (const auto* ticket = std::get_if<RSA2048Ticket>(&data)) {
  150. return ticket->sig_type;
  151. }
  152. if (const auto* ticket = std::get_if<ECDSATicket>(&data)) {
  153. return ticket->sig_type;
  154. }
  155. throw std::bad_variant_access{};
  156. }
  157. TicketData& Ticket::GetData() {
  158. if (auto* ticket = std::get_if<RSA4096Ticket>(&data)) {
  159. return ticket->data;
  160. }
  161. if (auto* ticket = std::get_if<RSA2048Ticket>(&data)) {
  162. return ticket->data;
  163. }
  164. if (auto* ticket = std::get_if<ECDSATicket>(&data)) {
  165. return ticket->data;
  166. }
  167. throw std::bad_variant_access{};
  168. }
  169. const TicketData& Ticket::GetData() const {
  170. if (const auto* ticket = std::get_if<RSA4096Ticket>(&data)) {
  171. return ticket->data;
  172. }
  173. if (const auto* ticket = std::get_if<RSA2048Ticket>(&data)) {
  174. return ticket->data;
  175. }
  176. if (const auto* ticket = std::get_if<ECDSATicket>(&data)) {
  177. return ticket->data;
  178. }
  179. throw std::bad_variant_access{};
  180. }
  181. u64 Ticket::GetSize() const {
  182. const auto sig_type = GetSignatureType();
  183. return sizeof(SignatureType) + GetSignatureTypeDataSize(sig_type) +
  184. GetSignatureTypePaddingSize(sig_type) + sizeof(TicketData);
  185. }
  186. Ticket Ticket::SynthesizeCommon(Key128 title_key, const std::array<u8, 16>& rights_id) {
  187. RSA2048Ticket out{};
  188. out.sig_type = SignatureType::RSA_2048_SHA256;
  189. out.data.rights_id = rights_id;
  190. out.data.title_key_common = title_key;
  191. return Ticket{out};
  192. }
  193. Key128 GenerateKeyEncryptionKey(Key128 source, Key128 master, Key128 kek_seed, Key128 key_seed) {
  194. Key128 out{};
  195. AESCipher<Key128> cipher1(master, Mode::ECB);
  196. cipher1.Transcode(kek_seed.data(), kek_seed.size(), out.data(), Op::Decrypt);
  197. AESCipher<Key128> cipher2(out, Mode::ECB);
  198. cipher2.Transcode(source.data(), source.size(), out.data(), Op::Decrypt);
  199. if (key_seed != Key128{}) {
  200. AESCipher<Key128> cipher3(out, Mode::ECB);
  201. cipher3.Transcode(key_seed.data(), key_seed.size(), out.data(), Op::Decrypt);
  202. }
  203. return out;
  204. }
  205. Key128 DeriveKeyblobKey(const Key128& sbk, const Key128& tsec, Key128 source) {
  206. AESCipher<Key128> sbk_cipher(sbk, Mode::ECB);
  207. AESCipher<Key128> tsec_cipher(tsec, Mode::ECB);
  208. tsec_cipher.Transcode(source.data(), source.size(), source.data(), Op::Decrypt);
  209. sbk_cipher.Transcode(source.data(), source.size(), source.data(), Op::Decrypt);
  210. return source;
  211. }
  212. Key128 DeriveMasterKey(const std::array<u8, 0x90>& keyblob, const Key128& master_source) {
  213. Key128 master_root;
  214. std::memcpy(master_root.data(), keyblob.data(), sizeof(Key128));
  215. AESCipher<Key128> master_cipher(master_root, Mode::ECB);
  216. Key128 master{};
  217. master_cipher.Transcode(master_source.data(), master_source.size(), master.data(), Op::Decrypt);
  218. return master;
  219. }
  220. std::array<u8, 144> DecryptKeyblob(const std::array<u8, 176>& encrypted_keyblob,
  221. const Key128& key) {
  222. std::array<u8, 0x90> keyblob;
  223. AESCipher<Key128> cipher(key, Mode::CTR);
  224. cipher.SetIV(std::vector<u8>(encrypted_keyblob.data() + 0x10, encrypted_keyblob.data() + 0x20));
  225. cipher.Transcode(encrypted_keyblob.data() + 0x20, keyblob.size(), keyblob.data(), Op::Decrypt);
  226. return keyblob;
  227. }
  228. void KeyManager::DeriveGeneralPurposeKeys(std::size_t crypto_revision) {
  229. const auto kek_generation_source =
  230. GetKey(S128KeyType::Source, static_cast<u64>(SourceKeyType::AESKekGeneration));
  231. const auto key_generation_source =
  232. GetKey(S128KeyType::Source, static_cast<u64>(SourceKeyType::AESKeyGeneration));
  233. if (HasKey(S128KeyType::Master, crypto_revision)) {
  234. for (auto kak_type :
  235. {KeyAreaKeyType::Application, KeyAreaKeyType::Ocean, KeyAreaKeyType::System}) {
  236. if (HasKey(S128KeyType::Source, static_cast<u64>(SourceKeyType::KeyAreaKey),
  237. static_cast<u64>(kak_type))) {
  238. const auto source =
  239. GetKey(S128KeyType::Source, static_cast<u64>(SourceKeyType::KeyAreaKey),
  240. static_cast<u64>(kak_type));
  241. const auto kek =
  242. GenerateKeyEncryptionKey(source, GetKey(S128KeyType::Master, crypto_revision),
  243. kek_generation_source, key_generation_source);
  244. SetKey(S128KeyType::KeyArea, kek, crypto_revision, static_cast<u64>(kak_type));
  245. }
  246. }
  247. AESCipher<Key128> master_cipher(GetKey(S128KeyType::Master, crypto_revision), Mode::ECB);
  248. for (auto key_type : {SourceKeyType::Titlekek, SourceKeyType::Package2}) {
  249. if (HasKey(S128KeyType::Source, static_cast<u64>(key_type))) {
  250. Key128 key{};
  251. master_cipher.Transcode(
  252. GetKey(S128KeyType::Source, static_cast<u64>(key_type)).data(), key.size(),
  253. key.data(), Op::Decrypt);
  254. SetKey(key_type == SourceKeyType::Titlekek ? S128KeyType::Titlekek
  255. : S128KeyType::Package2,
  256. key, crypto_revision);
  257. }
  258. }
  259. }
  260. }
  261. RSAKeyPair<2048> KeyManager::GetETicketRSAKey() const {
  262. if (IsAllZeroArray(eticket_extended_kek) || !HasKey(S128KeyType::ETicketRSAKek)) {
  263. return {};
  264. }
  265. const auto eticket_final = GetKey(S128KeyType::ETicketRSAKek);
  266. std::vector<u8> extended_iv(eticket_extended_kek.begin(), eticket_extended_kek.begin() + 0x10);
  267. std::array<u8, 0x230> extended_dec{};
  268. AESCipher<Key128> rsa_1(eticket_final, Mode::CTR);
  269. rsa_1.SetIV(extended_iv);
  270. rsa_1.Transcode(eticket_extended_kek.data() + 0x10, eticket_extended_kek.size() - 0x10,
  271. extended_dec.data(), Op::Decrypt);
  272. RSAKeyPair<2048> rsa_key{};
  273. std::memcpy(rsa_key.decryption_key.data(), extended_dec.data(), rsa_key.decryption_key.size());
  274. std::memcpy(rsa_key.modulus.data(), extended_dec.data() + 0x100, rsa_key.modulus.size());
  275. std::memcpy(rsa_key.exponent.data(), extended_dec.data() + 0x200, rsa_key.exponent.size());
  276. return rsa_key;
  277. }
  278. Key128 DeriveKeyblobMACKey(const Key128& keyblob_key, const Key128& mac_source) {
  279. AESCipher<Key128> mac_cipher(keyblob_key, Mode::ECB);
  280. Key128 mac_key{};
  281. mac_cipher.Transcode(mac_source.data(), mac_key.size(), mac_key.data(), Op::Decrypt);
  282. return mac_key;
  283. }
  284. std::optional<Key128> DeriveSDSeed() {
  285. const auto system_save_43_path =
  286. Common::FS::GetYuzuPath(Common::FS::YuzuPath::NANDDir) / "system/save/8000000000000043";
  287. const Common::FS::IOFile save_43{system_save_43_path, Common::FS::FileAccessMode::Read,
  288. Common::FS::FileType::BinaryFile};
  289. if (!save_43.IsOpen()) {
  290. return std::nullopt;
  291. }
  292. const auto sd_private_path =
  293. Common::FS::GetYuzuPath(Common::FS::YuzuPath::SDMCDir) / "Nintendo/Contents/private";
  294. const Common::FS::IOFile sd_private{sd_private_path, Common::FS::FileAccessMode::Read,
  295. Common::FS::FileType::BinaryFile};
  296. if (!sd_private.IsOpen()) {
  297. return std::nullopt;
  298. }
  299. std::array<u8, 0x10> private_seed{};
  300. if (sd_private.Read(private_seed) != private_seed.size()) {
  301. return std::nullopt;
  302. }
  303. std::array<u8, 0x10> buffer{};
  304. s64 offset = 0;
  305. for (; offset + 0x10 < static_cast<s64>(save_43.GetSize()); ++offset) {
  306. if (!save_43.Seek(offset)) {
  307. return std::nullopt;
  308. }
  309. if (save_43.Read(buffer) != buffer.size()) {
  310. return std::nullopt;
  311. }
  312. if (buffer == private_seed) {
  313. break;
  314. }
  315. }
  316. if (!save_43.Seek(offset + 0x10)) {
  317. return std::nullopt;
  318. }
  319. Key128 seed{};
  320. if (save_43.Read(seed) != seed.size()) {
  321. return std::nullopt;
  322. }
  323. return seed;
  324. }
  325. Loader::ResultStatus DeriveSDKeys(std::array<Key256, 2>& sd_keys, KeyManager& keys) {
  326. if (!keys.HasKey(S128KeyType::Source, static_cast<u64>(SourceKeyType::SDKek))) {
  327. return Loader::ResultStatus::ErrorMissingSDKEKSource;
  328. }
  329. if (!keys.HasKey(S128KeyType::Source, static_cast<u64>(SourceKeyType::AESKekGeneration))) {
  330. return Loader::ResultStatus::ErrorMissingAESKEKGenerationSource;
  331. }
  332. if (!keys.HasKey(S128KeyType::Source, static_cast<u64>(SourceKeyType::AESKeyGeneration))) {
  333. return Loader::ResultStatus::ErrorMissingAESKeyGenerationSource;
  334. }
  335. const auto sd_kek_source =
  336. keys.GetKey(S128KeyType::Source, static_cast<u64>(SourceKeyType::SDKek));
  337. const auto aes_kek_gen =
  338. keys.GetKey(S128KeyType::Source, static_cast<u64>(SourceKeyType::AESKekGeneration));
  339. const auto aes_key_gen =
  340. keys.GetKey(S128KeyType::Source, static_cast<u64>(SourceKeyType::AESKeyGeneration));
  341. const auto master_00 = keys.GetKey(S128KeyType::Master);
  342. const auto sd_kek =
  343. GenerateKeyEncryptionKey(sd_kek_source, master_00, aes_kek_gen, aes_key_gen);
  344. keys.SetKey(S128KeyType::SDKek, sd_kek);
  345. if (!keys.HasKey(S128KeyType::SDSeed)) {
  346. return Loader::ResultStatus::ErrorMissingSDSeed;
  347. }
  348. const auto sd_seed = keys.GetKey(S128KeyType::SDSeed);
  349. if (!keys.HasKey(S256KeyType::SDKeySource, static_cast<u64>(SDKeyType::Save))) {
  350. return Loader::ResultStatus::ErrorMissingSDSaveKeySource;
  351. }
  352. if (!keys.HasKey(S256KeyType::SDKeySource, static_cast<u64>(SDKeyType::NCA))) {
  353. return Loader::ResultStatus::ErrorMissingSDNCAKeySource;
  354. }
  355. std::array<Key256, 2> sd_key_sources{
  356. keys.GetKey(S256KeyType::SDKeySource, static_cast<u64>(SDKeyType::Save)),
  357. keys.GetKey(S256KeyType::SDKeySource, static_cast<u64>(SDKeyType::NCA)),
  358. };
  359. // Combine sources and seed
  360. for (auto& source : sd_key_sources) {
  361. for (std::size_t i = 0; i < source.size(); ++i) {
  362. source[i] = static_cast<u8>(source[i] ^ sd_seed[i & 0xF]);
  363. }
  364. }
  365. AESCipher<Key128> cipher(sd_kek, Mode::ECB);
  366. // The transform manipulates sd_keys as part of the Transcode, so the return/output is
  367. // unnecessary. This does not alter sd_keys_sources.
  368. std::transform(sd_key_sources.begin(), sd_key_sources.end(), sd_keys.begin(),
  369. sd_key_sources.begin(), [&cipher](const Key256& source, Key256& out) {
  370. cipher.Transcode(source.data(), source.size(), out.data(), Op::Decrypt);
  371. return source; ///< Return unaltered source to satisfy output requirement.
  372. });
  373. keys.SetKey(S256KeyType::SDKey, sd_keys[0], static_cast<u64>(SDKeyType::Save));
  374. keys.SetKey(S256KeyType::SDKey, sd_keys[1], static_cast<u64>(SDKeyType::NCA));
  375. return Loader::ResultStatus::Success;
  376. }
  377. std::vector<Ticket> GetTicketblob(const Common::FS::IOFile& ticket_save) {
  378. if (!ticket_save.IsOpen()) {
  379. return {};
  380. }
  381. std::vector<u8> buffer(ticket_save.GetSize());
  382. if (ticket_save.Read(buffer) != buffer.size()) {
  383. return {};
  384. }
  385. std::vector<Ticket> out;
  386. for (std::size_t offset = 0; offset + 0x4 < buffer.size(); ++offset) {
  387. if (buffer[offset] == 0x4 && buffer[offset + 1] == 0x0 && buffer[offset + 2] == 0x1 &&
  388. buffer[offset + 3] == 0x0) {
  389. out.emplace_back();
  390. auto& next = out.back();
  391. std::memcpy(&next, buffer.data() + offset, sizeof(Ticket));
  392. offset += FULL_TICKET_SIZE;
  393. }
  394. }
  395. return out;
  396. }
  397. template <size_t size>
  398. static std::array<u8, size> operator^(const std::array<u8, size>& lhs,
  399. const std::array<u8, size>& rhs) {
  400. std::array<u8, size> out;
  401. std::transform(lhs.begin(), lhs.end(), rhs.begin(), out.begin(),
  402. [](u8 lhs_elem, u8 rhs_elem) { return u8(lhs_elem ^ rhs_elem); });
  403. return out;
  404. }
  405. template <size_t target_size, size_t in_size>
  406. static std::array<u8, target_size> MGF1(const std::array<u8, in_size>& seed) {
  407. // Avoids truncation overflow within the loop below.
  408. static_assert(target_size <= 0xFF);
  409. std::array<u8, in_size + 4> seed_exp{};
  410. std::memcpy(seed_exp.data(), seed.data(), in_size);
  411. std::vector<u8> out;
  412. size_t i = 0;
  413. while (out.size() < target_size) {
  414. out.resize(out.size() + 0x20);
  415. seed_exp[in_size + 3] = static_cast<u8>(i);
  416. mbedtls_sha256_ret(seed_exp.data(), seed_exp.size(), out.data() + out.size() - 0x20, 0);
  417. ++i;
  418. }
  419. std::array<u8, target_size> target;
  420. std::memcpy(target.data(), out.data(), target_size);
  421. return target;
  422. }
  423. template <size_t size>
  424. static std::optional<u64> FindTicketOffset(const std::array<u8, size>& data) {
  425. u64 offset = 0;
  426. for (size_t i = 0x20; i < data.size() - 0x10; ++i) {
  427. if (data[i] == 0x1) {
  428. offset = i + 1;
  429. break;
  430. } else if (data[i] != 0x0) {
  431. return std::nullopt;
  432. }
  433. }
  434. return offset;
  435. }
  436. std::optional<std::pair<Key128, Key128>> ParseTicket(const Ticket& ticket,
  437. const RSAKeyPair<2048>& key) {
  438. const auto issuer = ticket.GetData().issuer;
  439. if (IsAllZeroArray(issuer)) {
  440. return std::nullopt;
  441. }
  442. if (issuer[0] != 'R' || issuer[1] != 'o' || issuer[2] != 'o' || issuer[3] != 't') {
  443. LOG_INFO(Crypto, "Attempting to parse ticket with non-standard certificate authority.");
  444. }
  445. Key128 rights_id = ticket.GetData().rights_id;
  446. if (rights_id == Key128{}) {
  447. return std::nullopt;
  448. }
  449. if (!std::any_of(ticket.GetData().title_key_common_pad.begin(),
  450. ticket.GetData().title_key_common_pad.end(), [](u8 b) { return b != 0; })) {
  451. return std::make_pair(rights_id, ticket.GetData().title_key_common);
  452. }
  453. mbedtls_mpi D; // RSA Private Exponent
  454. mbedtls_mpi N; // RSA Modulus
  455. mbedtls_mpi S; // Input
  456. mbedtls_mpi M; // Output
  457. mbedtls_mpi_init(&D);
  458. mbedtls_mpi_init(&N);
  459. mbedtls_mpi_init(&S);
  460. mbedtls_mpi_init(&M);
  461. mbedtls_mpi_read_binary(&D, key.decryption_key.data(), key.decryption_key.size());
  462. mbedtls_mpi_read_binary(&N, key.modulus.data(), key.modulus.size());
  463. mbedtls_mpi_read_binary(&S, ticket.GetData().title_key_block.data(), 0x100);
  464. mbedtls_mpi_exp_mod(&M, &S, &D, &N, nullptr);
  465. std::array<u8, 0x100> rsa_step;
  466. mbedtls_mpi_write_binary(&M, rsa_step.data(), rsa_step.size());
  467. u8 m_0 = rsa_step[0];
  468. std::array<u8, 0x20> m_1;
  469. std::memcpy(m_1.data(), rsa_step.data() + 0x01, m_1.size());
  470. std::array<u8, 0xDF> m_2;
  471. std::memcpy(m_2.data(), rsa_step.data() + 0x21, m_2.size());
  472. if (m_0 != 0) {
  473. return std::nullopt;
  474. }
  475. m_1 = m_1 ^ MGF1<0x20>(m_2);
  476. m_2 = m_2 ^ MGF1<0xDF>(m_1);
  477. const auto offset = FindTicketOffset(m_2);
  478. if (!offset) {
  479. return std::nullopt;
  480. }
  481. ASSERT(*offset > 0);
  482. Key128 key_temp{};
  483. std::memcpy(key_temp.data(), m_2.data() + *offset, key_temp.size());
  484. return std::make_pair(rights_id, key_temp);
  485. }
  486. KeyManager::KeyManager() {
  487. // Initialize keys
  488. const auto yuzu_keys_dir = Common::FS::GetYuzuPath(Common::FS::YuzuPath::KeysDir);
  489. if (!Common::FS::CreateDir(yuzu_keys_dir)) {
  490. LOG_ERROR(Core, "Failed to create the keys directory.");
  491. }
  492. if (Settings::values.use_dev_keys) {
  493. dev_mode = true;
  494. LoadFromFile(yuzu_keys_dir / "dev.keys", false);
  495. LoadFromFile(yuzu_keys_dir / "dev.keys_autogenerated", false);
  496. } else {
  497. dev_mode = false;
  498. LoadFromFile(yuzu_keys_dir / "prod.keys", false);
  499. LoadFromFile(yuzu_keys_dir / "prod.keys_autogenerated", false);
  500. }
  501. LoadFromFile(yuzu_keys_dir / "title.keys", true);
  502. LoadFromFile(yuzu_keys_dir / "title.keys_autogenerated", true);
  503. LoadFromFile(yuzu_keys_dir / "console.keys", false);
  504. LoadFromFile(yuzu_keys_dir / "console.keys_autogenerated", false);
  505. }
  506. static bool ValidCryptoRevisionString(std::string_view base, size_t begin, size_t length) {
  507. if (base.size() < begin + length) {
  508. return false;
  509. }
  510. return std::all_of(base.begin() + begin, base.begin() + begin + length,
  511. [](u8 c) { return std::isxdigit(c); });
  512. }
  513. void KeyManager::LoadFromFile(const std::filesystem::path& file_path, bool is_title_keys) {
  514. if (!Common::FS::Exists(file_path)) {
  515. return;
  516. }
  517. std::ifstream file;
  518. Common::FS::OpenFileStream(file, file_path, std::ios_base::in);
  519. if (!file.is_open()) {
  520. return;
  521. }
  522. std::string line;
  523. while (std::getline(file, line)) {
  524. std::vector<std::string> out;
  525. std::stringstream stream(line);
  526. std::string item;
  527. while (std::getline(stream, item, '=')) {
  528. out.push_back(std::move(item));
  529. }
  530. if (out.size() != 2) {
  531. continue;
  532. }
  533. out[0].erase(std::remove(out[0].begin(), out[0].end(), ' '), out[0].end());
  534. out[1].erase(std::remove(out[1].begin(), out[1].end(), ' '), out[1].end());
  535. if (out[0].compare(0, 1, "#") == 0) {
  536. continue;
  537. }
  538. if (is_title_keys) {
  539. auto rights_id_raw = Common::HexStringToArray<16>(out[0]);
  540. u128 rights_id{};
  541. std::memcpy(rights_id.data(), rights_id_raw.data(), rights_id_raw.size());
  542. Key128 key = Common::HexStringToArray<16>(out[1]);
  543. s128_keys[{S128KeyType::Titlekey, rights_id[1], rights_id[0]}] = key;
  544. } else {
  545. out[0] = Common::ToLower(out[0]);
  546. if (const auto iter128 = Find128ByName(out[0]); iter128 != s128_file_id.end()) {
  547. const auto& index = iter128->second;
  548. const Key128 key = Common::HexStringToArray<16>(out[1]);
  549. s128_keys[{index.type, index.field1, index.field2}] = key;
  550. } else if (const auto iter256 = Find256ByName(out[0]); iter256 != s256_file_id.end()) {
  551. const auto& index = iter256->second;
  552. const Key256 key = Common::HexStringToArray<32>(out[1]);
  553. s256_keys[{index.type, index.field1, index.field2}] = key;
  554. } else if (out[0].compare(0, 8, "keyblob_") == 0 &&
  555. out[0].compare(0, 9, "keyblob_k") != 0) {
  556. if (!ValidCryptoRevisionString(out[0], 8, 2)) {
  557. continue;
  558. }
  559. const auto index = std::stoul(out[0].substr(8, 2), nullptr, 16);
  560. keyblobs[index] = Common::HexStringToArray<0x90>(out[1]);
  561. } else if (out[0].compare(0, 18, "encrypted_keyblob_") == 0) {
  562. if (!ValidCryptoRevisionString(out[0], 18, 2)) {
  563. continue;
  564. }
  565. const auto index = std::stoul(out[0].substr(18, 2), nullptr, 16);
  566. encrypted_keyblobs[index] = Common::HexStringToArray<0xB0>(out[1]);
  567. } else if (out[0].compare(0, 20, "eticket_extended_kek") == 0) {
  568. eticket_extended_kek = Common::HexStringToArray<576>(out[1]);
  569. } else {
  570. for (const auto& kv : KEYS_VARIABLE_LENGTH) {
  571. if (!ValidCryptoRevisionString(out[0], kv.second.size(), 2)) {
  572. continue;
  573. }
  574. if (out[0].compare(0, kv.second.size(), kv.second) == 0) {
  575. const auto index =
  576. std::stoul(out[0].substr(kv.second.size(), 2), nullptr, 16);
  577. const auto sub = kv.first.second;
  578. if (sub == 0) {
  579. s128_keys[{kv.first.first, index, 0}] =
  580. Common::HexStringToArray<16>(out[1]);
  581. } else {
  582. s128_keys[{kv.first.first, kv.first.second, index}] =
  583. Common::HexStringToArray<16>(out[1]);
  584. }
  585. break;
  586. }
  587. }
  588. static constexpr std::array<const char*, 3> kak_names = {
  589. "key_area_key_application_", "key_area_key_ocean_", "key_area_key_system_"};
  590. for (size_t j = 0; j < kak_names.size(); ++j) {
  591. const auto& match = kak_names[j];
  592. if (out[0].compare(0, std::strlen(match), match) == 0) {
  593. const auto index =
  594. std::stoul(out[0].substr(std::strlen(match), 2), nullptr, 16);
  595. s128_keys[{S128KeyType::KeyArea, index, j}] =
  596. Common::HexStringToArray<16>(out[1]);
  597. }
  598. }
  599. }
  600. }
  601. }
  602. }
  603. bool KeyManager::BaseDeriveNecessary() const {
  604. const auto check_key_existence = [this](auto key_type, u64 index1 = 0, u64 index2 = 0) {
  605. return !HasKey(key_type, index1, index2);
  606. };
  607. if (check_key_existence(S256KeyType::Header)) {
  608. return true;
  609. }
  610. for (size_t i = 0; i < CURRENT_CRYPTO_REVISION; ++i) {
  611. if (check_key_existence(S128KeyType::Master, i) ||
  612. check_key_existence(S128KeyType::KeyArea, i,
  613. static_cast<u64>(KeyAreaKeyType::Application)) ||
  614. check_key_existence(S128KeyType::KeyArea, i, static_cast<u64>(KeyAreaKeyType::Ocean)) ||
  615. check_key_existence(S128KeyType::KeyArea, i,
  616. static_cast<u64>(KeyAreaKeyType::System)) ||
  617. check_key_existence(S128KeyType::Titlekek, i))
  618. return true;
  619. }
  620. return false;
  621. }
  622. bool KeyManager::HasKey(S128KeyType id, u64 field1, u64 field2) const {
  623. return s128_keys.find({id, field1, field2}) != s128_keys.end();
  624. }
  625. bool KeyManager::HasKey(S256KeyType id, u64 field1, u64 field2) const {
  626. return s256_keys.find({id, field1, field2}) != s256_keys.end();
  627. }
  628. Key128 KeyManager::GetKey(S128KeyType id, u64 field1, u64 field2) const {
  629. if (!HasKey(id, field1, field2)) {
  630. return {};
  631. }
  632. return s128_keys.at({id, field1, field2});
  633. }
  634. Key256 KeyManager::GetKey(S256KeyType id, u64 field1, u64 field2) const {
  635. if (!HasKey(id, field1, field2)) {
  636. return {};
  637. }
  638. return s256_keys.at({id, field1, field2});
  639. }
  640. Key256 KeyManager::GetBISKey(u8 partition_id) const {
  641. Key256 out{};
  642. for (const auto& bis_type : {BISKeyType::Crypto, BISKeyType::Tweak}) {
  643. if (HasKey(S128KeyType::BIS, partition_id, static_cast<u64>(bis_type))) {
  644. std::memcpy(
  645. out.data() + sizeof(Key128) * static_cast<u64>(bis_type),
  646. s128_keys.at({S128KeyType::BIS, partition_id, static_cast<u64>(bis_type)}).data(),
  647. sizeof(Key128));
  648. }
  649. }
  650. return out;
  651. }
  652. template <size_t Size>
  653. void KeyManager::WriteKeyToFile(KeyCategory category, std::string_view keyname,
  654. const std::array<u8, Size>& key) {
  655. const auto yuzu_keys_dir = Common::FS::GetYuzuPath(Common::FS::YuzuPath::KeysDir);
  656. std::string filename = "title.keys_autogenerated";
  657. if (category == KeyCategory::Standard) {
  658. filename = dev_mode ? "dev.keys_autogenerated" : "prod.keys_autogenerated";
  659. } else if (category == KeyCategory::Console) {
  660. filename = "console.keys_autogenerated";
  661. }
  662. const auto path = yuzu_keys_dir / filename;
  663. const auto add_info_text = !Common::FS::Exists(path);
  664. Common::FS::IOFile file{path, Common::FS::FileAccessMode::Append,
  665. Common::FS::FileType::TextFile};
  666. if (!file.IsOpen()) {
  667. return;
  668. }
  669. if (add_info_text) {
  670. void(file.WriteString(
  671. "# This file is autogenerated by Yuzu\n"
  672. "# It serves to store keys that were automatically generated from the normal keys\n"
  673. "# If you are experiencing issues involving keys, it may help to delete this file\n"));
  674. }
  675. void(file.WriteString(fmt::format("\n{} = {}", keyname, Common::HexToString(key))));
  676. LoadFromFile(path, category == KeyCategory::Title);
  677. }
  678. void KeyManager::SetKey(S128KeyType id, Key128 key, u64 field1, u64 field2) {
  679. if (s128_keys.find({id, field1, field2}) != s128_keys.end() || key == Key128{}) {
  680. return;
  681. }
  682. if (id == S128KeyType::Titlekey) {
  683. Key128 rights_id;
  684. std::memcpy(rights_id.data(), &field2, sizeof(u64));
  685. std::memcpy(rights_id.data() + sizeof(u64), &field1, sizeof(u64));
  686. WriteKeyToFile(KeyCategory::Title, Common::HexToString(rights_id), key);
  687. }
  688. auto category = KeyCategory::Standard;
  689. if (id == S128KeyType::Keyblob || id == S128KeyType::KeyblobMAC || id == S128KeyType::TSEC ||
  690. id == S128KeyType::SecureBoot || id == S128KeyType::SDSeed || id == S128KeyType::BIS) {
  691. category = KeyCategory::Console;
  692. }
  693. const auto iter2 = std::find_if(
  694. s128_file_id.begin(), s128_file_id.end(), [&id, &field1, &field2](const auto& elem) {
  695. return std::tie(elem.second.type, elem.second.field1, elem.second.field2) ==
  696. std::tie(id, field1, field2);
  697. });
  698. if (iter2 != s128_file_id.end()) {
  699. WriteKeyToFile(category, iter2->first, key);
  700. }
  701. // Variable cases
  702. if (id == S128KeyType::KeyArea) {
  703. static constexpr std::array<const char*, 3> kak_names = {
  704. "key_area_key_application_{:02X}",
  705. "key_area_key_ocean_{:02X}",
  706. "key_area_key_system_{:02X}",
  707. };
  708. WriteKeyToFile(category, fmt::format(fmt::runtime(kak_names.at(field2)), field1), key);
  709. } else if (id == S128KeyType::Master) {
  710. WriteKeyToFile(category, fmt::format("master_key_{:02X}", field1), key);
  711. } else if (id == S128KeyType::Package1) {
  712. WriteKeyToFile(category, fmt::format("package1_key_{:02X}", field1), key);
  713. } else if (id == S128KeyType::Package2) {
  714. WriteKeyToFile(category, fmt::format("package2_key_{:02X}", field1), key);
  715. } else if (id == S128KeyType::Titlekek) {
  716. WriteKeyToFile(category, fmt::format("titlekek_{:02X}", field1), key);
  717. } else if (id == S128KeyType::Keyblob) {
  718. WriteKeyToFile(category, fmt::format("keyblob_key_{:02X}", field1), key);
  719. } else if (id == S128KeyType::KeyblobMAC) {
  720. WriteKeyToFile(category, fmt::format("keyblob_mac_key_{:02X}", field1), key);
  721. } else if (id == S128KeyType::Source && field1 == static_cast<u64>(SourceKeyType::Keyblob)) {
  722. WriteKeyToFile(category, fmt::format("keyblob_key_source_{:02X}", field2), key);
  723. }
  724. s128_keys[{id, field1, field2}] = key;
  725. }
  726. void KeyManager::SetKey(S256KeyType id, Key256 key, u64 field1, u64 field2) {
  727. if (s256_keys.find({id, field1, field2}) != s256_keys.end() || key == Key256{}) {
  728. return;
  729. }
  730. const auto iter = std::find_if(
  731. s256_file_id.begin(), s256_file_id.end(), [&id, &field1, &field2](const auto& elem) {
  732. return std::tie(elem.second.type, elem.second.field1, elem.second.field2) ==
  733. std::tie(id, field1, field2);
  734. });
  735. if (iter != s256_file_id.end()) {
  736. WriteKeyToFile(KeyCategory::Standard, iter->first, key);
  737. }
  738. s256_keys[{id, field1, field2}] = key;
  739. }
  740. bool KeyManager::KeyFileExists(bool title) {
  741. const auto yuzu_keys_dir = Common::FS::GetYuzuPath(Common::FS::YuzuPath::KeysDir);
  742. if (title) {
  743. return Common::FS::Exists(yuzu_keys_dir / "title.keys");
  744. }
  745. if (Settings::values.use_dev_keys) {
  746. return Common::FS::Exists(yuzu_keys_dir / "dev.keys");
  747. }
  748. return Common::FS::Exists(yuzu_keys_dir / "prod.keys");
  749. }
  750. void KeyManager::DeriveSDSeedLazy() {
  751. if (HasKey(S128KeyType::SDSeed)) {
  752. return;
  753. }
  754. const auto res = DeriveSDSeed();
  755. if (res) {
  756. SetKey(S128KeyType::SDSeed, *res);
  757. }
  758. }
  759. static Key128 CalculateCMAC(const u8* source, size_t size, const Key128& key) {
  760. Key128 out{};
  761. mbedtls_cipher_cmac(mbedtls_cipher_info_from_type(MBEDTLS_CIPHER_AES_128_ECB), key.data(),
  762. key.size() * 8, source, size, out.data());
  763. return out;
  764. }
  765. void KeyManager::DeriveBase() {
  766. if (!BaseDeriveNecessary()) {
  767. return;
  768. }
  769. if (!HasKey(S128KeyType::SecureBoot) || !HasKey(S128KeyType::TSEC)) {
  770. return;
  771. }
  772. const auto has_bis = [this](u64 id) {
  773. return HasKey(S128KeyType::BIS, id, static_cast<u64>(BISKeyType::Crypto)) &&
  774. HasKey(S128KeyType::BIS, id, static_cast<u64>(BISKeyType::Tweak));
  775. };
  776. const auto copy_bis = [this](u64 id_from, u64 id_to) {
  777. SetKey(S128KeyType::BIS,
  778. GetKey(S128KeyType::BIS, id_from, static_cast<u64>(BISKeyType::Crypto)), id_to,
  779. static_cast<u64>(BISKeyType::Crypto));
  780. SetKey(S128KeyType::BIS,
  781. GetKey(S128KeyType::BIS, id_from, static_cast<u64>(BISKeyType::Tweak)), id_to,
  782. static_cast<u64>(BISKeyType::Tweak));
  783. };
  784. if (has_bis(2) && !has_bis(3)) {
  785. copy_bis(2, 3);
  786. } else if (has_bis(3) && !has_bis(2)) {
  787. copy_bis(3, 2);
  788. }
  789. std::bitset<32> revisions(0xFFFFFFFF);
  790. for (size_t i = 0; i < revisions.size(); ++i) {
  791. if (!HasKey(S128KeyType::Source, static_cast<u64>(SourceKeyType::Keyblob), i) ||
  792. encrypted_keyblobs[i] == std::array<u8, 0xB0>{}) {
  793. revisions.reset(i);
  794. }
  795. }
  796. if (!revisions.any()) {
  797. return;
  798. }
  799. const auto sbk = GetKey(S128KeyType::SecureBoot);
  800. const auto tsec = GetKey(S128KeyType::TSEC);
  801. for (size_t i = 0; i < revisions.size(); ++i) {
  802. if (!revisions[i]) {
  803. continue;
  804. }
  805. // Derive keyblob key
  806. const auto key = DeriveKeyblobKey(
  807. sbk, tsec, GetKey(S128KeyType::Source, static_cast<u64>(SourceKeyType::Keyblob), i));
  808. SetKey(S128KeyType::Keyblob, key, i);
  809. // Derive keyblob MAC key
  810. if (!HasKey(S128KeyType::Source, static_cast<u64>(SourceKeyType::KeyblobMAC))) {
  811. continue;
  812. }
  813. const auto mac_key = DeriveKeyblobMACKey(
  814. key, GetKey(S128KeyType::Source, static_cast<u64>(SourceKeyType::KeyblobMAC)));
  815. SetKey(S128KeyType::KeyblobMAC, mac_key, i);
  816. Key128 cmac = CalculateCMAC(encrypted_keyblobs[i].data() + 0x10, 0xA0, mac_key);
  817. if (std::memcmp(cmac.data(), encrypted_keyblobs[i].data(), cmac.size()) != 0) {
  818. continue;
  819. }
  820. // Decrypt keyblob
  821. if (keyblobs[i] == std::array<u8, 0x90>{}) {
  822. keyblobs[i] = DecryptKeyblob(encrypted_keyblobs[i], key);
  823. WriteKeyToFile<0x90>(KeyCategory::Console, fmt::format("keyblob_{:02X}", i),
  824. keyblobs[i]);
  825. }
  826. Key128 package1;
  827. std::memcpy(package1.data(), keyblobs[i].data() + 0x80, sizeof(Key128));
  828. SetKey(S128KeyType::Package1, package1, i);
  829. // Derive master key
  830. if (HasKey(S128KeyType::Source, static_cast<u64>(SourceKeyType::Master))) {
  831. SetKey(S128KeyType::Master,
  832. DeriveMasterKey(keyblobs[i], GetKey(S128KeyType::Source,
  833. static_cast<u64>(SourceKeyType::Master))),
  834. i);
  835. }
  836. }
  837. revisions.set();
  838. for (size_t i = 0; i < revisions.size(); ++i) {
  839. if (!HasKey(S128KeyType::Master, i)) {
  840. revisions.reset(i);
  841. }
  842. }
  843. if (!revisions.any()) {
  844. return;
  845. }
  846. for (size_t i = 0; i < revisions.size(); ++i) {
  847. if (!revisions[i]) {
  848. continue;
  849. }
  850. // Derive general purpose keys
  851. DeriveGeneralPurposeKeys(i);
  852. }
  853. if (HasKey(S128KeyType::Master, 0) &&
  854. HasKey(S128KeyType::Source, static_cast<u64>(SourceKeyType::AESKeyGeneration)) &&
  855. HasKey(S128KeyType::Source, static_cast<u64>(SourceKeyType::AESKekGeneration)) &&
  856. HasKey(S128KeyType::Source, static_cast<u64>(SourceKeyType::HeaderKek)) &&
  857. HasKey(S256KeyType::HeaderSource)) {
  858. const auto header_kek = GenerateKeyEncryptionKey(
  859. GetKey(S128KeyType::Source, static_cast<u64>(SourceKeyType::HeaderKek)),
  860. GetKey(S128KeyType::Master, 0),
  861. GetKey(S128KeyType::Source, static_cast<u64>(SourceKeyType::AESKekGeneration)),
  862. GetKey(S128KeyType::Source, static_cast<u64>(SourceKeyType::AESKeyGeneration)));
  863. SetKey(S128KeyType::HeaderKek, header_kek);
  864. AESCipher<Key128> header_cipher(header_kek, Mode::ECB);
  865. Key256 out = GetKey(S256KeyType::HeaderSource);
  866. header_cipher.Transcode(out.data(), out.size(), out.data(), Op::Decrypt);
  867. SetKey(S256KeyType::Header, out);
  868. }
  869. }
  870. void KeyManager::DeriveETicket(PartitionDataManager& data,
  871. const FileSys::ContentProvider& provider) {
  872. // ETicket keys
  873. const auto es = provider.GetEntry(0x0100000000000033, FileSys::ContentRecordType::Program);
  874. if (es == nullptr) {
  875. return;
  876. }
  877. const auto exefs = es->GetExeFS();
  878. if (exefs == nullptr) {
  879. return;
  880. }
  881. const auto main = exefs->GetFile("main");
  882. if (main == nullptr) {
  883. return;
  884. }
  885. const auto bytes = main->ReadAllBytes();
  886. const auto eticket_kek = FindKeyFromHex16(bytes, eticket_source_hashes[0]);
  887. const auto eticket_kekek = FindKeyFromHex16(bytes, eticket_source_hashes[1]);
  888. const auto seed3 = data.GetRSAKekSeed3();
  889. const auto mask0 = data.GetRSAKekMask0();
  890. if (eticket_kek != Key128{}) {
  891. SetKey(S128KeyType::Source, eticket_kek, static_cast<size_t>(SourceKeyType::ETicketKek));
  892. }
  893. if (eticket_kekek != Key128{}) {
  894. SetKey(S128KeyType::Source, eticket_kekek,
  895. static_cast<size_t>(SourceKeyType::ETicketKekek));
  896. }
  897. if (seed3 != Key128{}) {
  898. SetKey(S128KeyType::RSAKek, seed3, static_cast<size_t>(RSAKekType::Seed3));
  899. }
  900. if (mask0 != Key128{}) {
  901. SetKey(S128KeyType::RSAKek, mask0, static_cast<size_t>(RSAKekType::Mask0));
  902. }
  903. if (eticket_kek == Key128{} || eticket_kekek == Key128{} || seed3 == Key128{} ||
  904. mask0 == Key128{}) {
  905. return;
  906. }
  907. const Key128 rsa_oaep_kek = seed3 ^ mask0;
  908. if (rsa_oaep_kek == Key128{}) {
  909. return;
  910. }
  911. SetKey(S128KeyType::Source, rsa_oaep_kek,
  912. static_cast<u64>(SourceKeyType::RSAOaepKekGeneration));
  913. Key128 temp_kek{};
  914. Key128 temp_kekek{};
  915. Key128 eticket_final{};
  916. // Derive ETicket RSA Kek
  917. AESCipher<Key128> es_master(GetKey(S128KeyType::Master), Mode::ECB);
  918. es_master.Transcode(rsa_oaep_kek.data(), rsa_oaep_kek.size(), temp_kek.data(), Op::Decrypt);
  919. AESCipher<Key128> es_kekek(temp_kek, Mode::ECB);
  920. es_kekek.Transcode(eticket_kekek.data(), eticket_kekek.size(), temp_kekek.data(), Op::Decrypt);
  921. AESCipher<Key128> es_kek(temp_kekek, Mode::ECB);
  922. es_kek.Transcode(eticket_kek.data(), eticket_kek.size(), eticket_final.data(), Op::Decrypt);
  923. if (eticket_final == Key128{}) {
  924. return;
  925. }
  926. SetKey(S128KeyType::ETicketRSAKek, eticket_final);
  927. // Titlekeys
  928. data.DecryptProdInfo(GetBISKey(0));
  929. eticket_extended_kek = data.GetETicketExtendedKek();
  930. WriteKeyToFile(KeyCategory::Console, "eticket_extended_kek", eticket_extended_kek);
  931. PopulateTickets();
  932. }
  933. void KeyManager::PopulateTickets() {
  934. const auto rsa_key = GetETicketRSAKey();
  935. if (rsa_key == RSAKeyPair<2048>{}) {
  936. return;
  937. }
  938. if (!common_tickets.empty() && !personal_tickets.empty()) {
  939. return;
  940. }
  941. const auto system_save_e1_path =
  942. Common::FS::GetYuzuPath(Common::FS::YuzuPath::NANDDir) / "system/save/80000000000000e1";
  943. const Common::FS::IOFile save_e1{system_save_e1_path, Common::FS::FileAccessMode::Read,
  944. Common::FS::FileType::BinaryFile};
  945. const auto system_save_e2_path =
  946. Common::FS::GetYuzuPath(Common::FS::YuzuPath::NANDDir) / "system/save/80000000000000e2";
  947. const Common::FS::IOFile save_e2{system_save_e2_path, Common::FS::FileAccessMode::Read,
  948. Common::FS::FileType::BinaryFile};
  949. const auto blob2 = GetTicketblob(save_e2);
  950. auto res = GetTicketblob(save_e1);
  951. const auto idx = res.size();
  952. res.insert(res.end(), blob2.begin(), blob2.end());
  953. for (std::size_t i = 0; i < res.size(); ++i) {
  954. const auto common = i < idx;
  955. const auto pair = ParseTicket(res[i], rsa_key);
  956. if (!pair) {
  957. continue;
  958. }
  959. const auto& [rid, key] = *pair;
  960. u128 rights_id;
  961. std::memcpy(rights_id.data(), rid.data(), rid.size());
  962. if (common) {
  963. common_tickets[rights_id] = res[i];
  964. } else {
  965. personal_tickets[rights_id] = res[i];
  966. }
  967. SetKey(S128KeyType::Titlekey, key, rights_id[1], rights_id[0]);
  968. }
  969. }
  970. void KeyManager::SynthesizeTickets() {
  971. for (const auto& key : s128_keys) {
  972. if (key.first.type != S128KeyType::Titlekey) {
  973. continue;
  974. }
  975. u128 rights_id{key.first.field1, key.first.field2};
  976. Key128 rights_id_2;
  977. std::memcpy(rights_id_2.data(), rights_id.data(), rights_id_2.size());
  978. const auto ticket = Ticket::SynthesizeCommon(key.second, rights_id_2);
  979. common_tickets.insert_or_assign(rights_id, ticket);
  980. }
  981. }
  982. void KeyManager::SetKeyWrapped(S128KeyType id, Key128 key, u64 field1, u64 field2) {
  983. if (key == Key128{}) {
  984. return;
  985. }
  986. SetKey(id, key, field1, field2);
  987. }
  988. void KeyManager::SetKeyWrapped(S256KeyType id, Key256 key, u64 field1, u64 field2) {
  989. if (key == Key256{}) {
  990. return;
  991. }
  992. SetKey(id, key, field1, field2);
  993. }
  994. void KeyManager::PopulateFromPartitionData(PartitionDataManager& data) {
  995. if (!BaseDeriveNecessary()) {
  996. return;
  997. }
  998. if (!data.HasBoot0()) {
  999. return;
  1000. }
  1001. for (size_t i = 0; i < encrypted_keyblobs.size(); ++i) {
  1002. if (encrypted_keyblobs[i] != std::array<u8, 0xB0>{}) {
  1003. continue;
  1004. }
  1005. encrypted_keyblobs[i] = data.GetEncryptedKeyblob(i);
  1006. WriteKeyToFile<0xB0>(KeyCategory::Console, fmt::format("encrypted_keyblob_{:02X}", i),
  1007. encrypted_keyblobs[i]);
  1008. }
  1009. SetKeyWrapped(S128KeyType::Source, data.GetPackage2KeySource(),
  1010. static_cast<u64>(SourceKeyType::Package2));
  1011. SetKeyWrapped(S128KeyType::Source, data.GetAESKekGenerationSource(),
  1012. static_cast<u64>(SourceKeyType::AESKekGeneration));
  1013. SetKeyWrapped(S128KeyType::Source, data.GetTitlekekSource(),
  1014. static_cast<u64>(SourceKeyType::Titlekek));
  1015. SetKeyWrapped(S128KeyType::Source, data.GetMasterKeySource(),
  1016. static_cast<u64>(SourceKeyType::Master));
  1017. SetKeyWrapped(S128KeyType::Source, data.GetKeyblobMACKeySource(),
  1018. static_cast<u64>(SourceKeyType::KeyblobMAC));
  1019. for (size_t i = 0; i < PartitionDataManager::MAX_KEYBLOB_SOURCE_HASH; ++i) {
  1020. SetKeyWrapped(S128KeyType::Source, data.GetKeyblobKeySource(i),
  1021. static_cast<u64>(SourceKeyType::Keyblob), i);
  1022. }
  1023. if (data.HasFuses()) {
  1024. SetKeyWrapped(S128KeyType::SecureBoot, data.GetSecureBootKey());
  1025. }
  1026. DeriveBase();
  1027. Key128 latest_master{};
  1028. for (s8 i = 0x1F; i >= 0; --i) {
  1029. if (GetKey(S128KeyType::Master, static_cast<u8>(i)) != Key128{}) {
  1030. latest_master = GetKey(S128KeyType::Master, static_cast<u8>(i));
  1031. break;
  1032. }
  1033. }
  1034. const auto masters = data.GetTZMasterKeys(latest_master);
  1035. for (size_t i = 0; i < masters.size(); ++i) {
  1036. if (masters[i] != Key128{} && !HasKey(S128KeyType::Master, i)) {
  1037. SetKey(S128KeyType::Master, masters[i], i);
  1038. }
  1039. }
  1040. DeriveBase();
  1041. if (!data.HasPackage2())
  1042. return;
  1043. std::array<Key128, 0x20> package2_keys{};
  1044. for (size_t i = 0; i < package2_keys.size(); ++i) {
  1045. if (HasKey(S128KeyType::Package2, i)) {
  1046. package2_keys[i] = GetKey(S128KeyType::Package2, i);
  1047. }
  1048. }
  1049. data.DecryptPackage2(package2_keys, Package2Type::NormalMain);
  1050. SetKeyWrapped(S128KeyType::Source, data.GetKeyAreaKeyApplicationSource(),
  1051. static_cast<u64>(SourceKeyType::KeyAreaKey),
  1052. static_cast<u64>(KeyAreaKeyType::Application));
  1053. SetKeyWrapped(S128KeyType::Source, data.GetKeyAreaKeyOceanSource(),
  1054. static_cast<u64>(SourceKeyType::KeyAreaKey),
  1055. static_cast<u64>(KeyAreaKeyType::Ocean));
  1056. SetKeyWrapped(S128KeyType::Source, data.GetKeyAreaKeySystemSource(),
  1057. static_cast<u64>(SourceKeyType::KeyAreaKey),
  1058. static_cast<u64>(KeyAreaKeyType::System));
  1059. SetKeyWrapped(S128KeyType::Source, data.GetSDKekSource(),
  1060. static_cast<u64>(SourceKeyType::SDKek));
  1061. SetKeyWrapped(S256KeyType::SDKeySource, data.GetSDSaveKeySource(),
  1062. static_cast<u64>(SDKeyType::Save));
  1063. SetKeyWrapped(S256KeyType::SDKeySource, data.GetSDNCAKeySource(),
  1064. static_cast<u64>(SDKeyType::NCA));
  1065. SetKeyWrapped(S128KeyType::Source, data.GetHeaderKekSource(),
  1066. static_cast<u64>(SourceKeyType::HeaderKek));
  1067. SetKeyWrapped(S256KeyType::HeaderSource, data.GetHeaderKeySource());
  1068. SetKeyWrapped(S128KeyType::Source, data.GetAESKeyGenerationSource(),
  1069. static_cast<u64>(SourceKeyType::AESKeyGeneration));
  1070. DeriveBase();
  1071. }
  1072. const std::map<u128, Ticket>& KeyManager::GetCommonTickets() const {
  1073. return common_tickets;
  1074. }
  1075. const std::map<u128, Ticket>& KeyManager::GetPersonalizedTickets() const {
  1076. return personal_tickets;
  1077. }
  1078. bool KeyManager::AddTicketCommon(Ticket raw) {
  1079. const auto rsa_key = GetETicketRSAKey();
  1080. if (rsa_key == RSAKeyPair<2048>{}) {
  1081. return false;
  1082. }
  1083. const auto pair = ParseTicket(raw, rsa_key);
  1084. if (!pair) {
  1085. return false;
  1086. }
  1087. const auto& [rid, key] = *pair;
  1088. u128 rights_id;
  1089. std::memcpy(rights_id.data(), rid.data(), rid.size());
  1090. common_tickets[rights_id] = raw;
  1091. SetKey(S128KeyType::Titlekey, key, rights_id[1], rights_id[0]);
  1092. return true;
  1093. }
  1094. bool KeyManager::AddTicketPersonalized(Ticket raw) {
  1095. const auto rsa_key = GetETicketRSAKey();
  1096. if (rsa_key == RSAKeyPair<2048>{}) {
  1097. return false;
  1098. }
  1099. const auto pair = ParseTicket(raw, rsa_key);
  1100. if (!pair) {
  1101. return false;
  1102. }
  1103. const auto& [rid, key] = *pair;
  1104. u128 rights_id;
  1105. std::memcpy(rights_id.data(), rid.data(), rid.size());
  1106. common_tickets[rights_id] = raw;
  1107. SetKey(S128KeyType::Titlekey, key, rights_id[1], rights_id[0]);
  1108. return true;
  1109. }
  1110. } // namespace Core::Crypto