114 lines
6.2 KiB
C#
114 lines
6.2 KiB
C#
// Decompiled with JetBrains decompiler
|
|
// Type: SEGATools.Security.InitialProgramConverter
|
|
// Assembly: SEGATools, Version=1.0.3.0, Culture=neutral, PublicKeyToken=611be24fdeb07e08
|
|
// MVID: D631183F-57B1-40A1-B502-5364D288307A
|
|
// Assembly location: SEGATools.dll
|
|
|
|
using SEGATools.Graphics;
|
|
using System;
|
|
using System.Globalization;
|
|
using System.Text;
|
|
|
|
namespace SEGATools.Security
|
|
{
|
|
public class InitialProgramConverter
|
|
{
|
|
public static readonly int INITIAL_PROGRAM_SIZE = 32768;
|
|
private static readonly Logger.ILog logger = Logger.CreateLog();
|
|
private static readonly string HARDWARE_ID = "SEGA SEGAKATANA";
|
|
private static readonly string MAKER_ID = "SEGA ENTERPRISES";
|
|
private static readonly int OFFSET_HARDWARE_ID = 0;
|
|
private static readonly int OFFSET_MAKER_ID = 16;
|
|
private static readonly int OFFSET_CRC = 32;
|
|
private static readonly int OFFSET_DEVICE_INFORMATION = 37;
|
|
private static readonly int OFFSET_AREA_SYMBOLS = 48;
|
|
private static readonly int OFFSET_PERIPHERALS = 56;
|
|
private static readonly int OFFSET_PRODUCT_ID = 64;
|
|
private static readonly int OFFSET_PRODUCT_VERSION = 74;
|
|
private static readonly int OFFSET_RELEASE_DATE = 80;
|
|
private static readonly int OFFSET_MAIN_BINARY = 96;
|
|
private static readonly int OFFSET_COMPAGNY_NAME = 112;
|
|
private static readonly int OFFSET_SOFWARE_NAME = 128;
|
|
private static readonly int OFFSET_TOC = 256;
|
|
private static readonly int OFFSET_SEGA_LICENSE_LOGO = 9111;
|
|
private static readonly int OFFSET_SEGA_TRADEMARK_LOGO = 8812;
|
|
private static readonly int OFFSET_SEGA_CUSTOM_BRANDING_LOGO = 14368;
|
|
|
|
public static InitialProgram ToInitialProgram(byte[] buffer, int startIndex)
|
|
{
|
|
if (startIndex < 0 || buffer.Length - startIndex < InitialProgramConverter.INITIAL_PROGRAM_SIZE)
|
|
throw new ArgumentOutOfRangeException();
|
|
InitialProgram initialProgram = new InitialProgram();
|
|
initialProgram.HardwareID = InitialProgramConverter.ParseField("hardware ID", buffer, startIndex + InitialProgramConverter.OFFSET_HARDWARE_ID, 15);
|
|
if (!initialProgram.HardwareID.Equals(InitialProgramConverter.HARDWARE_ID))
|
|
throw new InitialProgramInvalidHardwareIdException();
|
|
initialProgram.MakerID = InitialProgramConverter.ParseField("maker ID", buffer, startIndex + InitialProgramConverter.OFFSET_MAKER_ID, 16);
|
|
if (!initialProgram.MakerID.Equals(InitialProgramConverter.MAKER_ID))
|
|
throw new InitialProgramInvalidMakerIdException();
|
|
initialProgram.DeviceInformation = InitialProgramConverter.ParseField("device information", buffer, startIndex + InitialProgramConverter.OFFSET_DEVICE_INFORMATION, 11);
|
|
initialProgram.AreaSymbols = InitialProgramConverter.ParseField("area symbols", buffer, startIndex + InitialProgramConverter.OFFSET_AREA_SYMBOLS, 7);
|
|
initialProgram.RawPeripherals = InitialProgramConverter.ParseField("area symbols", buffer, startIndex + InitialProgramConverter.OFFSET_PERIPHERALS, 7);
|
|
initialProgram.ProductID = InitialProgramConverter.ParseField("product ID", buffer, startIndex + InitialProgramConverter.OFFSET_PRODUCT_ID, 10);
|
|
initialProgram.ProductVersion = InitialProgramConverter.ParseField("product version", buffer, startIndex + InitialProgramConverter.OFFSET_PRODUCT_VERSION, 6);
|
|
initialProgram.CRC = InitialProgramConverter.ParseField("CRC", buffer, startIndex + InitialProgramConverter.OFFSET_CRC, 4);
|
|
initialProgram.ComputedCRC = InitialProgramUtils.ComputeCRC(initialProgram.ProductID, initialProgram.ProductVersion).ToString("X4");
|
|
string field = InitialProgramConverter.ParseField("release date", buffer, startIndex + InitialProgramConverter.OFFSET_RELEASE_DATE, 8);
|
|
try
|
|
{
|
|
initialProgram.ReleaseDate = DateTime.ParseExact(field, "yyyyMMdd", (IFormatProvider) CultureInfo.InvariantCulture, DateTimeStyles.None);
|
|
}
|
|
catch (Exception ex)
|
|
{
|
|
throw new InitialProgramReleaseDateParsingException(field, ex);
|
|
}
|
|
initialProgram.MainBinary = InitialProgramConverter.ParseField("main binary", buffer, startIndex + InitialProgramConverter.OFFSET_MAIN_BINARY, 16);
|
|
initialProgram.CompanyName = InitialProgramConverter.ParseField("company name", buffer, startIndex + InitialProgramConverter.OFFSET_COMPAGNY_NAME, 16);
|
|
initialProgram.SoftwareName = InitialProgramConverter.ParseField("software name", buffer, startIndex + InitialProgramConverter.OFFSET_SOFWARE_NAME, 128);
|
|
try
|
|
{
|
|
initialProgram.TableOfContent = InitialProgramTocConverter.ToInitialProgramToc(buffer, startIndex + InitialProgramConverter.OFFSET_TOC);
|
|
}
|
|
catch (InitialProgramTocException ex)
|
|
{
|
|
logger.Error(ex);
|
|
}
|
|
byte[] numArray = new byte[InitialProgramConverter.INITIAL_PROGRAM_SIZE];
|
|
Buffer.BlockCopy((Array) buffer, startIndex, (Array) numArray, 0, InitialProgramConverter.INITIAL_PROGRAM_SIZE);
|
|
initialProgram.RawData = numArray;
|
|
initialProgram.SegaLicenseImage = InitialProgramConverter.GetMRImage(buffer, startIndex + InitialProgramConverter.OFFSET_SEGA_LICENSE_LOGO);
|
|
initialProgram.SegaTradeMarkImage = InitialProgramConverter.GetMRImage(buffer, startIndex + InitialProgramConverter.OFFSET_SEGA_TRADEMARK_LOGO);
|
|
initialProgram.CustomBrandingImage = InitialProgramConverter.GetMRImage(buffer, startIndex + InitialProgramConverter.OFFSET_SEGA_CUSTOM_BRANDING_LOGO);
|
|
return initialProgram;
|
|
}
|
|
|
|
private static string ParseField(string fieldName, byte[] buffer, int startIndex, int lenght)
|
|
{
|
|
try
|
|
{
|
|
return Encoding.Default.GetString(buffer, startIndex, lenght);
|
|
}
|
|
catch (Exception ex)
|
|
{
|
|
throw new InitialProgramFieldParsingException(fieldName, startIndex, ex);
|
|
}
|
|
}
|
|
|
|
private static MRImage GetMRImage(byte[] buffer, int startIndex)
|
|
{
|
|
try
|
|
{
|
|
return MRImageConverter.ToMRImage(buffer, startIndex);
|
|
}
|
|
catch (MRImageIdentifierMissingException ex)
|
|
{
|
|
logger.Error(ex);
|
|
return (MRImage) null;
|
|
}
|
|
catch (MRImageDecompressionException ex)
|
|
{
|
|
InitialProgramConverter.logger.ErrorFormat("Unable to decompress MR image: {0}", (object) ex);
|
|
throw new InitialProgramInvalidMRImageException(startIndex, (Exception) ex);
|
|
}
|
|
}
|
|
}
|
|
}
|