Lockpick_RCM payload - Official Thread


Description

Lockpick_RCM is a bare metal Nintendo Switch payload that derives encryption keys for use in Switch file handling software like hactool, hactoolnet/LibHac, ChoiDujour, etc. without booting Horizon OS.

Source: https://github.com/shchmue/Lockpick_RCM
Payload: https://github.com/shchmue/Lockpick_RCM/releases

Due to changes imposed by firmware 7.0.0, Lockpick homebrew can no longer derive the latest keys. In the boot-time environment however, there are fewer limitations. That means the new keys are finally easy to dump!

Usage
  • Launch Lockpick_RCM.bin using your favorite payload injector or chainload from Hekate by placing it in /bootloader/payloads
  • Upon completion, keys will be saved to /switch/prod.keys on SD
  • If the console has Firmware 7.x, the /sept/ folder from Atmosphère or Kosmos release zip containing both sept-primary.bin and sept-secondary.enc must be present on SD or else only keyblob master key derivation is possible (ie. up to master_key_05 only)
Big thanks to CTCaer
For Hekate and all the advice while developing this!

Known Issues
  • Chainloading from SX will hang immediately due to quirks in their hwinit code, please launch payload directly
 

Attachments

  • AB1248EA-8BB9-448B-83F5-FF68C2579FB1.jpeg
    AB1248EA-8BB9-448B-83F5-FF68C2579FB1.jpeg
    11.2 KB · Views: 0
Last edited by shchmue,
I thought that there was no need to update Lockpick any further?
there isn't a need for it other than consistency;

it has a feature for dumping the latest keys regardless if its updated or not; but one can keep it up to date despite that.

it's more of a fallback feature i added incase for whatever reason it becomes DMCA target by nintendo again (although the original DMCA takedown was false, not filed by nintendo or legal firm representing nintendo)
 
some tools like hactool need you have a local copy of the keys on your hard drive and lockpick is a easy and quick way to get them
Doesn't hactool have a built in keygenerator yet? It should get modded to just drag a firmware folder onto it and build a keyfile. Maybe that would be a good feature and relatively easy to add.
 
Doesn't hactool have a built in keygenerator yet? It should get modded to just drag a firmware folder onto it and build a keyfile. Maybe that would be a good feature and relatively easy to add.
That is a cool idea, the repo is public, nothing stop you to make the pr. thanks.
 
That is a cool idea, the repo is public, nothing stop you to make the pr. thanks.
I already have a working windows keygen (and all the new keys) so no need for me to make it, but obviously it can't be shared on here due to the rules, but yes you're correct and I could implement it if I wanted, I just wondered if it's already been done or not.
 
Doesn't hactool have a built in keygenerator yet? It should get modded to just drag a firmware folder onto it and build a keyfile. Maybe that would be a good feature and relatively easy to add.
my version of hactool is capable of that: https://github.com/borntohonk/hactool/blob/master/pk11_extract_key_sources.c
I more or less just copied my other work for the lockpick change that does more or less the same.
I already have a working windows keygen (and all the new keys) so no need for me to make it, but obviously it can't be shared on here due to the rules, but yes you're correct and I could implement it if I wanted, I just wondered if it's already been done or not.
i have an universal pure python library capable of it, as well as automatically deriving keys from input firmware files
https://github.com/borntohonk/Switch-Ghidra-Guides/blob/master/scripts/process_firmware.py#L164-L199

and yes it has already been done, just as you describe, but i will consider adding a sub-command specifically for taking firmware input and outputting new keyset into hactool as well
 
my version of hactool is capable of that: https://github.com/borntohonk/hactool/blob/master/pk11_extract_key_sources.c
I more or less just copied my other work for the lockpick change that does more or less the same.
:wub::wub::wub:

i have an universal pure python library capable of it, as well as automatically deriving keys from input firmware files
https://github.com/borntohonk/Switch-Ghidra-Guides/blob/master/scripts/process_firmware.py#L164-L199

and yes it has already been done, just as you describe, but i will consider adding a sub-command specifically for taking firmware input and outputting new keyset into hactool as well
Wow, that is nice, and will be great to have the parameters to read a folder and extract the pod.keys.

We will never be able to thank you enough.
 
:wub::wub::wub:


Wow, that is nice, and will be great to have the parameters to read a folder and extract the pod.keys.

We will never be able to thank you enough.
https://github.com/borntohonk/hactool/releases/tag/1.5.4

I updated hactool to be able to produce latest keyset from input firmware folder files



ex:
hactool -t keygen path_to_firmware_folder --keys prod.keys


