Files
2025-12-19 17:54:45 -07:00

189 lines
7.6 KiB
C#

using Mono.Options;
using XboxToolkit;
using XboxToolkit.Interface;
using XboxToolkit.Models.Xbe;
using XboxToolkit.Internal;
namespace Repackinator.Shell.Console
{
public static class ConsoleXbeInfo
{
public const string Action = "XbeInfo";
public static string Input { get; set; } = string.Empty;
public static string Output { get; set; } = string.Empty;
public static bool ShowHelp { get; set; } = false;
public static bool Wait { get; set; } = false;
public static bool Quiet { get; set; } = false;
public static OptionSet GetOptions()
{
return new OptionSet {
{ "i|input=", "Input file (ISO or CCI)", i => Input = i },
{ "o|output=", "Output file (optional, defaults to console)", o => Output = o },
{ "h|help", "show help", h => ShowHelp = h != null },
{ "w|wait", "Wait on exit", w => Wait = w != null },
{ "q|quiet", "Suppress status output", q => Quiet = q != null }
};
}
public static void ShowOptionDescription()
{
System.Console.WriteLine();
System.Console.WriteLine("XbeInfo Action...");
System.Console.WriteLine();
System.Console.WriteLine("This action extracts XBE certificate information from Xbox disk images.");
System.Console.WriteLine();
GetOptions().WriteOptionDescriptions(System.Console.Out);
}
public static void Process(string version, string[] args)
{
try
{
var options = GetOptions();
options.Parse(args);
if (ShowHelp)
{
ConsoleUtil.ShowHelpHeaderForAction(version, Action, options);
ConsoleUtil.ProcessWait(Wait);
return;
}
if (string.IsNullOrEmpty(Input))
{
throw new OptionException("Input file not specified.", "input");
}
if (!File.Exists(Input))
{
throw new OptionException("Input file does not exist.", "input");
}
StreamWriter? outputWriter = null;
if (!string.IsNullOrEmpty(Output))
{
var outputPath = Path.GetFullPath(Output);
var outputDir = Path.GetDirectoryName(outputPath);
if (!string.IsNullOrEmpty(outputDir) && !Directory.Exists(outputDir))
{
Directory.CreateDirectory(outputDir);
}
outputWriter = new StreamWriter(outputPath, false, System.Text.Encoding.UTF8);
}
try
{
if (!Quiet)
{
System.Console.WriteLine("Extracting XBE Info From:");
var slices = ContainerUtility.GetSlicesFromFile(Input);
foreach (var slice in slices)
{
System.Console.WriteLine(Path.GetFileName(slice));
}
System.Console.WriteLine();
}
if (!ContainerUtility.TryAutoDetectContainerType(Input, out var containerReader) || containerReader == null)
{
throw new Exception("Unable to detect container type.");
}
using (containerReader)
{
if (!containerReader.TryMount())
{
throw new Exception("Unable to mount container.");
}
try
{
if (!Quiet)
{
System.Console.Write("Processing...");
}
if (!containerReader.TryGetDefault(out var xbeData, out var containerType))
{
throw new Exception("Unable to extract XBE from container.");
}
if (!Quiet)
{
System.Console.CursorLeft = 0;
System.Console.WriteLine("Processing... Complete");
}
if (containerType != ContainerType.XboxOriginal)
{
throw new Exception("Input is not an Xbox Original disk image.");
}
if (!XbeUtility.TryGetXbeCert(xbeData, out var cert) || cert == null)
{
throw new Exception("Unable to extract XBE certificate.");
}
Action<string> writeLine = (line) =>
{
if (outputWriter != null)
{
outputWriter.WriteLine(line);
}
else
{
System.Console.WriteLine(line);
}
};
writeLine("XBE Certificate Information:");
writeLine("============================");
var certInstance = new XbeCertificate();
writeLine($"Title ID: {cert.Title_Id:X08}");
writeLine($"Title Name: {UnicodeHelper.GetUnicodeString(cert.Title_Name)}");
writeLine($"Game Region: {XbeCertificate.GameRegionToString(cert.Game_Region)}");
writeLine($"Version: {cert.Version:X08}");
writeLine($"Allowed Media: {certInstance.AllowedMediaToString(cert.Allowed_Media)}");
writeLine($"Game Ratings: {cert.Game_Ratings:X08}");
writeLine($"Disk Number: {cert.Disk_Number}");
writeLine($"Time Date: {cert.Time_Date:X08}");
if (!Quiet && outputWriter == null)
{
System.Console.WriteLine();
System.Console.WriteLine("XbeInfo completed.");
}
else if (outputWriter != null && !Quiet)
{
System.Console.WriteLine($"XBE info saved to: {Output}");
}
}
finally
{
containerReader.Dismount();
}
}
}
finally
{
outputWriter?.Dispose();
}
}
catch (OptionException e)
{
ConsoleUtil.ShowOptionException(e, Action, version);
Environment.ExitCode = 1;
}
catch (Exception e)
{
if (!Quiet)
{
System.Console.WriteLine($"Error: {e.Message}");
}
Environment.ExitCode = 1;
}
ConsoleUtil.ProcessWait(Wait);
}
}
}