public void Load(System.IO.Stream stream) { string homeFolder = Environment.GetFolderPath(Environment.SpecialFolder.UserProfile); string KeyFile = Path.Combine(homeFolder, ".switch", "prod.keys"); string TitleKeyFile = Path.Combine(homeFolder, ".switch", "title.keys"); var Keys = ExternalKeys.ReadKeyFile(KeyFile, TitleKeyFile); Stream Input; var Pfs = new Pfs(stream.AsStorage()); var CnmtNca = new Nca(Keys, Pfs.OpenFile(Pfs.Files.FirstOrDefault(s => s.Name.Contains(".cnmt.nca"))), false); var CnmtPfs = new Pfs(CnmtNca.OpenSection(0, false, IntegrityCheckLevel.None, true)); var Cnmt = new Cnmt(CnmtPfs.OpenFile(CnmtPfs.Files[0]).AsStream()); var Program = Cnmt.ContentEntries.FirstOrDefault(c => c.Type == CnmtContentType.Program); var CtrlEntry = Cnmt.ContentEntries.FirstOrDefault(c => c.Type == CnmtContentType.Control); if (CtrlEntry != null) { Control = new Nca(Keys, Pfs.OpenFile($"{CtrlEntry.NcaId.ToHexString().ToLower()}.nca"), false); } Input = Pfs.OpenFile($"{Program.NcaId.ToHexString().ToLower()}.nca").AsStream(); var Nca = new Nca(Keys, Input.AsStorage(), true); Romfs romfs = new Romfs( Nca.OpenSection(Nca.Sections.FirstOrDefault (s => s?.Type == SectionType.Romfs || s?.Type == SectionType.Bktr) .SectionNum, false, IntegrityCheckLevel.None, true)); for (int i = 0; i < romfs.Files.Count; i++) { files.Add(new FileEntry(romfs, romfs.Files[i])); } }
public static void ExtractSection(this Nca nca, int index, string outputDir, bool verify = false, IProgressReport logger = null) { if (index < 0 || index > 3) { throw new IndexOutOfRangeException(); } if (nca.Sections[index] == null) { return; } NcaSection section = nca.Sections[index]; Stream stream = nca.OpenSection(index, false, verify); switch (section.Type) { case SectionType.Invalid: break; case SectionType.Pfs0: var pfs0 = new Pfs(stream); pfs0.Extract(outputDir, logger); break; case SectionType.Romfs: var romfs = new Romfs(stream); romfs.Extract(outputDir, logger); break; case SectionType.Bktr: break; } }
private long OpenNcaFs(ServiceCtx context, string ncaPath, LibHac.IO.IStorage ncaStorage) { Nca nca = new Nca(context.Device.System.KeySet, ncaStorage, false); NcaSection romfsSection = nca.Sections.FirstOrDefault(x => x?.Type == SectionType.Romfs); NcaSection pfsSection = nca.Sections.FirstOrDefault(x => x?.Type == SectionType.Pfs0); if (romfsSection != null) { LibHac.IO.IStorage romfsStorage = nca.OpenSection(romfsSection.SectionNum, false, context.Device.System.FsIntegrityCheckLevel, false); IFileSystem ncaFileSystem = new IFileSystem(ncaPath, new RomFsProvider(romfsStorage)); MakeObject(context, ncaFileSystem); } else if (pfsSection != null) { LibHac.IO.IStorage pfsStorage = nca.OpenSection(pfsSection.SectionNum, false, context.Device.System.FsIntegrityCheckLevel, false); Pfs pfs = new Pfs(pfsStorage); IFileSystem ncaFileSystem = new IFileSystem(ncaPath, new PFsProvider(pfs)); MakeObject(context, ncaFileSystem); } else { return(MakeError(ErrorModule.Fs, FsErr.PartitionNotFound)); } return(0); }
private long OpenNcaFs(ServiceCtx Context, string NcaPath, Stream NcaStream) { Nca Nca = new Nca(Context.Device.System.KeySet, NcaStream, false); NcaSection RomfsSection = Nca.Sections.FirstOrDefault(x => x?.Type == SectionType.Romfs); NcaSection PfsSection = Nca.Sections.FirstOrDefault(x => x?.Type == SectionType.Pfs0); if (RomfsSection != null) { Stream RomfsStream = Nca.OpenSection(RomfsSection.SectionNum, false, Context.Device.System.FsIntegrityCheckLevel); IFileSystem NcaFileSystem = new IFileSystem(NcaPath, new RomFsProvider(RomfsStream)); MakeObject(Context, NcaFileSystem); } else if (PfsSection != null) { Stream PfsStream = Nca.OpenSection(PfsSection.SectionNum, false, Context.Device.System.FsIntegrityCheckLevel); Pfs Pfs = new Pfs(PfsStream); IFileSystem NcaFileSystem = new IFileSystem(NcaPath, new PFsProvider(Pfs)); MakeObject(Context, NcaFileSystem); } else { return(MakeError(ErrorModule.Fs, FsErr.PartitionNotFound)); } return(0); }
private long OpenFileSystemFromInternalFile(ServiceCtx context, string fullPath) { DirectoryInfo archivePath = new DirectoryInfo(fullPath).Parent; while (string.IsNullOrWhiteSpace(archivePath.Extension)) { archivePath = archivePath.Parent; } if (archivePath.Extension == ".nsp" && File.Exists(archivePath.FullName)) { FileStream pfsFile = new FileStream( archivePath.FullName.TrimEnd(Path.DirectorySeparatorChar), FileMode.Open, FileAccess.Read); Pfs nsp = new Pfs(pfsFile.AsStorage()); ImportTitleKeysFromNsp(nsp, context.Device.System.KeySet); string filename = fullPath.Replace(archivePath.FullName, string.Empty).TrimStart('\\'); if (nsp.FileExists(filename)) { return(OpenNcaFs(context, fullPath, nsp.OpenFile(filename))); } } return(MakeError(ErrorModule.Fs, FsErr.PathDoesNotExist)); }
public void Load(System.IO.Stream stream) { var Keys = Forms.SwitchKeySelectionForm.ShowKeySelector(); if (Keys == null) { throw new Exception("Failed to get keys. Please select valid paths!"); } var Nca = new Nca(Keys, stream.AsStorage(), true); Romfs romfs = new Romfs( Nca.OpenSection(Nca.Sections.FirstOrDefault (s => s?.Type == SectionType.Romfs || s?.Type == SectionType.Bktr) .SectionNum, false, IntegrityCheckLevel.None, true)); if (Nca.CanOpenSection((int)ProgramPartitionType.Code)) { var exefs = new Pfs(Nca.OpenSection((int)ProgramPartitionType.Code, false, IntegrityCheckLevel.None, true)); foreach (var file in exefs.Files) { files.Add(new NSP.ExefsEntry(exefs, file)); } } for (int i = 0; i < romfs.Files.Count; i++) { files.Add(new NSP.FileEntry(romfs, romfs.Files[i])); } }
private static string Print(this Pfs pfs) { const int colLen = 36; const int fileNameLen = 39; var sb = new StringBuilder(); sb.AppendLine(); sb.AppendLine("PFS0:"); PrintItem(sb, colLen, "Magic:", pfs.Header.Magic); PrintItem(sb, colLen, "Number of files:", pfs.Header.NumFiles); for (int i = 0; i < pfs.Files.Length; i++) { PfsFileEntry file = pfs.Files[i]; string label = i == 0 ? "Files:" : ""; string offsets = $"{file.Offset:x12}-{file.Offset + file.Size:x12}{file.HashValidity.GetValidityString()}"; string data = $"pfs0:/{file.Name}".PadRight(fileNameLen) + offsets; PrintItem(sb, colLen, label, data); } return(sb.ToString()); }
public void Load(System.IO.Stream stream) { var Keys = Forms.SwitchKeySelectionForm.ShowKeySelector(); if (Keys == null) { throw new Exception("Failed to get keys. Please select valid paths!"); } var Pfs = new Pfs(stream.AsStorage()); var CnmtNca = new Nca(Keys, Pfs.OpenFile(Pfs.Files.FirstOrDefault(s => s.Name.Contains(".cnmt.nca"))), false); var CnmtPfs = new Pfs(CnmtNca.OpenSection(0, false, IntegrityCheckLevel.None, true)); var Cnmt = new Cnmt(CnmtPfs.OpenFile(CnmtPfs.Files[0]).AsStream()); foreach (var entry in Cnmt.ContentEntries) { if (entry.Type == CnmtContentType.Program) { var Program = entry; string ncaFileName = $"{Program.NcaId.ToHexString().ToLower()}.nca"; Stream Input = Pfs.OpenFile(ncaFileName).AsStream(); var Nca = new Nca(Keys, Input.AsStorage(), true); string root = Nca.Header.TitleId.ToString("X"); Romfs romfs = new Romfs( Nca.OpenSection(Nca.Sections.FirstOrDefault (s => s?.Type == SectionType.Romfs || s?.Type == SectionType.Bktr) .SectionNum, false, IntegrityCheckLevel.None, true)); if (Nca.CanOpenSection((int)ProgramPartitionType.Code)) { var exefs = new Pfs(Nca.OpenSection((int)ProgramPartitionType.Code, false, IntegrityCheckLevel.None, true)); foreach (var file in exefs.Files) { files.Add(new ExefsEntry(exefs, file, root)); } } for (int i = 0; i < romfs.Files.Count; i++) { files.Add(new FileEntry(romfs, romfs.Files[i], root)); } } } var CtrlEntry = Cnmt.ContentEntries.FirstOrDefault(c => c.Type == CnmtContentType.Control); if (CtrlEntry != null) { Control = new Nca(Keys, Pfs.OpenFile($"{CtrlEntry.NcaId.ToHexString().ToLower()}.nca"), false); } }
public ExefsEntry(Pfs pfs, PfsFileEntry entry, string root = "") : base(pfs, entry) { if (root != string.Empty) { FileName = $"{root}/Exefs/{entry.Name}"; } else { FileName = $"Exefs/{entry.Name}"; } }
private void ImportTitleKeysFromNsp(Pfs nsp, Keyset keySet) { foreach (PfsFileEntry ticketEntry in nsp.Files.Where(x => x.Name.EndsWith(".tik"))) { Ticket ticket = new Ticket(nsp.OpenFile(ticketEntry).AsStream()); if (!keySet.TitleKeys.ContainsKey(ticket.RightsId)) { keySet.TitleKeys.Add(ticket.RightsId, ticket.GetTitleKey(keySet)); } } }
private void DrawPfsPages(PaintEventArgs e) { if (Pfs != null) { for (var i = 0; i < (VisibleExtents * 8) && i + (WindowPosition * 8) < ExtentCount * 8; i++) { var pageId = i + (WindowPosition * 8); pfsRenderer.DrawPfsPage(e.Graphics, PagePosition(i), Pfs.PagePfsByte(pageId)); } } }
public static void Process(Context ctx) { using (var file = new FileStream(ctx.Options.InFile, FileMode.Open, FileAccess.Read)) { Pfs pfs = new Pfs(file); ctx.Logger.LogMessage(pfs.Print()); if (ctx.Options.OutDir != null) { pfs.Extract(ctx.Options.OutDir, ctx.Logger); } } }
private long OpenNsp(ServiceCtx context, string pfsPath) { FileStream pfsFile = new FileStream(pfsPath, FileMode.Open, FileAccess.Read); Pfs nsp = new Pfs(pfsFile.AsStorage()); ImportTitleKeysFromNsp(nsp, context.Device.System.KeySet); IFileSystem nspFileSystem = new IFileSystem(pfsPath, new PFsProvider(nsp)); MakeObject(context, nspFileSystem); return(0); }
public void LoadNsp(string NspFile) { FileStream File = new FileStream(NspFile, FileMode.Open, FileAccess.Read); Pfs Nsp = new Pfs(File); PfsFileEntry TicketFile = Nsp.Files.FirstOrDefault(x => x.Name.EndsWith(".tik")); // Load title key from the NSP's ticket in case the user doesn't have a title key file if (TicketFile != null) { // todo Change when Ticket(Stream) overload is added Ticket Ticket = new Ticket(new BinaryReader(Nsp.OpenFile(TicketFile))); KeySet.TitleKeys[Ticket.RightsId] = Ticket.GetTitleKey(KeySet); } Nca MainNca = null; Nca ControlNca = null; foreach (PfsFileEntry NcaFile in Nsp.Files.Where(x => x.Name.EndsWith(".nca"))) { Nca Nca = new Nca(KeySet, Nsp.OpenFile(NcaFile), true); if (Nca.Header.ContentType == ContentType.Program) { MainNca = Nca; } else if (Nca.Header.ContentType == ContentType.Control) { ControlNca = Nca; } } if (MainNca != null) { LoadNca(MainNca, ControlNca); return; } Device.Log.PrintError(LogClass.Loader, "Could not find an Application NCA in the provided NSP file"); }
public void LoadNsp(string nspFile) { FileStream file = new FileStream(nspFile, FileMode.Open, FileAccess.Read); Pfs nsp = new Pfs(file); PfsFileEntry ticketFile = nsp.Files.FirstOrDefault(x => x.Name.EndsWith(".tik")); // Load title key from the NSP's ticket in case the user doesn't have a title key file if (ticketFile != null) { Ticket ticket = new Ticket(nsp.OpenFile(ticketFile)); KeySet.TitleKeys[ticket.RightsId] = ticket.GetTitleKey(KeySet); } Nca mainNca = null; Nca controlNca = null; foreach (PfsFileEntry ncaFile in nsp.Files.Where(x => x.Name.EndsWith(".nca"))) { Nca nca = new Nca(KeySet, nsp.OpenFile(ncaFile), true); if (nca.Header.ContentType == ContentType.Program) { mainNca = nca; } else if (nca.Header.ContentType == ContentType.Control) { controlNca = nca; } } if (mainNca != null) { LoadNca(mainNca, controlNca); return; } Logger.PrintError(LogClass.Loader, "Could not find an Application NCA in the provided NSP file"); }
public void LoadNsp(string nspFile) { FileStream file = new FileStream(nspFile, FileMode.Open, FileAccess.Read); Pfs nsp = new Pfs(file.AsStorage(false)); foreach (PfsFileEntry ticketEntry in nsp.Files.Where(x => x.Name.EndsWith(".tik"))) { Ticket ticket = new Ticket(nsp.OpenFile(ticketEntry).AsStream()); if (!KeySet.TitleKeys.ContainsKey(ticket.RightsId)) { KeySet.TitleKeys.Add(ticket.RightsId, ticket.GetTitleKey(KeySet)); } } Nca mainNca = null; Nca controlNca = null; foreach (PfsFileEntry ncaFile in nsp.Files.Where(x => x.Name.EndsWith(".nca"))) { Nca nca = new Nca(KeySet, nsp.OpenFile(ncaFile), true); if (nca.Header.ContentType == ContentType.Program) { mainNca = nca; } else if (nca.Header.ContentType == ContentType.Control) { controlNca = nca; } } if (mainNca != null) { LoadNca(mainNca, controlNca); return; } Logger.PrintError(LogClass.Loader, "Could not find an Application NCA in the provided NSP file"); }
private long OpenNsp(ServiceCtx context, string pfsPath) { FileStream pfsFile = new FileStream(pfsPath, FileMode.Open, FileAccess.Read); Pfs nsp = new Pfs(pfsFile); PfsFileEntry ticketFile = nsp.Files.FirstOrDefault(x => x.Name.EndsWith(".tik")); if (ticketFile != null) { Ticket ticket = new Ticket(nsp.OpenFile(ticketFile)); context.Device.System.KeySet.TitleKeys[ticket.RightsId] = ticket.GetTitleKey(context.Device.System.KeySet); } IFileSystem nspFileSystem = new IFileSystem(pfsPath, new PFsProvider(nsp)); MakeObject(context, nspFileSystem); return(0); }
private long OpenNsp(ServiceCtx Context, string PfsPath) { FileStream PfsFile = new FileStream(PfsPath, FileMode.Open, FileAccess.Read); Pfs Nsp = new Pfs(PfsFile); PfsFileEntry TicketFile = Nsp.Files.FirstOrDefault(x => x.Name.EndsWith(".tik")); if (TicketFile != null) { Ticket Ticket = new Ticket(Nsp.OpenFile(TicketFile)); Context.Device.System.KeySet.TitleKeys[Ticket.RightsId] = Ticket.GetTitleKey(Context.Device.System.KeySet); } IFileSystem NspFileSystem = new IFileSystem(PfsPath, new PFsProvider(Nsp)); MakeObject(Context, NspFileSystem); return(0); }
private long OpenFileSystemFromInternalFile(ServiceCtx context, string fullPath) { DirectoryInfo archivePath = new DirectoryInfo(fullPath).Parent; while (string.IsNullOrWhiteSpace(archivePath.Extension)) { archivePath = archivePath.Parent; } if (archivePath.Extension == ".nsp" && File.Exists(archivePath.FullName)) { FileStream pfsFile = new FileStream( archivePath.FullName.TrimEnd(Path.DirectorySeparatorChar), FileMode.Open, FileAccess.Read); Pfs nsp = new Pfs(pfsFile); PfsFileEntry ticketFile = nsp.Files.FirstOrDefault(x => x.Name.EndsWith(".tik")); if (ticketFile != null) { Ticket ticket = new Ticket(nsp.OpenFile(ticketFile)); context.Device.System.KeySet.TitleKeys[ticket.RightsId] = ticket.GetTitleKey(context.Device.System.KeySet); } string filename = fullPath.Replace(archivePath.FullName, string.Empty).TrimStart('\\'); if (nsp.FileExists(filename)) { return(OpenNcaFs(context, fullPath, nsp.OpenFile(filename))); } } return(MakeError(ErrorModule.Fs, FsErr.PathDoesNotExist)); }
private long OpenFileSystemFromInternalFile(ServiceCtx Context, string FullPath) { DirectoryInfo ArchivePath = new DirectoryInfo(FullPath).Parent; while (string.IsNullOrWhiteSpace(ArchivePath.Extension)) { ArchivePath = ArchivePath.Parent; } if (ArchivePath.Extension == ".nsp" && File.Exists(ArchivePath.FullName)) { FileStream PfsFile = new FileStream( ArchivePath.FullName.TrimEnd(Path.DirectorySeparatorChar), FileMode.Open, FileAccess.Read); Pfs Nsp = new Pfs(PfsFile); PfsFileEntry TicketFile = Nsp.Files.FirstOrDefault(x => x.Name.EndsWith(".tik")); if (TicketFile != null) { Ticket Ticket = new Ticket(Nsp.OpenFile(TicketFile)); Context.Device.System.KeySet.TitleKeys[Ticket.RightsId] = Ticket.GetTitleKey(Context.Device.System.KeySet); } string Filename = FullPath.Replace(ArchivePath.FullName, string.Empty).TrimStart('\\'); if (Nsp.FileExists(Filename)) { return(OpenNcaFs(Context, FullPath, Nsp.OpenFile(Filename))); } } return(MakeError(ErrorModule.Fs, FsErr.PathDoesNotExist)); }
public PartEntry(Pfs pfs, PfsFileEntry entry) { ParentPfs = pfs; fileEntry = entry; FileName = fileEntry.Name; }
static void Main(string[] args) { Console.WriteLine("Nintendo Switch NSP Verifier v1.00"); Console.WriteLine("Copyright 2018 CaitSith2"); Console.WriteLine(""); _path = args.Length >= 1 ? string.Join(" ", args) : Environment.CurrentDirectory; if (new[] { "--help", "-h" }.Any(x => x.Equals(_path, StringComparison.InvariantCultureIgnoreCase))) { Console.WriteLine("Usage: NSPVerify [path to NSP directory]"); Console.WriteLine(""); Console.WriteLine("If the tool is run without specifying a path, it will look for NSPs in the current directory and ALL sub-directories of current directory"); return; } if (!Directory.Exists(_path)) { Console.WriteLine("ERROR: Specified directory does not exist. specify --help for usage information."); return; } var fs = new FileSystem(_path); var keys = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.UserProfile), ".switch", "prod.keys"); if (File.Exists("keys.txt")) { keys = "keys.txt"; } if (!File.Exists(keys)) { Console.WriteLine($"Cannot verify NSPs without keys.txt. Either put it in the same directory as this tool,"); Console.WriteLine($"or place it in \"{Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.UserProfile), ".switch")}\" named as prod.keys"); PressAnyKey(); return; } var keyset = ExternalKeys.ReadKeyFile(keys); var badlist = new List <string>(); var exceptionlist = new List <string>(); var files = fs.GetFileSystemEntries("", "*.nsp", SearchOption.AllDirectories).ToList(); files.AddRange(fs.GetFileSystemEntries("", "*.nsx", SearchOption.AllDirectories)); if (files.Count == 0) { Console.WriteLine("Error: No NSP/NSX files in specified directory"); PressAnyKey(); return; } foreach (var file in files) { var filename = Path.GetFileName(file); var relativefilename = Util.GetRelativePath(file, Path.GetFullPath(_path)); Console.Write($"Checking {filename}: "); try { bool ok = true; using (var nspfile = fs.OpenFile(file, FileMode.Open, FileAccess.Read)) { var nspdata = new Pfs(nspfile); var cnmtfile = nspdata.Files.FirstOrDefault(x => x.Name.ToLowerInvariant().EndsWith(".cnmt.nca")); if (cnmtfile == null) { Console.WriteLine($"\rChecking {filename}: No cnmt.nca file present"); badlist.Add(relativefilename); continue; } var cnmtdata = nspdata.OpenFile(cnmtfile); Cnmt cnmt; using (var sr = new BinaryReader(cnmtdata)) { var cnmthash = SHA256.Create().ComputeHash(sr.ReadBytes((int)cnmtdata.Length)); if (!cnmtfile.Name.ToLowerInvariant().Contains(cnmthash.Take(16).ToArray().ToHexString())) { //Put failure here Console.WriteLine($"\rChecking {filename}: cnmt.nca file is corrupted"); badlist.Add(relativefilename); cnmtdata.Dispose(); continue; } cnmtdata.Position = 0; var cnmtnca = new Nca(keyset, cnmtdata, false); var section = cnmtnca.OpenSection(0, false); var sectionpfs = new Pfs(section); cnmt = new Cnmt(sectionpfs.OpenFile(sectionpfs.Files[0])); } foreach (var entry in cnmt.ContentEntries) { var entryfile = nspdata.Files.FirstOrDefault(x => x.Name.ToLowerInvariant().EndsWith(entry.NcaId.ToHexString() + ".nca")); if (entryfile == null) { if (entry.Type != CnmtContentType.UpdatePatch) { //Put failure here Console.WriteLine($"\rChecking {filename}: one of the entries required by the cnmt.nca is missing."); badlist.Add(relativefilename); break; } continue; } using (var entrynca = nspdata.OpenFile(entryfile)) { var hash = SHA256.Create(); using (var sr = new BinaryReader(entrynca)) { while (entrynca.Length != entrynca.Position) { var entryncadata = sr.ReadBytes(0x100000); hash.TransformBlock(entryncadata, 0, entryncadata.Length, entryncadata, 0); Console.Write($"\rChecking {filename}: {((entrynca.Position * 100.0) / entrynca.Length):0.0}%"); } hash.TransformFinalBlock(new byte[0], 0, 0); } if (hash.Hash.ToHexString().Equals(entry.Hash.ToHexString())) { Console.Write($"\rChecking {filename}: {100:0.0}%"); continue; } //Put failure here Console.WriteLine($"\rChecking {filename}: one of the entries required by the cnmt.nca is corrupted"); badlist.Add(relativefilename); ok = false; break; } } if (ok) { Console.WriteLine($"\rChecking {filename}: OK "); } //Put Success here } } catch (Exception ex) { Console.WriteLine(ex.Message); Console.WriteLine(ex.StackTrace); exceptionlist.Add($"{relativefilename}{Environment.NewLine}Exception: \"{ex.GetType()}\" {ex.Message}{Environment.NewLine}Stack Trace: {ex.StackTrace}{Environment.NewLine}"); } } badlist.Insert(0, badlist.Count == 0 ? "None of the files are corrupted. :)" : "The following NSP/NSX files are corrupted:"); exceptionlist.Insert(0, exceptionlist.Count == 0 ? "No exceptions to log. :)" : "Exceptions caused while parsing the following NSP/NSX files:"); try { File.WriteAllText("Corrupted NSPs.txt", string.Join(Environment.NewLine, badlist)); File.WriteAllText("Exception Log.txt", string.Join(Environment.NewLine, exceptionlist)); } catch (Exception ex) { Console.WriteLine($"Could not write the output files \"Corrupted NSPs.txt\" and \"Exception Log.txt\" due to the following exception."); Console.WriteLine($"Exception: \"{ex.GetType()}\" {ex.Message}"); Console.WriteLine($"Stack Trace: {ex.StackTrace}{Environment.NewLine}"); Console.WriteLine(string.Join(Environment.NewLine, badlist)); Console.WriteLine(); Console.WriteLine(string.Join(Environment.NewLine, exceptionlist)); Console.WriteLine(); } Console.WriteLine("Done."); PressAnyKey(); }
//Open update only private void Open_NSP_Update(object sender, EventArgs e) { var Dialog = openFileDialog1.ShowDialog(); if (Dialog != DialogResult.Cancel) { Console.WriteLine("LOADING."); label8.Visible = true; this.Update(); treeView1.Nodes.Clear(); string FileToOpen = null; if (Program.FileArg != null) { FileToOpen = Program.FileArg; } else { FileToOpen = openFileDialog1.FileName; } Program.FileArg = null; Stream Input = null; try { string ExpEnv(string In) => Environment.ExpandEnvironmentVariables(In); var ProdKeys = ExpEnv(@"%USERPROFILE%\.switch\prod.keys"); var TitleKeys = ExpEnv(@"%USERPROFILE%\.switch\title.keys"); Console.WriteLine(FileToOpen); var Keys = ExternalKeys.ReadKeyFile(ProdKeys, TitleKeys); var Ext = (new FileInfo(FileToOpen).Extension); if (Ext == ".nsp") { var InputPFS = File.OpenRead(FileToOpen); var Pfs = new Pfs(InputPFS.AsStorage()); var CnmtNca = new Nca(Keys, Pfs.OpenFile(Pfs.Files.FirstOrDefault(s => s.Name.Contains(".cnmt.nca"))), false); var CnmtPfs = new Pfs(CnmtNca.OpenSection(0, false, IntegrityCheckLevel.None, true)); var Cnmt = new Cnmt(CnmtPfs.OpenFile(CnmtPfs.Files[0]).AsStream()); var Program = Cnmt.ContentEntries.FirstOrDefault(c => c.Type == CnmtContentType.Program); var CtrlEntry = Cnmt.ContentEntries.FirstOrDefault(c => c.Type == CnmtContentType.Control); if (CtrlEntry != null) { Control = new Nca(Keys, Pfs.OpenFile($"{CtrlEntry.NcaId.ToHexString().ToLower()}.nca"), false); } Input = Pfs.OpenFile($"{Program.NcaId.ToHexString().ToLower()}.nca").AsStream(); } else { Input = File.OpenRead(FileToOpen); } try { Nca = new Nca(Keys, Input.AsStorage(), true); if (Nca.HasRightsId && !Keys.TitleKeys.Keys.Any(k => k.SequenceEqual(Nca.Header.RightsId))) { MessageBox.Show($"Error: the titlekey for {Nca.Header.RightsId.ToHexString().ToLower()} is not present in your key file."); } else { var isUpdateNca = false; if (Nca.Sections.Any(s => s?.Type == SectionType.Bktr)) { isUpdateNca = true; } if (isUpdateNca) { var InputPFS = File.OpenRead(FileToOpen); var Pfs = new Pfs(InputPFS.AsStorage()); var CnmtNca = new Nca(Keys, Pfs.OpenFile(Pfs.Files.FirstOrDefault(s => s.Name.Contains(".cnmt.nca"))), false); var CnmtPfs = new Pfs(CnmtNca.OpenSection(0, false, IntegrityCheckLevel.None, true)); var Cnmt = new Cnmt(CnmtPfs.OpenFile(CnmtPfs.Files[0]).AsStream()); var Program = Cnmt.ContentEntries.FirstOrDefault(c => c.Type == CnmtContentType.Program); var CtrlEntry = Cnmt.ContentEntries.FirstOrDefault(c => c.Type == CnmtContentType.Control); if (CtrlEntry != null) { Control = new Nca(Keys, Pfs.OpenFile($"{CtrlEntry.NcaId.ToHexString().ToLower()}.nca"), false); } Input = Pfs.OpenFile($"{Program.NcaId.ToHexString().ToLower()}.nca").AsStream(); var Input2 = Pfs.OpenFile($"{Program.NcaId.ToHexString().ToLower()}.nca").AsStream(); Patch = new Nca(Keys, Input2.AsStorage(), true); Nca.SetBaseNca(Patch); } new Thread (() => { Thread.CurrentThread.IsBackground = true; var Info = GetTitleMeta($"{Nca.Header.TitleId:x16}"); label2.Invoke(new Action(() => { label2.Text = Info[0]; label3.Text = Info[1]; })); }).Start(); Rom = new Romfs( Nca.OpenSection(Nca.Sections.FirstOrDefault (s => s?.Type == SectionType.Romfs || s?.Type == SectionType.Bktr) .SectionNum, false, IntegrityCheckLevel.None, true) ); IO.PopulateTreeView(treeView1.Nodes, Rom.RootDir); Console.WriteLine("DONE."); fileToolStripMenuItem.Text = "File / Explore"; label8.Visible = false; this.Update(); } } catch { MessageBox.Show("There was an error reading the NCA. Are you sure the correct keys are present in your keyfiles?"); } } catch (ArgumentNullException) { MessageBox.Show("Error: key files are missing!"); } } }
public void LoadNca(Nca mainNca, Nca controlNca) { if (mainNca.Header.ContentType != ContentType.Program) { Logger.PrintError(LogClass.Loader, "Selected NCA is not a \"Program\" NCA"); return; } Stream romfsStream = mainNca.OpenSection(ProgramPartitionType.Data, false, FsIntegrityCheckLevel); Stream exefsStream = mainNca.OpenSection(ProgramPartitionType.Code, false, FsIntegrityCheckLevel); if (exefsStream == null) { Logger.PrintError(LogClass.Loader, "No ExeFS found in NCA"); return; } if (romfsStream == null) { Logger.PrintWarning(LogClass.Loader, "No RomFS found in NCA"); } else { Device.FileSystem.SetRomFs(romfsStream); } Pfs exefs = new Pfs(exefsStream); Npdm metaData = null; if (exefs.FileExists("main.npdm")) { Logger.PrintInfo(LogClass.Loader, "Loading main.npdm..."); metaData = new Npdm(exefs.OpenFile("main.npdm")); } else { Logger.PrintWarning(LogClass.Loader, $"NPDM file not found, using default values!"); metaData = GetDefaultNpdm(); } List <IExecutable> staticObjects = new List <IExecutable>(); void LoadNso(string filename) { foreach (PfsFileEntry file in exefs.Files.Where(x => x.Name.StartsWith(filename))) { if (Path.GetExtension(file.Name) != string.Empty) { continue; } Logger.PrintInfo(LogClass.Loader, $"Loading {filename}..."); NxStaticObject staticObject = new NxStaticObject(exefs.OpenFile(file)); staticObjects.Add(staticObject); } } Nacp ReadControlData() { Romfs controlRomfs = new Romfs(controlNca.OpenSection(0, false, FsIntegrityCheckLevel)); byte[] controlFile = controlRomfs.GetFile("/control.nacp"); BinaryReader reader = new BinaryReader(new MemoryStream(controlFile)); Nacp controlData = new Nacp(reader); CurrentTitle = controlData.Languages[(int)State.DesiredTitleLanguage].Title; if (string.IsNullOrWhiteSpace(CurrentTitle)) { CurrentTitle = controlData.Languages.ToList().Find(x => !string.IsNullOrWhiteSpace(x.Title)).Title; } return(controlData); } if (controlNca != null) { ReadControlData(); } else { CurrentTitle = metaData.Aci0.TitleId.ToString("x16"); } if (!metaData.Is64Bits) { throw new NotImplementedException("32-bit titles are not supported!"); } LoadNso("rtld"); LoadNso("main"); LoadNso("subsdk"); LoadNso("sdk"); ContentManager.LoadEntries(); ProgramLoader.LoadStaticObjects(this, metaData, staticObjects.ToArray()); }
public static Title processNsp(string filename) { Title title = new Title(); using (var filestream = new FileStream(filename, FileMode.Open, FileAccess.Read)) { Pfs pfs; string biggestNca = null, controlNca = null; try { pfs = new Pfs(filestream.AsStorage()); title.distribution = Title.Distribution.Digital; log?.WriteLine("Processing NSP {0}", filename); PfsFileEntry[] fileEntries = pfs.Files; foreach (PfsFileEntry entry in fileEntries) { if (entry.Name.EndsWith(".cnmt.xml")) { try { using (var cnmtXml = pfs.OpenFile(entry)) { (biggestNca, controlNca) = processCnmtXml(cnmtXml, ref title); } } catch (FileNotFoundException) { } title.structure.Add(Title.Structure.CnmtXml); } else if (entry.Name.EndsWith(".cnmt.nca")) { try { using (var cnmtNca = pfs.OpenFile(entry)) { var nca = processCnmtNca(cnmtNca, ref title); if (nca.Item1 != null && (nca.Item2 != null || title.type == TitleType.AddOnContent)) { (biggestNca, controlNca) = nca; } } } catch (FileNotFoundException) { if (pfs.FileExists(entry.Name.Replace(".nca", ".ncz"))) { title.error = "Unsupported Format: Compressed NCA"; } } title.structure.Add(Title.Structure.CnmtNca); } else if (entry.Name.EndsWith(".cert")) { title.structure.Add(Title.Structure.Cert); } else if (entry.Name.EndsWith(".tik")) { try { using (var tik = pfs.OpenFile(entry)) { if (entry.Name.Split('.')[0].TryToBytes(out byte[] rightsId)) { processTik(tik, rightsId, ref keyset, out byte[] titleKey); title.titleKey = BitConverter.ToString(titleKey).Replace("-", "").ToUpper(); } } } catch (FileNotFoundException) { if (pfs.FileExists(entry.Name.Replace(".nca", ".ncz"))) { title.error = "Unsupported Format: Compressed NCA"; } } title.structure.Add(Title.Structure.Tik); } else if (entry.Name.EndsWith(".legalinfo.xml")) { title.structure.Add(Title.Structure.LegalinfoXml); } else if (entry.Name.EndsWith(".nacp.xml")) { try { using (var nacpXml = pfs.OpenFile(entry)) { processNacpXml(nacpXml, ref title); } } catch (FileNotFoundException) { } title.structure.Add(Title.Structure.NacpXml); } else if (entry.Name.EndsWith(".programinfo.xml")) { title.structure.Add(Title.Structure.PrograminfoXml); } else if (entry.Name.Equals("cardspec.xml")) { title.structure.Add(Title.Structure.CardspecXml); } else if (entry.Name.Equals("authoringtoolinfo.xml")) { title.structure.Add(Title.Structure.AuthoringtoolinfoXml); } } if (!String.IsNullOrEmpty(biggestNca)) { try { using (var biggest = pfs.OpenFile(biggestNca)) { processBiggestNca(biggest, ref title); } } catch (FileNotFoundException) { if (pfs.FileExists(biggestNca.Replace(".nca", ".ncz"))) { title.error = "Unsupported Format: Compressed NCA"; } } } if (!String.IsNullOrEmpty(controlNca)) { try { using (var control = pfs.OpenFile(controlNca)) { processControlNca(control, ref title); } } catch (FileNotFoundException) { if (pfs.FileExists(controlNca.Replace(".nca", ".ncz"))) { title.error = "Unsupported Format: Compressed NCA"; } } } } catch (InvalidDataException) { return(null); } } if (title.type == TitleType.Application || title.type == TitleType.Patch) { if (versionList.TryGetValue(title.baseTitleID, out uint version)) { title.latestVersion = version; } } log?.WriteLine("NSP information for {0}: [{1}] {2}", filename, title.titleID, title.titleName); return(title); }
public void LoadNsp(string nspFile) { FileStream file = new FileStream(nspFile, FileMode.Open, FileAccess.Read); Pfs nsp = new Pfs(file.AsStorage(false)); foreach (PfsFileEntry ticketEntry in nsp.Files.Where(x => x.Name.EndsWith(".tik"))) { Ticket ticket = new Ticket(nsp.OpenFile(ticketEntry).AsStream()); if (!KeySet.TitleKeys.ContainsKey(ticket.RightsId)) { KeySet.TitleKeys.Add(ticket.RightsId, ticket.GetTitleKey(KeySet)); } } Nca mainNca = null; Nca controlNca = null; foreach (PfsFileEntry ncaFile in nsp.Files.Where(x => x.Name.EndsWith(".nca"))) { Nca nca = new Nca(KeySet, nsp.OpenFile(ncaFile), true); if (nca.Header.ContentType == ContentType.Program) { mainNca = nca; } else if (nca.Header.ContentType == ContentType.Control) { controlNca = nca; } } if (mainNca != null) { LoadNca(mainNca, controlNca); return; } // This is not a normal NSP, it's actually a ExeFS as a NSP Npdm metaData = null; PfsFileEntry npdmFile = nsp.Files.FirstOrDefault(x => x.Name.Equals("main.npdm")); if (npdmFile != null) { Logger.PrintInfo(LogClass.Loader, $"Loading main.npdm..."); metaData = new Npdm(nsp.OpenFile(npdmFile).AsStream()); } else { Logger.PrintWarning(LogClass.Loader, $"NPDM file not found, using default values!"); metaData = GetDefaultNpdm(); } List <IExecutable> staticObjects = new List <IExecutable>(); void LoadNso(string searchPattern) { PfsFileEntry entry = nsp.Files.FirstOrDefault(x => x.Name.Equals(searchPattern)); if (entry != null) { Logger.PrintInfo(LogClass.Loader, $"Loading {entry.Name}..."); NxStaticObject staticObject = new NxStaticObject(nsp.OpenFile(entry).AsStream()); staticObjects.Add(staticObject); } } CurrentTitle = metaData.Aci0.TitleId.ToString("x16"); LoadNso("rtld"); LoadNso("main"); LoadNso("subsdk*"); LoadNso("sdk"); ContentManager.LoadEntries(); if (staticObjects.Count == 0) { Logger.PrintError(LogClass.Loader, "Could not find an Application NCA in the provided NSP file"); } else { ProgramLoader.LoadStaticObjects(this, metaData, staticObjects.ToArray()); } }
public static void Main(string[] Args) { usbnsp: Console.Clear(); Initialize(); try { var pat = new KLST_PATTERN_MATCH { DeviceID = @"USB\VID_057E&PID_3000" }; var lst = new LstK(0, ref pat); lst.MoveNext(out var dinfo); USB = new UsbK(dinfo); } catch { Error.Log("No USB connection was found. Make sure you have Goldleaf open before running Goldtree."); } try { Command c = new Command(CommandId.ConnectionRequest); USB.Write(c); Log.Log("Attempting to connect to Goldleaf via USB..."); Command rc = USB.Read(); if (rc.MagicOk()) { if (rc.IsCommandId(CommandId.ConnectionResponse)) { Log.Log("Connection was established with Goldleaf."); Log.Log("Select the NSP to send to Goldleaf on the dialog."); OpenFileDialog fd = new OpenFileDialog() { Title = "Select NSP to send to Goldleaf via USB", Filter = "NSP / Nintendo Submission Package (*.nsp)|*.nsp", Multiselect = false, }; if (fd.ShowDialog() == DialogResult.OK) { string nsp = fd.FileName; string nspname = Path.GetFileName(nsp); c = new Command(CommandId.NSPName); USB.Write(c); USB.Write((uint)nspname.Length); USB.Write(nspname); Log.Log("Selected NSP's name was sent to Goldleaf. Waiting for install approval from Goldleaf..."); Command rc2 = USB.Read(); if (rc2.MagicOk()) { if (rc2.IsCommandId(CommandId.Start)) { Log.Log("Goldleaf is ready for the installation. Preparing everything..."); try { FileStream fs = new FileStream(nsp, FileMode.Open); StreamStorage ist = new StreamStorage(fs, true); Pfs pnsp = new Pfs(ist); ist.Dispose(); fs.Close(); fs = new FileStream(nsp, FileMode.Open); uint filecount = (uint)pnsp.Files.Length; c = new Command(CommandId.NSPData); USB.Write(c); USB.Write(filecount); int tikidx = -1; int certidx = -1; int tmpidx = 0; foreach (var file in pnsp.Files) { ulong offset = (ulong)pnsp.HeaderSize + (ulong)file.Offset; ulong size = (ulong)file.Size; uint len = (uint)file.Name.Length; USB.Write(len); USB.Write(file.Name); USB.Write(offset); USB.Write(size); if (Path.GetExtension(file.Name).Replace(".", "").ToLower() == "tik") { tikidx = tmpidx; } else if (Path.GetExtension(file.Name).Replace(".", "").ToLower() == "cert") { certidx = tmpidx; } tmpidx++; } BinaryReader br = new BinaryReader(fs); while (true) { Command ccmd = USB.Read(); if (ccmd.MagicOk()) { if (ccmd.IsCommandId(CommandId.NSPContent)) { USB.Read(out uint idx); Log.Log("Sending content \'" + pnsp.Files[idx].Name + "\'... (" + (idx + 1) + " of " + pnsp.Files.Length + ")"); PfsFileEntry ent = pnsp.Files[idx]; long rsize = 0x800000; long coffset = pnsp.HeaderSize + ent.Offset; long toread = ent.Size; long tmpread = 1; byte[] bufb; while ((tmpread > 0) && (toread > 0) && (coffset < (coffset + ent.Size))) { if (rsize >= ent.Size) { rsize = ent.Size; } int tor = (int)Math.Min(rsize, toread); br.BaseStream.Position = coffset; bufb = br.ReadBytes(tor); tmpread = bufb.Length; USB.Write(bufb); coffset += tmpread; toread -= tmpread; } Log.Log("Content was sent to Goldleaf."); } else if (ccmd.IsCommandId(CommandId.NSPTicket)) { Log.Log("Sending ticket file..."); PfsFileEntry tik = pnsp.Files[tikidx]; br.BaseStream.Seek(pnsp.HeaderSize + tik.Offset, SeekOrigin.Begin); byte[] file = br.ReadBytes((int)tik.Size); USB.Write(file); Log.Log("Ticket was sent to Goldleaf."); } else if (ccmd.IsCommandId(CommandId.Finish)) { break; } else { USB = null; Error.Log("An invalid command was received. Are you sure Goldleaf is active?"); } } else { USB = null; Error.Log("An invalid command was received. Are you sure Goldleaf is active?"); } } } catch { Error.Log("An error ocurred opening the selected NSP. Are you sure it's a valid NSP?"); } } else if (rc2.IsCommandId(CommandId.Finish)) { USB = null; Error.Log("Goldleaf has canceled the installation."); } else { USB = null; Error.Log("An invalid command was received. Are you sure Goldleaf is active?"); } } else { USB = null; Error.Log("An invalid command was received. Are you sure Goldleaf is active?"); } } else { Error.Log("The dialog was closed without selecting a NSP, or another error ocurred. Reopen Goldleaf and Goldtree and try again."); } } else if (rc.IsCommandId(CommandId.Finish)) { USB = null; Error.Log("Goldleaf has canceled the installation."); } else { USB = null; Error.Log("An invalid command was received. Are you sure Goldleaf is active?"); } } else { USB = null; Error.Log("An invalid command was received. Are you sure Goldleaf is active?"); } } catch { Error.Log("An error ocurred selecting the NSP to be sent."); } Log.Log("The installation has finished. Press ENTER to close Goldtree, or any other key to start another USB installation.", true); ConsoleKeyInfo ki = Console.ReadKey(); if (ki.Key == ConsoleKey.Enter) { if (USB != null) { Command cmd = new Command(CommandId.Finish); USB.Write(cmd); } Environment.Exit(0); } else { goto usbnsp; } }
private static (string, string) processCnmtNca(Nca nca, ref Title title, bool cnmtContent = true) { string biggestNca = null, controlNca = null; log?.WriteLine("Processing CNMT NCA"); try { Pfs ncaPfs = new Pfs(nca.OpenSection(0, false, IntegrityCheckLevel.ErrorOnInvalid, true)); PfsFileEntry[] ncaFileEntries = ncaPfs.Files; foreach (PfsFileEntry pfsEntry in ncaFileEntries) { Cnmt cnmt = new Cnmt(ncaPfs.OpenFile(pfsEntry).AsStream()); if (title.version == unchecked ((uint)-1) || cnmt.TitleVersion?.Version > title.version) { title.type = cnmt.Type; title.titleID = String.Format("{0:X16}", cnmt.TitleId); title.baseTitleID = String.Format("{0:X16}", cnmt.ApplicationTitleId); title.version = cnmt.TitleVersion?.Version ?? title.version; title.systemVersion = cnmt.MinimumSystemVersion?.Version ?? unchecked ((uint)-1); title.applicationVersion = cnmt.MinimumApplicationVersion?.Version ?? unchecked ((uint)-1); if (cnmtContent) { CnmtContentEntry[] contentEntries = cnmt.ContentEntries; foreach (CnmtContentEntry contentEntry in contentEntries) { if (title.type == TitleType.Application || title.type == TitleType.Patch) { if (contentEntry.Type == CnmtContentType.Program) { biggestNca = BitConverter.ToString(contentEntry.NcaId).Replace("-", "").ToLower() + ".nca"; log?.WriteLine("Found Biggest NCA {0}", biggestNca); } else if (contentEntry.Type == CnmtContentType.Control) { controlNca = BitConverter.ToString(contentEntry.NcaId).Replace("-", "").ToLower() + ".nca"; log?.WriteLine("Found Control NCA {0}", controlNca); } } else if (title.type == TitleType.AddOnContent) { if (contentEntry.Type == CnmtContentType.Data) { biggestNca = BitConverter.ToString(contentEntry.NcaId).Replace("-", "").ToLower() + ".nca"; log?.WriteLine("Found Biggest NCA {0}", biggestNca); } } } } } } } catch (MissingKeyException ex) { title.error = String.Format("Missing {0}: {1}", ex.Type == KeyType.Title ? "Title Key" : "Key", ex.Name.Replace("key_area_key_application", "master_key")); log?.WriteLine(title.error); } catch (FileNotFoundException) { } return(biggestNca, controlNca); }
private void Open() { treeView1.Nodes.Clear(); string FileToOpen = null; if (Program.FileArg != null) { FileToOpen = Program.FileArg; } else { FileToOpen = openFileDialog1.FileName; } Program.FileArg = null; Stream Input = null; try { string ExpEnv(string In) => Environment.ExpandEnvironmentVariables(In); var ProdKeys = ExpEnv(@"%USERPROFILE%\.switch\prod.keys"); var TitleKeys = ExpEnv(@"%USERPROFILE%\.switch\title.keys"); var Keys = ExternalKeys.ReadKeyFile(ProdKeys, TitleKeys); var Ext = (new FileInfo(FileToOpen).Extension); if (Ext == ".nsp") { var InputPFS = File.OpenRead(FileToOpen); var Pfs = new Pfs(InputPFS); var CnmtNca = new Nca(Keys, Pfs.OpenFile(Pfs.Files.FirstOrDefault(s => s.Name.Contains(".cnmt.nca"))), false); var CnmtPfs = new Pfs(CnmtNca.OpenSection(0, false, IntegrityCheckLevel.None)); var Cnmt = new Cnmt(CnmtPfs.OpenFile(CnmtPfs.Files[0])); var Program = Cnmt.ContentEntries.FirstOrDefault(c => c.Type == CnmtContentType.Program); var CtrlEntry = Cnmt.ContentEntries.FirstOrDefault(c => c.Type == CnmtContentType.Control); if (CtrlEntry != null) { Control = new Nca(Keys, Pfs.OpenFile($"{CtrlEntry.NcaId.ToHexString().ToLower()}.nca"), false); } Input = Pfs.OpenFile($"{Program.NcaId.ToHexString().ToLower()}.nca"); } else if (Ext == ".xci") { var InputPFS = File.OpenRead(FileToOpen); var Xci = new Xci(Keys, InputPFS); var CnmtNca = new Nca(Keys, Xci.SecurePartition.OpenFile(Xci.SecurePartition.Files.FirstOrDefault(s => s.Name.Contains(".cnmt.nca"))), false); var CnmtPfs = new Pfs(CnmtNca.OpenSection(0, false, IntegrityCheckLevel.None)); var Cnmt = new Cnmt(CnmtPfs.OpenFile(CnmtPfs.Files[0])); var Program = Cnmt.ContentEntries.FirstOrDefault(c => c.Type == CnmtContentType.Program); var CtrlEntry = Cnmt.ContentEntries.FirstOrDefault(c => c.Type == CnmtContentType.Control); if (CtrlEntry != null) { Control = new Nca(Keys, Xci.SecurePartition.OpenFile($"{CtrlEntry.NcaId.ToHexString().ToLower()}.nca"), false); } Input = Xci.SecurePartition.OpenFile($"{Program.NcaId.ToHexString().ToLower()}.nca"); } else if (FileToOpen.Split('.')[1] == "cnmt" && Ext == ".nca") { var TargetFile = File.OpenRead(FileToOpen); var CnmtNca = new Nca(Keys, TargetFile, false); var CnmtPfs = new Pfs(CnmtNca.OpenSection(0, false, IntegrityCheckLevel.None)); var Cnmt = new Cnmt(CnmtPfs.OpenFile(CnmtPfs.Files[0])); var Program = Cnmt.ContentEntries.FirstOrDefault(c => c.Type == CnmtContentType.Program); var CtrlEntry = Cnmt.ContentEntries.FirstOrDefault(c => c.Type == CnmtContentType.Control); if (CtrlEntry != null) { Control = new Nca(Keys, File.OpenRead($"{CtrlEntry.NcaId.ToHexString().ToLower()}.nca"), false); } Input = File.OpenRead($"{Program.NcaId.ToHexString().ToLower()}.nca"); } else { Input = File.OpenRead(FileToOpen); } try { Nca = new Nca(Keys, Input, true); if (Nca.HasRightsId && !Keys.TitleKeys.Keys.Any(k => k.SequenceEqual(Nca.Header.RightsId))) { MessageBox.Show($"Error: the titlekey for {Nca.Header.RightsId.ToHexString().ToLower()} is not present in your key file."); } else { bool isUpdateNca = false; if (Nca.Sections.Any(s => s?.Type == SectionType.Bktr)) { isUpdateNca = true; } if (isUpdateNca) { openFileDialog1.Title = "Select base Nca"; openFileDialog1.ShowDialog(); var Input2 = File.OpenRead(openFileDialog1.FileName); Patch = new Nca(Keys, Input2, true); Nca.SetBaseNca(Patch); } new Thread ( () => { Thread.CurrentThread.IsBackground = true; var Info = GetTitleMeta($"{Nca.Header.TitleId:x16}"); label2.Invoke(new Action(() => { label2.Text = Info[0]; label3.Text = Info[1]; })); } ) .Start(); Rom = new Romfs ( Nca.OpenSection ( Nca.Sections.FirstOrDefault (s => s?.Type == SectionType.Romfs || s?.Type == SectionType.Bktr) .SectionNum, false, IntegrityCheckLevel.None ) ); IO.PopulateTreeView(treeView1.Nodes, Rom.RootDir); } } catch { MessageBox.Show("There was an error reading the NCA. Are you sure the correct keys are present in your keyfiles?"); } } catch (ArgumentNullException) { MessageBox.Show("Error: key files are missing!"); } }
public ExefsEntry(Pfs pfs, PfsFileEntry entry) { ParentPfs = pfs; fileEntry = entry; FileName = $"Exefs/{fileEntry.Name}"; }