--keys being optional argument, defaults to ~/.switch/prod.keys (C:/user/YourUser/.switch/prod.keys // /home/YourUser/.switch/prod.keys)
 
https://github.com/borntohonk/hactool/releases/tag/1.5.4

I updated hactool to be able to produce latest keyset from input firmware folder files



ex:
hactool -t keygen path_to_firmware_folder --keys prod.keys


--keys being optional argument, defaults to ~/.switch/prod.keys (C:/user/YourUser/.switch/prod.keys // /home/YourUser/.switch/prod.keys)
You should make a static build because this throws an error about libcapstone.dll being missing. Also you probably should cross compile on linux to make the exe size far smaller as this looks like it was compiled on windows. Generally cross compiled on linux exe's are very much smaller.
 
  • Like
Reactions: bth
You should make a static build because this throws an error about libcapstone.dll being missing. Also you probably should cross compile on linux to make the exe size far smaller as this looks like it was compiled on windows. Generally cross compiled on linux exe's are very much smaller.
rename your capstone.dll to libcapstone.dll
 
rename your capstone.dll to libcapstone.dll
No i don't think I will be renaming anything, I already have a keygen working which is just over 100kb so I don't need this. Not that I don't appreciate the effort, but there's no need for that capstone library at all.
 
No i don't think I will be renaming anything, I already have a keygen working which is just over 100kb so I don't need this. Not that I don't appreciate the effort, but there's no need for that capstone library at all.
I only provide an alt solution that worked for me, use it or not is your choice
 
You should make a static build because this throws an error about libcapstone.dll being missing. Also you probably should cross compile on linux to make the exe size far smaller as this looks like it was compiled on windows. Generally cross compiled on linux exe's are very much smaller.
I re-did the binaries to only do the parts of libcapstone we care about while at it, and static linked them

https://github.com/borntohonk/hactool/commit/b759a8a94177be42981835e75756bae5427672c3 (quick change to do both x64 and arm64 macos outputs)
https://github.com/borntohonk/hactool/releases/tag/1.5.4 (re-released with new change)


(the capstone dependency is kind of silly and just for one feature; which is used in conjuction with the -t swipc output)
(hactool -t findpatterns)

all it does is output the pattern diffs as arm instructions ex:



Code:
hactool -t findpatterns --batch=patch_database/swipc_patches.json

=== [es] out/programs/ETicket_services (0xF47E8 bytes) ===
    Build ID: 702CD302FB341300BB1D69C96C7FC66FB80BE599
    IPS out:  out/exefs_patches/es_patches/702CD302FB341300BB1D69C96C7FC66FB80BE599.ips
  Rule[0]: "A0630091????FE97A08300D1????FE97"  patch -> "E0031FAA" offset=16 matchpos=0
    1 match:
    [0] 0x0004E678: A0 63 00 91 39 CF FE 97 A0 83 00 D1 5B D4 FE 97
       0x0004E658:  mov        w8, #0x2e91
       0x0004E65C:  csel       w8, wzr, w8, eq
       0x0004E660:  cmp        w0, #0
       0x0004E664:  csel       w19, w8, w0, eq
       0x0004E668:  b          #0x4e670
       0x0004E66C:  mov        w19, wzr
       0x0004E670:  add        x0, sp, #0x1c
       0x0004E674:  bl         #0x8bd80
    => 0x0004E678:  add        x0, x29, #0x18
    => 0x0004E67C:  bl         #0x2360
    => 0x0004E680:  sub        x0, x29, #0x20
    => 0x0004E684:  bl         #0x37f0
       0x0004E688:  mov        w0, w19
       0x0004E68C:  ldp        x20, x19, [sp, #0x120]
       0x0004E690:  ldr        x28, [sp, #0x110]
       0x0004E694:  ldp        x29, x30, [sp, #0x100]
       0x0004E698:  add        sp, sp, #0x130
       0x0004E69C:  ret       
       0x0004E6A0:  mov        w19, #0x491
       0x0004E6A4:  b          #0x4e678
       0x0004E6A8:  mov        w19, #0x4891
       0x0004E6AC:  movk       w19, #0x3f, lsl #16
       0x0004E6B0:  b          #0x4e678
       0x0004E6B4:  mov        w19, #0x291
       0x0004E6B8:  b          #0x4e670
       0x0004E6BC:  udf        #0
       0x0004E6C0:  stp        x29, x30, [sp, #-0x40]!
       0x0004E6C4:  stp        x28, x23, [sp, #0x10]
    Using match[0] 0x0004E678, patch at 0x0004E688 (+16)
Wrote IPS patch file "out/exefs_patches/es_patches/702CD302FB341300BB1D69C96C7FC66FB80BE599.ips" (1 record)
 
Last edited by bth,
I re-did the binaries to only do the parts of libcapstone we care about while at it, and static linked them

https://github.com/borntohonk/hactool/commit/b759a8a94177be42981835e75756bae5427672c3 (quick change to do both x64 and arm64 macos outputs)
https://github.com/borntohonk/hactool/releases/tag/1.5.4 (re-released with new change)


(the capstone dependency is kind of silly and just for one feature; which is used in conjuction with the -t swipc output)
(hactool -t findpatterns)

all it does is output the pattern diffs as arm instructions ex:



Code:
hactool -t findpatterns --batch=patch_database/swipc_patches.json

=== [es] out/programs/ETicket_services (0xF47E8 bytes) ===
    Build ID: 702CD302FB341300BB1D69C96C7FC66FB80BE599
    IPS out:  out/exefs_patches/es_patches/702CD302FB341300BB1D69C96C7FC66FB80BE599.ips
  Rule[0]: "A0630091????FE97A08300D1????FE97"  patch -> "E0031FAA" offset=16 matchpos=0
    1 match:
    [0] 0x0004E678: A0 63 00 91 39 CF FE 97 A0 83 00 D1 5B D4 FE 97
       0x0004E658:  mov        w8, #0x2e91
       0x0004E65C:  csel       w8, wzr, w8, eq
       0x0004E660:  cmp        w0, #0
       0x0004E664:  csel       w19, w8, w0, eq
       0x0004E668:  b          #0x4e670
       0x0004E66C:  mov        w19, wzr
       0x0004E670:  add        x0, sp, #0x1c
       0x0004E674:  bl         #0x8bd80
    => 0x0004E678:  add        x0, x29, #0x18
    => 0x0004E67C:  bl         #0x2360
    => 0x0004E680:  sub        x0, x29, #0x20
    => 0x0004E684:  bl         #0x37f0
       0x0004E688:  mov        w0, w19
       0x0004E68C:  ldp        x20, x19, [sp, #0x120]
       0x0004E690:  ldr        x28, [sp, #0x110]
       0x0004E694:  ldp        x29, x30, [sp, #0x100]
       0x0004E698:  add        sp, sp, #0x130
       0x0004E69C:  ret     
       0x0004E6A0:  mov        w19, #0x491
       0x0004E6A4:  b          #0x4e678
       0x0004E6A8:  mov        w19, #0x4891
       0x0004E6AC:  movk       w19, #0x3f, lsl #16
       0x0004E6B0:  b          #0x4e678
       0x0004E6B4:  mov        w19, #0x291
       0x0004E6B8:  b          #0x4e670
       0x0004E6BC:  udf        #0
       0x0004E6C0:  stp        x29, x30, [sp, #-0x40]!
       0x0004E6C4:  stp        x28, x23, [sp, #0x10]
    Using match[0] 0x0004E678, patch at 0x0004E688 (+16)
Wrote IPS patch file "out/exefs_patches/es_patches/702CD302FB341300BB1D69C96C7FC66FB80BE599.ips" (1 record)
Thanks, that's working without needing to provide any dll files now.

I static linked/compiled the version you posted yesterday and was able to generate keys no problem, but in the new release you posted today i am getting this output when testing the keygen feature:

Version from yesterday
Code:
[WARN] prod.keys does not exist.
[keygen] Scanning firmware NCAs in: firm
[keygen] Found System Version NCA: 2377a6f36c2cc42c121cad2ffac236a9.nca (Master Key Revision 16)
[keygen] Found FS Data NCA: 4c9cf6825c1861680abed1fdace7eecf.nca
[keygen] Firmware Master Key Revision: 16 (23.0.0-)
[keygen] Extracted nx/package1 (0x2f440 bytes)
[keygen] no new keys detected, writing to file at out.txt
[keygen] Wrote complete keyset to out.txt
Done!

Version from today
Code:
[WARN] prod.keys does not exist.
[keygen] Scanning firmware NCAs in: firm
[keygen] Found System Version NCA: 2377a6f36c2cc42c121cad2ffac236a9.nca (Master Key Revision 16)
[keygen] Found FS Data NCA: 4c9cf6825c1861680abed1fdace7eecf.nca
[keygen] Firmware Master Key Revision: 16 (23.0.0-)
[keygen] Extracted nx/package1 (0x2f440 bytes)
[keygen] no new keys detected, writing to file at prod.keys
[keygen] Error: failed to render keyset for writing
Done!

Did you change some code on writing the output file if it doesn't exist?
 
Last edited by snuffbot1,

Site & Scene News

Popular threads in this forum