Go back !! GO BACK!
This commit is contained in:
parent
cdb7b7e3f1
commit
3787e96e43
|
@ -1,102 +0,0 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project DefaultTargets="Build" ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup Label="ProjectConfigurations">
|
||||
<ProjectConfiguration Include="Debug|Win32">
|
||||
<Configuration>Debug</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|Win32">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="chovy-gen.c" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="key_vault.h" />
|
||||
</ItemGroup>
|
||||
<PropertyGroup Label="Globals">
|
||||
<VCProjectVersion>15.0</VCProjectVersion>
|
||||
<ProjectGuid>{DCDBF747-DFB6-450E-A403-1C592D20EAEB}</ProjectGuid>
|
||||
<Keyword>Win32Proj</Keyword>
|
||||
<RootNamespace>CHOVYGEN</RootNamespace>
|
||||
<WindowsTargetPlatformVersion>10.0</WindowsTargetPlatformVersion>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<UseDebugLibraries>true</UseDebugLibraries>
|
||||
<PlatformToolset>v142</PlatformToolset>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<UseDebugLibraries>false</UseDebugLibraries>
|
||||
<PlatformToolset>v142</PlatformToolset>
|
||||
<WholeProgramOptimization>true</WholeProgramOptimization>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
|
||||
<ImportGroup Label="ExtensionSettings">
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="Shared">
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<PropertyGroup Label="UserMacros" />
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
||||
<LinkIncremental>true</LinkIncremental>
|
||||
<OutDir>$(SolutionDir)CHOVY-SIGN\bin\$(Configuration)</OutDir>
|
||||
<TargetName>$(ProjectName)</TargetName>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<LinkIncremental>false</LinkIncremental>
|
||||
<IgnoreImportLibrary />
|
||||
<TargetName>$(ProjectName)</TargetName>
|
||||
<OutDir>$(SolutionDir)CHOVY-SIGN\bin\$(Configuration)</OutDir>
|
||||
</PropertyGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
||||
<ClCompile>
|
||||
<PrecompiledHeader>
|
||||
</PrecompiledHeader>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<Optimization>Disabled</Optimization>
|
||||
<PreprocessorDefinitions>WIN32;_DEBUG;_WINDOWS;_USRDLL;CHOVYGEN_EXPORTS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<AdditionalIncludeDirectories>C:\openssl\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<RuntimeLibrary>MultiThreaded</RuntimeLibrary>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>Windows</SubSystem>
|
||||
<AdditionalLibraryDirectories>C:\openssl\lib;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
|
||||
<AdditionalDependencies>ws2_32.lib;libsslMT.lib;Crypt32.lib;libcryptoMT.lib;%(AdditionalDependencies)</AdditionalDependencies>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<PrecompiledHeader>
|
||||
</PrecompiledHeader>
|
||||
<Optimization>MaxSpeed</Optimization>
|
||||
<FunctionLevelLinking>true</FunctionLevelLinking>
|
||||
<IntrinsicFunctions>true</IntrinsicFunctions>
|
||||
<PreprocessorDefinitions>WIN32;NDEBUG;_WINDOWS;_USRDLL;CHOVYGEN_EXPORTS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<RuntimeLibrary>MultiThreaded</RuntimeLibrary>
|
||||
<AdditionalIncludeDirectories>C:\openssl\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>Windows</SubSystem>
|
||||
<EnableCOMDATFolding>true</EnableCOMDATFolding>
|
||||
<OptimizeReferences>true</OptimizeReferences>
|
||||
<AdditionalLibraryDirectories>C:\openssl\lib;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
|
||||
<AdditionalDependencies>ws2_32.lib;libsslMT.lib;Crypt32.lib;libcryptoMT.lib;%(AdditionalDependencies)</AdditionalDependencies>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
|
||||
<ImportGroup Label="ExtensionTargets">
|
||||
</ImportGroup>
|
||||
</Project>
|
|
@ -1,27 +0,0 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup>
|
||||
<Filter Include="Source Files">
|
||||
<UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
|
||||
<Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
|
||||
</Filter>
|
||||
<Filter Include="Header Files">
|
||||
<UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
|
||||
<Extensions>h;hh;hpp;hxx;hm;inl;inc;xsd</Extensions>
|
||||
</Filter>
|
||||
<Filter Include="Resource Files">
|
||||
<UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
|
||||
<Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
|
||||
</Filter>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="key_vault.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="chovy-gen.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
</Project>
|
|
@ -1,13 +0,0 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<LocalDebuggerCommand>$(SolutionDir)CHOVY\bin\$(Configuration)\CHOVY-SIGN.EXE</LocalDebuggerCommand>
|
||||
<DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
|
||||
<LocalDebuggerDebuggerType>Mixed</LocalDebuggerDebuggerType>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
||||
<LocalDebuggerCommand>$(SolutionDir)CHOVY\bin\$(Configuration)\CHOVY-SIGN.EXE</LocalDebuggerCommand>
|
||||
<DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
|
||||
<LocalDebuggerDebuggerType>Mixed</LocalDebuggerDebuggerType>
|
||||
</PropertyGroup>
|
||||
</Project>
|
|
@ -1,289 +0,0 @@
|
|||
//Project Chovy - __sce_ebootpbp generator by @dots_tb and motoharu
|
||||
// With CBPS help especially: @SiliCart, @nyaaasen, @notzecoxao (and his friends?)
|
||||
|
||||
//Check out motoharu's project: https://github.com/motoharu-gosuto/psvcmd56/blob/master/src/CMD56Reversed/F00D/GcAuthMgrService.cpp#L1102
|
||||
#define PACK( __Declaration__ ) __pragma( pack(push, 1) ) __Declaration__ __pragma( pack(pop) )
|
||||
|
||||
#include <string.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <inttypes.h>
|
||||
|
||||
#include <openssl/evp.h>
|
||||
#include <openssl/hmac.h>
|
||||
#include <openssl/sha.h>
|
||||
#include <openssl/obj_mac.h>
|
||||
#include <openssl/ec.h>
|
||||
|
||||
#include "key_vault.h"
|
||||
PACK(typedef struct
|
||||
{
|
||||
uint8_t r[0x1c];
|
||||
uint8_t s[0x1c];
|
||||
} ECDSA_SIG_0x1c);
|
||||
|
||||
PACK(typedef struct sce_ebootpbp {
|
||||
uint64_t magic;
|
||||
uint32_t key_type;// set to 1 (maybe keytype?)
|
||||
uint32_t type;// 03 - ps1, 02 - psp
|
||||
uint8_t np_title[0x30];
|
||||
uint64_t aid;
|
||||
uint64_t secure_tick;
|
||||
uint64_t filesz;
|
||||
uint64_t sw_ver;
|
||||
uint8_t padding[0xf8];
|
||||
ECDSA_SIG_0x1c ebootpbp_hdr_sig;
|
||||
ECDSA_SIG_0x1c NPUMDIMG_sig;
|
||||
ECDSA_SIG_0x1c sceebootpbp_sig;
|
||||
} sce_ebootpbp);
|
||||
|
||||
|
||||
typedef struct pbp_hdr {
|
||||
uint32_t magic;
|
||||
uint32_t unk;
|
||||
uint32_t sfo_offset;
|
||||
uint32_t icon0_offset;
|
||||
uint32_t icon1_offset;
|
||||
uint32_t pic0_offset;
|
||||
uint32_t pic1_offset;
|
||||
uint32_t snd0_offset;
|
||||
uint32_t data_psp_offset;
|
||||
uint32_t data_psar_offset;
|
||||
} pbp_hdr;
|
||||
|
||||
|
||||
#define PSAR_SZ 0x1C0000
|
||||
#define WORK_BUF_SZ 0x7c0
|
||||
|
||||
|
||||
//based motoharu
|
||||
__declspec(dllexport) int can_be_reversed_80C17A(const uint8_t* src, int some_size, uint8_t* iv, uint8_t* src_xored_digest)
|
||||
{
|
||||
unsigned char src_xored[0x20];
|
||||
memcpy(src_xored, iv, 0x20);
|
||||
|
||||
if (some_size > 0x20)
|
||||
return 0x12;
|
||||
|
||||
for(int i = 0; i < some_size; i++)
|
||||
src_xored[i] = src[i] ^ iv[i];
|
||||
|
||||
int r0;
|
||||
|
||||
SHA256_CTX sha256_ctx;
|
||||
SHA256_Init(&sha256_ctx);
|
||||
SHA256_Update(&sha256_ctx, src_xored, 0x20);
|
||||
r0 = SHA256_Final(src_xored_digest, &sha256_ctx);
|
||||
if(r0 != 1)
|
||||
return 0x11;
|
||||
|
||||
for(int i = 0; i < 0x20; i++)
|
||||
iv[i] = src_xored_digest[i] ^ iv[i];
|
||||
|
||||
for(int i = 0; i < 0x20; i++)
|
||||
{
|
||||
if(iv[i] != 0xFF)
|
||||
{
|
||||
iv[i] = iv[i] + 1;
|
||||
break;
|
||||
}
|
||||
|
||||
iv[i] = 0;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
__declspec(dllexport) int f00d_KIRK0x22(const uint8_t *hash, ECDSA_SIG_0x1c *signature, int key_sel) {
|
||||
|
||||
|
||||
uint8_t hmac_in[0x38];
|
||||
uint8_t hmac_hash_iv[0x38];
|
||||
memcpy(&hmac_in, hash, 0x1c);
|
||||
memcpy(&hmac_in[0x1c], &keyvault_ec_privkey[key_sel], 0x1c);
|
||||
|
||||
HMAC_CTX *hmac_ctx = HMAC_CTX_new();
|
||||
HMAC_Init_ex(hmac_ctx, &hmac_key_0x22, 0x40, EVP_sha256(), NULL);
|
||||
HMAC_Update(hmac_ctx, &hmac_in, 0x1c << 1);
|
||||
unsigned int len;
|
||||
HMAC_Final(hmac_ctx, &hmac_hash_iv, &len);
|
||||
HMAC_CTX_free(hmac_ctx);
|
||||
|
||||
uint8_t sha256_out[0x40];
|
||||
int ret = 0;
|
||||
do {
|
||||
ret = can_be_reversed_80C17A(hash, 0x1c, hmac_hash_iv, &sha256_out[0]);
|
||||
if(ret != 0 || (ret = can_be_reversed_80C17A(hash, 0x1c, hmac_hash_iv, &sha256_out[0x20])) != 0)
|
||||
return 0;
|
||||
|
||||
} while(ret != 0);
|
||||
|
||||
//ECDSA
|
||||
|
||||
BIGNUM *a = BN_bin2bn(keyvault_ec_a, 0x1c, NULL),
|
||||
*b = BN_bin2bn(keyvault_ec_b, 0x1c, NULL),
|
||||
*p = BN_bin2bn(keyvault_ec_p, 0x1c, NULL),
|
||||
*order = BN_bin2bn(keyvault_ec_N, 0x1c, NULL),
|
||||
*x = BN_bin2bn(keyvault_ec_Gx, 0x1c, NULL),
|
||||
*y = BN_bin2bn(keyvault_ec_Gy, 0x1c, NULL),
|
||||
*priv_key = BN_bin2bn(keyvault_ec_privkey[key_sel], 0x1c, NULL),
|
||||
*m = BN_bin2bn(sha256_out, 0x3c, NULL);
|
||||
|
||||
BN_CTX *bn_ctx = BN_CTX_new();
|
||||
BN_MONT_CTX *bn_mon_ctx = BN_MONT_CTX_new();
|
||||
BN_MONT_CTX_set(bn_mon_ctx, order, bn_ctx);
|
||||
|
||||
EC_GROUP *curve = EC_GROUP_new_curve_GFp(p, a, b, bn_ctx);
|
||||
EC_POINT *generator = EC_POINT_new(curve);
|
||||
EC_POINT_set_affine_coordinates_GFp(curve, generator, x, y, bn_ctx);
|
||||
EC_GROUP_set_generator(curve, generator, order, NULL);
|
||||
|
||||
EC_KEY *eckey=EC_KEY_new();
|
||||
EC_KEY_set_group(eckey,curve);
|
||||
EC_KEY_set_private_key(eckey, priv_key);
|
||||
|
||||
|
||||
m = BN_bin2bn(sha256_out, 0x3c, NULL);
|
||||
BN_mod(m, m, order, bn_ctx);
|
||||
|
||||
|
||||
|
||||
//Generate R in order to get custom "random number"
|
||||
BIGNUM *sig_r = BN_new();
|
||||
EC_POINT_mul(curve, generator, m, NULL, NULL, bn_ctx);
|
||||
EC_POINT_get_affine_coordinates_GFp(curve, generator, sig_r, NULL, bn_ctx);
|
||||
BN_nnmod(sig_r, sig_r, order, bn_ctx);
|
||||
|
||||
//Generate M^-1
|
||||
BIGNUM *exp = BN_new();
|
||||
BIGNUM *minv = BN_new();
|
||||
|
||||
BN_set_word(exp, (BN_ULONG)2);
|
||||
BN_sub(exp, order, exp);
|
||||
BN_mod_exp_mont(minv, m, exp, order, bn_ctx, bn_mon_ctx);
|
||||
|
||||
|
||||
ECDSA_SIG *sig = ECDSA_do_sign_ex(hash, 0x1c, minv, sig_r, eckey);
|
||||
|
||||
|
||||
if(!sig) {
|
||||
ret = 0;
|
||||
goto error;
|
||||
|
||||
}
|
||||
BIGNUM *sig_s;
|
||||
ECDSA_SIG_get0(sig, NULL, &sig_s);
|
||||
BN_bn2bin(sig_r, &signature->r);
|
||||
BN_bn2bin(sig_s, &signature->s);
|
||||
ECDSA_SIG_free(sig);
|
||||
//BN_free(sig_s);
|
||||
ret = 1;
|
||||
|
||||
error:
|
||||
BN_free(sig_r);
|
||||
|
||||
EC_POINT_free(generator);
|
||||
BN_free(y);
|
||||
BN_free(x);
|
||||
BN_free(order);
|
||||
BN_free(p);
|
||||
BN_free(b);
|
||||
BN_free(a);
|
||||
BN_free(minv);
|
||||
BN_free(exp);
|
||||
BN_free(priv_key);
|
||||
BN_CTX_free(bn_ctx);
|
||||
BN_MONT_CTX_free(bn_mon_ctx);
|
||||
return ret;
|
||||
|
||||
}
|
||||
|
||||
|
||||
__declspec(dllexport) int chovy_gen(char *ebootpbp, uint64_t signaid, char *outscefile)
|
||||
{
|
||||
|
||||
int ret = 1;
|
||||
FILE *fin = 0, *fout = 0;
|
||||
|
||||
uint8_t *work_buf = (unsigned char*) calloc (1, WORK_BUF_SZ);
|
||||
sce_ebootpbp *sceebootpbp_file = (unsigned char*) calloc (1, sizeof(sce_ebootpbp));
|
||||
|
||||
|
||||
fin = fopen(ebootpbp, "rb");
|
||||
if (!fin) {
|
||||
|
||||
goto error;
|
||||
}
|
||||
memcpy(&sceebootpbp_file->magic, "NPUMDSIG", 0x8);
|
||||
sceebootpbp_file->type = 2;
|
||||
sceebootpbp_file->key_type = 1;
|
||||
sceebootpbp_file->aid = signaid;
|
||||
|
||||
|
||||
fseek(fin, 0, SEEK_END);
|
||||
sceebootpbp_file->filesz = ftell(fin);
|
||||
|
||||
pbp_hdr hdr;
|
||||
fseek(fin, 0, SEEK_SET);
|
||||
fread(&hdr, sizeof(pbp_hdr),1,fin);
|
||||
|
||||
|
||||
fseek(fin, 0, SEEK_SET);
|
||||
fread(work_buf, hdr.icon0_offset, 1,fin);
|
||||
|
||||
uint8_t work_hash[0x1c];
|
||||
SHA256_CTX sha256_ctx;
|
||||
SHA224_Init(&sha256_ctx);
|
||||
SHA224_Update(&sha256_ctx, work_buf, hdr.icon0_offset);
|
||||
SHA224_Final(work_hash, &sha256_ctx);
|
||||
f00d_KIRK0x22(work_hash, &sceebootpbp_file->ebootpbp_hdr_sig, sceebootpbp_file->key_type);
|
||||
|
||||
SHA224_Init(&sha256_ctx);
|
||||
fseek(fin, hdr.data_psar_offset, SEEK_SET);
|
||||
|
||||
size_t size = PSAR_SZ;
|
||||
int to_read = size > WORK_BUF_SZ ? WORK_BUF_SZ : size;
|
||||
|
||||
|
||||
fread(work_buf, to_read, 1,fin);
|
||||
if(memcmp(work_buf, "NPUMDIMG", 0x8) == 0)
|
||||
memcpy(&sceebootpbp_file->np_title, work_buf + 0x10, sizeof(sceebootpbp_file->np_title));
|
||||
else {
|
||||
memcpy(&sceebootpbp_file->magic, "NPPS1SIG", sizeof(sceebootpbp_file->magic));
|
||||
sceebootpbp_file->type = 3;
|
||||
}
|
||||
|
||||
do {
|
||||
size -= to_read;
|
||||
SHA224_Update(&sha256_ctx, work_buf, to_read);
|
||||
to_read = size > WORK_BUF_SZ ? WORK_BUF_SZ : size;
|
||||
fread(work_buf, to_read, 1,fin);
|
||||
} while(size > 0);
|
||||
|
||||
SHA224_Final(work_hash, &sha256_ctx);
|
||||
|
||||
f00d_KIRK0x22(work_hash, &sceebootpbp_file->NPUMDIMG_sig, sceebootpbp_file->key_type);
|
||||
|
||||
SHA224_Init(&sha256_ctx);
|
||||
SHA224_Update(&sha256_ctx, sceebootpbp_file, 0x1C8);
|
||||
SHA224_Final(work_hash, &sha256_ctx);
|
||||
|
||||
f00d_KIRK0x22(work_hash, &sceebootpbp_file->sceebootpbp_sig, sceebootpbp_file->key_type);
|
||||
|
||||
fout = fopen(outscefile, "wb");
|
||||
if (!fout) {
|
||||
goto error;
|
||||
}
|
||||
fwrite(sceebootpbp_file, 1, sizeof(sce_ebootpbp), fout);
|
||||
|
||||
ret = 0;
|
||||
error:
|
||||
if (fin)
|
||||
fclose(fin);
|
||||
if (fout)
|
||||
fclose(fout);
|
||||
free(work_buf);
|
||||
free(sceebootpbp_file);
|
||||
return ret;
|
||||
}
|
|
@ -1,17 +0,0 @@
|
|||
uint8_t keyvault_ec_p[0x1c] = {0xA5, 0x3E, 0x11, 0x3E, 0x46, 0xD8, 0xC9, 0xC1, 0xF0, 0x9D, 0x9B, 0xCB, 0x2A, 0x53, 0x73, 0xD3, 0x79, 0xF6, 0x9D, 0xA2, 0x8D, 0x09, 0x99, 0x9F, 0xED, 0x57, 0xA9, 0x0F};
|
||||
uint8_t keyvault_ec_a[0x1c] = {0xA5, 0x3E, 0x11, 0x3E, 0x46, 0xD8, 0xC9, 0xC1, 0xF0, 0x9D, 0x9B, 0xCB, 0x2A, 0x53, 0x73, 0xD3, 0x79, 0xF6, 0x9D, 0xA2, 0x8D, 0x09, 0x99, 0x9F, 0xED, 0x57, 0xA9, 0x0C};
|
||||
uint8_t keyvault_ec_b[0x1c] = {0x90, 0x65, 0x94, 0x1D, 0x29, 0x37, 0x4A, 0x8F, 0x11, 0xDD, 0x1E, 0x54, 0x01, 0x89, 0x43, 0x4E, 0x4A, 0x6E, 0xBF, 0xAF, 0x54, 0x77, 0xF6, 0xC1, 0x72, 0xF6, 0x85, 0x5E};
|
||||
uint8_t keyvault_ec_N[0x1c] = { 0xA5, 0x3E, 0x11, 0x3E, 0x46, 0xD8, 0xC9, 0xC1, 0xF0, 0x9D, 0x9B, 0xCB, 0x2A, 0x52, 0x26, 0x98, 0xDE, 0xEF, 0x58, 0xDB, 0x1A, 0xD9, 0xAB, 0x7F, 0x04, 0xE3, 0xAE, 0x7F};
|
||||
uint8_t keyvault_ec_Gx[0x1c] = {0x7E, 0x06, 0x09, 0x82, 0x47, 0xE6, 0xB5, 0x9F, 0x31, 0x10, 0xBC, 0xBB, 0x3A, 0xB6, 0xC2, 0x50, 0xBC, 0x5A, 0xB0, 0x6C, 0x03, 0x2D, 0xAD, 0x43, 0x68, 0x4C, 0x24, 0x8F};
|
||||
uint8_t keyvault_ec_Gy[0x1c] = {0x0B, 0xD9, 0x41, 0x8D, 0xE8, 0xE3, 0xE4, 0x5D, 0x2D, 0x70, 0x1E, 0x02, 0x37, 0xFD, 0x7F, 0x2A, 0xDE, 0x0D, 0x48, 0xB7, 0x4C, 0xEE, 0xF2, 0xF1, 0xC8, 0xAC, 0x48, 0x4E};
|
||||
uint8_t keyvault_ec_pubkey[2][0x38] = {
|
||||
{0x5F, 0x9D, 0x17, 0x1A, 0x2B, 0xDD, 0xA8, 0xD4, 0x08, 0x78, 0xBF, 0x98, 0x5A, 0xC3, 0x26, 0xED, 0x5E, 0xFF, 0x43, 0xC9, 0x37, 0x6C, 0x77, 0xEC, 0x0A, 0x00, 0xC7, 0xBB, 0xA3, 0x44, 0xE4, 0x4E, 0x6E, 0xAC, 0x25, 0x52, 0x35, 0xF9, 0x54, 0xF5, 0xB6, 0x17, 0xC7, 0xBD, 0x49, 0xF1, 0x80, 0x26, 0x24, 0x54, 0xAA, 0xE1, 0xB6, 0x2A, 0x9F, 0x2C},
|
||||
{0x67, 0x00, 0x2D, 0x9B, 0xB8, 0xE4, 0x2D, 0x2B, 0xF9, 0x61, 0x0B, 0x27, 0xFE, 0xAB, 0x9B, 0x34, 0x56, 0x15, 0x50, 0x92, 0x13, 0x12, 0xDF, 0xEE, 0x7A, 0x3A, 0x86, 0xEC, 0x6C, 0xA7, 0x14, 0x42, 0x6F, 0x6D, 0x4E, 0x96, 0x09, 0xA6, 0x38, 0xBF, 0x4A, 0xFB, 0x18, 0x2B, 0xFA, 0x50, 0xC8, 0x2F, 0xF2, 0xB4, 0xC5, 0xEC, 0x6C, 0xCD, 0x97, 0x65}
|
||||
};
|
||||
|
||||
uint8_t keyvault_ec_privkey[2][0x1c] = {
|
||||
{0x76, 0x74, 0x36, 0xA6, 0x99, 0x9D, 0x88, 0x48, 0x0E, 0xC8, 0x56, 0xF5, 0x5C, 0xEA, 0xBB, 0x43, 0x96, 0x85, 0x9E, 0x37, 0x45, 0x99, 0x40, 0x39, 0x21, 0xF5, 0x55, 0x98},
|
||||
{0x60, 0x7A, 0x2E, 0x55, 0x68, 0xB4, 0xB9, 0xA0, 0x32, 0xF4, 0x52, 0x53, 0xCF, 0xED, 0x20, 0xDB, 0x2E, 0x6E, 0x44, 0x6C, 0x37, 0x82, 0xE8, 0x2A, 0x1A, 0xB9, 0xC9, 0x23}
|
||||
};
|
||||
|
||||
uint8_t hmac_key_0x22[0x40] = {0x54, 0x88, 0xA9, 0x81, 0x1C, 0x9A, 0x2C, 0xBC, 0xCC, 0x59, 0x6B, 0x1F, 0xAD, 0x1A, 0x7E, 0x29, 0xE0, 0x75, 0x84, 0x0F, 0x47, 0x43, 0x1F, 0x37, 0xAC, 0x06, 0x02, 0x46, 0x4A, 0x27, 0x9E, 0x02, 0xDF, 0x2E, 0x71, 0x65, 0xF1, 0x13, 0x7B, 0xF6, 0x9A, 0xE6, 0xDC, 0xB9, 0xDC, 0x38, 0x8C, 0x9D, 0xCC, 0xB3, 0x64, 0xC4, 0xCA, 0x26, 0xCB, 0x8F, 0x1A, 0xF0, 0x63, 0x8A, 0x6E, 0xAD, 0xB5, 0x4D};
|
|
@ -1,121 +0,0 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project DefaultTargets="Build" ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup Label="ProjectConfigurations">
|
||||
<ProjectConfiguration Include="CHOVY|Win32">
|
||||
<Configuration>CHOVY</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Debug|Win32">
|
||||
<Configuration>Debug</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|Win32">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
</ItemGroup>
|
||||
<PropertyGroup Label="Globals">
|
||||
<VCProjectVersion>15.0</VCProjectVersion>
|
||||
<ProjectGuid>{C441ACC2-EC4E-424B-AA99-3F5D1A997A4F}</ProjectGuid>
|
||||
<Keyword>Win32Proj</Keyword>
|
||||
<RootNamespace>KIRK</RootNamespace>
|
||||
<WindowsTargetPlatformVersion>10.0</WindowsTargetPlatformVersion>
|
||||
<ProjectName>CHOVY-KIRK</ProjectName>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<UseDebugLibraries>true</UseDebugLibraries>
|
||||
<PlatformToolset>v142</PlatformToolset>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<UseDebugLibraries>false</UseDebugLibraries>
|
||||
<PlatformToolset>v142</PlatformToolset>
|
||||
<WholeProgramOptimization>true</WholeProgramOptimization>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Label="Configuration" Condition="'$(Configuration)|$(Platform)'=='CHOVY|Win32'">
|
||||
<PlatformToolset>v142</PlatformToolset>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
|
||||
<ImportGroup Label="ExtensionSettings">
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="Shared">
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<PropertyGroup Label="UserMacros" />
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
||||
<LinkIncremental>true</LinkIncremental>
|
||||
<OutDir>$(SolutionDir)CHOVY-SIGN\bin\$(Configuration)</OutDir>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<LinkIncremental>false</LinkIncremental>
|
||||
<OutDir>$(SolutionDir)CHOVY-SIGN\bin\$(Configuration)</OutDir>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='CHOVY|Win32'">
|
||||
<OutDir>$(SolutionDir)CHOVY-SIGN\bin\$(Configuration)</OutDir>
|
||||
</PropertyGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
||||
<ClCompile>
|
||||
<PrecompiledHeader>
|
||||
</PrecompiledHeader>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<Optimization>Disabled</Optimization>
|
||||
<PreprocessorDefinitions>WIN32;_DEBUG;_WINDOWS;_USRDLL;KIRK_EXPORTS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>Windows</SubSystem>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<PrecompiledHeader>
|
||||
</PrecompiledHeader>
|
||||
<Optimization>MaxSpeed</Optimization>
|
||||
<FunctionLevelLinking>true</FunctionLevelLinking>
|
||||
<IntrinsicFunctions>true</IntrinsicFunctions>
|
||||
<PreprocessorDefinitions>WIN32;NDEBUG;_WINDOWS;_USRDLL;KIRK_EXPORTS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<RuntimeLibrary>MultiThreaded</RuntimeLibrary>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>Windows</SubSystem>
|
||||
<EnableCOMDATFolding>true</EnableCOMDATFolding>
|
||||
<OptimizeReferences>true</OptimizeReferences>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemGroup>
|
||||
<Text Include="ReadMe.txt" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="..\..\..\Downloads\sign_np-master\tlzrc.c" />
|
||||
<ClCompile Include="amctrl.c" />
|
||||
<ClCompile Include="bn.c" />
|
||||
<ClCompile Include="crypto.c" />
|
||||
<ClCompile Include="dnas.c" />
|
||||
<ClCompile Include="ec.c" />
|
||||
<ClCompile Include="edata.c" />
|
||||
<ClCompile Include="kirk_engine.c" />
|
||||
<ClCompile Include="pgd.c" />
|
||||
<ClCompile Include="utils.c" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="..\..\..\Downloads\sign_np-master\tlzrc.h" />
|
||||
<ClInclude Include="amctrl.h" />
|
||||
<ClInclude Include="crypto.h" />
|
||||
<ClInclude Include="ecdsa.h" />
|
||||
<ClInclude Include="kirk_engine.h" />
|
||||
<ClInclude Include="psp_headers.h" />
|
||||
<ClInclude Include="utils.h" />
|
||||
</ItemGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
|
||||
<ImportGroup Label="ExtensionTargets">
|
||||
</ImportGroup>
|
||||
</Project>
|
|
@ -1,75 +0,0 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup>
|
||||
<Filter Include="Source Files">
|
||||
<UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
|
||||
<Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
|
||||
</Filter>
|
||||
<Filter Include="Header Files">
|
||||
<UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
|
||||
<Extensions>h;hh;hpp;hxx;hm;inl;inc;xsd</Extensions>
|
||||
</Filter>
|
||||
<Filter Include="Resource Files">
|
||||
<UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
|
||||
<Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
|
||||
</Filter>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Text Include="ReadMe.txt" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="amctrl.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="bn.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="crypto.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="ec.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="kirk_engine.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="edata.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="pgd.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="dnas.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="utils.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\..\..\Downloads\sign_np-master\tlzrc.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="kirk_engine.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="amctrl.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="crypto.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="ecdsa.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="psp_headers.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="utils.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="..\..\..\Downloads\sign_np-master\tlzrc.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
</ItemGroup>
|
||||
</Project>
|
|
@ -1,13 +0,0 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
||||
<DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
|
||||
<LocalDebuggerCommand>$(SolutionDir)CHOVY-SIGN\bin\$(Configuration)\CHOVY-SIGN.EXE</LocalDebuggerCommand>
|
||||
<LocalDebuggerDebuggerType>Mixed</LocalDebuggerDebuggerType>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
|
||||
<LocalDebuggerCommand>$(SolutionDir)CHOVY-SIGN\bin\$(Configuration)\CHOVY-SIGN.EXE</LocalDebuggerCommand>
|
||||
<LocalDebuggerDebuggerType>Mixed</LocalDebuggerDebuggerType>
|
||||
</PropertyGroup>
|
||||
</Project>
|
1463
CHOVY-KIRK/aes.c
1463
CHOVY-KIRK/aes.c
File diff suppressed because it is too large
Load Diff
|
@ -1,694 +0,0 @@
|
|||
/*
|
||||
* amctrl.c -- Reverse engineering of amctrl.prx
|
||||
* written by tpu.
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "crypto.h"
|
||||
#include "kirk_engine.h"
|
||||
#include "psp_headers.h"
|
||||
#include "amctrl.h"
|
||||
|
||||
/*************************************************************/
|
||||
|
||||
static u8 loc_1CD4[16] = {0xE3, 0x50, 0xED, 0x1D, 0x91, 0x0A, 0x1F, 0xD0, 0x29, 0xBB, 0x1C, 0x3E, 0xF3, 0x40, 0x77, 0xFB};
|
||||
static u8 loc_1CE4[16] = {0x13, 0x5F, 0xA4, 0x7C, 0xAB, 0x39, 0x5B, 0xA4, 0x76, 0xB8, 0xCC, 0xA9, 0x8F, 0x3A, 0x04, 0x45};
|
||||
static u8 loc_1CF4[16] = {0x67, 0x8D, 0x7F, 0xA3, 0x2A, 0x9C, 0xA0, 0xD1, 0x50, 0x8A, 0xD8, 0x38, 0x5E, 0x4B, 0x01, 0x7E};
|
||||
|
||||
static u8 kirk_buf[0x0814]; // 1DC0 1DD4
|
||||
|
||||
/*************************************************************/
|
||||
|
||||
static int kirk4(u8 *buf, int size, int type)
|
||||
{
|
||||
int retv;
|
||||
u32 *header = (u32*)buf;
|
||||
|
||||
header[0] = 4;
|
||||
header[1] = 0;
|
||||
header[2] = 0;
|
||||
header[3] = type;
|
||||
header[4] = size;
|
||||
|
||||
retv = sceUtilsBufferCopyWithRange(buf, size+0x14, buf, size, 4);
|
||||
|
||||
if(retv)
|
||||
return 0x80510311;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int kirk7(u8 *buf, int size, int type)
|
||||
{
|
||||
int retv;
|
||||
u32 *header = (u32*)buf;
|
||||
|
||||
header[0] = 5;
|
||||
header[1] = 0;
|
||||
header[2] = 0;
|
||||
header[3] = type;
|
||||
header[4] = size;
|
||||
|
||||
retv = sceUtilsBufferCopyWithRange(buf, size+0x14, buf, size, 7);
|
||||
if(retv)
|
||||
return 0x80510311;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int kirk5(u8 *buf, int size)
|
||||
{
|
||||
int retv;
|
||||
u32 *header = (u32*)buf;
|
||||
|
||||
header[0] = 4;
|
||||
header[1] = 0;
|
||||
header[2] = 0;
|
||||
header[3] = 0x0100;
|
||||
header[4] = size;
|
||||
|
||||
retv = sceUtilsBufferCopyWithRange(buf, size+0x14, buf, size, 5);
|
||||
if(retv)
|
||||
return 0x80510312;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int kirk8(u8 *buf, int size)
|
||||
{
|
||||
int retv;
|
||||
u32 *header = (u32*)buf;
|
||||
|
||||
header[0] = 5;
|
||||
header[1] = 0;
|
||||
header[2] = 0;
|
||||
header[3] = 0x0100;
|
||||
header[4] = size;
|
||||
|
||||
retv = sceUtilsBufferCopyWithRange(buf, size+0x14, buf, size, 8);
|
||||
if(retv)
|
||||
return 0x80510312;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int kirk14(u8 *buf)
|
||||
{
|
||||
int retv;
|
||||
|
||||
retv = sceUtilsBufferCopyWithRange(buf, 0x14, 0, 0, 14);
|
||||
if(retv)
|
||||
return 0x80510315;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*************************************************************/
|
||||
|
||||
// Called by sceDrmBBMacUpdate
|
||||
// encrypt_buf
|
||||
static int sub_158(u8 *buf, int size, u8 *key, int key_type)
|
||||
{
|
||||
int i, retv;
|
||||
|
||||
for(i=0; i<16; i++){
|
||||
buf[0x14+i] ^= key[i];
|
||||
}
|
||||
|
||||
retv = kirk4(buf, size, key_type);
|
||||
if(retv)
|
||||
return retv;
|
||||
|
||||
// copy last 16 bytes to keys
|
||||
memcpy(key, buf+size+4, 16);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
// type:
|
||||
// 2: use fuse id
|
||||
// 3: use fixed id
|
||||
__declspec(dllexport) int sceDrmBBMacInit(MAC_KEY *mkey, int type)
|
||||
{
|
||||
mkey->type = type;
|
||||
mkey->pad_size = 0;
|
||||
|
||||
memset(mkey->key, 0, 16);
|
||||
memset(mkey->pad, 0, 16);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
__declspec(dllexport) int sceDrmBBMacUpdate(MAC_KEY *mkey, u8 *buf, int size)
|
||||
{
|
||||
int retv = 0, ksize, p, type;
|
||||
u8 *kbuf;
|
||||
|
||||
if(mkey->pad_size>16){
|
||||
retv = 0x80510302;
|
||||
goto _exit;
|
||||
}
|
||||
|
||||
if(mkey->pad_size+size<=16){
|
||||
memcpy(mkey->pad+mkey->pad_size, buf, size);
|
||||
mkey->pad_size += size;
|
||||
retv = 0;
|
||||
}else{
|
||||
kbuf = kirk_buf+0x14;
|
||||
// copy pad data first
|
||||
memcpy(kbuf, mkey->pad, mkey->pad_size);
|
||||
|
||||
p = mkey->pad_size;
|
||||
|
||||
mkey->pad_size += size;
|
||||
mkey->pad_size &= 0x0f;
|
||||
if(mkey->pad_size==0)
|
||||
mkey->pad_size = 16;
|
||||
|
||||
size -= mkey->pad_size;
|
||||
// save last data to pad buf
|
||||
memcpy(mkey->pad, buf+size, mkey->pad_size);
|
||||
|
||||
type = (mkey->type==2)? 0x3A : 0x38;
|
||||
|
||||
while(size){
|
||||
ksize = (size+p>=0x0800)? 0x0800 : size+p;
|
||||
memcpy(kbuf+p, buf, ksize-p);
|
||||
retv = sub_158(kirk_buf, ksize, mkey->key, type);
|
||||
if(retv)
|
||||
goto _exit;
|
||||
size -= (ksize-p);
|
||||
buf += ksize-p;
|
||||
p = 0;
|
||||
}
|
||||
}
|
||||
|
||||
_exit:
|
||||
return retv;
|
||||
|
||||
}
|
||||
|
||||
__declspec(dllexport) int sceDrmBBMacFinal(MAC_KEY *mkey, u8 *buf, u8 *vkey)
|
||||
{
|
||||
int i, retv, code;
|
||||
u8 *kbuf, tmp[16], tmp1[16];
|
||||
u32 t0, v0, v1;
|
||||
|
||||
if(mkey->pad_size>16)
|
||||
return 0x80510302;
|
||||
|
||||
code = (mkey->type==2)? 0x3A : 0x38;
|
||||
kbuf = kirk_buf+0x14;
|
||||
|
||||
memset(kbuf, 0, 16);
|
||||
retv = kirk4(kirk_buf, 16, code);
|
||||
if(retv)
|
||||
goto _exit;
|
||||
memcpy(tmp, kbuf, 16);
|
||||
|
||||
// left shift tmp 1 bit
|
||||
t0 = (tmp[0]&0x80)? 0x87 : 0;
|
||||
for(i=0; i<15; i++){
|
||||
v1 = tmp[i+0];
|
||||
v0 = tmp[i+1];
|
||||
v1 <<= 1;
|
||||
v0 >>= 7;
|
||||
v0 |= v1;
|
||||
tmp[i+0] = v0;
|
||||
}
|
||||
v0 = tmp[15];
|
||||
v0 <<= 1;
|
||||
v0 ^= t0;
|
||||
tmp[15] = v0;
|
||||
|
||||
// padding remain data
|
||||
if(mkey->pad_size<16){
|
||||
// left shift tmp 1 bit
|
||||
t0 = (tmp[0]&0x80)? 0x87 : 0;
|
||||
for(i=0; i<15; i++){
|
||||
v1 = tmp[i+0];
|
||||
v0 = tmp[i+1];
|
||||
v1 <<= 1;
|
||||
v0 >>= 7;
|
||||
v0 |= v1;
|
||||
tmp[i+0] = v0;
|
||||
}
|
||||
v0 = tmp[15];
|
||||
v0 <<= 1;
|
||||
v0 ^= t0;
|
||||
tmp[15] = v0;
|
||||
|
||||
mkey->pad[mkey->pad_size] = 0x80;
|
||||
if(mkey->pad_size+1<16)
|
||||
memset(mkey->pad+mkey->pad_size+1, 0, 16-mkey->pad_size-1);
|
||||
}
|
||||
|
||||
for(i=0; i<16; i++){
|
||||
mkey->pad[i] ^= tmp[i];
|
||||
}
|
||||
|
||||
memcpy(kbuf, mkey->pad, 16);
|
||||
memcpy(tmp1, mkey->key, 16);
|
||||
|
||||
retv = sub_158(kirk_buf, 0x10, tmp1, code);
|
||||
if(retv)
|
||||
return retv;
|
||||
|
||||
for(i=0; i<0x10; i++){
|
||||
tmp1[i] ^= loc_1CD4[i];
|
||||
}
|
||||
|
||||
if(mkey->type==2){
|
||||
memcpy(kbuf, tmp1, 16);
|
||||
|
||||
retv = kirk5(kirk_buf, 0x10);
|
||||
if(retv)
|
||||
goto _exit;
|
||||
|
||||
retv = kirk4(kirk_buf, 0x10, code);
|
||||
if(retv)
|
||||
goto _exit;
|
||||
|
||||
memcpy(tmp1, kbuf, 16);
|
||||
}
|
||||
|
||||
if(vkey){
|
||||
for(i=0; i<0x10; i++){
|
||||
tmp1[i] ^= vkey[i];
|
||||
}
|
||||
memcpy(kbuf, tmp1, 16);
|
||||
|
||||
retv = kirk4(kirk_buf, 0x10, code);
|
||||
if(retv)
|
||||
goto _exit;
|
||||
|
||||
memcpy(tmp1, kbuf, 16);
|
||||
}
|
||||
|
||||
memcpy(buf, tmp1, 16);
|
||||
|
||||
memset(mkey->key, 0, 16);
|
||||
memset(mkey->pad, 0, 16);
|
||||
|
||||
mkey->pad_size = 0;
|
||||
mkey->type = 0;
|
||||
retv = 0;
|
||||
|
||||
_exit:
|
||||
return retv;
|
||||
}
|
||||
|
||||
__declspec(dllexport) int sceDrmBBMacFinal2(MAC_KEY *mkey, u8 *out, u8 *vkey)
|
||||
{
|
||||
int i, retv, type;
|
||||
u8 *kbuf, tmp[16];
|
||||
|
||||
type = mkey->type;
|
||||
retv = sceDrmBBMacFinal(mkey, tmp, vkey);
|
||||
if(retv)
|
||||
return retv;
|
||||
|
||||
kbuf = kirk_buf+0x14;
|
||||
|
||||
// decrypt bbmac
|
||||
if(type==3){
|
||||
memcpy(kbuf, out, 0x10);
|
||||
kirk7(kirk_buf, 0x10, 0x63);
|
||||
}else{
|
||||
memcpy(kirk_buf, out, 0x10);
|
||||
}
|
||||
|
||||
retv = 0;
|
||||
for(i=0; i<0x10; i++){
|
||||
if(kirk_buf[i]!=tmp[i]){
|
||||
retv = 0x80510300;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return retv;
|
||||
}
|
||||
|
||||
__declspec(dllexport) int bbmac_build_final2(int type, u8 *mac)
|
||||
{
|
||||
u8 *kbuf = kirk_buf+0x14;
|
||||
|
||||
if(type==3){
|
||||
memcpy(kbuf, mac, 16);
|
||||
kirk4(kirk_buf, 0x10, 0x63);
|
||||
memcpy(mac, kbuf, 16);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
// get key from bbmac
|
||||
__declspec(dllexport) int bbmac_getkey(MAC_KEY *mkey, u8 *bbmac, u8 *vkey)
|
||||
{
|
||||
int i, retv, type, code;
|
||||
u8 *kbuf, tmp[16], tmp1[16];
|
||||
|
||||
type = mkey->type;
|
||||
retv = sceDrmBBMacFinal(mkey, tmp, NULL);
|
||||
if(retv)
|
||||
return retv;
|
||||
|
||||
kbuf = kirk_buf+0x14;
|
||||
|
||||
// decrypt bbmac
|
||||
if(type==3){
|
||||
memcpy(kbuf, bbmac, 0x10);
|
||||
kirk7(kirk_buf, 0x10, 0x63);
|
||||
}else{
|
||||
memcpy(kirk_buf, bbmac, 0x10);
|
||||
}
|
||||
|
||||
memcpy(tmp1, kirk_buf, 16);
|
||||
memcpy(kbuf, tmp1, 16);
|
||||
|
||||
code = (type==2)? 0x3A : 0x38;
|
||||
kirk7(kirk_buf, 0x10, code);
|
||||
|
||||
for(i=0; i<0x10; i++){
|
||||
vkey[i] = tmp[i] ^ kirk_buf[i];
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
__declspec(dllexport) int bbmac_forge(MAC_KEY *mkey, u8 *bbmac, u8 *vkey, u8 *buf)
|
||||
{
|
||||
int i, retv, type;
|
||||
u8 *kbuf, tmp[16], tmp1[16];
|
||||
u32 t0, v0, v1;
|
||||
|
||||
if(mkey->pad_size>16)
|
||||
return 0x80510302;
|
||||
|
||||
type = (mkey->type==2)? 0x3A : 0x38;
|
||||
kbuf = kirk_buf+0x14;
|
||||
|
||||
memset(kbuf, 0, 16);
|
||||
retv = kirk4(kirk_buf, 16, type);
|
||||
if(retv)
|
||||
return retv;
|
||||
memcpy(tmp, kbuf, 16);
|
||||
|
||||
// left shift tmp 1 bit
|
||||
t0 = (tmp[0]&0x80)? 0x87 : 0;
|
||||
for(i=0; i<15; i++){
|
||||
v1 = tmp[i+0];
|
||||
v0 = tmp[i+1];
|
||||
v1 <<= 1;
|
||||
v0 >>= 7;
|
||||
v0 |= v1;
|
||||
tmp[i+0] = v0;
|
||||
}
|
||||
v0 = tmp[15];
|
||||
v0 <<= 1;
|
||||
v0 ^= t0;
|
||||
tmp[15] = v0;
|
||||
|
||||
// padding remain data
|
||||
if(mkey->pad_size<16){
|
||||
// left shift tmp 1 bit
|
||||
t0 = (tmp[0]&0x80)? 0x87 : 0;
|
||||
for(i=0; i<15; i++){
|
||||
v1 = tmp[i+0];
|
||||
v0 = tmp[i+1];
|
||||
v1 <<= 1;
|
||||
v0 >>= 7;
|
||||
v0 |= v1;
|
||||
tmp[i+0] = v0;
|
||||
}
|
||||
v0 = tmp[15];
|
||||
v0 <<= 1;
|
||||
v0 ^= t0;
|
||||
tmp[15] = t0;
|
||||
|
||||
mkey->pad[mkey->pad_size] = 0x80;
|
||||
if(mkey->pad_size+1<16)
|
||||
memset(mkey->pad+mkey->pad_size+1, 0, 16-mkey->pad_size-1);
|
||||
}
|
||||
|
||||
for(i=0; i<16; i++){
|
||||
mkey->pad[i] ^= tmp[i];
|
||||
}
|
||||
for(i=0; i<0x10; i++){
|
||||
mkey->pad[i] ^= mkey->key[i];
|
||||
}
|
||||
|
||||
// reverse order
|
||||
memcpy(kbuf, bbmac, 0x10);
|
||||
kirk7(kirk_buf, 0x10, 0x63);
|
||||
|
||||
memcpy(kbuf, kirk_buf, 0x10);
|
||||
kirk7(kirk_buf, 0x10, type);
|
||||
|
||||
memcpy(tmp1, kirk_buf, 0x10);
|
||||
for(i=0; i<0x10; i++){
|
||||
tmp1[i] ^= vkey[i];
|
||||
}
|
||||
for(i=0; i<0x10; i++){
|
||||
tmp1[i] ^= loc_1CD4[i];
|
||||
}
|
||||
|
||||
memcpy(kbuf, tmp1, 0x10);
|
||||
kirk7(kirk_buf, 0x10, type);
|
||||
|
||||
memcpy(tmp1, kirk_buf, 0x10);
|
||||
for(i=0; i<16; i++){
|
||||
mkey->pad[i] ^= tmp1[i];
|
||||
}
|
||||
|
||||
// modify the last 16 bytes
|
||||
for(i=0; i<16; i++){
|
||||
buf[i] ^= mkey->pad[i];
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/*************************************************************/
|
||||
|
||||
static int sub_1F8(u8 *buf, int size, u8 *key, int key_type)
|
||||
{
|
||||
int i, retv;
|
||||
u8 tmp[16];
|
||||
|
||||
// copy last 16 bytes to tmp
|
||||
memcpy(tmp, buf+size+0x14-16, 16);
|
||||
|
||||
retv = kirk7(buf, size, key_type);
|
||||
if(retv)
|
||||
return retv;
|
||||
|
||||
for(i=0; i<16; i++){
|
||||
buf[i] ^= key[i];
|
||||
}
|
||||
|
||||
// copy last 16 bytes to keys
|
||||
memcpy(key, tmp, 16);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
static int sub_428(u8 *kbuf, u8 *dbuf, int size, CIPHER_KEY *ckey)
|
||||
{
|
||||
int i, retv;
|
||||
u8 tmp1[16], tmp2[16];
|
||||
|
||||
memcpy(kbuf+0x14, ckey->key, 16);
|
||||
|
||||
for(i=0; i<16; i++){
|
||||
kbuf[0x14+i] ^= loc_1CF4[i];
|
||||
}
|
||||
|
||||
if(ckey->type==2)
|
||||
retv = kirk8(kbuf, 16);
|
||||
else
|
||||
retv = kirk7(kbuf, 16, 0x39);
|
||||
if(retv)
|
||||
return retv;
|
||||
|
||||
for(i=0; i<16; i++){
|
||||
kbuf[i] ^= loc_1CE4[i];
|
||||
}
|
||||
|
||||
memcpy(tmp2, kbuf, 0x10);
|
||||
|
||||
if(ckey->seed==1){
|
||||
memset(tmp1, 0, 0x10);
|
||||
}else{
|
||||
memcpy(tmp1, tmp2, 0x10);
|
||||
*(u32*)(tmp1+0x0c) = ckey->seed-1;
|
||||
}
|
||||
|
||||
for(i=0; i<size; i+=16){
|
||||
memcpy(kbuf+0x14+i, tmp2, 12);
|
||||
*(u32*)(kbuf+0x14+i+12) = ckey->seed;
|
||||
ckey->seed += 1;
|
||||
}
|
||||
|
||||
retv = sub_1F8(kbuf, size, tmp1, 0x63);
|
||||
if(retv)
|
||||
return retv;
|
||||
|
||||
for(i=0; i<size; i++){
|
||||
dbuf[i] ^= kbuf[i];
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
// type: 1 use fixed key
|
||||
// 2 use fuse id
|
||||
// mode: 1 for encrypt
|
||||
// 2 for decrypt
|
||||
__declspec(dllexport) int sceDrmBBCipherInit(CIPHER_KEY *ckey, int type, int mode, u8 *header_key, u8 *version_key, u32 seed)
|
||||
{
|
||||
int i, retv;
|
||||
u8 *kbuf;
|
||||
|
||||
kbuf = kirk_buf+0x14;
|
||||
ckey->type = type;
|
||||
if(mode==2){
|
||||
ckey->seed = seed+1;
|
||||
for(i=0; i<16; i++){
|
||||
ckey->key[i] = header_key[i];
|
||||
}
|
||||
if(version_key){
|
||||
for(i=0; i<16; i++){
|
||||
ckey->key[i] ^= version_key[i];
|
||||
}
|
||||
}
|
||||
retv = 0;
|
||||
}else if(mode==1){
|
||||
ckey->seed = 1;
|
||||
retv = kirk14(kirk_buf);
|
||||
if(retv)
|
||||
return retv;
|
||||
|
||||
memcpy(kbuf, kirk_buf, 0x10);
|
||||
memset(kbuf+0x0c, 0, 4);
|
||||
|
||||
if(ckey->type==2){
|
||||
for(i=0; i<16; i++){
|
||||
kbuf[i] ^= loc_1CE4[i];
|
||||
}
|
||||
retv = kirk5(kirk_buf, 0x10);
|
||||
for(i=0; i<16; i++){
|
||||
kbuf[i] ^= loc_1CF4[i];
|
||||
}
|
||||
}else{
|
||||
for(i=0; i<16; i++){
|
||||
kbuf[i] ^= loc_1CE4[i];
|
||||
}
|
||||
retv = kirk4(kirk_buf, 0x10, 0x39);
|
||||
for(i=0; i<16; i++){
|
||||
kbuf[i] ^= loc_1CF4[i];
|
||||
}
|
||||
}
|
||||
if(retv)
|
||||
return retv;
|
||||
|
||||
memcpy(ckey->key, kbuf, 0x10);
|
||||
memcpy(header_key, kbuf, 0x10);
|
||||
|
||||
if(version_key){
|
||||
for(i=0; i<16; i++){
|
||||
ckey->key[i] ^= version_key[i];
|
||||
}
|
||||
}
|
||||
}else{
|
||||
retv = 0;
|
||||
}
|
||||
|
||||
return retv;
|
||||
}
|
||||
|
||||
__declspec(dllexport) int sceDrmBBCipherUpdate(CIPHER_KEY *ckey, u8 *data, int size)
|
||||
{
|
||||
int p, retv, dsize;
|
||||
|
||||
retv = 0;
|
||||
p = 0;
|
||||
|
||||
while(size>0){
|
||||
dsize = (size>=0x0800)? 0x0800 : size;
|
||||
retv = sub_428(kirk_buf, data+p, dsize, ckey);
|
||||
if(retv)
|
||||
break;
|
||||
size -= dsize;
|
||||
p += dsize;
|
||||
}
|
||||
|
||||
return retv;
|
||||
}
|
||||
|
||||
__declspec(dllexport) int sceDrmBBCipherFinal(CIPHER_KEY *ckey)
|
||||
{
|
||||
memset(ckey->key, 0, 16);
|
||||
ckey->type = 0;
|
||||
ckey->seed = 0;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*************************************************************/
|
||||
|
||||
// AES128 encrypt key
|
||||
static u8 key_357C[0x30] = {
|
||||
0x07,0x3D,0x9E,0x9D,0xA8,0xFD,0x3B,0x2F,0x63,0x18,0x93,0x2E,0xF8,0x57,0xA6,0x64,
|
||||
0x37,0x49,0xB7,0x01,0xCA,0xE2,0xE0,0xC5,0x44,0x2E,0x06,0xB6,0x1E,0xFF,0x84,0xF2,
|
||||
0x9D,0x31,0xB8,0x5A,0xC8,0xFA,0x16,0x80,0x73,0x60,0x18,0x82,0x18,0x77,0x91,0x9D,
|
||||
};
|
||||
|
||||
static u8 key_363C[16] = {
|
||||
0x38,0x20,0xD0,0x11,0x07,0xA3,0xFF,0x3E,0x0A,0x4C,0x20,0x85,0x39,0x10,0xB5,0x54,
|
||||
};
|
||||
|
||||
int sceNpDrmGetFixedKey(u8 *key, char *npstr, int type)
|
||||
{
|
||||
AES_ctx akey;
|
||||
MAC_KEY mkey;
|
||||
char strbuf[0x30];
|
||||
int retv;
|
||||
|
||||
if((type&0x01000000)==0)
|
||||
return 0x80550901;
|
||||
type &= 0x000000ff;
|
||||
|
||||
memset(strbuf, 0, 0x30);
|
||||
strncpy(strbuf, npstr, 0x30);
|
||||
|
||||
retv = sceDrmBBMacInit(&mkey, 1);
|
||||
if(retv)
|
||||
return retv;
|
||||
|
||||
retv = sceDrmBBMacUpdate(&mkey, (u8*)strbuf, 0x30);
|
||||
if(retv)
|
||||
return retv;
|
||||
|
||||
retv = sceDrmBBMacFinal(&mkey, key, key_363C);
|
||||
if(retv)
|
||||
return 0x80550902;
|
||||
|
||||
if(type==0)
|
||||
return 0;
|
||||
if(type>3)
|
||||
return 0x80550901;
|
||||
type = (type-1)*16;
|
||||
|
||||
AES_set_key(&akey, &key_357C[type], 128);
|
||||
AES_encrypt(&akey, key, key);
|
||||
|
||||
return 0;
|
||||
}
|
|
@ -1,41 +0,0 @@
|
|||
#ifndef AMCTRL_H
|
||||
#define AMCTRL_H
|
||||
|
||||
typedef struct {
|
||||
int type;
|
||||
u8 key[16];
|
||||
u8 pad[16];
|
||||
int pad_size;
|
||||
} MAC_KEY;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
u32 type;
|
||||
u32 seed;
|
||||
u8 key[16];
|
||||
} CIPHER_KEY;
|
||||
|
||||
// type:
|
||||
// 2: use fuse id
|
||||
// 3: use fixed key. MAC need encrypt again
|
||||
__declspec(dllexport) int sceDrmBBMacInit(MAC_KEY *mkey, int type);
|
||||
__declspec(dllexport) int sceDrmBBMacUpdate(MAC_KEY *mkey, u8 *buf, int size);
|
||||
__declspec(dllexport) int sceDrmBBMacFinal(MAC_KEY *mkey, u8 *buf, u8 *vkey);
|
||||
__declspec(dllexport) int sceDrmBBMacFinal2(MAC_KEY *mkey, u8 *out, u8 *vkey);
|
||||
|
||||
__declspec(dllexport) int bbmac_build_final2(int type, u8 *mac);
|
||||
__declspec(dllexport) int bbmac_getkey(MAC_KEY *mkey, u8 *bbmac, u8 *vkey);
|
||||
__declspec(dllexport) int bbmac_forge(MAC_KEY *mkey, u8 *bbmac, u8 *vkey, u8 *buf);
|
||||
|
||||
// type: 1 use fixed key
|
||||
// 2 use fuse id
|
||||
// mode: 1 for encrypt
|
||||
// 2 for decrypt
|
||||
__declspec(dllexport) int sceDrmBBCipherInit(CIPHER_KEY *ckey, int type, int mode, u8 *header_key, u8 *version_key, u32 seed);
|
||||
__declspec(dllexport) int sceDrmBBCipherUpdate(CIPHER_KEY *ckey, u8 *data, int size);
|
||||
__declspec(dllexport) int sceDrmBBCipherFinal(CIPHER_KEY *ckey);
|
||||
|
||||
// npdrm.prx
|
||||
__declspec(dllexport) int sceNpDrmGetFixedKey(u8 *key, char *npstr, int type);
|
||||
|
||||
#endif
|
305
CHOVY-KIRK/bn.c
305
CHOVY-KIRK/bn.c
|
@ -1,305 +0,0 @@
|
|||
// Copyright 2007,2008,2010 Segher Boessenkool <segher@kernel.crashing.org>
|
||||
// Licensed under the terms of the GNU GPL, version 2
|
||||
// http://www.gnu.org/licenses/old-licenses/gpl-2.0.txt
|
||||
|
||||
#include <string.h>
|
||||
#include <stdio.h>
|
||||
|
||||
#include "kirk_engine.h"
|
||||
#include "ecdsa.h"
|
||||
|
||||
|
||||
void bn_dump(char *str, u8 *buf, u32 size)
|
||||
{
|
||||
u32 i;
|
||||
|
||||
printf("%16s: ", str);
|
||||
for(i=0; i<size; i++){
|
||||
printf("%02x", buf[i]);
|
||||
}
|
||||
printf("\n");
|
||||
}
|
||||
static void bn_zero(u8* d, u32 n)
|
||||
{
|
||||
memset(d, 0, n);
|
||||
}
|
||||
|
||||
void bn_copy(u8* d, u8* a, u32 n)
|
||||
{
|
||||
memcpy(d, a, n);
|
||||
}
|
||||
|
||||
int bn_is_zero(u8 *d, u32 n)
|
||||
{
|
||||
int i;
|
||||
|
||||
for(i=0; i<n; i++){
|
||||
if(d[i])
|
||||
return 0;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
int bn_compare(u8* a, u8* b, u32 n)
|
||||
{
|
||||
u32 i;
|
||||
|
||||
for (i = 0; i < n; i++) {
|
||||
if (a[i] < b[i])
|
||||
return -1;
|
||||
if (a[i] > b[i])
|
||||
return 1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
static u8 bn_add_1(u8* d, u8* a, u8* b, u32 n)
|
||||
{
|
||||
u32 i;
|
||||
u32 dig;
|
||||
u8 c;
|
||||
|
||||
c = 0;
|
||||
for (i = n - 1; i < n; i--) {
|
||||
dig = a[i] + b[i] + c;
|
||||
c = dig >> 8;
|
||||
d[i] = dig;
|
||||
}
|
||||
|
||||
return c;
|
||||
}
|
||||
|
||||
static u8 bn_sub_1(u8* d, u8* a, u8* b, u32 n)
|
||||
{
|
||||
u32 i;
|
||||
u32 dig;
|
||||
u8 c;
|
||||
|
||||
c = 1;
|
||||
for (i = n - 1; i < n; i--) {
|
||||
dig = a[i] + 255 - b[i] + c;
|
||||
c = dig >> 8;
|
||||
d[i] = dig;
|
||||
}
|
||||
|
||||
return 1 - c;
|
||||
}
|
||||
|
||||
void bn_reduce(u8* d, u8* N, u32 n)
|
||||
{
|
||||
if (bn_compare(d, N, n) >= 0)
|
||||
bn_sub_1(d, d, N, n);
|
||||
}
|
||||
|
||||
void bn_add(u8* d, u8* a, u8* b, u8* N, u32 n)
|
||||
{
|
||||
if (bn_add_1(d, a, b, n))
|
||||
bn_sub_1(d, d, N, n);
|
||||
|
||||
bn_reduce(d, N, n);
|
||||
}
|
||||
|
||||
void bn_sub(u8* d, u8* a, u8* b, u8* N, u32 n)
|
||||
{
|
||||
if (bn_sub_1(d, a, b, n))
|
||||
bn_add_1(d, d, N, n);
|
||||
}
|
||||
static const u8 inv256[0x80] = {
|
||||
0x01, 0xab, 0xcd, 0xb7, 0x39, 0xa3, 0xc5, 0xef,
|
||||
0xf1, 0x1b, 0x3d, 0xa7, 0x29, 0x13, 0x35, 0xdf,
|
||||
0xe1, 0x8b, 0xad, 0x97, 0x19, 0x83, 0xa5, 0xcf,
|
||||
0xd1, 0xfb, 0x1d, 0x87, 0x09, 0xf3, 0x15, 0xbf,
|
||||
0xc1, 0x6b, 0x8d, 0x77, 0xf9, 0x63, 0x85, 0xaf,
|
||||
0xb1, 0xdb, 0xfd, 0x67, 0xe9, 0xd3, 0xf5, 0x9f,
|
||||
0xa1, 0x4b, 0x6d, 0x57, 0xd9, 0x43, 0x65, 0x8f,
|
||||
0x91, 0xbb, 0xdd, 0x47, 0xc9, 0xb3, 0xd5, 0x7f,
|
||||
0x81, 0x2b, 0x4d, 0x37, 0xb9, 0x23, 0x45, 0x6f,
|
||||
0x71, 0x9b, 0xbd, 0x27, 0xa9, 0x93, 0xb5, 0x5f,
|
||||
0x61, 0x0b, 0x2d, 0x17, 0x99, 0x03, 0x25, 0x4f,
|
||||
0x51, 0x7b, 0x9d, 0x07, 0x89, 0x73, 0x95, 0x3f,
|
||||
0x41, 0xeb, 0x0d, 0xf7, 0x79, 0xe3, 0x05, 0x2f,
|
||||
0x31, 0x5b, 0x7d, 0xe7, 0x69, 0x53, 0x75, 0x1f,
|
||||
0x21, 0xcb, 0xed, 0xd7, 0x59, 0xc3, 0xe5, 0x0f,
|
||||
0x11, 0x3b, 0x5d, 0xc7, 0x49, 0x33, 0x55, 0xff,
|
||||
};
|
||||
|
||||
static void bn_mon_muladd_dig(u8* d, u8* a, u8 b, u8* N, u32 n)
|
||||
{
|
||||
u32 dig;
|
||||
u32 i;
|
||||
|
||||
u8 z = -(d[n - 1] + a[n - 1] * b) * inv256[N[n - 1] / 2];
|
||||
|
||||
dig = d[n - 1] + a[n - 1] * b + N[n - 1] * z;
|
||||
dig >>= 8;
|
||||
|
||||
for (i = n - 2; i < n; i--) {
|
||||
dig += d[i] + a[i] * b + N[i] * z;
|
||||
d[i + 1] = dig;
|
||||
dig >>= 8;
|
||||
}
|
||||
|
||||
d[0] = dig;
|
||||
dig >>= 8;
|
||||
|
||||
if (dig)
|
||||
bn_sub_1(d, d, N, n);
|
||||
|
||||
bn_reduce(d, N, n);
|
||||
}
|
||||
|
||||
void bn_mon_mul(u8* d, u8* a, u8* b, u8* N, u32 n)
|
||||
{
|
||||
u8 t[512];
|
||||
u32 i;
|
||||
|
||||
bn_zero(t, n);
|
||||
|
||||
for (i = n - 1; i < n; i--)
|
||||
bn_mon_muladd_dig(t, a, b[i], N, n);
|
||||
|
||||
bn_copy(d, t, n);
|
||||
}
|
||||
|
||||
void bn_to_mon(u8* d, u8* N, u32 n)
|
||||
{
|
||||
u32 i;
|
||||
|
||||
for (i = 0; i < 8 * n; i++)
|
||||
bn_add(d, d, d, N, n);
|
||||
}
|
||||
|
||||
void bn_from_mon(u8* d, u8* N, u32 n)
|
||||
{
|
||||
u8 t[512];
|
||||
|
||||
bn_zero(t, n);
|
||||
t[n - 1] = 1;
|
||||
bn_mon_mul(d, d, t, N, n);
|
||||
}
|
||||
|
||||
static void bn_mon_exp(u8* d, u8* a, u8* N, u32 n, u8* e, u32 en)
|
||||
{
|
||||
u8 t[512];
|
||||
u32 i;
|
||||
u8 mask;
|
||||
|
||||
bn_zero(d, n);
|
||||
d[n - 1] = 1;
|
||||
bn_to_mon(d, N, n);
|
||||
|
||||
for (i = 0; i < en; i++)
|
||||
for (mask = 0x80; mask != 0; mask >>= 1) {
|
||||
bn_mon_mul(t, d, d, N, n);
|
||||
if ((e[i] & mask) != 0)
|
||||
bn_mon_mul(d, t, a, N, n);
|
||||
else
|
||||
bn_copy(d, t, n);
|
||||
}
|
||||
}
|
||||
|
||||
void bn_mon_inv(u8* d, u8* a, u8* N, u32 n)
|
||||
{
|
||||
u8 t[512], s[512];
|
||||
|
||||
bn_zero(s, n);
|
||||
s[n - 1] = 2;
|
||||
bn_sub_1(t, N, s, n);
|
||||
bn_mon_exp(d, a, N, n, t, n);
|
||||
}
|
||||
|
||||
/*************************************************************/
|
||||
|
||||
void bn_mul(u8 *d, u8 *a, u8 *b, u8 *N, u32 n)
|
||||
{
|
||||
u32 i;
|
||||
u8 mask;
|
||||
u8 td[512];
|
||||
|
||||
bn_zero(td, 512);
|
||||
|
||||
for (i = 0; i < n; i++){
|
||||
for (mask = 0x80; mask != 0; mask >>= 1) {
|
||||
bn_add(td, td, td, N, n);
|
||||
if ((a[i] & mask) != 0)
|
||||
bn_add(td, td, b, N, n);
|
||||
}
|
||||
}
|
||||
|
||||
bn_copy(d, td, n);
|
||||
}
|
||||
|
||||
/*************************************************************/
|
||||
|
||||
static int bn_is_odd(u8 *d, u32 n)
|
||||
{
|
||||
return (d[n-1])&1;
|
||||
}
|
||||
|
||||
static void bn_rshift1(u8 *d, u8 *a, u32 n)
|
||||
{
|
||||
u8 b, c;
|
||||
int i;
|
||||
|
||||
c = 0;
|
||||
for(i=0; i<n; i++){
|
||||
b = a[i];
|
||||
a[i] = (b>>1)|c;
|
||||
c = (b<<7)&0x80;
|
||||
}
|
||||
}
|
||||
|
||||
void bn_gcd(u8 *out_d, u8 *in_a, u8 *in_b, u32 n)
|
||||
{
|
||||
u8 a[512], b[512], t[512], mn[512];
|
||||
int shift;
|
||||
|
||||
shift = 0;
|
||||
memset(mn, 0, 512);
|
||||
mn[0] = 0x80;
|
||||
|
||||
memcpy(a, in_a, n);
|
||||
memcpy(b, in_b, n);
|
||||
|
||||
if(bn_compare(a, b, n)<0){
|
||||
memcpy(t, a, n);
|
||||
memcpy(a, b, n);
|
||||
memcpy(b, t, n);
|
||||
}
|
||||
|
||||
while(!bn_is_zero(b, n)){
|
||||
if(bn_is_odd(a, n)){
|
||||
if(bn_is_odd(b, n)){
|
||||
bn_sub(a, a, b, mn, n);
|
||||
bn_rshift1(a, a, n);
|
||||
if(bn_compare(a, b, n)<0){
|
||||
memcpy(t, a, n);
|
||||
memcpy(a, b, n);
|
||||
memcpy(b, t, n);
|
||||
}
|
||||
}else{
|
||||
bn_rshift1(b, b, n);
|
||||
}
|
||||
}else{
|
||||
if(bn_is_odd(b, n)){
|
||||
bn_rshift1(a, a, n);
|
||||
if(bn_compare(a, b, n)<0){
|
||||
memcpy(t, a, n);
|
||||
memcpy(a, b, n);
|
||||
memcpy(b, t, n);
|
||||
}
|
||||
}else{
|
||||
bn_rshift1(a, a, n);
|
||||
bn_rshift1(b, b, n);
|
||||
shift += 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// skip this step
|
||||
//bn_lshift(a, a, shift, n);
|
||||
|
||||
memcpy(out_d, a, n);
|
||||
}
|
||||
|
1537
CHOVY-KIRK/crypto.c
1537
CHOVY-KIRK/crypto.c
File diff suppressed because it is too large
Load Diff
|
@ -1,56 +0,0 @@
|
|||
#ifndef __RIJNDAEL_H
|
||||
#define __RIJNDAEL_H
|
||||
|
||||
#include "kirk_engine.h"
|
||||
|
||||
#define AES_KEY_LEN_128 (128)
|
||||
#define AES_KEY_LEN_192 (192)
|
||||
#define AES_KEY_LEN_256 (256)
|
||||
|
||||
#define AES_BUFFER_SIZE (16)
|
||||
|
||||
#define AES_MAXKEYBITS (256)
|
||||
#define AES_MAXKEYBYTES (AES_MAXKEYBITS/8)
|
||||
/* for 256-bit keys, fewer for less */
|
||||
#define AES_MAXROUNDS 14
|
||||
|
||||
/* The structure for key information */
|
||||
typedef struct
|
||||
{
|
||||
int enc_only; /* context contains only encrypt schedule */
|
||||
int Nr; /* key-length-dependent number of rounds */
|
||||
u32 ek[4*(AES_MAXROUNDS + 1)]; /* encrypt key schedule */
|
||||
u32 dk[4*(AES_MAXROUNDS + 1)]; /* decrypt key schedule */
|
||||
} AES_ctx;
|
||||
|
||||
|
||||
int AES_set_key(AES_ctx *ctx, const u8 *key, int bits);
|
||||
void AES_encrypt(AES_ctx *ctx, const u8 *src, u8 *dst);
|
||||
void AES_decrypt(AES_ctx *ctx, const u8 *src, u8 *dst);
|
||||
void AES_cbc_encrypt(AES_ctx *ctx, u8 *src, u8 *dst, int size);
|
||||
void AES_cbc_decrypt(AES_ctx *ctx, u8 *src, u8 *dst, int size);
|
||||
void AES_CMAC(AES_ctx *ctx, unsigned char *input, int length, unsigned char *mac);
|
||||
void rijndael_encrypt(AES_ctx* ctx, const u8* src, u8* dst);
|
||||
void rijndael_decrypt(AES_ctx* ctx, const u8* src, u8* dst);
|
||||
int rijndael_set_key(AES_ctx* ctx, const u8* key, int bits);
|
||||
|
||||
typedef struct SHA1Context
|
||||
{
|
||||
unsigned Message_Digest[5]; /* Message Digest (output) */
|
||||
unsigned Length_Low; /* Message length in bits */
|
||||
unsigned Length_High; /* Message length in bits */
|
||||
unsigned char Message_Block[64]; /* 512-bit message blocks */
|
||||
int Message_Block_Index; /* Index into message block array */
|
||||
int Computed; /* Is the digest computed? */
|
||||
int Corrupted; /* Is the message digest corruped? */
|
||||
} SHA1Context;
|
||||
|
||||
/*
|
||||
* Function Prototypes
|
||||
*/
|
||||
void SHA1Reset(SHA1Context *);
|
||||
void SHA1Input(SHA1Context *, const unsigned char *, unsigned);
|
||||
int SHA1Result(SHA1Context *);
|
||||
void SHA1(unsigned char *d, size_t n, unsigned char *md);
|
||||
|
||||
#endif /* __RIJNDAEL_H */
|
|
@ -1,182 +0,0 @@
|
|||
/*
|
||||
* dnas.c -- Reverse engineering of iofilemgr_dnas.prx
|
||||
* written by tpu.
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "kirk_engine.h"
|
||||
#include "crypto.h"
|
||||
#include "psp_headers.h"
|
||||
#include "amctrl.h"
|
||||
|
||||
/*************************************************************/
|
||||
|
||||
typedef struct {
|
||||
unsigned __int8 key[16]; // 00: used to decrypt data content.
|
||||
unsigned __int32 version; // 10: always 00
|
||||
unsigned __int32 data_size; // 14
|
||||
unsigned __int32 block_size; // 18
|
||||
unsigned __int32 data_offset; // 1C
|
||||
unsigned __int8 unk_20[16];
|
||||
}PGD_DESC;
|
||||
|
||||
|
||||
typedef struct {
|
||||
PGD_DESC pgdesc;
|
||||
unsigned __int32 key_index; // 0x30
|
||||
unsigned __int8 pgd_key[16]; // 0x34
|
||||
unsigned __int32 flag; // 0x44
|
||||
unsigned __int32 flag_open; // 0x48
|
||||
unsigned __int32 pgd_offset; // 0x4C
|
||||
int seek_offset; // 0x50
|
||||
unsigned __int32 data_offset; // 0x54
|
||||
unsigned __int32 table_offset;// 0x58
|
||||
unsigned __int32 unk_5c;
|
||||
unsigned __int32 unk_60;
|
||||
}PspIoHookParam;
|
||||
|
||||
|
||||
unsigned __int8 dnas_key1A90[] = {0xED,0xE2,0x5D,0x2D,0xBB,0xF8,0x12,0xE5,0x3C,0x5C,0x59,0x32,0xFA,0xE3,0xE2,0x43};
|
||||
unsigned __int8 dnas_key1AA0[] = {0x27,0x74,0xFB,0xEB,0xA4,0xA0, 1,0xD7,2,0x56,0x9E,0x33,0x8C,0x19,0x57,0x83};
|
||||
|
||||
__declspec(dllexport) int process_pgd(unsigned __int8 *pgd_buf, int pgd_size, int pgd_flag)
|
||||
{
|
||||
MAC_KEY mkey;
|
||||
CIPHER_KEY ckey;
|
||||
unsigned __int8 *fkey, vkey[16];
|
||||
int key_index, mac_type, cipher_type, drm_type;
|
||||
int retv, file_size, block_size, data_offset, table_size, align_size;
|
||||
|
||||
|
||||
key_index = *(unsigned __int32*)(pgd_buf+4);
|
||||
drm_type = *(unsigned __int32*)(pgd_buf+8);
|
||||
|
||||
if(drm_type==1){
|
||||
mac_type = 1;
|
||||
pgd_flag |= 4;
|
||||
if(key_index>1){
|
||||
mac_type = 3;
|
||||
pgd_flag |= 8;
|
||||
}
|
||||
cipher_type = 1;
|
||||
}else{
|
||||
mac_type = 2;
|
||||
cipher_type = 2;
|
||||
}
|
||||
|
||||
// select fixed key
|
||||
fkey = NULL;
|
||||
if(pgd_flag&2)
|
||||
fkey = dnas_key1A90;
|
||||
if(pgd_flag&1)
|
||||
fkey = dnas_key1AA0;
|
||||
if(fkey==NULL){
|
||||
printf("invalid pgd_flag! %08x\n", pgd_flag);
|
||||
return -1;
|
||||
}
|
||||
|
||||
// MAC_0x80 check
|
||||
sceDrmBBMacInit(&mkey, mac_type);
|
||||
sceDrmBBMacUpdate(&mkey, pgd_buf+0x00, 0x80);
|
||||
retv = sceDrmBBMacFinal2(&mkey, pgd_buf+0x80, fkey);
|
||||
if(retv){
|
||||
printf("MAC_80 check failed!: %08x(%d)\n", retv, retv);
|
||||
return -2;
|
||||
}
|
||||
|
||||
// MAC_0x70
|
||||
sceDrmBBMacInit(&mkey, mac_type);
|
||||
sceDrmBBMacUpdate(&mkey, pgd_buf+0x00, 0x70);
|
||||
bbmac_getkey(&mkey, pgd_buf+0x70, vkey);
|
||||
hex_dump("Get version_key from MAC_70:", vkey, 16);
|
||||
|
||||
// decrypt PGD_DESC
|
||||
sceDrmBBCipherInit(&ckey, cipher_type, 2, pgd_buf+0x10, vkey, 0);
|
||||
sceDrmBBCipherUpdate(&ckey, pgd_buf+0x30, 0x30);
|
||||
sceDrmBBCipherFinal(&ckey);
|
||||
hex_dump("PGD header", pgd_buf, 0x90);
|
||||
|
||||
file_size = *(unsigned __int32*)(pgd_buf+0x44);
|
||||
block_size = *(unsigned __int32*)(pgd_buf+0x48);
|
||||
data_offset = *(unsigned __int32*)(pgd_buf+0x4c);
|
||||
|
||||
file_size = (file_size+15)&~15;
|
||||
align_size = (file_size+block_size-1)&~(block_size-1);
|
||||
table_size = align_size/block_size;
|
||||
table_size *= 16;
|
||||
|
||||
if(file_size+table_size>pgd_size){
|
||||
printf("invalid pgd data!\n");
|
||||
return -3;
|
||||
}
|
||||
|
||||
// table MAC check
|
||||
sceDrmBBMacInit(&mkey, mac_type);
|
||||
sceDrmBBMacUpdate(&mkey, pgd_buf+data_offset+file_size, table_size);
|
||||
retv = sceDrmBBMacFinal(&mkey, pgd_buf+0x60, vkey);
|
||||
if(retv){
|
||||
printf("MAC_table check failed!: %08x(%d)\n", retv, retv);
|
||||
return -4;
|
||||
}
|
||||
|
||||
// decrypt data
|
||||
sceDrmBBCipherInit(&ckey, cipher_type, 2, pgd_buf+0x30, vkey, 0);
|
||||
sceDrmBBCipherUpdate(&ckey, pgd_buf+0x90, file_size);
|
||||
sceDrmBBCipherFinal(&ckey);
|
||||
hex_dump("PGD data", pgd_buf+0x90, (file_size>0x100)? 0x100 : file_size);
|
||||
|
||||
file_size = *(unsigned __int32*)(pgd_buf+0x44);
|
||||
return file_size;
|
||||
}
|
||||
|
||||
int decrypt_pgd(unsigned __int8 *pgd_buf, int pgd_size, int pgd_flag, unsigned __int8 *pgd_vkey);
|
||||
|
||||
__declspec(dllexport) int process_pgd_file(char *pgd_file)
|
||||
{
|
||||
unsigned __int8 *data_buf, *pgd_buf;
|
||||
char fname[256];
|
||||
int retv, data_size, pgd_size, pgd_flag;
|
||||
|
||||
data_buf = load_file(pgd_file, &data_size);
|
||||
if(data_buf==NULL){
|
||||
printf("Open input file <%s> error!\n", pgd_file);
|
||||
return -1;
|
||||
}
|
||||
if(data_size<0x90){
|
||||
free(data_buf);
|
||||
return -1;
|
||||
}
|
||||
|
||||
if(*(unsigned __int32*)(data_buf+0)==0x44475000){
|
||||
pgd_buf = data_buf;
|
||||
pgd_size = data_size;
|
||||
}else if(*(unsigned __int32*)(data_buf+0x90)==0x44475000){
|
||||
pgd_buf = data_buf+0x90;
|
||||
pgd_size = data_size-0x90;
|
||||
}else{
|
||||
free(data_buf);
|
||||
return -1;
|
||||
}
|
||||
printf("\nProcess %s ...\n", pgd_file);
|
||||
|
||||
// 0x40xxxxxx : 2
|
||||
// 0x44xxxxxx : 1
|
||||
// default as 2
|
||||
pgd_flag = 2;
|
||||
|
||||
retv = decrypt_pgd(pgd_buf, pgd_size, pgd_flag, NULL);
|
||||
if(retv>0){
|
||||
sprintf(fname, "%s.decrypt", pgd_file);
|
||||
write_file(fname, pgd_buf+0x90, retv);
|
||||
printf("Save %s ...\n", fname);
|
||||
}
|
||||
|
||||
free(data_buf);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
|
407
CHOVY-KIRK/ec.c
407
CHOVY-KIRK/ec.c
|
@ -1,407 +0,0 @@
|
|||
// Copyright 2007,2008,2010 Segher Boessenkool <segher@kernel.crashing.org>
|
||||
// Licensed under the terms of the GNU GPL, version 2
|
||||
// http://www.gnu.org/licenses/old-licenses/gpl-2.0.txt
|
||||
|
||||
#include <string.h>
|
||||
#include <stdio.h>
|
||||
|
||||
#include "kirk_engine.h"
|
||||
|
||||
struct point {
|
||||
u8 x[20];
|
||||
u8 y[20];
|
||||
};
|
||||
|
||||
u8 ec_p[20];
|
||||
u8 ec_a[20];
|
||||
u8 ec_b[20];
|
||||
u8 ec_N[21];
|
||||
struct point ec_G; // mon
|
||||
struct point ec_Q; // mon
|
||||
u8 ec_k[21];
|
||||
|
||||
static void elt_copy(u8* d, u8* a)
|
||||
{
|
||||
memcpy(d, a, 20);
|
||||
}
|
||||
|
||||
static void elt_zero(u8* d)
|
||||
{
|
||||
memset(d, 0, 20);
|
||||
}
|
||||
|
||||
static int elt_is_zero(u8* d)
|
||||
{
|
||||
u32 i;
|
||||
|
||||
for (i = 0; i < 20; i++)
|
||||
if (d[i] != 0)
|
||||
return 0;
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static void elt_add(u8* d, u8* a, u8* b)
|
||||
{
|
||||
bn_add(d, a, b, ec_p, 20);
|
||||
}
|
||||
|
||||
static void elt_sub(u8* d, u8* a, u8* b)
|
||||
{
|
||||
bn_sub(d, a, b, ec_p, 20);
|
||||
}
|
||||
|
||||
static void elt_mul(u8* d, u8* a, u8* b)
|
||||
{
|
||||
bn_mon_mul(d, a, b, ec_p, 20);
|
||||
}
|
||||
|
||||
static void elt_square(u8* d, u8* a)
|
||||
{
|
||||
elt_mul(d, a, a);
|
||||
}
|
||||
|
||||
static void elt_inv(u8* d, u8* a)
|
||||
{
|
||||
u8 s[20];
|
||||
elt_copy(s, a);
|
||||
bn_mon_inv(d, s, ec_p, 20);
|
||||
}
|
||||
|
||||
static void point_to_mon(struct point* p)
|
||||
{
|
||||
bn_to_mon(p->x, ec_p, 20);
|
||||
bn_to_mon(p->y, ec_p, 20);
|
||||
}
|
||||
|
||||
static void point_from_mon(struct point* p)
|
||||
{
|
||||
bn_from_mon(p->x, ec_p, 20);
|
||||
bn_from_mon(p->y, ec_p, 20);
|
||||
}
|
||||
|
||||
#if 0
|
||||
static int point_is_on_curve(u8* p)
|
||||
{
|
||||
u8 s[20], t[20];
|
||||
u8* x, * y;
|
||||
|
||||
x = p;
|
||||
y = p + 20;
|
||||
|
||||
elt_square(t, x);
|
||||
elt_mul(s, t, x);
|
||||
|
||||
elt_mul(t, x, ec_a);
|
||||
elt_add(s, s, t);
|
||||
|
||||
elt_add(s, s, ec_b);
|
||||
|
||||
elt_square(t, y);
|
||||
elt_sub(s, s, t);
|
||||
|
||||
return elt_is_zero(s);
|
||||
}
|
||||
#endif
|
||||
|
||||
static void point_zero(struct point* p)
|
||||
{
|
||||
elt_zero(p->x);
|
||||
elt_zero(p->y);
|
||||
}
|
||||
|
||||
static int point_is_zero(struct point* p)
|
||||
{
|
||||
return elt_is_zero(p->x) && elt_is_zero(p->y);
|
||||
}
|
||||
|
||||
static void point_double(struct point* r, struct point* p)
|
||||
{
|
||||
u8 s[20], t[20];
|
||||
struct point pp;
|
||||
u8* px, * py, * rx, * ry;
|
||||
|
||||
pp = *p;
|
||||
|
||||
px = pp.x;
|
||||
py = pp.y;
|
||||
rx = r->x;
|
||||
ry = r->y;
|
||||
|
||||
if (elt_is_zero(py)) {
|
||||
point_zero(r);
|
||||
return;
|
||||
}
|
||||
|
||||
elt_square(t, px); // t = px*px
|
||||
elt_add(s, t, t); // s = 2*px*px
|
||||
elt_add(s, s, t); // s = 3*px*px
|
||||
elt_add(s, s, ec_a); // s = 3*px*px + a
|
||||
elt_add(t, py, py); // t = 2*py
|
||||
elt_inv(t, t); // t = 1/(2*py)
|
||||
elt_mul(s, s, t); // s = (3*px*px+a)/(2*py)
|
||||
|
||||
elt_square(rx, s); // rx = s*s
|
||||
elt_add(t, px, px); // t = 2*px
|
||||
elt_sub(rx, rx, t); // rx = s*s - 2*px
|
||||
|
||||
elt_sub(t, px, rx); // t = -(rx-px)
|
||||
elt_mul(ry, s, t); // ry = -s*(rx-px)
|
||||
elt_sub(ry, ry, py); // ry = -s*(rx-px) - py
|
||||
}
|
||||
|
||||
static void point_add(struct point* r, struct point* p, struct point* q)
|
||||
{
|
||||
u8 s[20], t[20], u[20];
|
||||
u8* px, * py, * qx, * qy, * rx, * ry;
|
||||
struct point pp, qq;
|
||||
|
||||
pp = *p;
|
||||
qq = *q;
|
||||
|
||||
px = pp.x;
|
||||
py = pp.y;
|
||||
qx = qq.x;
|
||||
qy = qq.y;
|
||||
rx = r->x;
|
||||
ry = r->y;
|
||||
|
||||
if (point_is_zero(&pp)) {
|
||||
elt_copy(rx, qx);
|
||||
elt_copy(ry, qy);
|
||||
return;
|
||||
}
|
||||
|
||||
if (point_is_zero(&qq)) {
|
||||
elt_copy(rx, px);
|
||||
elt_copy(ry, py);
|
||||
return;
|
||||
}
|
||||
|
||||
elt_sub(u, qx, px);
|
||||
|
||||
if (elt_is_zero(u)) {
|
||||
elt_sub(u, qy, py);
|
||||
if (elt_is_zero(u))
|
||||
point_double(r, &pp);
|
||||
else
|
||||
point_zero(r);
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
elt_inv(t, u); // t = 1/(qx-px)
|
||||
elt_sub(u, qy, py); // u = qy-py
|
||||
elt_mul(s, t, u); // s = (qy-py)/(qx-px)
|
||||
|
||||
elt_square(rx, s); // rx = s*s
|
||||
elt_add(t, px, qx); // t = px+qx
|
||||
elt_sub(rx, rx, t); // rx = s*s - (px+qx)
|
||||
|
||||
elt_sub(t, px, rx); // t = -(rx-px)
|
||||
elt_mul(ry, s, t); // ry = -s*(rx-px)
|
||||
elt_sub(ry, ry, py); // ry = -s*(rx-px) - py
|
||||
}
|
||||
|
||||
static void point_mul(struct point* d, u8* a, struct point* b)
|
||||
{
|
||||
u32 i;
|
||||
u8 mask;
|
||||
|
||||
point_zero(d);
|
||||
|
||||
for (i = 0; i < 21; i++)
|
||||
for (mask = 0x80; mask != 0; mask >>= 1) {
|
||||
point_double(d, d);
|
||||
if ((a[i] & mask) != 0)
|
||||
point_add(d, d, b);
|
||||
}
|
||||
}
|
||||
|
||||
static void generate_ecdsa(u8* outR, u8* outS, u8* k, u8* hash)
|
||||
{
|
||||
u8 e[21];
|
||||
u8 kk[21];
|
||||
u8 m[21];
|
||||
u8 R[21];
|
||||
u8 S[21];
|
||||
u8 minv[21];
|
||||
struct point mG;
|
||||
|
||||
e[0] = 0; R[0] = 0; S[0] = 0;
|
||||
memcpy(e + 1, hash, 20);
|
||||
bn_reduce(e, ec_N, 21);
|
||||
|
||||
kirk_CMD14(m + 1, 20);
|
||||
m[0] = 0;
|
||||
|
||||
point_mul(&mG, m, &ec_G);
|
||||
point_from_mon(&mG);
|
||||
R[0] = 0;
|
||||
elt_copy(R + 1, mG.x);
|
||||
|
||||
bn_copy(kk, k, 21);
|
||||
bn_reduce(kk, ec_N, 21);
|
||||
bn_to_mon(m, ec_N, 21);
|
||||
bn_to_mon(e, ec_N, 21);
|
||||
bn_to_mon(R, ec_N, 21);
|
||||
bn_to_mon(kk, ec_N, 21);
|
||||
|
||||
bn_mon_mul(S, R, kk, ec_N, 21);
|
||||
bn_add(kk, S, e, ec_N, 21);
|
||||
bn_mon_inv(minv, m, ec_N, 21);
|
||||
bn_mon_mul(S, minv, kk, ec_N, 21);
|
||||
|
||||
bn_from_mon(R, ec_N, 21);
|
||||
bn_from_mon(S, ec_N, 21);
|
||||
memcpy(outR, R + 1, 0x20);
|
||||
memcpy(outS, S + 1, 0x20);
|
||||
}
|
||||
|
||||
static int check_ecdsa(struct point* Q, u8* inR, u8* inS, u8* hash)
|
||||
{
|
||||
u8 Sinv[21];
|
||||
u8 e[21], R[21], S[21];
|
||||
u8 w1[21], w2[21];
|
||||
struct point r1, r2;
|
||||
u8 rr[21];
|
||||
|
||||
e[0] = 0;
|
||||
memcpy(e + 1, hash, 20);
|
||||
bn_reduce(e, ec_N, 21);
|
||||
R[0] = 0;
|
||||
memcpy(R + 1, inR, 20);
|
||||
bn_reduce(R, ec_N, 21);
|
||||
S[0] = 0;
|
||||
memcpy(S + 1, inS, 20);
|
||||
bn_reduce(S, ec_N, 21);
|
||||
|
||||
bn_to_mon(R, ec_N, 21);
|
||||
bn_to_mon(S, ec_N, 21);
|
||||
bn_to_mon(e, ec_N, 21);
|
||||
// make Sinv = 1/S
|
||||
bn_mon_inv(Sinv, S, ec_N, 21);
|
||||
// w1 = m * Sinv
|
||||
bn_mon_mul(w1, e, Sinv, ec_N, 21);
|
||||
// w2 = r * Sinv
|
||||
bn_mon_mul(w2, R, Sinv, ec_N, 21);
|
||||
|
||||
// mod N both
|
||||
bn_from_mon(w1, ec_N, 21);
|
||||
bn_from_mon(w2, ec_N, 21);
|
||||
|
||||
// r1 = m/s * G
|
||||
point_mul(&r1, w1, &ec_G);
|
||||
// r2 = r/s * P
|
||||
point_mul(&r2, w2, Q);
|
||||
|
||||
//r1 = r1 + r2
|
||||
point_add(&r1, &r1, &r2);
|
||||
|
||||
point_from_mon(&r1);
|
||||
|
||||
rr[0] = 0;
|
||||
memcpy(rr + 1, r1.x, 20);
|
||||
bn_reduce(rr, ec_N, 21);
|
||||
|
||||
bn_from_mon(R, ec_N, 21);
|
||||
bn_from_mon(S, ec_N, 21);
|
||||
|
||||
return (bn_compare(rr, R, 21) == 0);
|
||||
}
|
||||
|
||||
void ec_priv_to_pub(u8* k, u8* Q)
|
||||
{
|
||||
struct point ec_temp;
|
||||
bn_to_mon(k, ec_N, 21);
|
||||
point_mul(&ec_temp, k, &ec_G);
|
||||
point_from_mon(&ec_temp);
|
||||
memcpy(Q, ec_temp.x, 20);
|
||||
memcpy(Q + 20, ec_temp.y, 20);
|
||||
}
|
||||
|
||||
void ec_pub_mult(u8* k, u8* Q)
|
||||
{
|
||||
struct point ec_temp;
|
||||
point_mul(&ec_temp, k, &ec_Q);
|
||||
point_from_mon(&ec_temp);
|
||||
memcpy(Q, ec_temp.x, 20);
|
||||
memcpy(Q + 20, ec_temp.y, 20);
|
||||
}
|
||||
|
||||
int ecdsa_set_curve(u8* p, u8* a, u8* b, u8* N, u8* Gx, u8* Gy)
|
||||
{
|
||||
memcpy(ec_p, p, 20);
|
||||
memcpy(ec_a, a, 20);
|
||||
memcpy(ec_b, b, 20);
|
||||
memcpy(ec_N, N, 21);
|
||||
|
||||
bn_to_mon(ec_a, ec_p, 20);
|
||||
bn_to_mon(ec_b, ec_p, 20);
|
||||
|
||||
memcpy(ec_G.x, Gx, 20);
|
||||
memcpy(ec_G.y, Gy, 20);
|
||||
point_to_mon(&ec_G);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void ecdsa_set_pub(u8* Q)
|
||||
{
|
||||
memcpy(ec_Q.x, Q, 20);
|
||||
memcpy(ec_Q.y, Q + 20, 20);
|
||||
point_to_mon(&ec_Q);
|
||||
}
|
||||
|
||||
void ecdsa_set_priv(u8* ink)
|
||||
{
|
||||
u8 k[21];
|
||||
k[0] = 0;
|
||||
memcpy(k + 1, ink, 20);
|
||||
bn_reduce(k, ec_N, 21);
|
||||
|
||||
memcpy(ec_k, k, sizeof ec_k);
|
||||
}
|
||||
|
||||
int ecdsa_verify(u8* hash, u8* R, u8* S)
|
||||
{
|
||||
return check_ecdsa(&ec_Q, R, S, hash);
|
||||
}
|
||||
|
||||
void ecdsa_sign(u8* hash, u8* R, u8* S)
|
||||
{
|
||||
generate_ecdsa(R, S, ec_k, hash);
|
||||
}
|
||||
|
||||
int point_is_on_curve(u8* p)
|
||||
{
|
||||
u8 s[20], t[20];
|
||||
u8* x, * y;
|
||||
|
||||
x = p;
|
||||
y = p + 20;
|
||||
|
||||
elt_square(t, x);
|
||||
elt_mul(s, t, x);// s = x^3
|
||||
|
||||
elt_mul(t, x, ec_a);
|
||||
elt_add(s, s, t); //s = x^3 + a *x
|
||||
|
||||
elt_add(s, s, ec_b);//s = x^3 + a *x + b
|
||||
|
||||
elt_square(t, y); //t = y^2
|
||||
elt_sub(s, s, t); // is s - t = 0?
|
||||
hex_dump("S", s, 20);
|
||||
hex_dump("T", t, 20);
|
||||
return elt_is_zero(s);
|
||||
}
|
||||
|
||||
void dump_ecc(void)
|
||||
{
|
||||
hex_dump("P", ec_p, 20);
|
||||
hex_dump("a", ec_a, 20);
|
||||
hex_dump("b", ec_b, 20);
|
||||
hex_dump("N", ec_N, 21);
|
||||
hex_dump("Gx", ec_G.x, 20);
|
||||
hex_dump("Gy", ec_G.y, 20);
|
||||
}
|
|
@ -1,31 +0,0 @@
|
|||
// Copyright 2010 Sven Peter <svenpeter@gmail.com>
|
||||
// Copyright 2007,2008,2010 Segher Boessenkool <segher@kernel.crashing.org>
|
||||
// Licensed under the terms of the GNU GPL, version 2
|
||||
// http://www.gnu.org/licenses/old-licenses/gpl-2.0.txt
|
||||
|
||||
#ifndef ECDSA_H__
|
||||
#define ECDSA_H__ 1
|
||||
|
||||
int ecdsa_set_curve(u8* p, u8* a, u8* b, u8* N, u8* Gx, u8* Gy);
|
||||
void ecdsa_set_pub(u8 *Qx);
|
||||
void ecdsa_set_priv(u8 *k);
|
||||
int ecdsa_verify(u8 *hash, u8 *R, u8 *S);
|
||||
void ecdsa_sign(u8* hash, u8* R, u8* S);
|
||||
|
||||
void bn_dump(char *msg, u8 *d, u32 n);
|
||||
int bn_is_zero(u8 *d, u32 n);
|
||||
void bn_copy(u8 *d, u8 *a, u32 n);
|
||||
int bn_compare(u8 *a, u8 *b, u32 n);
|
||||
void bn_reduce(u8 *d, u8 *N, u32 n);
|
||||
void bn_add(u8 *d, u8 *a, u8 *b, u8 *N, u32 n);
|
||||
void bn_sub(u8 *d, u8 *a, u8 *b, u8 *N, u32 n);
|
||||
void bn_to_mon(u8 *d, u8 *N, u32 n);
|
||||
void bn_from_mon(u8 *d, u8 *N, u32 n);
|
||||
void bn_mon_mul(u8 *d, u8 *a, u8 *b, u8 *N, u32 n);
|
||||
void bn_mon_inv(u8 *d, u8 *a, u8 *N, u32 n);
|
||||
|
||||
void bn_mul(u8 *d, u8 *a, u8 *b, u8 *N, u32 n);
|
||||
void bn_gcd(u8 *out_d, u8 *in_a, u8 *in_b, u32 n);
|
||||
|
||||
#endif
|
||||
|
|
@ -1,155 +0,0 @@
|
|||
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include "kirk_engine.h"
|
||||
#include "amctrl.h"
|
||||
#include "crypto.h"
|
||||
#include "ecdsa.h"
|
||||
|
||||
|
||||
|
||||
unsigned __int8 pubkey_edat_x[20] = {0x1F,0x07,0x2B,0xCC,0xC1,0x62,0xF2,0xCF,0xAE,0xA0,0xE7,0xF4,0xCD,0xFD,0x9C,0xAE,0xC6,0xC4,0x55,0x21};
|
||||
unsigned __int8 pubkey_edat_y[20] = {0x53,0x01,0xF4,0xE3,0x70,0xC3,0xED,0xE2,0xD4,0xF5,0xDB,0xC3,0xA7,0xDE,0x8C,0xAA,0xE8,0xAD,0x5B,0x7D};
|
||||
|
||||
|
||||
unsigned __int8 edat_aeskey[16] = { 0xBA,0x87,0xE4,0xAB,0x2C,0x60,0x5F,0x59,0xB8,0x3B,0xDB,0xA6,0x82,0xFD,0xAE,0x14 };
|
||||
extern unsigned __int8 priv_key_edata[];
|
||||
|
||||
int verbose = 0;
|
||||
|
||||
/*************************************************************/
|
||||
|
||||
int edata_check_ecdsa(unsigned __int8 *edata_buf)
|
||||
{
|
||||
unsigned __int8 sha1_hash[20];
|
||||
int retv;
|
||||
|
||||
printf("EDATA ID: %s\n", (char*)(edata_buf+0x10));
|
||||
|
||||
ecdsa_set_curve(ec_p, ec_a, ec_b2, ec_N2, Gx2, Gy2);
|
||||
ecdsa_set_pub(pubkey_edat_x, pubkey_edat_y);
|
||||
|
||||
SHA1(edata_buf, 0x58, sha1_hash);
|
||||
retv = ecdsa_verify(sha1_hash, edata_buf+0x58, edata_buf+0x6c);
|
||||
if(retv==0){
|
||||
//printf("ECDSA verify passed!\n");
|
||||
}else{
|
||||
printf("edata_check_ecdsa: ECDSA verify failed!\n");
|
||||
}
|
||||
|
||||
return retv;
|
||||
}
|
||||
|
||||
|
||||
int edata_sign_free(unsigned __int8 *edata_buf, unsigned __int8 *pgd_key)
|
||||
{
|
||||
MAC_KEY mkey;
|
||||
AES_ctx aes;
|
||||
unsigned __int8 sha1_hash[20], license_key[16];
|
||||
int flag, i;
|
||||
|
||||
printf("re-sign EDATA ...\n");
|
||||
|
||||
flag = *(unsigned __int8*)(edata_buf+15);
|
||||
|
||||
// get license_key
|
||||
if(flag&1){
|
||||
sceDrmBBMacInit(&mkey, 3);
|
||||
sceDrmBBMacUpdate(&mkey, edata_buf, 0x80);
|
||||
bbmac_getkey(&mkey, edata_buf+0x80, license_key);
|
||||
if(verbose) hex_dump("license key", license_key, 16);
|
||||
}
|
||||
|
||||
// change to use free license
|
||||
*(unsigned __int32*)(edata_buf+8) = 0x01000000;
|
||||
|
||||
// build ecdsa
|
||||
ecdsa_set_curve(ec_p, ec_a, ec_b2, ec_N2, Gx2, Gy2);
|
||||
ecdsa_set_priv(priv_key_edata);
|
||||
SHA1(edata_buf, 0x58, sha1_hash);
|
||||
ecdsa_sign(sha1_hash, edata_buf+0x58, edata_buf+0x6c, NULL);
|
||||
|
||||
// build BBMAC
|
||||
if(flag&1){
|
||||
sceDrmBBMacInit(&mkey, 3);
|
||||
sceDrmBBMacUpdate(&mkey, edata_buf, 0x80);
|
||||
sceDrmBBMacFinal(&mkey, edata_buf+0x80, license_key);
|
||||
bbmac_build_final2(3, edata_buf+0x80);
|
||||
}
|
||||
|
||||
// build PGD key
|
||||
sceNpDrmGetFixedKey(pgd_key, (char*)(edata_buf+16), 0x01000000);
|
||||
if(verbose) hex_dump("get_fixed_key", pgd_key, 16);
|
||||
|
||||
if(flag&1){
|
||||
for(i=0; i<16; i++){
|
||||
pgd_key[i] ^= license_key[i];
|
||||
}
|
||||
}
|
||||
|
||||
AES_set_key(&aes, edat_aeskey, 128);
|
||||
AES_decrypt(&aes, pgd_key, pgd_key);
|
||||
if(verbose) hex_dump("new PGD key", pgd_key, 16);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*************************************************************/
|
||||
|
||||
|
||||
int decrypt_pgd(unsigned __int8 *pgd_buf, int pgd_size, int pgd_flag, unsigned __int8 *pgd_vkey);
|
||||
int encrypt_pgd(unsigned __int8 *pgd_buf, int pgd_flag, unsigned __int8 *vkey);
|
||||
|
||||
int free_edata(char *edata_name)
|
||||
{
|
||||
unsigned __int8 *edata_buf;
|
||||
unsigned __int32 *hd;
|
||||
unsigned __int8 pgd_key[16];
|
||||
int retv, edata_size, pgd_offset;
|
||||
|
||||
edata_buf = load_file(edata_name, &edata_size);
|
||||
if(edata_buf==NULL){
|
||||
printf("Open input file <%s> error!\n", edata_name);
|
||||
return -1;
|
||||
}
|
||||
|
||||
hd = (unsigned __int32*)edata_buf;
|
||||
if(hd[0]!=0x50535000 || hd[1]!=0x54414445){
|
||||
free(edata_buf);
|
||||
return -1;
|
||||
}
|
||||
printf("\nProcess %s ...\n", edata_name);
|
||||
|
||||
|
||||
retv = edata_check_ecdsa(edata_buf);
|
||||
if(retv)
|
||||
return retv;
|
||||
|
||||
edata_sign_free(edata_buf, pgd_key);
|
||||
|
||||
|
||||
// PGD
|
||||
pgd_offset = *(unsigned __int32*)(edata_buf+0x0c);
|
||||
pgd_offset &= 0x00ffffff;
|
||||
|
||||
retv = decrypt_pgd(edata_buf+pgd_offset, edata_size-pgd_offset, 2, NULL);
|
||||
if(retv<0){
|
||||
printf("pgd_decrypt failed! %08x(%d)\n", retv, retv);
|
||||
return -1;
|
||||
}
|
||||
|
||||
retv = encrypt_pgd(edata_buf+pgd_offset, 2, pgd_key);
|
||||
if(retv<0){
|
||||
printf("pgd_encrypt failed! %08x(%d)\n", retv, retv);
|
||||
return -1;
|
||||
}
|
||||
|
||||
write_file(edata_name, edata_buf, edata_size);
|
||||
printf("write %s\n\n", edata_name);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
@ -1,753 +0,0 @@
|
|||
/*
|
||||
KIRK ENGINE CODE
|
||||
Thx for coyotebean, Davee, hitchhikr, kgsws, Mathieulh, SilverSpring, Proxima
|
||||
*/
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <time.h>
|
||||
|
||||
#include "crypto.h"
|
||||
#include "ecdsa.h"
|
||||
|
||||
/* ------------------------- KEY VAULT ------------------------- */
|
||||
|
||||
|
||||
|
||||
|
||||
// ECDSA private key of kirk1
|
||||
u8 priv_key_kirk1[20] = {0xF3,0x92,0xE2,0x64,0x90,0xB8,0x0F,0xD8,0x89,0xF2,0xD9,0x72,0x2C,0x1F,0x34,0xD7,0x27,0x4F,0x98,0x3D};
|
||||
|
||||
// ECDSA public key of kirk1
|
||||
u8 pub_key_kirk1_x[20] = {0xED,0x9C,0xE5,0x82,0x34,0xE6,0x1A,0x53,0xC6,0x85,0xD6,0x4D,0x51,0xD0,0x23,0x6B,0xC3,0xB5,0xD4,0xB9 };
|
||||
u8 pub_key_kirk1_y[20] = {0x04,0x9D,0xF1,0xA0,0x75,0xC0,0xE0,0x4F,0xB3,0x44,0x85,0x8B,0x61,0xB7,0x9B,0x69,0xA6,0x3D,0x2C,0x39 };
|
||||
|
||||
|
||||
u8 kirk1_ec_m_header[20] = {0x7D,0x7E,0x46,0x85,0x4D,0x07,0xFA,0x0B,0xC6,0xE8,0xED,0x62,0x99,0x89,0x26,0x14,0x39,0x5F,0xEA,0xFC};
|
||||
u8 kirk1_ec_r_header[20] = {0x66,0x4f,0xe1,0xf2,0xe9,0xd6,0x63,0x36,0xf7,0x33,0x0b,0xca,0xb9,0x55,0x6d,0xb6,0xeb,0xe8,0x05,0xdc};
|
||||
|
||||
u8 kirk1_ec_m_data[20] = {0x15,0xee,0x16,0x24,0x12,0x09,0x58,0x16,0x0f,0x8b,0x1a,0x21,0x33,0x7a,0x38,0xf8,0x29,0xf7,0x2e,0x58};
|
||||
u8 kirk1_ec_r_data[20] = {0xcd,0xe3,0x88,0xa6,0x3c,0x1d,0x57,0xdc,0x5e,0x94,0xee,0xac,0x2e,0x6c,0x9f,0x2e,0x81,0xc7,0x1c,0x58};
|
||||
|
||||
// ECDSA param of applations
|
||||
|
||||
// ECDSA private key of EDATA
|
||||
u8 priv_key_edata[20] = {0xe5,0xc4,0xd0,0xa8,0x24,0x9a,0x6f,0x27,0xe5,0xe0,0xc9,0xd5,0x34,0xf4,0xda,0x15,0x22,0x3f,0x42,0xad};
|
||||
|
||||
|
||||
// AES key for kirk1
|
||||
u8 kirk1_key[16] = {0x98, 0xC9, 0x40, 0x97, 0x5C, 0x1D, 0x10, 0xE8, 0x7F, 0xE6, 0x0E, 0xA3, 0xFD, 0x03, 0xA8, 0xBA};
|
||||
|
||||
// AES key for kirk4/7
|
||||
u8 kirk7_key02[] = {0xB8, 0x13, 0xC3, 0x5E, 0xC6, 0x44, 0x41, 0xE3, 0xDC, 0x3C, 0x16, 0xF5, 0xB4, 0x5E, 0x64, 0x84};
|
||||
u8 kirk7_key03[] = {0x98, 0x02, 0xC4, 0xE6, 0xEC, 0x9E, 0x9E, 0x2F, 0xFC, 0x63, 0x4C, 0xE4, 0x2F, 0xBB, 0x46, 0x68};
|
||||
u8 kirk7_key04[] = {0x99, 0x24, 0x4C, 0xD2, 0x58, 0xF5, 0x1B, 0xCB, 0xB0, 0x61, 0x9C, 0xA7, 0x38, 0x30, 0x07, 0x5F};
|
||||
u8 kirk7_key05[] = {0x02, 0x25, 0xD7, 0xBA, 0x63, 0xEC, 0xB9, 0x4A, 0x9D, 0x23, 0x76, 0x01, 0xB3, 0xF6, 0xAC, 0x17};
|
||||
u8 kirk7_key07[] = {0x76, 0x36, 0x8B, 0x43, 0x8F, 0x77, 0xD8, 0x7E, 0xFE, 0x5F, 0xB6, 0x11, 0x59, 0x39, 0x88, 0x5C};
|
||||
u8 kirk7_key0C[] = {0x84, 0x85, 0xC8, 0x48, 0x75, 0x08, 0x43, 0xBC, 0x9B, 0x9A, 0xEC, 0xA7, 0x9C, 0x7F, 0x60, 0x18};
|
||||
u8 kirk7_key0D[] = {0xB5, 0xB1, 0x6E, 0xDE, 0x23, 0xA9, 0x7B, 0x0E, 0xA1, 0x7C, 0xDB, 0xA2, 0xDC, 0xDE, 0xC4, 0x6E};
|
||||
u8 kirk7_key0E[] = {0xC8, 0x71, 0xFD, 0xB3, 0xBC, 0xC5, 0xD2, 0xF2, 0xE2, 0xD7, 0x72, 0x9D, 0xDF, 0x82, 0x68, 0x82};
|
||||
u8 kirk7_key0F[] = {0x0A, 0xBB, 0x33, 0x6C, 0x96, 0xD4, 0xCD, 0xD8, 0xCB, 0x5F, 0x4B, 0xE0, 0xBA, 0xDB, 0x9E, 0x03};
|
||||
u8 kirk7_key10[] = {0x32, 0x29, 0x5B, 0xD5, 0xEA, 0xF7, 0xA3, 0x42, 0x16, 0xC8, 0x8E, 0x48, 0xFF, 0x50, 0xD3, 0x71};
|
||||
u8 kirk7_key11[] = {0x46, 0xF2, 0x5E, 0x8E, 0x4D, 0x2A, 0xA5, 0x40, 0x73, 0x0B, 0xC4, 0x6E, 0x47, 0xEE, 0x6F, 0x0A};
|
||||
u8 kirk7_key12[] = {0x5D, 0xC7, 0x11, 0x39, 0xD0, 0x19, 0x38, 0xBC, 0x02, 0x7F, 0xDD, 0xDC, 0xB0, 0x83, 0x7D, 0x9D};
|
||||
u8 kirk7_key38[] = {0x12, 0x46, 0x8D, 0x7E, 0x1C, 0x42, 0x20, 0x9B, 0xBA, 0x54, 0x26, 0x83, 0x5E, 0xB0, 0x33, 0x03};
|
||||
u8 kirk7_key39[] = {0xC4, 0x3B, 0xB6, 0xD6, 0x53, 0xEE, 0x67, 0x49, 0x3E, 0xA9, 0x5F, 0xBC, 0x0C, 0xED, 0x6F, 0x8A};
|
||||
u8 kirk7_key3A[] = {0x2C, 0xC3, 0xCF, 0x8C, 0x28, 0x78, 0xA5, 0xA6, 0x63, 0xE2, 0xAF, 0x2D, 0x71, 0x5E, 0x86, 0xBA};
|
||||
u8 kirk7_key44[] = {0x7D, 0xF4, 0x92, 0x65, 0xE3, 0xFA, 0xD6, 0x78, 0xD6, 0xFE, 0x78, 0xAD, 0xBB, 0x3D, 0xFB, 0x63};
|
||||
u8 kirk7_key4B[] = {0x0C, 0xFD, 0x67, 0x9A, 0xF9, 0xB4, 0x72, 0x4F, 0xD7, 0x8D, 0xD6, 0xE9, 0x96, 0x42, 0x28, 0x8B}; //1.xx game eboot.bin
|
||||
u8 kirk7_key53[] = {0xAF, 0xFE, 0x8E, 0xB1, 0x3D, 0xD1, 0x7E, 0xD8, 0x0A, 0x61, 0x24, 0x1C, 0x95, 0x92, 0x56, 0xB6};
|
||||
u8 kirk7_key57[] = {0x1C, 0x9B, 0xC4, 0x90, 0xE3, 0x06, 0x64, 0x81, 0xFA, 0x59, 0xFD, 0xB6, 0x00, 0xBB, 0x28, 0x70};
|
||||
u8 kirk7_key5D[] = {0x11, 0x5A, 0x5D, 0x20, 0xD5, 0x3A, 0x8D, 0xD3, 0x9C, 0xC5, 0xAF, 0x41, 0x0F, 0x0F, 0x18, 0x6F};
|
||||
u8 kirk7_key63[] = {0x9C, 0x9B, 0x13, 0x72, 0xF8, 0xC6, 0x40, 0xCF, 0x1C, 0x62, 0xF5, 0xD5, 0x92, 0xDD, 0xB5, 0x82};
|
||||
u8 kirk7_key64[] = {0x03, 0xB3, 0x02, 0xE8, 0x5F, 0xF3, 0x81, 0xB1, 0x3B, 0x8D, 0xAA, 0x2A, 0x90, 0xFF, 0x5E, 0x61};
|
||||
|
||||
// AES Key for kirk16
|
||||
u8 kirk16_key[0x10] = { 0x47, 0x5E, 0x09, 0xF4, 0xA2, 0x37, 0xDA, 0x9B, 0xEF, 0xFF, 0x3B, 0xC0, 0x77, 0x14, 0x3D, 0x8A };
|
||||
|
||||
/* ------------------------- INTERNAL STUFF ------------------------- */
|
||||
|
||||
typedef struct header_keys
|
||||
{
|
||||
u8 AES[16];
|
||||
u8 CMAC[16];
|
||||
}header_keys;
|
||||
|
||||
AES_ctx aes_kirk1;
|
||||
|
||||
int is_kirk_initialized = 0;
|
||||
|
||||
|
||||
|
||||
/* ------------------------- IMPLEMENTATION ------------------------- */
|
||||
|
||||
/*****************************************************************************/
|
||||
/* KIRK initial */
|
||||
/*****************************************************************************/
|
||||
|
||||
// Internal variables
|
||||
typedef struct kirk16_data
|
||||
{
|
||||
u8 fuseid[8];
|
||||
u8 mesh[0x40];
|
||||
} kirk16_data;
|
||||
|
||||
u32 g_fuse90;
|
||||
u32 g_fuse94;
|
||||
|
||||
AES_ctx aes_kirk1;
|
||||
u8 PRNG_DATA[0x14];
|
||||
|
||||
|
||||
// Internal functions
|
||||
u8* kirk_4_7_get_key(int key_type)
|
||||
{
|
||||
switch (key_type)
|
||||
{
|
||||
case(0x02): return kirk7_key02; break;
|
||||
case(0x03): return kirk7_key03; break;
|
||||
case(0x04): return kirk7_key04; break;
|
||||
case(0x05): return kirk7_key05; break;
|
||||
case(0x07): return kirk7_key07; break;
|
||||
case(0x0C): return kirk7_key0C; break;
|
||||
case(0x0D): return kirk7_key0D; break;
|
||||
case(0x0E): return kirk7_key0E; break;
|
||||
case(0x0F): return kirk7_key0F; break;
|
||||
case(0x10): return kirk7_key10; break;
|
||||
case(0x11): return kirk7_key11; break;
|
||||
case(0x12): return kirk7_key12; break;
|
||||
case(0x38): return kirk7_key38; break;
|
||||
case(0x39): return kirk7_key39; break;
|
||||
case(0x3A): return kirk7_key3A; break;
|
||||
case(0x44): return kirk7_key44; break;
|
||||
case(0x4B): return kirk7_key4B; break;
|
||||
case(0x53): return kirk7_key53; break;
|
||||
case(0x57): return kirk7_key57; break;
|
||||
case(0x5D): return kirk7_key5D; break;
|
||||
case(0x63): return kirk7_key63; break;
|
||||
case(0x64): return kirk7_key64; break;
|
||||
default: return (u8*)KIRK_INVALID_SIZE; break;
|
||||
}
|
||||
}
|
||||
|
||||
__declspec(dllexport) void decrypt_kirk16_private(u8* dA_out, u8* dA_enc)
|
||||
{
|
||||
int i, k;
|
||||
kirk16_data keydata;
|
||||
u8 subkey_1[0x10], subkey_2[0x10];
|
||||
AES_ctx aes_ctx;
|
||||
|
||||
keydata.fuseid[7] = g_fuse90 & 0xFF;
|
||||
keydata.fuseid[6] = (g_fuse90 >> 8) & 0xFF;
|
||||
keydata.fuseid[5] = (g_fuse90 >> 16) & 0xFF;
|
||||
keydata.fuseid[4] = (g_fuse90 >> 24) & 0xFF;
|
||||
keydata.fuseid[3] = g_fuse94 & 0xFF;
|
||||
keydata.fuseid[2] = (g_fuse94 >> 8) & 0xFF;
|
||||
keydata.fuseid[1] = (g_fuse94 >> 16) & 0xFF;
|
||||
keydata.fuseid[0] = (g_fuse94 >> 24) & 0xFF;
|
||||
|
||||
/* set encryption key */
|
||||
rijndael_set_key(&aes_ctx, kirk16_key, 128);
|
||||
|
||||
/* set the subkeys */
|
||||
for (i = 0; i < 0x10; i++)
|
||||
{
|
||||
/* set to the fuseid */
|
||||
subkey_2[i] = subkey_1[i] = keydata.fuseid[i % 8];
|
||||
}
|
||||
|
||||
/* do aes crypto */
|
||||
for (i = 0; i < 3; i++)
|
||||
{
|
||||
/* encrypt + decrypt */
|
||||
rijndael_encrypt(&aes_ctx, subkey_1, subkey_1);
|
||||
rijndael_decrypt(&aes_ctx, subkey_2, subkey_2);
|
||||
}
|
||||
|
||||
/* set new key */
|
||||
rijndael_set_key(&aes_ctx, subkey_1, 128);
|
||||
|
||||
/* now lets make the key mesh */
|
||||
for (i = 0; i < 3; i++)
|
||||
{
|
||||
/* do encryption in group of 3 */
|
||||
for (k = 0; k < 3; k++)
|
||||
{
|
||||
/* crypto */
|
||||
rijndael_encrypt(&aes_ctx, subkey_2, subkey_2);
|
||||
}
|
||||
|
||||
/* copy to out block */
|
||||
memcpy(&keydata.mesh[i * 0x10], subkey_2, 0x10);
|
||||
}
|
||||
|
||||
/* set the key to the mesh */
|
||||
rijndael_set_key(&aes_ctx, &keydata.mesh[0x20], 128);
|
||||
|
||||
/* do the encryption routines for the aes key */
|
||||
for (i = 0; i < 2; i++)
|
||||
{
|
||||
/* encrypt the data */
|
||||
rijndael_encrypt(&aes_ctx, &keydata.mesh[0x10], &keydata.mesh[0x10]);
|
||||
}
|
||||
|
||||
/* set the key to that mesh shit */
|
||||
rijndael_set_key(&aes_ctx, &keydata.mesh[0x10], 128);
|
||||
|
||||
/* cbc decrypt the dA */
|
||||
AES_cbc_decrypt((AES_ctx*)&aes_ctx, dA_enc, dA_out, 0x20);
|
||||
}
|
||||
|
||||
__declspec(dllexport) void encrypt_kirk16_private(u8* dA_out, u8* dA_dec)
|
||||
{
|
||||
int i, k;
|
||||
kirk16_data keydata;
|
||||
u8 subkey_1[0x10], subkey_2[0x10];
|
||||
AES_ctx aes_ctx;
|
||||
|
||||
keydata.fuseid[7] = g_fuse90 & 0xFF;
|
||||
keydata.fuseid[6] = (g_fuse90 >> 8) & 0xFF;
|
||||
keydata.fuseid[5] = (g_fuse90 >> 16) & 0xFF;
|
||||
keydata.fuseid[4] = (g_fuse90 >> 24) & 0xFF;
|
||||
keydata.fuseid[3] = g_fuse94 & 0xFF;
|
||||
keydata.fuseid[2] = (g_fuse94 >> 8) & 0xFF;
|
||||
keydata.fuseid[1] = (g_fuse94 >> 16) & 0xFF;
|
||||
keydata.fuseid[0] = (g_fuse94 >> 24) & 0xFF;
|
||||
/* set encryption key */
|
||||
rijndael_set_key(&aes_ctx, kirk16_key, 128);
|
||||
|
||||
/* set the subkeys */
|
||||
for (i = 0; i < 0x10; i++)
|
||||
{
|
||||
/* set to the fuseid */
|
||||
subkey_2[i] = subkey_1[i] = keydata.fuseid[i % 8];
|
||||
}
|
||||
|
||||
/* do aes crypto */
|
||||
for (i = 0; i < 3; i++)
|
||||
{
|
||||
/* encrypt + decrypt */
|
||||
rijndael_encrypt(&aes_ctx, subkey_1, subkey_1);
|
||||
rijndael_decrypt(&aes_ctx, subkey_2, subkey_2);
|
||||
}
|
||||
|
||||
/* set new key */
|
||||
rijndael_set_key(&aes_ctx, subkey_1, 128);
|
||||
|
||||
/* now lets make the key mesh */
|
||||
for (i = 0; i < 3; i++)
|
||||
{
|
||||
/* do encryption in group of 3 */
|
||||
for (k = 0; k < 3; k++)
|
||||
{
|
||||
/* crypto */
|
||||
rijndael_encrypt(&aes_ctx, subkey_2, subkey_2);
|
||||
}
|
||||
|
||||
/* copy to out block */
|
||||
memcpy(&keydata.mesh[i * 0x10], subkey_2, 0x10);
|
||||
}
|
||||
|
||||
/* set the key to the mesh */
|
||||
rijndael_set_key(&aes_ctx, &keydata.mesh[0x20], 128);
|
||||
|
||||
/* do the encryption routines for the aes key */
|
||||
for (i = 0; i < 2; i++)
|
||||
{
|
||||
/* encrypt the data */
|
||||
rijndael_encrypt(&aes_ctx, &keydata.mesh[0x10], &keydata.mesh[0x10]);
|
||||
}
|
||||
|
||||
/* set the key to that mesh shit */
|
||||
rijndael_set_key(&aes_ctx, &keydata.mesh[0x10], 128);
|
||||
|
||||
/* cbc encrypt the dA */
|
||||
AES_cbc_encrypt((AES_ctx*)&aes_ctx, dA_dec, dA_out, 0x20);
|
||||
}
|
||||
|
||||
|
||||
__declspec(dllexport) int kirk_init()
|
||||
{
|
||||
AES_set_key(&aes_kirk1, kirk1_key, 128);
|
||||
is_kirk_initialized = 1;
|
||||
srand(time(0));
|
||||
return KIRK_OPERATION_SUCCESS;
|
||||
}
|
||||
|
||||
int kirk_init2(u8* rnd_seed, u32 seed_size, u32 fuseid_90, u32 fuseid_94)
|
||||
{
|
||||
u8 temp[0x104];
|
||||
|
||||
KIRK_SHA1_HEADER* header = (KIRK_SHA1_HEADER*)temp;
|
||||
|
||||
// Another randomly selected data for a "key" to add to each randomization
|
||||
u8 key[0x10] = { 0x07, 0xAB, 0xEF, 0xF8, 0x96, 0x8C, 0xF3, 0xD6, 0x14, 0xE0, 0xEB, 0xB2, 0x9D, 0x8B, 0x4E, 0x74 };
|
||||
u32 curtime;
|
||||
|
||||
//Set PRNG_DATA initially, otherwise use what ever uninitialized data is in the buffer
|
||||
if (seed_size > 0) {
|
||||
u8* seedbuf;
|
||||
KIRK_SHA1_HEADER* seedheader;;
|
||||
seedbuf = (u8*)malloc(seed_size + 4);
|
||||
seedheader = (KIRK_SHA1_HEADER*)seedbuf;
|
||||
seedheader->data_size = seed_size;
|
||||
kirk_CMD11(PRNG_DATA, seedbuf, seed_size + 4);
|
||||
free(seedbuf);
|
||||
}
|
||||
|
||||
memcpy(temp + 4, PRNG_DATA, 0x14);
|
||||
|
||||
// This uses the standard C time function for portability.
|
||||
curtime = (u32)time(0);
|
||||
temp[0x18] = curtime & 0xFF;
|
||||
temp[0x19] = (curtime >> 8) & 0xFF;
|
||||
temp[0x1A] = (curtime >> 16) & 0xFF;
|
||||
temp[0x1B] = (curtime >> 24) & 0xFF;
|
||||
memcpy(&temp[0x1C], key, 0x10);
|
||||
|
||||
// This leaves the remainder of the 0x100 bytes in temp to whatever remains on the stack
|
||||
// in an uninitialized state. This should add unpredicableness to the results as well
|
||||
header->data_size = 0x100;
|
||||
kirk_CMD11(PRNG_DATA, temp, 0x104);
|
||||
|
||||
//Set Fuse ID
|
||||
g_fuse90 = fuseid_90;
|
||||
g_fuse94 = fuseid_94;
|
||||
|
||||
// Set KIRK1 main key
|
||||
AES_set_key(&aes_kirk1, kirk1_key, 128);
|
||||
|
||||
is_kirk_initialized = 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
/* KIRK 0x01 */
|
||||
/*****************************************************************************/
|
||||
|
||||
int kirk_CMD0(void* outbuff, void* inbuff, int size)
|
||||
{
|
||||
KIRK_CMD1_HEADER *header;
|
||||
header_keys *keys;
|
||||
AES_ctx k1, cmac_key;
|
||||
int chk_size;
|
||||
u8 cmac_header_hash[16];
|
||||
u8 cmac_data_hash[16];
|
||||
|
||||
if(is_kirk_initialized == 0)
|
||||
kirk_init();
|
||||
|
||||
header = (KIRK_CMD1_HEADER*)outbuff;
|
||||
memcpy(outbuff, inbuff, size);
|
||||
|
||||
if(header->mode != KIRK_MODE_CMD1)
|
||||
return KIRK_INVALID_MODE;
|
||||
|
||||
//0-15 AES key, 16-31 CMAC key
|
||||
keys = (header_keys *)outbuff;
|
||||
|
||||
//Make sure data is 16 aligned
|
||||
chk_size = header->data_size;
|
||||
if(chk_size%16)
|
||||
chk_size += 16-(chk_size%16);
|
||||
|
||||
//Encrypt data
|
||||
AES_set_key(&k1, keys->AES, 128);
|
||||
AES_cbc_encrypt(&k1, (char*)inbuff + sizeof(KIRK_CMD1_HEADER) + header->data_offset, (char*)outbuff + sizeof(KIRK_CMD1_HEADER) + header->data_offset, chk_size);
|
||||
|
||||
if(header->ecdsa==1){
|
||||
//ECDSA hash
|
||||
u8 *sign_s, *sign_r;
|
||||
u8 sign_e[20];
|
||||
|
||||
ecdsa_set_curve(ec_p, ec_a, ec_b1, ec_N1, Gx1, Gy1);
|
||||
ecdsa_set_priv(priv_key_kirk1);
|
||||
|
||||
SHA1((char*)outbuff+0x60, 0x30, sign_e);
|
||||
sign_r = (char*)outbuff+0x10;
|
||||
sign_s = (char*)outbuff+0x10+0x14;
|
||||
ecdsa_sign(sign_e, sign_r, sign_s);
|
||||
|
||||
SHA1((char*)outbuff+0x60, 0x30+chk_size+header->data_offset, sign_e);
|
||||
sign_r = (char*)outbuff+0x10+0x28;
|
||||
sign_s = (char*)outbuff+0x10+0x3C;
|
||||
ecdsa_sign(sign_e, sign_r, sign_s);
|
||||
|
||||
|
||||
//Encrypt keys
|
||||
AES_cbc_encrypt(&aes_kirk1, inbuff, outbuff, 16);
|
||||
}else{
|
||||
//CMAC hash
|
||||
AES_set_key(&cmac_key, keys->CMAC, 128);
|
||||
|
||||
AES_CMAC(&cmac_key, (char*)outbuff+0x60, 0x30, cmac_header_hash);
|
||||
AES_CMAC(&cmac_key, (char*)outbuff+0x60, 0x30+chk_size+header->data_offset, cmac_data_hash);
|
||||
|
||||
memcpy(header->CMAC_header_hash, cmac_header_hash, 16);
|
||||
memcpy(header->CMAC_data_hash, cmac_data_hash, 16);
|
||||
|
||||
//Encrypt keys
|
||||
AES_cbc_encrypt(&aes_kirk1, inbuff, outbuff, 16*2);
|
||||
}
|
||||
|
||||
return KIRK_OPERATION_SUCCESS;
|
||||
}
|
||||
|
||||
int kirk_CMD1(void* outbuff, void* inbuff, int size)
|
||||
{
|
||||
KIRK_CMD1_HEADER* header;
|
||||
header_keys keys; //0-15 AES key, 16-31 CMAC key
|
||||
AES_ctx k1;
|
||||
int retv;
|
||||
|
||||
if(is_kirk_initialized == 0)
|
||||
kirk_init();
|
||||
|
||||
header = (KIRK_CMD1_HEADER*)inbuff;
|
||||
if(header->mode != KIRK_MODE_CMD1)
|
||||
return KIRK_INVALID_MODE;
|
||||
|
||||
if(size < header->data_size)
|
||||
size = header->data_size;
|
||||
size = (size+15)&~15;
|
||||
|
||||
//decrypt AES & CMAC key to temp buffer
|
||||
AES_cbc_decrypt(&aes_kirk1, inbuff, (u8*)&keys, 16*2);
|
||||
|
||||
if(header->ecdsa==0){
|
||||
retv = kirk_CMD10(inbuff, size);
|
||||
if(retv != KIRK_OPERATION_SUCCESS)
|
||||
return retv;
|
||||
}else if(header->ecdsa==1){
|
||||
u8 *sign_s, *sign_r;
|
||||
u8 sign_e[20];
|
||||
|
||||
ecdsa_set_curve(ec_p, ec_a, ec_b1, ec_N1, Gx1, Gy1);
|
||||
ecdsa_set_pub(pub_key_kirk1_x, pub_key_kirk1_y);
|
||||
|
||||
SHA1((char*)inbuff+0x60, 0x30, sign_e);
|
||||
sign_r = (char*)inbuff+0x10;
|
||||
sign_s = (char*)inbuff+0x10+0x14;
|
||||
retv = ecdsa_verify(sign_e, sign_r, sign_s);
|
||||
if(retv){
|
||||
return KIRK_HEADER_HASH_INVALID;
|
||||
}
|
||||
|
||||
size = 0x30+header->data_size+header->data_offset;
|
||||
size = (size+15)&~15;
|
||||
SHA1((char*)inbuff+0x60, size, sign_e);
|
||||
sign_r = (char*)inbuff+0x10+0x28;
|
||||
sign_s = (char*)inbuff+0x10+0x3C;
|
||||
retv = ecdsa_verify(sign_e, sign_r, sign_s);
|
||||
if(retv){
|
||||
return KIRK_HEADER_HASH_INVALID;
|
||||
}
|
||||
}
|
||||
|
||||
AES_set_key(&k1, keys.AES, 128);
|
||||
AES_cbc_decrypt(&k1, (char*)inbuff+sizeof(KIRK_CMD1_HEADER)+header->data_offset, outbuff, header->data_size);
|
||||
|
||||
return KIRK_OPERATION_SUCCESS;
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
/* KIRK 0x04 0x05 0x06 0x07 0x08 0x09 */
|
||||
/*****************************************************************************/
|
||||
|
||||
int kirk_CMD4(void* outbuff, void* inbuff, int size)
|
||||
{
|
||||
KIRK_AES128CBC_HEADER *header;
|
||||
AES_ctx aesKey;
|
||||
u8 *key;
|
||||
|
||||
if(is_kirk_initialized == 0)
|
||||
kirk_init();
|
||||
|
||||
header = (KIRK_AES128CBC_HEADER*)inbuff;
|
||||
|
||||
if(header->mode != KIRK_MODE_ENCRYPT_CBC)
|
||||
return KIRK_INVALID_MODE;
|
||||
|
||||
if(header->data_size==0)
|
||||
return KIRK_DATA_SIZE_ZERO;
|
||||
|
||||
key = kirk_4_7_get_key(header->keyseed);
|
||||
if(key==NULL)
|
||||
return KIRK_INVALID_SIZE;
|
||||
|
||||
//Set the key
|
||||
AES_set_key(&aesKey, key, 128);
|
||||
AES_cbc_encrypt(&aesKey, (char*)inbuff+0x14, (char*)outbuff+0x14, header->data_size);
|
||||
|
||||
memcpy(outbuff, inbuff, 0x14);
|
||||
*(u32*)outbuff = KIRK_MODE_DECRYPT_CBC;
|
||||
|
||||
return KIRK_OPERATION_SUCCESS;
|
||||
}
|
||||
|
||||
int kirk_CMD7(void* outbuff, void* inbuff, int size)
|
||||
{
|
||||
KIRK_AES128CBC_HEADER *header;
|
||||
AES_ctx aesKey;
|
||||
u8 *key;
|
||||
|
||||
if(is_kirk_initialized == 0)
|
||||
kirk_init();
|
||||
|
||||
header = (KIRK_AES128CBC_HEADER*)inbuff;
|
||||
|
||||
if(header->mode != KIRK_MODE_DECRYPT_CBC)
|
||||
return KIRK_INVALID_MODE;
|
||||
|
||||
if(header->data_size==0)
|
||||
return KIRK_DATA_SIZE_ZERO;
|
||||
|
||||
key = kirk_4_7_get_key(header->keyseed);
|
||||
if(key==NULL)
|
||||
return KIRK_INVALID_SIZE;
|
||||
|
||||
size = size < header->data_size ? size : header->data_size;
|
||||
|
||||
//Set the key
|
||||
AES_set_key(&aesKey, key, 128);
|
||||
AES_cbc_decrypt(&aesKey, (char*)inbuff+0x14, outbuff, header->data_size);
|
||||
|
||||
return KIRK_OPERATION_SUCCESS;
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
/* KIRK 0x0A */
|
||||
/*****************************************************************************/
|
||||
|
||||
int kirk_CMD10(void* inbuff, int insize)
|
||||
{
|
||||
KIRK_CMD1_HEADER *header;
|
||||
header_keys keys; //0-15 AES key, 16-31 CMAC key
|
||||
AES_ctx cmac_key;
|
||||
u8 cmac_header_hash[16];
|
||||
u8 cmac_data_hash[16];
|
||||
int chk_size;
|
||||
|
||||
if(is_kirk_initialized == 0)
|
||||
kirk_init();
|
||||
|
||||
header = (KIRK_CMD1_HEADER*)inbuff;
|
||||
|
||||
if(!(header->mode == KIRK_MODE_CMD1 || header->mode == KIRK_MODE_CMD2 || header->mode == KIRK_MODE_CMD3))
|
||||
return KIRK_INVALID_MODE;
|
||||
|
||||
if(header->data_size==0)
|
||||
return KIRK_DATA_SIZE_ZERO;
|
||||
|
||||
if(header->mode == KIRK_MODE_CMD1) {
|
||||
//decrypt AES & CMAC key to temp buffer
|
||||
AES_cbc_decrypt(&aes_kirk1, inbuff, (u8*)&keys, 32);
|
||||
|
||||
AES_set_key(&cmac_key, keys.CMAC, 128);
|
||||
AES_CMAC(&cmac_key, (char*)inbuff+0x60, 0x30, cmac_header_hash);
|
||||
|
||||
//Make sure data is 16 aligned
|
||||
chk_size = header->data_size;
|
||||
if(chk_size % 16)
|
||||
chk_size += 16 - (chk_size % 16);
|
||||
|
||||
AES_CMAC(&cmac_key, (char*)inbuff+0x60, 0x30 + chk_size + header->data_offset, cmac_data_hash);
|
||||
|
||||
if(memcmp(cmac_header_hash, header->CMAC_header_hash, 16) != 0) {
|
||||
printf("header hash invalid\n");
|
||||
return KIRK_HEADER_HASH_INVALID;
|
||||
}
|
||||
|
||||
if(memcmp(cmac_data_hash, header->CMAC_data_hash, 16) != 0) {
|
||||
printf("data hash invalid\n");
|
||||
return KIRK_DATA_HASH_INVALID;
|
||||
}
|
||||
|
||||
return KIRK_OPERATION_SUCCESS;
|
||||
}
|
||||
|
||||
//Checks for cmd 2 & 3 not included right now
|
||||
return KIRK_SIG_CHECK_INVALID;
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
/* KIRK 0x0B */
|
||||
/*****************************************************************************/
|
||||
|
||||
int kirk_CMD11(void* outbuff, void* inbuff, int size)
|
||||
{
|
||||
int data_size;
|
||||
|
||||
if(is_kirk_initialized == 0)
|
||||
kirk_init();
|
||||
|
||||
data_size = *(int*)(inbuff);
|
||||
if(data_size==0 || size==0)
|
||||
return KIRK_DATA_SIZE_ZERO;
|
||||
|
||||
size = size<data_size ? size : data_size;
|
||||
SHA1((char*)inbuff+4, size, outbuff);
|
||||
|
||||
return KIRK_OPERATION_SUCCESS;
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
/* KIRK 0x0C: generate priv and pub */
|
||||
/*****************************************************************************/
|
||||
|
||||
|
||||
int kirk_CMD12(void *outbuff, int size)
|
||||
{
|
||||
u8 *priv_key = (u8*)outbuff;
|
||||
//u8 *pub_key = (u8*)outbuff+20;
|
||||
|
||||
if(size!=0x3c)
|
||||
return KIRK_INVALID_SIZE;
|
||||
|
||||
ecdsa_set_curve(ec_p, ec_a, ec_b2, ec_N2, Gx2, Gy2);
|
||||
|
||||
kirk_CMD14(priv_key, 20);
|
||||
|
||||
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/*****************************************************************************/
|
||||
/* KIRK 0x0E */
|
||||
/*****************************************************************************/
|
||||
|
||||
int kirk_CMD13(u8* outbuff, int outsize, u8* inbuff, int insize)
|
||||
{
|
||||
u8 k[0x15];
|
||||
KIRK_CMD13_BUFFER* pointmult = (KIRK_CMD13_BUFFER*)inbuff;
|
||||
k[0] = 0;
|
||||
|
||||
if (outsize != 0x28) return KIRK_INVALID_SIZE;
|
||||
if (insize != 0x3C) return KIRK_INVALID_SIZE;
|
||||
|
||||
ecdsa_set_curve(ec_p, ec_a, ec_b2, ec_N2, Gx2, Gy2);
|
||||
ecdsa_set_pub((u8*)pointmult->public_key.x, (u8*)pointmult->public_key.y);
|
||||
memcpy(k + 1, pointmult->multiplier, 0x14);
|
||||
ec_pub_mult(k, outbuff);
|
||||
|
||||
return KIRK_OPERATION_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
int kirk_CMD14(u8* outbuff, int outsize)
|
||||
{
|
||||
u8 temp[0x104];
|
||||
KIRK_SHA1_HEADER* header = (KIRK_SHA1_HEADER*)temp;
|
||||
|
||||
// Some randomly selected data for a "key" to add to each randomization
|
||||
u8 key[0x10] = { 0xA7, 0x2E, 0x4C, 0xB6, 0xC3, 0x34, 0xDF, 0x85, 0x70, 0x01, 0x49, 0xFC, 0xC0, 0x87, 0xC4, 0x77 };
|
||||
u32 curtime;
|
||||
|
||||
if (outsize <= 0) return KIRK_OPERATION_SUCCESS;
|
||||
|
||||
memcpy(temp + 4, PRNG_DATA, 0x14);
|
||||
|
||||
// This uses the standard C time function for portability.
|
||||
curtime = (u32)time(0);
|
||||
temp[0x18] = curtime & 0xFF;
|
||||
temp[0x19] = (curtime >> 8) & 0xFF;
|
||||
temp[0x1A] = (curtime >> 16) & 0xFF;
|
||||
temp[0x1B] = (curtime >> 24) & 0xFF;
|
||||
memcpy(&temp[0x1C], key, 0x10);
|
||||
|
||||
// This leaves the remainder of the 0x100 bytes in temp to whatever remains on the stack
|
||||
// in an uninitialized state. This should add unpredicableness to the results as well
|
||||
header->data_size = 0x100;
|
||||
kirk_CMD11(PRNG_DATA, temp, 0x104);
|
||||
|
||||
while (outsize)
|
||||
{
|
||||
int blockrem = outsize % 0x14;
|
||||
int block = outsize / 0x14;
|
||||
|
||||
if (block)
|
||||
{
|
||||
memcpy(outbuff, PRNG_DATA, 0x14);
|
||||
outbuff += 0x14;
|
||||
outsize -= 0x14;
|
||||
kirk_CMD14(outbuff, outsize);
|
||||
}
|
||||
else {
|
||||
if (blockrem)
|
||||
{
|
||||
memcpy(outbuff, PRNG_DATA, blockrem);
|
||||
outsize -= blockrem;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return KIRK_OPERATION_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
|
||||
int kirk_CMD16(u8* outbuff, int outsize, u8* inbuff, int insize)
|
||||
{
|
||||
u8 dec_private[0x20];
|
||||
KIRK_CMD16_BUFFER* signbuf = (KIRK_CMD16_BUFFER*)inbuff;
|
||||
ECDSA_SIG* sig = (ECDSA_SIG*)outbuff;
|
||||
|
||||
if (insize != 0x34) return KIRK_INVALID_SIZE;
|
||||
if (outsize != 0x28) return KIRK_INVALID_SIZE;
|
||||
|
||||
decrypt_kirk16_private(dec_private, signbuf->enc_private);
|
||||
|
||||
// Clear out the padding for safety
|
||||
memset(&dec_private[0x14], 0, 0xC);
|
||||
|
||||
ecdsa_set_curve(ec_p, ec_a, ec_b2, ec_N2, Gx2, Gy2);
|
||||
ecdsa_set_priv(dec_private);
|
||||
ecdsa_sign(signbuf->message_hash, sig->r, sig->s);
|
||||
|
||||
return KIRK_OPERATION_SUCCESS;
|
||||
}
|
||||
|
||||
int kirk_CMD17(u8* inbuff, int insize)
|
||||
{
|
||||
KIRK_CMD17_BUFFER* sig = (KIRK_CMD17_BUFFER*)inbuff;
|
||||
|
||||
if (insize != 0x64) return KIRK_INVALID_SIZE;
|
||||
|
||||
ecdsa_set_curve(ec_p, ec_a, ec_b2, ec_N2, Gx2, Gy2);
|
||||
ecdsa_set_pub(sig->public_key.x);
|
||||
|
||||
if (ecdsa_verify(sig->message_hash, sig->signature.r, sig->signature.s)) {
|
||||
return KIRK_OPERATION_SUCCESS;
|
||||
}
|
||||
else {
|
||||
return KIRK_SIG_CHECK_INVALID;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/*****************************************************************************/
|
||||
/* sceUtilsBufferCopyWithRange */
|
||||
/*****************************************************************************/
|
||||
|
||||
|
||||
__declspec(dllexport) int sceUtilsBufferCopyWithRange(u8* outbuff, int outsize, u8* inbuff, int insize, int cmd)
|
||||
{
|
||||
switch(cmd)
|
||||
{
|
||||
case KIRK_CMD_DECRYPT_PRIVATE: return kirk_CMD1(outbuff, inbuff, insize); break;
|
||||
case KIRK_CMD_ENCRYPT_IV_0: return kirk_CMD4(outbuff, inbuff, insize); break;
|
||||
case KIRK_CMD_DECRYPT_IV_0: return kirk_CMD7(outbuff, inbuff, insize); break;
|
||||
case KIRK_CMD_PRIV_SIGN_CHECK: return kirk_CMD10(inbuff, insize); break;
|
||||
case KIRK_CMD_SHA1_HASH: return kirk_CMD11(outbuff, inbuff, insize); break;
|
||||
case KIRK_CMD_ECDSA_GEN_KEYS: return kirk_CMD12(outbuff,outsize); break;
|
||||
case KIRK_CMD_ECDSA_MULTIPLY_POINT: return kirk_CMD13(outbuff,outsize, inbuff, insize); break;
|
||||
case KIRK_CMD_PRNG: return kirk_CMD14(outbuff,outsize); break;
|
||||
case KIRK_CMD_ECDSA_SIGN: return kirk_CMD16(outbuff, outsize, inbuff, insize); break;
|
||||
case KIRK_CMD_ECDSA_VERIFY: return kirk_CMD17(inbuff, insize); break;
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
|
@ -1,194 +0,0 @@
|
|||
#ifndef KIRK_ENGINE
|
||||
#define KIRK_ENGINE
|
||||
|
||||
typedef unsigned char u8;
|
||||
typedef unsigned short int u16;
|
||||
typedef unsigned int u32;
|
||||
|
||||
//Kirk return values
|
||||
#define KIRK_OPERATION_SUCCESS 0
|
||||
#define KIRK_NOT_ENABLED 1
|
||||
#define KIRK_INVALID_MODE 2
|
||||
#define KIRK_HEADER_HASH_INVALID 3
|
||||
#define KIRK_DATA_HASH_INVALID 4
|
||||
#define KIRK_SIG_CHECK_INVALID 5
|
||||
#define KIRK_UNK_1 6
|
||||
#define KIRK_UNK_2 7
|
||||
#define KIRK_UNK_3 8
|
||||
#define KIRK_UNK_4 9
|
||||
#define KIRK_UNK_5 0xA
|
||||
#define KIRK_UNK_6 0xB
|
||||
#define KIRK_NOT_INITIALIZED 0xC
|
||||
#define KIRK_INVALID_OPERATION 0xD
|
||||
#define KIRK_INVALID_SEED_CODE 0xE
|
||||
#define KIRK_INVALID_SIZE 0xF
|
||||
#define KIRK_DATA_SIZE_ZERO 0x10
|
||||
|
||||
typedef struct
|
||||
{
|
||||
int mode; //0
|
||||
int unk_4; //4
|
||||
int unk_8; //8
|
||||
int keyseed; //C
|
||||
int data_size; //10
|
||||
} KIRK_AES128CBC_HEADER; //0x14
|
||||
|
||||
typedef struct
|
||||
{
|
||||
u8 AES_key[16]; //0
|
||||
u8 CMAC_key[16]; //10
|
||||
u8 CMAC_header_hash[16]; //20
|
||||
u8 CMAC_data_hash[16]; //30
|
||||
u8 unused[32]; //40
|
||||
u32 mode; //60
|
||||
u32 ecdsa; //64
|
||||
u8 unk3[8]; //68
|
||||
u32 data_size; //70
|
||||
u32 data_offset; //74
|
||||
u8 unk4[8]; //78
|
||||
u8 unk5[16]; //80
|
||||
} KIRK_CMD1_HEADER; //0x90
|
||||
|
||||
typedef struct
|
||||
{
|
||||
u8 r[0x14];
|
||||
u8 s[0x14];
|
||||
} ECDSA_SIG;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
u8 x[0x14];
|
||||
u8 y[0x14];
|
||||
} ECDSA_POINT;
|
||||
|
||||
|
||||
typedef struct
|
||||
{
|
||||
u32 data_size; //0
|
||||
} KIRK_SHA1_HEADER; //4
|
||||
|
||||
typedef struct
|
||||
{
|
||||
u8 private_key[0x14];
|
||||
ECDSA_POINT public_key;
|
||||
} KIRK_CMD12_BUFFER;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
u8 multiplier[0x14];
|
||||
ECDSA_POINT public_key;
|
||||
} KIRK_CMD13_BUFFER;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
u8 enc_private[0x20];
|
||||
u8 message_hash[0x14];
|
||||
} KIRK_CMD16_BUFFER;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
ECDSA_POINT public_key;
|
||||
u8 message_hash[0x14];
|
||||
ECDSA_SIG signature;
|
||||
} KIRK_CMD17_BUFFER;
|
||||
|
||||
|
||||
// sceUtilsBufferCopyWithRange modes
|
||||
#define KIRK_CMD_DECRYPT_PRIVATE 1
|
||||
#define KIRK_CMD_2 2
|
||||
#define KIRK_CMD_3 3
|
||||
#define KIRK_CMD_ENCRYPT_IV_0 4
|
||||
#define KIRK_CMD_ENCRYPT_IV_FUSE 5
|
||||
#define KIRK_CMD_ENCRYPT_IV_USER 6
|
||||
#define KIRK_CMD_DECRYPT_IV_0 7
|
||||
#define KIRK_CMD_DECRYPT_IV_FUSE 8
|
||||
#define KIRK_CMD_DECRYPT_IV_USER 9
|
||||
#define KIRK_CMD_PRIV_SIGN_CHECK 10
|
||||
#define KIRK_CMD_SHA1_HASH 11
|
||||
#define KIRK_CMD_ECDSA_GEN_KEYS 12
|
||||
#define KIRK_CMD_ECDSA_MULTIPLY_POINT 13
|
||||
#define KIRK_CMD_PRNG 14
|
||||
#define KIRK_CMD_15 15
|
||||
#define KIRK_CMD_ECDSA_SIGN 16
|
||||
#define KIRK_CMD_ECDSA_VERIFY 17
|
||||
|
||||
//"mode" in header
|
||||
#define KIRK_MODE_CMD1 1
|
||||
#define KIRK_MODE_CMD2 2
|
||||
#define KIRK_MODE_CMD3 3
|
||||
#define KIRK_MODE_ENCRYPT_CBC 4
|
||||
#define KIRK_MODE_DECRYPT_CBC 5
|
||||
|
||||
//sceUtilsBufferCopyWithRange errors
|
||||
#define SUBCWR_NOT_16_ALGINED 0x90A
|
||||
#define SUBCWR_HEADER_HASH_INVALID 0x920
|
||||
#define SUBCWR_BUFFER_TOO_SMALL 0x1000
|
||||
|
||||
/*
|
||||
// Private Sig + Cipher
|
||||
0x01: Super-Duper decryption (no inverse)
|
||||
0x02: Encrypt Operation (inverse of 0x03)
|
||||
0x03: Decrypt Operation (inverse of 0x02)
|
||||
|
||||
// Cipher
|
||||
0x04: Encrypt Operation (inverse of 0x07) (IV=0)
|
||||
0x05: Encrypt Operation (inverse of 0x08) (IV=FuseID)
|
||||
0x06: Encrypt Operation (inverse of 0x09) (IV=UserDefined)
|
||||
0x07: Decrypt Operation (inverse of 0x04)
|
||||
0x08: Decrypt Operation (inverse of 0x05)
|
||||
0x09: Decrypt Operation (inverse of 0x06)
|
||||
|
||||
// Sig Gens
|
||||
0x0A: Private Signature Check (checks for private SCE sig)
|
||||
0x0B: SHA1 Hash
|
||||
0x0C: Mul1
|
||||
0x0D: Mul2
|
||||
0x0E: Random Number Gen
|
||||
0x0F: (absolutely no idea – could be KIRK initialization)
|
||||
0x10: Signature Gen
|
||||
// Sig Checks
|
||||
0x11: Signature Check (checks for generated sigs)
|
||||
0x12: Certificate Check (idstorage signatures)
|
||||
*/
|
||||
|
||||
//kirk-like funcs
|
||||
int kirk_CMD0(void* outbuff, void* inbuff, int size);
|
||||
int kirk_CMD1(void* outbuff, void* inbuff, int size);
|
||||
int kirk_CMD4(void* outbuff, void* inbuff, int size);
|
||||
int kirk_CMD7(void* outbuff, void* inbuff, int size);
|
||||
int kirk_CMD10(void* inbuff, int insize);
|
||||
int kirk_CMD11(void* outbuff, void* inbuff, int size);
|
||||
int kirk_CMD14(void* outbuff, int size);
|
||||
__declspec(dllexport) int kirk_init(); //CMD 0xF?
|
||||
|
||||
//helper funcs
|
||||
u8* kirk_4_7_get_key(int key_type);
|
||||
|
||||
//kirk "ex" functions
|
||||
int kirk_CMD1_ex(void* outbuff, void* inbuff, int size, KIRK_CMD1_HEADER* header);
|
||||
|
||||
//sce-like funcs
|
||||
int sceUtilsSetFuseID(void*fuse);
|
||||
__declspec(dllexport) int sceUtilsBufferCopyWithRange(void* outbuff, int outsize, void* inbuff, int insize, int cmd);
|
||||
|
||||
/* ECC Curves for Kirk 1 and Kirk 0x11 */
|
||||
// Common Curve paramters p and a
|
||||
static u8 ec_p[0x14] = { 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x01, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF };
|
||||
static u8 ec_a[0x14] = { 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x01, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFC }; // mon
|
||||
|
||||
// Kirk 0xC,0xD,0x10,0x11,(likely 0x12)- Unique curve parameters for b, N, and base point G for Kirk 0xC,0xD,0x10,0x11,(likely 0x12) service
|
||||
// Since public key is variable, it is not specified here
|
||||
static u8 ec_b2[0x14] = { 0xA6, 0x8B, 0xED, 0xC3, 0x34, 0x18, 0x02, 0x9C, 0x1D, 0x3C, 0xE3, 0x3B, 0x9A, 0x32, 0x1F, 0xCC, 0xBB, 0x9E, 0x0F, 0x0B };// mon
|
||||
static u8 ec_N2[0x15] = { 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFE, 0xFF, 0xFF, 0xB5, 0xAE, 0x3C, 0x52, 0x3E, 0x63, 0x94, 0x4F, 0x21, 0x27 };
|
||||
static u8 Gx2[0x14] = { 0x12, 0x8E, 0xC4, 0x25, 0x64, 0x87, 0xFD, 0x8F, 0xDF, 0x64, 0xE2, 0x43, 0x7B, 0xC0, 0xA1, 0xF6, 0xD5, 0xAF, 0xDE, 0x2C };
|
||||
static u8 Gy2[0x14] = { 0x59, 0x58, 0x55, 0x7E, 0xB1, 0xDB, 0x00, 0x12, 0x60, 0x42, 0x55, 0x24, 0xDB, 0xC3, 0x79, 0xD5, 0xAC, 0x5F, 0x4A, 0xDF };
|
||||
|
||||
// KIRK 1 - Unique curve parameters for b, N, and base point G
|
||||
// Since public key is hard coded, it is also included
|
||||
static u8 ec_b1[0x14] = { 0x65, 0xD1, 0x48, 0x8C, 0x03, 0x59, 0xE2, 0x34, 0xAD, 0xC9, 0x5B, 0xD3, 0x90, 0x80, 0x14, 0xBD, 0x91, 0xA5, 0x25, 0xF9 };
|
||||
static u8 ec_N1[0x15] = { 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x01, 0xB5, 0xC6, 0x17, 0xF2, 0x90, 0xEA, 0xE1, 0xDB, 0xAD, 0x8F };
|
||||
static u8 Gx1[0x14] = { 0x22, 0x59, 0xAC, 0xEE, 0x15, 0x48, 0x9C, 0xB0, 0x96, 0xA8, 0x82, 0xF0, 0xAE, 0x1C, 0xF9, 0xFD, 0x8E, 0xE5, 0xF8, 0xFA };
|
||||
static u8 Gy1[0x14] = { 0x60, 0x43, 0x58, 0x45, 0x6D, 0x0A, 0x1C, 0xB2, 0x90, 0x8D, 0xE9, 0x0F, 0x27, 0xD7, 0x5C, 0x82, 0xBE, 0xC1, 0x08, 0xC0 };
|
||||
|
||||
|
||||
#endif
|
295
CHOVY-KIRK/pgd.c
295
CHOVY-KIRK/pgd.c
|
@ -1,295 +0,0 @@
|
|||
|
||||
// Copyright (C) 2013 tpu
|
||||
// Copyright (C) 2015 Hykem <hykem@hotmail.com>
|
||||
// Licensed under the terms of the GNU GPL, version 3
|
||||
// http://www.gnu.org/licenses/gpl-3.0.txt
|
||||
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "kirk_engine.h"
|
||||
#include "crypto.h"
|
||||
#include "amctrl.h"
|
||||
|
||||
/*************************************************************/
|
||||
|
||||
|
||||
typedef struct {
|
||||
unsigned char vkey[16];
|
||||
|
||||
int open_flag;
|
||||
int key_index;
|
||||
int drm_type;
|
||||
int mac_type;
|
||||
int cipher_type;
|
||||
|
||||
int data_size;
|
||||
int align_size;
|
||||
int block_size;
|
||||
int block_nr;
|
||||
int data_offset;
|
||||
int table_offset;
|
||||
|
||||
unsigned char* buf;
|
||||
} PGD_HEADER;
|
||||
|
||||
/*
|
||||
typedef struct {
|
||||
PGD_DESC pgdesc;
|
||||
unsigned __int32 key_index; // 0x30
|
||||
unsigned __int8 pgd_key[16]; // 0x34
|
||||
unsigned __int32 flag; // 0x44
|
||||
unsigned __int32 flag_open; // 0x48
|
||||
unsigned __int32 pgd_offset; // 0x4C
|
||||
int seek_offset; // 0x50
|
||||
unsigned __int32 data_offset; // 0x54
|
||||
unsigned __int32 table_offset;// 0x58
|
||||
unsigned __int32 unk_5c;
|
||||
unsigned __int32 unk_60;
|
||||
}PspIoHookParam;
|
||||
*/
|
||||
|
||||
unsigned __int8 dnas_key1A90_pgd[] = {0xED,0xE2,0x5D,0x2D,0xBB,0xF8,0x12,0xE5,0x3C,0x5C,0x59,0x32,0xFA,0xE3,0xE2,0x43};
|
||||
unsigned __int8 dnas_key1AA0_pgd[] = {0x27,0x74,0xFB,0xEB,0xA4,0xA0, 1,0xD7, 2,0x56,0x9E,0x33,0x8C,0x19,0x57,0x83};
|
||||
|
||||
__declspec(dllexport) int encrypt_pgd(u8* data, int data_size, int block_size, int key_index, int drm_type, int flag, u8* key, u8* pgd_data)
|
||||
{
|
||||
MAC_KEY mkey;
|
||||
CIPHER_KEY ckey;
|
||||
|
||||
// Additional size variables.
|
||||
int data_offset = 0x90;
|
||||
int align_size = (data_size + 15) & ~15;
|
||||
int table_offset = data_offset + align_size;
|
||||
int block_nr = ((align_size + block_size - 1) & ~(block_size - 1)) / block_size;
|
||||
int pgd_size = 0x90 + align_size + block_nr * 16;
|
||||
|
||||
// Build new PGD header.
|
||||
u8* pgd = (u8*)malloc(pgd_size);
|
||||
memset(pgd, 0, pgd_size);
|
||||
memcpy(pgd + data_offset, data, data_size);
|
||||
|
||||
// Set magic PGD.
|
||||
pgd[0] = 0x00;
|
||||
pgd[1] = 0x50;
|
||||
pgd[2] = 0x47;
|
||||
pgd[3] = 0x44;
|
||||
|
||||
// Set key index and drm type.
|
||||
*(u32*)(pgd + 4) = key_index;
|
||||
*(u32*)(pgd + 8) = drm_type;
|
||||
|
||||
// Select the hashing, crypto and open modes.
|
||||
int mac_type;
|
||||
int cipher_type;
|
||||
int open_flag = flag;
|
||||
if (drm_type == 1)
|
||||
{
|
||||
mac_type = 1;
|
||||
open_flag |= 4;
|
||||
if (key_index > 1)
|
||||
{
|
||||
mac_type = 3;
|
||||
open_flag |= 8;
|
||||
}
|
||||
cipher_type = 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
mac_type = 2;
|
||||
cipher_type = 2;
|
||||
}
|
||||
|
||||
// Select the fixed DNAS key.
|
||||
u8* fkey = NULL;
|
||||
if ((open_flag & 0x2) == 0x2)
|
||||
fkey = dnas_key1A90_pgd;
|
||||
if ((open_flag & 0x1) == 0x1)
|
||||
fkey = dnas_key1AA0_pgd;
|
||||
|
||||
if (fkey == NULL)
|
||||
{
|
||||
printf("PGD: Invalid PGD DNAS flag! %08x\n", flag);
|
||||
return -1;
|
||||
}
|
||||
|
||||
// Set the decryption parameters in the decrypted header.
|
||||
*(u32*)(pgd + 0x44) = data_size;
|
||||
*(u32*)(pgd + 0x48) = block_size;
|
||||
*(u32*)(pgd + 0x4C) = data_offset;
|
||||
|
||||
// Generate random header and data keys.
|
||||
sceUtilsBufferCopyWithRange(pgd + 0x10, 0x30, 0, 0, KIRK_CMD_PRNG);
|
||||
|
||||
// Encrypt the data.
|
||||
sceDrmBBCipherInit(&ckey, cipher_type, 2, pgd + 0x30, key, 0);
|
||||
sceDrmBBCipherUpdate(&ckey, pgd + data_offset, align_size);
|
||||
sceDrmBBCipherFinal(&ckey);
|
||||
|
||||
// Build data MAC hash.
|
||||
int i;
|
||||
for (i = 0; i < block_nr; i++)
|
||||
{
|
||||
int rsize = align_size - i * block_size;
|
||||
if (rsize > block_size)
|
||||
rsize = block_size;
|
||||
|
||||
sceDrmBBMacInit(&mkey, mac_type);
|
||||
sceDrmBBMacUpdate(&mkey, pgd + data_offset + i * block_size, rsize);
|
||||
sceDrmBBMacFinal(&mkey, pgd + table_offset + i * 16, key);
|
||||
}
|
||||
|
||||
// Build table MAC hash.
|
||||
sceDrmBBMacInit(&mkey, mac_type);
|
||||
sceDrmBBMacUpdate(&mkey, pgd + table_offset, block_nr * 16);
|
||||
sceDrmBBMacFinal(&mkey, pgd + 0x60, key);
|
||||
|
||||
// Encrypt the PGD header block (0x30 bytes).
|
||||
sceDrmBBCipherInit(&ckey, cipher_type, 2, pgd + 0x10, key, 0);
|
||||
sceDrmBBCipherUpdate(&ckey, pgd + 0x30, 0x30);
|
||||
sceDrmBBCipherFinal(&ckey);
|
||||
|
||||
// Build MAC hash at 0x70 (key hash).
|
||||
sceDrmBBMacInit(&mkey, mac_type);
|
||||
sceDrmBBMacUpdate(&mkey, pgd + 0x00, 0x70);
|
||||
sceDrmBBMacFinal(&mkey, pgd + 0x70, key);
|
||||
|
||||
// Build MAC hash at 0x80 (DNAS hash).
|
||||
sceDrmBBMacInit(&mkey, mac_type);
|
||||
sceDrmBBMacUpdate(&mkey, pgd + 0x00, 0x80);
|
||||
sceDrmBBMacFinal(&mkey, pgd + 0x80, fkey);
|
||||
|
||||
// Copy back the generated PGD file.
|
||||
memcpy(pgd_data, pgd, pgd_size);
|
||||
|
||||
return pgd_size;
|
||||
}
|
||||
|
||||
/*
|
||||
PGD decrypt function.
|
||||
*/
|
||||
__declspec(dllexport) int decrypt_pgd(u8* pgd_data, int pgd_size, int flag, u8* key)
|
||||
{
|
||||
int result;
|
||||
PGD_HEADER PGD[sizeof(PGD_HEADER)];
|
||||
MAC_KEY mkey;
|
||||
CIPHER_KEY ckey;
|
||||
u8* fkey;
|
||||
|
||||
// Read in the PGD header parameters.
|
||||
memset(PGD, 0, sizeof(PGD_HEADER));
|
||||
|
||||
PGD->buf = pgd_data;
|
||||
PGD->key_index = *(u32*)(pgd_data + 4);
|
||||
PGD->drm_type = *(u32*)(pgd_data + 8);
|
||||
|
||||
// Set the hashing, crypto and open modes.
|
||||
if (PGD->drm_type == 1)
|
||||
{
|
||||
PGD->mac_type = 1;
|
||||
flag |= 4;
|
||||
|
||||
if (PGD->key_index > 1)
|
||||
{
|
||||
PGD->mac_type = 3;
|
||||
flag |= 8;
|
||||
}
|
||||
PGD->cipher_type = 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
PGD->mac_type = 2;
|
||||
PGD->cipher_type = 2;
|
||||
}
|
||||
PGD->open_flag = flag;
|
||||
|
||||
// Get the fixed DNAS key.
|
||||
fkey = NULL;
|
||||
if ((flag & 0x2) == 0x2)
|
||||
fkey = dnas_key1A90_pgd;
|
||||
if ((flag & 0x1) == 0x1)
|
||||
fkey = dnas_key1AA0_pgd;
|
||||
|
||||
if (fkey == NULL)
|
||||
{
|
||||
printf("PGD: Invalid PGD DNAS flag! %08x\n", flag);
|
||||
return -1;
|
||||
}
|
||||
|
||||
// Test MAC hash at 0x80 (DNAS hash).
|
||||
sceDrmBBMacInit(&mkey, PGD->mac_type);
|
||||
sceDrmBBMacUpdate(&mkey, pgd_data, 0x80);
|
||||
result = sceDrmBBMacFinal2(&mkey, pgd_data + 0x80, fkey);
|
||||
|
||||
if (result)
|
||||
{
|
||||
printf("PGD: Invalid PGD 0x80 MAC hash!\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
// Test MAC hash at 0x70 (key hash).
|
||||
sceDrmBBMacInit(&mkey, PGD->mac_type);
|
||||
sceDrmBBMacUpdate(&mkey, pgd_data, 0x70);
|
||||
|
||||
// If a key was provided, check it against MAC 0x70.
|
||||
if (!isEmpty(key, 0x10))
|
||||
{
|
||||
result = sceDrmBBMacFinal2(&mkey, pgd_data + 0x70, key);
|
||||
if (result)
|
||||
{
|
||||
printf("PGD: Invalid PGD 0x70 MAC hash!\n");
|
||||
return -1;
|
||||
}
|
||||
else
|
||||
{
|
||||
memcpy(PGD->vkey, key, 16);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// Generate the key from MAC 0x70.
|
||||
bbmac_getkey(&mkey, pgd_data + 0x70, PGD->vkey);
|
||||
}
|
||||
|
||||
// Decrypt the PGD header block (0x30 bytes).
|
||||
sceDrmBBCipherInit(&ckey, PGD->cipher_type, 2, pgd_data + 0x10, PGD->vkey, 0);
|
||||
sceDrmBBCipherUpdate(&ckey, pgd_data + 0x30, 0x30);
|
||||
sceDrmBBCipherFinal(&ckey);
|
||||
|
||||
// Get the decryption parameters from the decrypted header.
|
||||
PGD->data_size = *(u32*)(pgd_data + 0x44);
|
||||
PGD->block_size = *(u32*)(pgd_data + 0x48);
|
||||
PGD->data_offset = *(u32*)(pgd_data + 0x4c);
|
||||
|
||||
// Additional size variables.
|
||||
PGD->align_size = (PGD->data_size + 15) & ~15;
|
||||
PGD->table_offset = PGD->data_offset + PGD->align_size;
|
||||
PGD->block_nr = (PGD->align_size + PGD->block_size - 1) & ~(PGD->block_size - 1);
|
||||
PGD->block_nr = PGD->block_nr / PGD->block_size;
|
||||
|
||||
if ((PGD->align_size + PGD->block_nr * 16) > pgd_size)
|
||||
{
|
||||
printf("ERROR: Invalid PGD data size!\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
// Test MAC hash at 0x60 (table hash).
|
||||
sceDrmBBMacInit(&mkey, PGD->mac_type);
|
||||
sceDrmBBMacUpdate(&mkey, pgd_data + PGD->table_offset, PGD->block_nr * 16);
|
||||
result = sceDrmBBMacFinal2(&mkey, pgd_data + 0x60, PGD->vkey);
|
||||
|
||||
if (result)
|
||||
{
|
||||
printf("ERROR: Invalid PGD 0x60 MAC hash!\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
// Decrypt the data.
|
||||
sceDrmBBCipherInit(&ckey, PGD->cipher_type, 2, pgd_data + 0x30, PGD->vkey, 0);
|
||||
sceDrmBBCipherUpdate(&ckey, pgd_data + 0x90, PGD->align_size);
|
||||
sceDrmBBCipherFinal(&ckey);
|
||||
|
||||
return PGD->data_size;
|
||||
}
|
|
@ -1,156 +0,0 @@
|
|||
|
||||
#define PACK( __Declaration__ ) __pragma( pack(push, 1) ) __Declaration__ __pragma( pack(pop) )
|
||||
|
||||
/*************************************************************/
|
||||
PACK(
|
||||
typedef struct
|
||||
{
|
||||
u32 e_magic;
|
||||
u8 e_class;
|
||||
u8 e_data;
|
||||
u8 e_idver;
|
||||
u8 e_pad[9];
|
||||
u16 e_type;
|
||||
u16 e_machine;
|
||||
u32 e_version;
|
||||
u32 e_entry;
|
||||
u32 e_phoff;
|
||||
u32 e_shoff;
|
||||
u32 e_flags;
|
||||
u16 e_ehsize;
|
||||
u16 e_phentsize;
|
||||
u16 e_phnum;
|
||||
u16 e_shentsize;
|
||||
u16 e_shnum;
|
||||
u16 e_shstrndx;
|
||||
}Elf32_Ehdr);
|
||||
|
||||
PACK(
|
||||
typedef struct
|
||||
{
|
||||
u32 p_type;
|
||||
u32 p_offset;
|
||||
u32 p_vaddr;
|
||||
u32 p_paddr;
|
||||
u32 p_filesz;
|
||||
u32 p_memsz;
|
||||
u32 p_flags;
|
||||
u32 p_align;
|
||||
} Elf32_Phdr);
|
||||
PACK(
|
||||
typedef struct
|
||||
{
|
||||
u32 sh_name;
|
||||
u32 sh_type;
|
||||
u32 sh_flags;
|
||||
u32 sh_addr;
|
||||
u32 sh_offset;
|
||||
u32 sh_size;
|
||||
u32 sh_link;
|
||||
u32 sh_info;
|
||||
u32 sh_addralign;
|
||||
u32 sh_entsize;
|
||||
} Elf32_Shdr);
|
||||
|
||||
typedef struct {
|
||||
u32 r_offset;
|
||||
u32 r_info; /* sym, type: ELF32_R_... */
|
||||
} Elf32_Rel;
|
||||
|
||||
/* Values for p_type. */
|
||||
#define PT_LOAD 1 /* Loadable segment. */
|
||||
|
||||
/* Values for p_flags. */
|
||||
#define PF_X 0x1 /* Executable. */
|
||||
#define PF_W 0x2 /* Writable. */
|
||||
#define PF_R 0x4 /* Readable. */
|
||||
#define PF_RW (PF_R|PF_W)
|
||||
|
||||
/*************************************************************/
|
||||
|
||||
typedef struct {
|
||||
u16 modattribute;
|
||||
u8 modversion[2]; /* minor, major, etc... */
|
||||
char modname[28];
|
||||
void *gp_value;
|
||||
void *ent_top;
|
||||
void *ent_end;
|
||||
void *stub_top;
|
||||
void *stub_end;
|
||||
} SceModuleInfo;
|
||||
|
||||
PACK(
|
||||
typedef struct
|
||||
{
|
||||
u32 signature; //0
|
||||
u16 mod_attribute; //4
|
||||
u16 comp_attribute; //6 compress method:
|
||||
// 0x0001=PRX Compress
|
||||
// 0x0002=ELF Packed
|
||||
// 0x0008=GZIP overlap
|
||||
// 0x0200=KL4E(if not set, GZIP)
|
||||
u8 module_ver_lo; //8
|
||||
u8 module_ver_hi; //9
|
||||
char modname[28]; //0xA
|
||||
u8 mod_version; //0x26
|
||||
u8 nsegments; //0x27
|
||||
u32 elf_size; //0x28
|
||||
u32 psp_size; //0x2C
|
||||
u32 boot_entry; //0x30
|
||||
u32 modinfo_offset; //0x34
|
||||
int bss_size; //0x38
|
||||
u16 seg_align[4]; //0x3C
|
||||
u32 seg_address[4]; //0x44
|
||||
int seg_size[4]; //0x54
|
||||
u32 reserved[5]; //0x64
|
||||
u32 devkit_version; //0x78
|
||||
u8 decrypt_mode; //0x7C
|
||||
u8 padding; //0x7D
|
||||
u16 overlap_size; //0x7E
|
||||
u8 key_data[0x30]; //0x80
|
||||
u32 comp_size; //0xB0 kirk data_size
|
||||
int _80; //0xB4 kirk data_offset
|
||||
u32 unk_B8; //0xB8
|
||||
u32 unk_BC; //0xBC
|
||||
u8 key_data2[0x10]; //0xC0
|
||||
u32 tag; //0xD0
|
||||
u8 scheck[0x58]; //0xD4
|
||||
u8 sha1_hash[0x14]; //0x12C
|
||||
u8 key_data4[0x10]; //0x140
|
||||
} PSP_Header2); //0x150
|
||||
|
||||
PACK(
|
||||
typedef struct
|
||||
{
|
||||
u32 signature; // 0
|
||||
u16 attribute;
|
||||
u8 module_ver_lo;
|
||||
u8 module_ver_hi;
|
||||
char modname[28];
|
||||
u8 version; // 26
|
||||
u8 nsegments; // 27
|
||||
int elf_size; // 28
|
||||
int psp_size; // 2C
|
||||
u32 entry; // 30
|
||||
u32 modinfo_offset; // 34
|
||||
int bss_size; // 38
|
||||
u16 seg_align[4]; // 3C
|
||||
u32 seg_address[4]; // 44
|
||||
int seg_size[4]; // 54
|
||||
u32 reserved[5]; // 64
|
||||
u32 devkitversion; // 78
|
||||
u32 decrypt_mode; // 7C
|
||||
u8 key_data0[0x30]; // 80
|
||||
int comp_size; // B0
|
||||
int _80; // B4
|
||||
int reserved2[2]; // B8
|
||||
u8 key_data1[0x10]; // C0
|
||||
u32 tag; // D0
|
||||
u8 scheck[0x58]; // D4
|
||||
u32 key_data2; // 12C
|
||||
u32 oe_tag; // 130
|
||||
u8 key_data3[0x1C]; // 134
|
||||
} PSP_Header);
|
||||
|
||||
/*************************************************************/
|
||||
|
|
@ -1,691 +0,0 @@
|
|||
// Copyright (C) 2013 tpu
|
||||
// Copyright (C) 2015 Hykem <hykem@hotmail.com>
|
||||
// Licensed under the terms of the GNU GPL, version 3
|
||||
// http://www.gnu.org/licenses/gpl-3.0.txt
|
||||
|
||||
#include "tlzrc.h"
|
||||
|
||||
static u8 text_buf[65536];
|
||||
static int t_start, t_end, t_fill, sp_fill;
|
||||
static int t_len, t_pos;
|
||||
|
||||
static int prev[65536], next[65536];
|
||||
static int root[65536];
|
||||
|
||||
/*
|
||||
LZRC decoder
|
||||
*/
|
||||
static u8 rc_getbyte(LZRC_DECODE *rc)
|
||||
{
|
||||
if (rc->in_ptr == rc->in_len) {
|
||||
printf("End of input!\n");
|
||||
exit(-1);
|
||||
}
|
||||
|
||||
return rc->input[rc->in_ptr++];
|
||||
}
|
||||
|
||||
static void rc_putbyte(LZRC_DECODE *rc, u8 byte)
|
||||
{
|
||||
if (rc->out_ptr == rc->out_len) {
|
||||
printf("Output overflow!\n");
|
||||
exit(-1);
|
||||
}
|
||||
|
||||
rc->output[rc->out_ptr++] = byte;
|
||||
}
|
||||
|
||||
static void rc_init(LZRC_DECODE *rc, void *out, int out_len, void *in, int in_len)
|
||||
{
|
||||
rc->input = in;
|
||||
rc->in_len = in_len;
|
||||
rc->in_ptr = 0;
|
||||
|
||||
rc->output = out;
|
||||
rc->out_len = out_len;
|
||||
rc->out_ptr = 0;
|
||||
|
||||
rc->range = 0xffffffff;
|
||||
rc->lc = rc_getbyte(rc);
|
||||
rc->code = (rc_getbyte(rc)<<24) |
|
||||
(rc_getbyte(rc)<<16) |
|
||||
(rc_getbyte(rc)<< 8) |
|
||||
(rc_getbyte(rc)<< 0) ;
|
||||
rc->out_code = 0xffffffff;
|
||||
|
||||
memset(rc->bm_literal, 0x80, 2048);
|
||||
memset(rc->bm_dist_bits, 0x80, 312);
|
||||
memset(rc->bm_dist, 0x80, 144);
|
||||
memset(rc->bm_match, 0x80, 64);
|
||||
memset(rc->bm_len, 0x80, 248);
|
||||
}
|
||||
|
||||
static void normalize(LZRC_DECODE *rc)
|
||||
{
|
||||
if (rc->range < 0x01000000) {
|
||||
rc->range <<= 8;
|
||||
rc->code = (rc->code << 8) + rc->input[rc->in_ptr];
|
||||
rc->in_ptr++;
|
||||
}
|
||||
}
|
||||
|
||||
static int rc_bit(LZRC_DECODE *rc, u8 *prob)
|
||||
{
|
||||
u32 bound;
|
||||
|
||||
normalize(rc);
|
||||
|
||||
bound = (rc->range >> 8) * (*prob);
|
||||
*prob -= *prob >> 3;
|
||||
|
||||
if (rc->code < bound) {
|
||||
rc->range = bound;
|
||||
*prob += 31;
|
||||
return 1;
|
||||
} else {
|
||||
rc->code -= bound;
|
||||
rc->range -= bound;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
static int rc_bittree(LZRC_DECODE *rc, u8 *probs, int limit)
|
||||
{
|
||||
int number = 1;
|
||||
|
||||
do {
|
||||
number = (number << 1) + rc_bit(rc, probs + number);
|
||||
} while(number < limit);
|
||||
|
||||
return number;
|
||||
}
|
||||
|
||||
static int rc_number(LZRC_DECODE *rc, u8 *prob, int n)
|
||||
{
|
||||
int i, number = 1;
|
||||
|
||||
if (n > 3) {
|
||||
number = (number << 1) + rc_bit(rc, prob + 3);
|
||||
if (n > 4) {
|
||||
number = (number << 1) + rc_bit(rc, prob + 3);
|
||||
if (n > 5) {
|
||||
normalize(rc);
|
||||
for (i = 0; i < n - 5; i++)
|
||||
{
|
||||
rc->range >>= 1;
|
||||
number <<= 1;
|
||||
if (rc->code < rc->range) {
|
||||
number += 1;
|
||||
} else {
|
||||
rc->code -= rc->range;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (n > 0) {
|
||||
number = (number << 1) + rc_bit(rc, prob);
|
||||
if (n > 1) {
|
||||
number = (number << 1) + rc_bit(rc, prob + 1);
|
||||
if(n > 2) {
|
||||
number = (number << 1) + rc_bit(rc, prob + 2);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return number;
|
||||
}
|
||||
|
||||
__declspec(dllexport) int lzrc_decompress(void *out, int out_len, void *in, int in_len)
|
||||
{
|
||||
LZRC_DECODE rc;
|
||||
int match_step, rc_state, len_state, dist_state;
|
||||
int i, bit, byte, last_byte;
|
||||
int match_len, len_bits;
|
||||
int match_dist, dist_bits, limit;
|
||||
u8 *match_src;
|
||||
int round = -1;
|
||||
|
||||
rc_init(&rc, out, out_len, in, in_len);
|
||||
|
||||
if (rc.lc & 0x80) {
|
||||
memcpy(rc.output, rc.input + 5, rc.code);
|
||||
return rc.code;
|
||||
}
|
||||
|
||||
rc_state = 0;
|
||||
last_byte = 0;
|
||||
|
||||
while (1)
|
||||
{
|
||||
round += 1;
|
||||
match_step = 0;
|
||||
|
||||
bit = rc_bit(&rc, &rc.bm_match[rc_state][match_step]);
|
||||
if (bit == 0)
|
||||
{
|
||||
if (rc_state > 0)
|
||||
rc_state -= 1;
|
||||
|
||||
byte = rc_bittree(&rc, &rc.bm_literal[((last_byte >> rc.lc) & 0x07)][0], 0x100);
|
||||
byte -= 0x100;
|
||||
|
||||
rc_putbyte(&rc, byte);
|
||||
}
|
||||
else
|
||||
{
|
||||
len_bits = 0;
|
||||
for (i = 0; i < 7; i++)
|
||||
{
|
||||
match_step += 1;
|
||||
bit = rc_bit(&rc, &rc.bm_match[rc_state][match_step]);
|
||||
if (bit == 0)
|
||||
break;
|
||||
len_bits += 1;
|
||||
}
|
||||
|
||||
if(len_bits == 0) {
|
||||
match_len = 1;
|
||||
} else {
|
||||
len_state = ((len_bits - 1) << 2) + ((rc.out_ptr << (len_bits - 1)) & 0x03);
|
||||
match_len = rc_number(&rc, &rc.bm_len[rc_state][len_state], len_bits);
|
||||
if (match_len == 0xFF) {
|
||||
return rc.out_ptr;
|
||||
}
|
||||
}
|
||||
|
||||
dist_state = 0;
|
||||
limit = 8;
|
||||
if (match_len > 2) {
|
||||
dist_state += 7;
|
||||
limit = 44;
|
||||
}
|
||||
dist_bits = rc_bittree(&rc, &rc.bm_dist_bits[len_bits][dist_state], limit);
|
||||
dist_bits -= limit;
|
||||
|
||||
if (dist_bits > 0) {
|
||||
match_dist = rc_number(&rc, &rc.bm_dist[dist_bits][0], dist_bits);
|
||||
} else {
|
||||
match_dist = 1;
|
||||
}
|
||||
|
||||
if (match_dist > rc.out_ptr || match_dist < 0) {
|
||||
printf("match_dist out of range! %08x\n", match_dist);
|
||||
return -1;
|
||||
}
|
||||
match_src = rc.output + rc.out_ptr - match_dist;
|
||||
for (i = 0; i < match_len + 1; i++) {
|
||||
rc_putbyte(&rc, *match_src++);
|
||||
}
|
||||
rc_state = 6 + ((rc.out_ptr + 1) & 1);
|
||||
}
|
||||
last_byte = rc.output[rc.out_ptr - 1];
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
LZRC encoder
|
||||
*/
|
||||
static u8 re_getbyte(LZRC_DECODE *re)
|
||||
{
|
||||
if (re->in_ptr == re->in_len) {
|
||||
printf("End of input!\n");
|
||||
exit(-1);
|
||||
}
|
||||
|
||||
return re->input[re->in_ptr++];
|
||||
}
|
||||
|
||||
static void re_putbyte(LZRC_DECODE *re, u8 byte)
|
||||
{
|
||||
if (re->out_ptr == re->out_len) {
|
||||
printf("Output overflow!\n");
|
||||
exit(-1);
|
||||
}
|
||||
|
||||
re->output[re->out_ptr++] = byte;
|
||||
}
|
||||
|
||||
static void re_init(LZRC_DECODE *re, void *out, int out_len, void *in, int in_len)
|
||||
{
|
||||
re->input = in;
|
||||
re->in_len = in_len;
|
||||
re->in_ptr = 0;
|
||||
|
||||
re->output = out;
|
||||
re->out_len = out_len;
|
||||
re->out_ptr = 0;
|
||||
|
||||
re->range = 0xffffffff;
|
||||
re->code = 0x00000000;
|
||||
re->lc = 5;
|
||||
re->out_code = 0xffffffff;
|
||||
|
||||
re_putbyte(re, re->lc);
|
||||
|
||||
memset(re->bm_literal, 0x80, 2048);
|
||||
memset(re->bm_dist_bits, 0x80, 312);
|
||||
memset(re->bm_dist, 0x80, 144);
|
||||
memset(re->bm_match, 0x80, 64);
|
||||
memset(re->bm_len, 0x80, 248);
|
||||
}
|
||||
|
||||
static void re_flush(LZRC_DECODE *re)
|
||||
{
|
||||
re_putbyte(re, (re->out_code) & 0xff);
|
||||
re_putbyte(re, (re->code >> 24) & 0xff);
|
||||
re_putbyte(re, (re->code >> 16) & 0xff);
|
||||
re_putbyte(re, (re->code >> 8) & 0xff);
|
||||
re_putbyte(re, (re->code >> 0) & 0xff);
|
||||
}
|
||||
|
||||
static void re_normalize(LZRC_DECODE *re)
|
||||
{
|
||||
if (re->range < 0x01000000) {
|
||||
if (re->out_code != 0xffffffff) {
|
||||
if (re->out_code > 255)
|
||||
{
|
||||
int p, old_c;
|
||||
p = re->out_ptr - 1;
|
||||
do {
|
||||
old_c = re->output[p];
|
||||
re->output[p] += 1;
|
||||
p -= 1;
|
||||
} while (old_c == 0xff);
|
||||
}
|
||||
|
||||
re_putbyte(re, re->out_code & 0xff);
|
||||
}
|
||||
re->out_code = (re->code >> 24) & 0xff;
|
||||
re->range <<= 8;
|
||||
re->code <<= 8;
|
||||
}
|
||||
}
|
||||
|
||||
static void re_bit(LZRC_DECODE *re, u8 *prob, int bit)
|
||||
{
|
||||
u32 bound;
|
||||
u32 old_r, old_c;
|
||||
u8 old_p;
|
||||
|
||||
re_normalize(re);
|
||||
|
||||
old_r = re->range;
|
||||
old_c = re->code;
|
||||
old_p = *prob;
|
||||
|
||||
bound = (re->range >> 8) * (*prob);
|
||||
*prob -= *prob >> 3;
|
||||
|
||||
if (bit) {
|
||||
re->range = bound;
|
||||
*prob += 31;
|
||||
} else {
|
||||
re->code += bound;
|
||||
if (re->code < old_c)
|
||||
re->out_code += 1;
|
||||
re->range -= bound;
|
||||
}
|
||||
}
|
||||
|
||||
static void re_bittree(LZRC_DECODE *re, u8 *probs, int limit, int number)
|
||||
{
|
||||
int n, tmp, bit;
|
||||
|
||||
number += limit;
|
||||
|
||||
tmp = number;
|
||||
n = 0;
|
||||
while (tmp > 1) {
|
||||
tmp >>= 1;
|
||||
n++;
|
||||
}
|
||||
|
||||
do {
|
||||
tmp = number >> n;
|
||||
bit = (number >> (n - 1)) & 1;
|
||||
re_bit(re, probs + tmp, bit);
|
||||
n -= 1;
|
||||
} while (n);
|
||||
}
|
||||
|
||||
static void re_number(LZRC_DECODE *re, u8 *prob, int n, int number)
|
||||
{
|
||||
int i;
|
||||
u32 old_c;
|
||||
|
||||
i = 1;
|
||||
|
||||
if (n > 3) {
|
||||
re_bit(re, prob + 3, (number >> (n - i)) & 1);
|
||||
i += 1;
|
||||
if (n > 4) {
|
||||
re_bit(re, prob + 3, (number >> (n - i)) & 1);
|
||||
i += 1;
|
||||
if (n > 5) {
|
||||
re_normalize(re);
|
||||
for (i = 3; i < n - 2; i++) {
|
||||
re->range >>= 1;
|
||||
if (((number >> (n - i)) & 1) == 0) {
|
||||
old_c = re->code;
|
||||
re->code += re->range;
|
||||
if (re->code < old_c)
|
||||
re->out_code += 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (n > 0) {
|
||||
re_bit(re, prob + 0, (number >> (n - i - 0)) & 1);
|
||||
if (n > 1) {
|
||||
re_bit(re, prob + 1, (number >> (n - i - 1)) & 1);
|
||||
if (n > 2) {
|
||||
re_bit(re, prob + 2, (number >> (n - i - 2)) & 1);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void init_tree(void)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < 65536; i++)
|
||||
{
|
||||
root[i] = -1;
|
||||
prev[i] = -1;
|
||||
next[i] = -1;
|
||||
}
|
||||
|
||||
t_start = 0;
|
||||
t_end = 0;
|
||||
t_fill = 0;
|
||||
sp_fill = 0;
|
||||
}
|
||||
|
||||
static void remove_node(LZRC_DECODE *re, int p)
|
||||
{
|
||||
int t, q;
|
||||
|
||||
if (prev[p] == -1)
|
||||
return;
|
||||
|
||||
t = text_buf[p + 0];
|
||||
t = (t << 8) | text_buf[p + 1];
|
||||
|
||||
q = next[p];
|
||||
if (q != -1)
|
||||
prev[q] = prev[p];
|
||||
|
||||
if (prev[p] == -2)
|
||||
root[t] = q;
|
||||
else
|
||||
next[prev[p]] = q;
|
||||
|
||||
prev[p] = -1;
|
||||
next[p] = -1;
|
||||
}
|
||||
|
||||
static int insert_node(LZRC_DECODE *re, int pos, int *match_len, int *match_dist, int do_cmp)
|
||||
{
|
||||
u8 *src, *win;
|
||||
int i, t, p;
|
||||
int content_size;
|
||||
|
||||
src = text_buf + pos;
|
||||
win = text_buf + t_start;
|
||||
content_size = (t_fill < pos) ? (65280 + t_fill - pos) : (t_fill - pos);
|
||||
t_len = 1;
|
||||
t_pos = 0;
|
||||
*match_len = t_len;
|
||||
*match_dist = t_pos;
|
||||
|
||||
if (re->in_ptr == re->in_len) {
|
||||
*match_len = 256;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (re->in_ptr == (re->in_len - 1))
|
||||
return 0;
|
||||
|
||||
t = src[0];
|
||||
t = (t << 8) | src[1];
|
||||
if (root[t] == -1)
|
||||
{
|
||||
root[t] = pos;
|
||||
prev[pos] = -2;
|
||||
next[pos] = -1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
p = root[t];
|
||||
root[t] = pos;
|
||||
prev[pos] = -2;
|
||||
next[pos] = p;
|
||||
|
||||
if (p != -1)
|
||||
prev[p] = pos;
|
||||
|
||||
while (do_cmp == 1 && p != -1)
|
||||
{
|
||||
for (i = 0; (i < 255 && i < content_size); i++) {
|
||||
if (src[i] != text_buf[p + i])
|
||||
break;
|
||||
}
|
||||
|
||||
if (i > t_len) {
|
||||
t_len = i;
|
||||
t_pos = pos - p;
|
||||
} else if (i == t_len) {
|
||||
int mp = pos - p;
|
||||
if (mp < 0)
|
||||
mp += 65280;
|
||||
if (mp < t_pos) {
|
||||
t_len = i;
|
||||
t_pos = pos-p;
|
||||
}
|
||||
}
|
||||
if (i == 255) {
|
||||
remove_node(re, p);
|
||||
break;
|
||||
}
|
||||
|
||||
p = next[p];
|
||||
}
|
||||
|
||||
*match_len = t_len;
|
||||
*match_dist = t_pos;
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static void fill_buffer(LZRC_DECODE *re)
|
||||
{
|
||||
int content_size, back_size, front_size;
|
||||
|
||||
if (sp_fill == re->in_len)
|
||||
return;
|
||||
|
||||
content_size = (t_fill < t_end) ? (65280 + t_fill - t_end) : (t_fill - t_end);
|
||||
if (content_size >= 509)
|
||||
return;
|
||||
|
||||
if (t_fill < t_start) {
|
||||
back_size = t_start - t_fill - 1;
|
||||
if (sp_fill + back_size > re->in_len)
|
||||
back_size = re->in_len - sp_fill;
|
||||
memcpy(text_buf + t_fill, re->input + sp_fill, back_size);
|
||||
sp_fill += back_size;
|
||||
t_fill += back_size;
|
||||
} else {
|
||||
back_size = 65280 - t_fill;
|
||||
if (t_start == 0)
|
||||
back_size -= 1;
|
||||
if (sp_fill + back_size > re->in_len)
|
||||
back_size = re->in_len - sp_fill;
|
||||
memcpy(text_buf + t_fill, re->input + sp_fill, back_size);
|
||||
sp_fill += back_size;
|
||||
t_fill += back_size;
|
||||
|
||||
front_size = t_start;
|
||||
if (t_start != 0)
|
||||
front_size -= 1;
|
||||
if (sp_fill + front_size > re->in_len)
|
||||
front_size = re->in_len - sp_fill;
|
||||
memcpy(text_buf, re->input + sp_fill, front_size);
|
||||
sp_fill += front_size;
|
||||
memcpy(text_buf + 65280, text_buf, 255);
|
||||
t_fill += front_size;
|
||||
if (t_fill >= 65280)
|
||||
t_fill -= 65280;
|
||||
}
|
||||
}
|
||||
|
||||
static void update_tree(LZRC_DECODE *re, int length)
|
||||
{
|
||||
int i, win_size;
|
||||
int tmp_len, tmp_pos;
|
||||
|
||||
win_size = (t_end >= t_start) ? (t_end - t_start) : (65280 + t_end - t_start);
|
||||
|
||||
for (i = 0; i < length; i++)
|
||||
{
|
||||
if (win_size == 16384) {
|
||||
remove_node(re, t_start);
|
||||
t_start += 1;
|
||||
if (t_start == 65280)
|
||||
t_start = 0;
|
||||
} else {
|
||||
win_size += 1;
|
||||
}
|
||||
|
||||
if (i > 0) {
|
||||
insert_node(re, t_end, &tmp_len, &tmp_pos, 0);
|
||||
}
|
||||
t_end += 1;
|
||||
if (t_end >= 65280)
|
||||
t_end -= 65280;
|
||||
}
|
||||
}
|
||||
|
||||
static void re_find_match(LZRC_DECODE *re, int *match_len, int *match_dist)
|
||||
{
|
||||
int cp, win_p, i, j;
|
||||
u8 *pbuf, *cbuf;
|
||||
|
||||
cp = re->in_ptr;
|
||||
|
||||
if (cp == re->in_len) {
|
||||
*match_len = 256;
|
||||
return;
|
||||
} else {
|
||||
*match_len = 1;
|
||||
}
|
||||
|
||||
win_p = (cp < 16384) ? cp : 16384;
|
||||
|
||||
for (i = 1; i <= win_p; i++) {
|
||||
j = 0;
|
||||
cbuf = re->input + cp;
|
||||
pbuf = cbuf - i;
|
||||
while ((j < 255) && (cp + j < re->in_len) && (pbuf[j] == cbuf[j]))
|
||||
j += 1;
|
||||
|
||||
if (j >= 2 && *match_len < j) {
|
||||
*match_len = j;
|
||||
*match_dist = i;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
__declspec(dllexport) int lzrc_compress(void *out, int out_len, void *in, int in_len)
|
||||
{
|
||||
LZRC_DECODE re;
|
||||
int match_step, re_state, len_state, dist_state;
|
||||
int i, byte, last_byte;
|
||||
int match_len, len_bits;
|
||||
int match_dist, dist_bits, limit;
|
||||
int round = -1;
|
||||
|
||||
re_init(&re, out, out_len, in, in_len);
|
||||
init_tree();
|
||||
|
||||
re_state = 0;
|
||||
last_byte = 0;
|
||||
match_len = 0;
|
||||
match_dist = 0;
|
||||
|
||||
while (1)
|
||||
{
|
||||
round += 1;
|
||||
match_step = 0;
|
||||
|
||||
fill_buffer(&re);
|
||||
insert_node(&re, t_end, &match_len, &match_dist, 1);
|
||||
if (match_len < 256) {
|
||||
if (match_len < 4 && match_dist > 255)
|
||||
match_len = 1;
|
||||
update_tree(&re, match_len);
|
||||
}
|
||||
|
||||
if (match_len == 1 || (match_len < 4 && match_dist > 255))
|
||||
{
|
||||
re_bit(&re, &re.bm_match[re_state][match_step], 0);
|
||||
|
||||
if (re_state > 0)
|
||||
re_state -= 1;
|
||||
|
||||
byte = re_getbyte(&re);
|
||||
re_bittree(&re, &re.bm_literal[((last_byte >> re.lc) & 0x07)][0], 0x100, byte);
|
||||
} else {
|
||||
re_bit(&re, &re.bm_match[re_state][match_step], 1);
|
||||
|
||||
len_bits = 0;
|
||||
for (i = 1; i < 8; i++) {
|
||||
match_step += 1;
|
||||
if ((match_len - 1) < (1 << i))
|
||||
break;
|
||||
re_bit(&re, &re.bm_match[re_state][match_step], 1);
|
||||
len_bits += 1;
|
||||
}
|
||||
if (i != 8) {
|
||||
re_bit(&re, &re.bm_match[re_state][match_step], 0);
|
||||
}
|
||||
|
||||
if (len_bits > 0) {
|
||||
len_state = ((len_bits - 1) << 2) + ((re.in_ptr << (len_bits - 1)) & 0x03);
|
||||
re_number(&re, &re.bm_len[re_state][len_state], len_bits, (match_len - 1));
|
||||
if (match_len == 0x100) {
|
||||
re_normalize(&re);
|
||||
re_flush(&re);
|
||||
return re.out_ptr;
|
||||
}
|
||||
}
|
||||
|
||||
dist_state = 0;
|
||||
limit = 8;
|
||||
if (match_len > 3) {
|
||||
dist_state += 7;
|
||||
limit = 44;
|
||||
}
|
||||
|
||||
dist_bits = 0;
|
||||
while ((match_dist >> dist_bits) !=1 ) {
|
||||
dist_bits += 1;
|
||||
}
|
||||
|
||||
re_bittree(&re, &re.bm_dist_bits[len_bits][dist_state], limit, dist_bits);
|
||||
|
||||
if (dist_bits > 0) {
|
||||
re_number(&re, &re.bm_dist[dist_bits][0], dist_bits, match_dist);
|
||||
}
|
||||
|
||||
re.in_ptr += match_len;
|
||||
re_state = 6 + ((re.in_ptr + 1) & 1);
|
||||
}
|
||||
last_byte = re.input[re.in_ptr - 1];
|
||||
}
|
||||
}
|
|
@ -1,34 +0,0 @@
|
|||
// Copyright (C) 2013 tpu
|
||||
// Copyright (C) 2015 Hykem <hykem@hotmail.com>
|
||||
// Licensed under the terms of the GNU GPL, version 3
|
||||
// http://www.gnu.org/licenses/gpl-3.0.txt
|
||||
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <malloc.h>
|
||||
|
||||
#include "utils.h"
|
||||
|
||||
typedef struct {
|
||||
u8 *input;
|
||||
int in_ptr;
|
||||
int in_len;
|
||||
|
||||
u8 *output;
|
||||
int out_ptr;
|
||||
int out_len;
|
||||
|
||||
u32 range;
|
||||
u32 code;
|
||||
u32 out_code;
|
||||
u8 lc;
|
||||
|
||||
u8 bm_literal[8][256];
|
||||
u8 bm_dist_bits[8][39];
|
||||
u8 bm_dist[18][8];
|
||||
u8 bm_match[8][8];
|
||||
u8 bm_len[8][31];
|
||||
} LZRC_DECODE;
|
||||
|
||||
__declspec(dllexport) int lzrc_compress(void *out, int out_len, void *in, int in_len);
|
||||
__declspec(dllexport) int lzrc_decompress(void *out, int out_len, void *in, int in_len);
|
|
@ -1,197 +0,0 @@
|
|||
|
||||
|
||||
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
#include <sys/stat.h>
|
||||
#include <io.h>
|
||||
|
||||
|
||||
|
||||
typedef unsigned char u8;
|
||||
|
||||
/**************************************************************/
|
||||
|
||||
char ownisgraph (u8 c)
|
||||
{
|
||||
if ( c >= 0x21 && c <= 0x7e )
|
||||
return 1;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void hex_dump(const char *str, void *addr, int size)
|
||||
{
|
||||
int i;
|
||||
u8 *p = (u8*)addr;
|
||||
|
||||
if (addr == NULL) {
|
||||
printf("hexdump: <NULL>\n");
|
||||
return;
|
||||
}
|
||||
|
||||
if (size == 0) {
|
||||
printf("hexdump: size 0\n");
|
||||
return;
|
||||
}
|
||||
|
||||
if(str)
|
||||
printf("%s:\n", str);
|
||||
|
||||
#if 0
|
||||
printf("Address: ");
|
||||
i=0; for(;i<16; ++i) {
|
||||
if (i == 8)
|
||||
printf("- ");
|
||||
|
||||
printf("%02X ", i);
|
||||
}
|
||||
|
||||
i=0; for(;i<16; ++i) {
|
||||
printf("%1X", i);
|
||||
}
|
||||
|
||||
printf("\n-----------------------------------------------------------------------------\n");
|
||||
#endif
|
||||
|
||||
i=0;
|
||||
printf("0x%08X ", i);
|
||||
|
||||
for(; i<size; ++i) {
|
||||
if (i != 0 && i % 16 == 0) {
|
||||
int j;
|
||||
|
||||
for(j=16; j>0; --j) {
|
||||
if(ownisgraph(p[i-j])) {
|
||||
printf("%c", p[i-j]);
|
||||
} else {
|
||||
printf(".");
|
||||
}
|
||||
}
|
||||
printf("\n0x%08X ", i);
|
||||
}
|
||||
|
||||
if (i != 0 && i % 8 == 0 && i % 16 != 0) {
|
||||
printf("- ");
|
||||
}
|
||||
|
||||
printf("%02X ", p[i]);
|
||||
}
|
||||
|
||||
int rest = (16-(i%16));
|
||||
|
||||
rest = rest == 16 ? 0 : rest;
|
||||
int j; for(j=0; j<rest; j++) {
|
||||
if (j+(i%16) == 8)
|
||||
printf(" ");
|
||||
printf(" ");
|
||||
}
|
||||
|
||||
rest = i % 16;
|
||||
rest = rest == 0 ? 16 : rest;
|
||||
|
||||
for(j=rest; j>0; --j) {
|
||||
if(ownisgraph(p[i-j])) {
|
||||
printf("%c", p[i-j]);
|
||||
} else {
|
||||
printf(".");
|
||||
}
|
||||
}
|
||||
|
||||
printf("\n\n");
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************/
|
||||
|
||||
FILE *open_file(char *name, int *size)
|
||||
{
|
||||
FILE *fp;
|
||||
|
||||
fp = fopen(name, "rb");
|
||||
if(fp==NULL){
|
||||
//printf("Open file %s failed!\n", name);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
fseek(fp, 0, SEEK_END);
|
||||
*size = ftell(fp);
|
||||
fseek(fp, 0, SEEK_SET);
|
||||
|
||||
return fp;
|
||||
}
|
||||
|
||||
u8 *load_file(char *name, int *size)
|
||||
{
|
||||
FILE *fp;
|
||||
u8 *buf;
|
||||
|
||||
fp = open_file(name, size);
|
||||
if(fp==NULL)
|
||||
return NULL;
|
||||
buf = malloc(*size);
|
||||
fread(buf, *size, 1, fp);
|
||||
fclose(fp);
|
||||
|
||||
return buf;
|
||||
}
|
||||
|
||||
int isEmpty(unsigned char* buf, int buf_size)
|
||||
{
|
||||
if (buf != NULL)
|
||||
{
|
||||
int i;
|
||||
for (i = 0; i < buf_size; i++)
|
||||
{
|
||||
if (buf[i] != 0) return 0;
|
||||
}
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
int write_file(char *file, void *buf, int size)
|
||||
{
|
||||
FILE *fp;
|
||||
int written;
|
||||
|
||||
fp = fopen(file, "wb");
|
||||
if(fp==NULL)
|
||||
return -1;
|
||||
written = fwrite(buf, 1, size, fp);
|
||||
fclose(fp);
|
||||
|
||||
return written;
|
||||
}
|
||||
|
||||
/**************************************************************/
|
||||
|
||||
void mkdir_p(char *dname)
|
||||
{
|
||||
char name[256];
|
||||
char *p, *cp;
|
||||
|
||||
strcpy(name, dname);
|
||||
|
||||
cp = name;
|
||||
while(1){
|
||||
p = strchr(cp, '/');
|
||||
if(p==NULL)
|
||||
p = strchr(cp, '\\');
|
||||
if(p==NULL)
|
||||
break;
|
||||
|
||||
*p = 0;
|
||||
//mkdir(name, 0777);
|
||||
mkdir(name);
|
||||
*p = '/';
|
||||
cp = p+1;
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************/
|
||||
|
||||
|
||||
|
||||
|
|
@ -1,19 +0,0 @@
|
|||
#ifndef UTILS_H
|
||||
#define UTILS_H
|
||||
#include <stdio.h>
|
||||
#define MAX(a, b) (((a) > (b)) ? (a) : (b))
|
||||
#define MIN(a, b) (((a) < (b)) ? (a) : (b))
|
||||
#define NELEMS(a) (sizeof(a) / sizeof(a[0]))
|
||||
|
||||
void hex_dump(const char *str, void *addr, int size);
|
||||
|
||||
|
||||
FILE *open_file(char *name, int *size);
|
||||
unsigned __int8 *load_file(char *name, int *size);
|
||||
int write_file(char *file, void *buf, int size);
|
||||
int isEmpty(unsigned char* buf, int buf_size);
|
||||
int walk_dir(char *dname, void *func_ptr, int verbose);
|
||||
void mkdir_p(char *dname);
|
||||
|
||||
#endif
|
||||
|
|
@ -1,37 +0,0 @@
|
|||
|
||||
Microsoft Visual Studio Solution File, Format Version 12.00
|
||||
# Visual Studio Version 16
|
||||
VisualStudioVersion = 16.0.30114.105
|
||||
MinimumVisualStudioVersion = 10.0.40219.1
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "CHOVY-SIGN", "CHOVY-SIGN\CHOVY-SIGN.csproj", "{D46AA2C2-2BDC-45C7-ACA5-D7A2295564E8}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "CHOVY-KIRK", "CHOVY-KIRK\CHOVY-KIRK.vcxproj", "{C441ACC2-EC4E-424B-AA99-3F5D1A997A4F}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "CHOVY-GEN", "CHOVY-GEN\CHOVY-GEN.vcxproj", "{DCDBF747-DFB6-450E-A403-1C592D20EAEB}"
|
||||
EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
Debug|x86 = Debug|x86
|
||||
Release|x86 = Release|x86
|
||||
EndGlobalSection
|
||||
GlobalSection(ProjectConfigurationPlatforms) = postSolution
|
||||
{D46AA2C2-2BDC-45C7-ACA5-D7A2295564E8}.Debug|x86.ActiveCfg = Debug|x86
|
||||
{D46AA2C2-2BDC-45C7-ACA5-D7A2295564E8}.Debug|x86.Build.0 = Debug|x86
|
||||
{D46AA2C2-2BDC-45C7-ACA5-D7A2295564E8}.Release|x86.ActiveCfg = Release|x86
|
||||
{D46AA2C2-2BDC-45C7-ACA5-D7A2295564E8}.Release|x86.Build.0 = Release|x86
|
||||
{C441ACC2-EC4E-424B-AA99-3F5D1A997A4F}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{C441ACC2-EC4E-424B-AA99-3F5D1A997A4F}.Debug|x86.Build.0 = Debug|Win32
|
||||
{C441ACC2-EC4E-424B-AA99-3F5D1A997A4F}.Release|x86.ActiveCfg = Release|Win32
|
||||
{C441ACC2-EC4E-424B-AA99-3F5D1A997A4F}.Release|x86.Build.0 = Release|Win32
|
||||
{DCDBF747-DFB6-450E-A403-1C592D20EAEB}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{DCDBF747-DFB6-450E-A403-1C592D20EAEB}.Debug|x86.Build.0 = Debug|Win32
|
||||
{DCDBF747-DFB6-450E-A403-1C592D20EAEB}.Release|x86.ActiveCfg = Release|Win32
|
||||
{DCDBF747-DFB6-450E-A403-1C592D20EAEB}.Release|x86.Build.0 = Release|Win32
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
EndGlobalSection
|
||||
GlobalSection(ExtensibilityGlobals) = postSolution
|
||||
SolutionGuid = {FE98FF5E-D850-40E5-BCA1-34C5F217333E}
|
||||
EndGlobalSection
|
||||
EndGlobal
|
|
@ -1,14 +0,0 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<configuration>
|
||||
<startup>
|
||||
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.5" />
|
||||
</startup>
|
||||
<runtime>
|
||||
<assemblyBinding xmlns="urn:schemas-microsoft-com:asm.v1">
|
||||
<dependentAssembly>
|
||||
<assemblyIdentity name="System.Buffers" publicKeyToken="cc7b13ffcd2ddd51" culture="neutral" />
|
||||
<bindingRedirect oldVersion="0.0.0.0-4.0.3.0" newVersion="4.0.3.0" />
|
||||
</dependentAssembly>
|
||||
</assemblyBinding>
|
||||
</runtime>
|
||||
</configuration>
|
|
@ -1,495 +0,0 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" />
|
||||
<PropertyGroup>
|
||||
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
|
||||
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
|
||||
<ProjectGuid>{D46AA2C2-2BDC-45C7-ACA5-D7A2295564E8}</ProjectGuid>
|
||||
<OutputType>WinExe</OutputType>
|
||||
<RootNamespace>CHOVY_SIGN</RootNamespace>
|
||||
<AssemblyName>CHOVY-SIGN</AssemblyName>
|
||||
<TargetFrameworkVersion>v4.5</TargetFrameworkVersion>
|
||||
<FileAlignment>512</FileAlignment>
|
||||
<AutoGenerateBindingRedirects>true</AutoGenerateBindingRedirects>
|
||||
<TargetFrameworkProfile />
|
||||
</PropertyGroup>
|
||||
<PropertyGroup>
|
||||
<StartupObject />
|
||||
</PropertyGroup>
|
||||
<PropertyGroup>
|
||||
<ApplicationIcon>Icon.ico</ApplicationIcon>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)' == 'Debug|x86'">
|
||||
<DebugSymbols>true</DebugSymbols>
|
||||
<OutputPath>bin\Debug\</OutputPath>
|
||||
<DefineConstants>DEBUG;TRACE</DefineConstants>
|
||||
<AllowUnsafeBlocks>true</AllowUnsafeBlocks>
|
||||
<DebugType>full</DebugType>
|
||||
<PlatformTarget>x86</PlatformTarget>
|
||||
<LangVersion>7.3</LangVersion>
|
||||
<ErrorReport>prompt</ErrorReport>
|
||||
<CodeAnalysisRuleSet>MinimumRecommendedRules.ruleset</CodeAnalysisRuleSet>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)' == 'Release|x86'">
|
||||
<OutputPath>bin\Release\</OutputPath>
|
||||
<DefineConstants>TRACE</DefineConstants>
|
||||
<AllowUnsafeBlocks>true</AllowUnsafeBlocks>
|
||||
<Optimize>true</Optimize>
|
||||
<DebugType>pdbonly</DebugType>
|
||||
<PlatformTarget>x86</PlatformTarget>
|
||||
<LangVersion>7.3</LangVersion>
|
||||
<ErrorReport>prompt</ErrorReport>
|
||||
<CodeAnalysisRuleSet>MinimumRecommendedRules.ruleset</CodeAnalysisRuleSet>
|
||||
</PropertyGroup>
|
||||
<ItemGroup>
|
||||
<Reference Include="BouncyCastle.Crypto, Version=1.8.6.0, Culture=neutral, PublicKeyToken=0e99375e54769942">
|
||||
<HintPath>..\packages\BouncyCastle.1.8.6.1\lib\BouncyCastle.Crypto.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="DotNetZip, Version=1.13.8.0, Culture=neutral, PublicKeyToken=6583c7c814667745, processorArchitecture=MSIL">
|
||||
<HintPath>..\packages\DotNetZip.1.13.8\lib\net40\DotNetZip.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="HtmlAgilityPack, Version=1.11.24.0, Culture=neutral, PublicKeyToken=bd319b19eaf3b43a, processorArchitecture=MSIL">
|
||||
<HintPath>..\packages\HtmlAgilityPack.1.11.24\lib\Net45\HtmlAgilityPack.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="System" />
|
||||
<Reference Include="System.Buffers, Version=4.0.3.0, Culture=neutral, PublicKeyToken=cc7b13ffcd2ddd51, processorArchitecture=MSIL">
|
||||
<HintPath>..\packages\System.Buffers.4.5.1\lib\netstandard1.1\System.Buffers.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="System.Core" />
|
||||
<Reference Include="System.Xml.Linq" />
|
||||
<Reference Include="System.Data.DataSetExtensions" />
|
||||
<Reference Include="Microsoft.CSharp" />
|
||||
<Reference Include="System.Data" />
|
||||
<Reference Include="System.Deployment" />
|
||||
<Reference Include="System.Drawing" />
|
||||
<Reference Include="System.Net.Http" />
|
||||
<Reference Include="System.Windows.Forms" />
|
||||
<Reference Include="System.Xml" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Compile Include="CHOVYPspBuilder.cs">
|
||||
<SubType>Form</SubType>
|
||||
</Compile>
|
||||
<Compile Include="CHOVYPspBuilder.Designer.cs">
|
||||
<DependentUpon>CHOVYPspBuilder.cs</DependentUpon>
|
||||
</Compile>
|
||||
<Compile Include="CHOVYCmaSelector.cs">
|
||||
<SubType>Form</SubType>
|
||||
</Compile>
|
||||
<Compile Include="CHOVYCmaSelector.Designer.cs">
|
||||
<DependentUpon>CHOVYCmaSelector.cs</DependentUpon>
|
||||
</Compile>
|
||||
<Compile Include="CHOVYPopsBuilder.cs">
|
||||
<SubType>Form</SubType>
|
||||
</Compile>
|
||||
<Compile Include="CHOVYPopsBuilder.Designer.cs">
|
||||
<DependentUpon>CHOVYPopsBuilder.cs</DependentUpon>
|
||||
</Compile>
|
||||
<Compile Include="CmaKeys.cs" />
|
||||
<Compile Include="DiscUtils\ApplePartitionMap\BlockZero.cs" />
|
||||
<Compile Include="DiscUtils\ApplePartitionMap\PartitionMap.cs" />
|
||||
<Compile Include="DiscUtils\ApplePartitionMap\PartitionMapEntry.cs" />
|
||||
<Compile Include="DiscUtils\ApplePartitionMap\PartitionMapFactory.cs" />
|
||||
<Compile Include="DiscUtils\Archives\FileRecord.cs" />
|
||||
<Compile Include="DiscUtils\Archives\TarFile.cs" />
|
||||
<Compile Include="DiscUtils\Archives\TarFileBuilder.cs" />
|
||||
<Compile Include="DiscUtils\Archives\TarHeader.cs" />
|
||||
<Compile Include="DiscUtils\Archives\TarHeaderExtent.cs" />
|
||||
<Compile Include="DiscUtils\Archives\UnixBuildFileRecord.cs" />
|
||||
<Compile Include="DiscUtils\ChsAddress.cs" />
|
||||
<Compile Include="DiscUtils\ClusterMap.cs" />
|
||||
<Compile Include="DiscUtils\ClusterRoles.cs" />
|
||||
<Compile Include="DiscUtils\Compression\Adler32.cs" />
|
||||
<Compile Include="DiscUtils\Compression\BigEndianBitStream.cs" />
|
||||
<Compile Include="DiscUtils\Compression\BitStream.cs" />
|
||||
<Compile Include="DiscUtils\Compression\BlockCompressor.cs" />
|
||||
<Compile Include="DiscUtils\Compression\BZip2BlockDecoder.cs" />
|
||||
<Compile Include="DiscUtils\Compression\BZip2CombinedHuffmanTrees.cs" />
|
||||
<Compile Include="DiscUtils\Compression\BZip2DecoderStream.cs" />
|
||||
<Compile Include="DiscUtils\Compression\BZip2Randomizer.cs" />
|
||||
<Compile Include="DiscUtils\Compression\BZip2RleStream.cs" />
|
||||
<Compile Include="DiscUtils\Compression\CompressionResult.cs" />
|
||||
<Compile Include="DiscUtils\Compression\DataBlockTransform.cs" />
|
||||
<Compile Include="DiscUtils\Compression\HuffmanTree.cs" />
|
||||
<Compile Include="DiscUtils\Compression\InverseBurrowsWheeler.cs" />
|
||||
<Compile Include="DiscUtils\Compression\MoveToFront.cs" />
|
||||
<Compile Include="DiscUtils\Compression\SizedDeflateStream.cs" />
|
||||
<Compile Include="DiscUtils\Compression\ZlibBuffer.cs" />
|
||||
<Compile Include="DiscUtils\Compression\ZlibStream.cs" />
|
||||
<Compile Include="DiscUtils\CoreCompat\EncodingHelper.cs" />
|
||||
<Compile Include="DiscUtils\CoreCompat\ReflectionHelper.cs" />
|
||||
<Compile Include="DiscUtils\CoreCompat\StringExtensions.cs" />
|
||||
<Compile Include="DiscUtils\DiscDirectoryInfo.cs" />
|
||||
<Compile Include="DiscUtils\DiscFileInfo.cs" />
|
||||
<Compile Include="DiscUtils\DiscFileLocator.cs" />
|
||||
<Compile Include="DiscUtils\DiscFileSystem.cs" />
|
||||
<Compile Include="DiscUtils\DiscFileSystemChecker.cs" />
|
||||
<Compile Include="DiscUtils\DiscFileSystemInfo.cs" />
|
||||
<Compile Include="DiscUtils\DiscFileSystemOptions.cs" />
|
||||
<Compile Include="DiscUtils\DiskImageBuilder.cs" />
|
||||
<Compile Include="DiscUtils\DiskImageFileSpecification.cs" />
|
||||
<Compile Include="DiscUtils\FileLocator.cs" />
|
||||
<Compile Include="DiscUtils\FileSystemInfo.cs" />
|
||||
<Compile Include="DiscUtils\FileSystemManager.cs" />
|
||||
<Compile Include="DiscUtils\FileSystemParameters.cs" />
|
||||
<Compile Include="DiscUtils\FileTransport.cs" />
|
||||
<Compile Include="DiscUtils\FloppyDiskType.cs" />
|
||||
<Compile Include="DiscUtils\GenericDiskAdapterType.cs" />
|
||||
<Compile Include="DiscUtils\Geometry.cs" />
|
||||
<Compile Include="DiscUtils\GeometryCalculation.cs" />
|
||||
<Compile Include="DiscUtils\GeometryTranslation.cs" />
|
||||
<Compile Include="DiscUtils\IClusterBasedFileSystem.cs" />
|
||||
<Compile Include="DiscUtils\IDiagnosticTraceable.cs" />
|
||||
<Compile Include="DiscUtils\IFileSystem.cs" />
|
||||
<Compile Include="DiscUtils\Internal\Crc32.cs" />
|
||||
<Compile Include="DiscUtils\Internal\Crc32Algorithm.cs" />
|
||||
<Compile Include="DiscUtils\Internal\Crc32BigEndian.cs" />
|
||||
<Compile Include="DiscUtils\Internal\Crc32LittleEndian.cs" />
|
||||
<Compile Include="DiscUtils\Internal\LocalFileLocator.cs" />
|
||||
<Compile Include="DiscUtils\Internal\LogicalVolumeFactory.cs" />
|
||||
<Compile Include="DiscUtils\Internal\LogicalVolumeFactoryAttribute.cs" />
|
||||
<Compile Include="DiscUtils\Internal\ObjectCache.cs" />
|
||||
<Compile Include="DiscUtils\Internal\Utilities.cs" />
|
||||
<Compile Include="DiscUtils\Internal\VirtualDiskFactory.cs" />
|
||||
<Compile Include="DiscUtils\Internal\VirtualDiskFactoryAttribute.cs" />
|
||||
<Compile Include="DiscUtils\Internal\VirtualDiskTransport.cs" />
|
||||
<Compile Include="DiscUtils\Internal\VirtualDiskTransportAttribute.cs" />
|
||||
<Compile Include="DiscUtils\InvalidFileSystemException.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\BaseVolumeDescriptor.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\BootDeviceEmulation.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\BootInitialEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\BootValidationEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\BootVolumeDescriptor.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\BootVolumeDescriptorRegion.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\BuildDirectoryInfo.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\BuildDirectoryMember.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\BuildFileInfo.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\BuildParameters.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\CDBuilder.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\CDReader.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\CommonVolumeDescriptor.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\DirectoryExtent.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\DirectoryRecord.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\ExtentStream.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\File.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\FileExtent.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\FileFlags.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\Iso9660Variant.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\IsoContext.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\IsoUtilities.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\PathTable.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\PathTableRecord.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\PrimaryVolumeDescriptor.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\PrimaryVolumeDescriptorRegion.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\ReaderDirectory.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\ReaderDirEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\RockRidge\ChildLinkSystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\RockRidge\FileTimeSystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\RockRidge\PosixFileInfoSystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\RockRidge\PosixNameSystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\RockRidge\RockRidgeExtension.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\SupplementaryVolumeDescriptor.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\SupplementaryVolumeDescriptorRegion.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\Susp\ContinuationSystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\Susp\ExtensionSelectSystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\Susp\ExtensionSystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\Susp\GenericSuspExtension.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\Susp\GenericSystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\Susp\PaddingSystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\Susp\SharingProtocolSystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\Susp\SuspExtension.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\Susp\SuspRecords.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\Susp\SystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\VfsCDReader.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\VolumeDescriptorDiskRegion.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\VolumeDescriptorSetTerminator.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\VolumeDescriptorSetTerminatorRegion.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660Ps1\VolumeDescriptorType.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\BaseVolumeDescriptor.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\BootDeviceEmulation.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\BootInitialEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\BootValidationEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\BootVolumeDescriptor.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\BootVolumeDescriptorRegion.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\BuildDirectoryInfo.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\BuildDirectoryMember.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\BuildFileInfo.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\BuildParameters.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\CDBuilder.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\CDReader.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\CommonVolumeDescriptor.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\DirectoryExtent.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\DirectoryRecord.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\ExtentStream.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\File.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\FileExtent.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\FileFlags.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\Iso9660Variant.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\IsoContext.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\IsoUtilities.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\PathTable.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\PathTableRecord.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\PrimaryVolumeDescriptor.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\PrimaryVolumeDescriptorRegion.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\ReaderDirectory.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\ReaderDirEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\RockRidge\ChildLinkSystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\RockRidge\FileTimeSystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\RockRidge\PosixFileInfoSystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\RockRidge\PosixNameSystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\RockRidge\RockRidgeExtension.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\SupplementaryVolumeDescriptor.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\SupplementaryVolumeDescriptorRegion.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\Susp\ContinuationSystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\Susp\ExtensionSelectSystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\Susp\ExtensionSystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\Susp\GenericSuspExtension.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\Susp\GenericSystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\Susp\PaddingSystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\Susp\SharingProtocolSystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\Susp\SuspExtension.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\Susp\SuspRecords.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\Susp\SystemUseEntry.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\VfsCDReader.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\VolumeDescriptorDiskRegion.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\VolumeDescriptorSetTerminator.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\VolumeDescriptorSetTerminatorRegion.cs" />
|
||||
<Compile Include="DiscUtils\Iso9660\VolumeDescriptorType.cs" />
|
||||
<Compile Include="DiscUtils\IUnixFileSystem.cs" />
|
||||
<Compile Include="DiscUtils\IWindowsFileSystem.cs" />
|
||||
<Compile Include="DiscUtils\LogicalDiskManager\ComponentRecord.cs" />
|
||||
<Compile Include="DiscUtils\LogicalDiskManager\Database.cs" />
|
||||
<Compile Include="DiscUtils\LogicalDiskManager\DatabaseHeader.cs" />
|
||||
<Compile Include="DiscUtils\LogicalDiskManager\DatabaseRecord.cs" />
|
||||
<Compile Include="DiscUtils\LogicalDiskManager\DiskGroupRecord.cs" />
|
||||
<Compile Include="DiscUtils\LogicalDiskManager\DiskRecord.cs" />
|
||||
<Compile Include="DiscUtils\LogicalDiskManager\DynamicDisk.cs" />
|
||||
<Compile Include="DiscUtils\LogicalDiskManager\DynamicDiskGroup.cs" />
|
||||
<Compile Include="DiscUtils\LogicalDiskManager\DynamicDiskManager.cs" />
|
||||
<Compile Include="DiscUtils\LogicalDiskManager\DynamicDiskManagerFactory.cs" />
|
||||
<Compile Include="DiscUtils\LogicalDiskManager\DynamicVolume.cs" />
|
||||
<Compile Include="DiscUtils\LogicalDiskManager\ExtentMergeType.cs" />
|
||||
<Compile Include="DiscUtils\LogicalDiskManager\ExtentRecord.cs" />
|
||||
<Compile Include="DiscUtils\LogicalDiskManager\PrivateHeader.cs" />
|
||||
<Compile Include="DiscUtils\LogicalDiskManager\RecordType.cs" />
|
||||
<Compile Include="DiscUtils\LogicalDiskManager\TocBlock.cs" />
|
||||
<Compile Include="DiscUtils\LogicalDiskManager\VolumeRecord.cs" />
|
||||
<Compile Include="DiscUtils\LogicalVolumeInfo.cs" />
|
||||
<Compile Include="DiscUtils\LogicalVolumeStatus.cs" />
|
||||
<Compile Include="DiscUtils\NativeFileSystem.cs" />
|
||||
<Compile Include="DiscUtils\Partitions\BiosExtendedPartitionTable.cs" />
|
||||
<Compile Include="DiscUtils\Partitions\BiosPartitionedDiskBuilder.cs" />
|
||||
<Compile Include="DiscUtils\Partitions\BiosPartitionInfo.cs" />
|
||||
<Compile Include="DiscUtils\Partitions\BiosPartitionRecord.cs" />
|
||||
<Compile Include="DiscUtils\Partitions\BiosPartitionTable.cs" />
|
||||
<Compile Include="DiscUtils\Partitions\BiosPartitionTypes.cs" />
|
||||
<Compile Include="DiscUtils\Partitions\DefaultPartitionTableFactory.cs" />
|
||||
<Compile Include="DiscUtils\Partitions\GptEntry.cs" />
|
||||
<Compile Include="DiscUtils\Partitions\GptHeader.cs" />
|
||||
<Compile Include="DiscUtils\Partitions\GuidPartitionInfo.cs" />
|
||||
<Compile Include="DiscUtils\Partitions\GuidPartitionTable.cs" />
|
||||
<Compile Include="DiscUtils\Partitions\GuidPartitionTypes.cs" />
|
||||
<Compile Include="DiscUtils\Partitions\PartitionInfo.cs" />
|
||||
<Compile Include="DiscUtils\Partitions\PartitionTable.cs" />
|
||||
<Compile Include="DiscUtils\Partitions\PartitionTableFactory.cs" />
|
||||
<Compile Include="DiscUtils\Partitions\PartitionTableFactoryAttribute.cs" />
|
||||
<Compile Include="DiscUtils\Partitions\WellKnownPartitionType.cs" />
|
||||
<Compile Include="DiscUtils\PhysicalVolumeInfo.cs" />
|
||||
<Compile Include="DiscUtils\PhysicalVolumeType.cs" />
|
||||
<Compile Include="DiscUtils\Plist.cs" />
|
||||
<Compile Include="DiscUtils\Raw\Disk.cs" />
|
||||
<Compile Include="DiscUtils\Raw\DiskFactory.cs" />
|
||||
<Compile Include="DiscUtils\Raw\DiskImageFile.cs" />
|
||||
<Compile Include="DiscUtils\ReadOnlyDiscFileSystem.cs" />
|
||||
<Compile Include="DiscUtils\ReparsePoint.cs" />
|
||||
<Compile Include="DiscUtils\ReportLevels.cs" />
|
||||
<Compile Include="DiscUtils\Setup\FileOpenEventArgs.cs" />
|
||||
<Compile Include="DiscUtils\Setup\SetupHelper.cs" />
|
||||
<Compile Include="DiscUtils\Streams\AligningStream.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Block\Block.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Block\BlockCache.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Block\BlockCacheSettings.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Block\BlockCacheStatistics.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Block\BlockCacheStream.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Buffer\Buffer.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Buffer\BufferStream.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Buffer\IBuffer.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Buffer\IMappedBuffer.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Buffer\SubBuffer.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Builder\BuilderBufferExtent.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Builder\BuilderBufferExtentSource.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Builder\BuilderBytesExtent.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Builder\BuilderExtent.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Builder\BuilderExtentSource.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Builder\BuilderSparseStreamExtent.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Builder\BuilderStreamExtent.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Builder\BuilderStreamExtentSource.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Builder\PassthroughStreamBuilder.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Builder\StreamBuilder.cs" />
|
||||
<Compile Include="DiscUtils\Streams\BuiltStream.cs" />
|
||||
<Compile Include="DiscUtils\Streams\CircularStream.cs" />
|
||||
<Compile Include="DiscUtils\Streams\ConcatStream.cs" />
|
||||
<Compile Include="DiscUtils\Streams\IByteArraySerializable.cs" />
|
||||
<Compile Include="DiscUtils\Streams\LengthWrappingStream.cs" />
|
||||
<Compile Include="DiscUtils\Streams\MappedStream.cs" />
|
||||
<Compile Include="DiscUtils\Streams\MirrorStream.cs" />
|
||||
<Compile Include="DiscUtils\Streams\PositionWrappingStream.cs" />
|
||||
<Compile Include="DiscUtils\Streams\PumpProgressEventArgs.cs" />
|
||||
<Compile Include="DiscUtils\Streams\ReaderWriter\BigEndianDataReader.cs" />
|
||||
<Compile Include="DiscUtils\Streams\ReaderWriter\BigEndianDataWriter.cs" />
|
||||
<Compile Include="DiscUtils\Streams\ReaderWriter\DataReader.cs" />
|
||||
<Compile Include="DiscUtils\Streams\ReaderWriter\DataWriter.cs" />
|
||||
<Compile Include="DiscUtils\Streams\ReaderWriter\LittleEndianDataReader.cs" />
|
||||
<Compile Include="DiscUtils\Streams\SnapshotStream.cs" />
|
||||
<Compile Include="DiscUtils\Streams\SparseMemoryBuffer.cs" />
|
||||
<Compile Include="DiscUtils\Streams\SparseMemoryStream.cs" />
|
||||
<Compile Include="DiscUtils\Streams\SparseStream.cs" />
|
||||
<Compile Include="DiscUtils\Streams\SparseStreamOpenDelegate.cs" />
|
||||
<Compile Include="DiscUtils\Streams\StreamBuffer.cs" />
|
||||
<Compile Include="DiscUtils\Streams\StreamExtent.cs" />
|
||||
<Compile Include="DiscUtils\Streams\StreamPump.cs" />
|
||||
<Compile Include="DiscUtils\Streams\StripedStream.cs" />
|
||||
<Compile Include="DiscUtils\Streams\SubStream.cs" />
|
||||
<Compile Include="DiscUtils\Streams\System\Func.cs" />
|
||||
<Compile Include="DiscUtils\Streams\ThreadSafeStream.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Util\BitCounter.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Util\EndianUtilities.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Util\MathUtilities.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Util\Numbers.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Util\Ownership.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Util\Range.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Util\Sizes.cs" />
|
||||
<Compile Include="DiscUtils\Streams\Util\StreamUtilities.cs" />
|
||||
<Compile Include="DiscUtils\Streams\WrappingMappedStream.cs" />
|
||||
<Compile Include="DiscUtils\Streams\WrappingStream.cs" />
|
||||
<Compile Include="DiscUtils\Streams\ZeroStream.cs" />
|
||||
<Compile Include="DiscUtils\System\DateTimeOffsetExtensions.cs" />
|
||||
<Compile Include="DiscUtils\System\ExtensionAttribute.cs" />
|
||||
<Compile Include="DiscUtils\System\HashSet.cs" />
|
||||
<Compile Include="DiscUtils\System\Tuple.cs" />
|
||||
<Compile Include="DiscUtils\TimeConverter.cs" />
|
||||
<Compile Include="DiscUtils\UnixFilePermissions.cs" />
|
||||
<Compile Include="DiscUtils\UnixFileSystemInfo.cs" />
|
||||
<Compile Include="DiscUtils\UnixFileType.cs" />
|
||||
<Compile Include="DiscUtils\Vfs\IVfsDirectory.cs" />
|
||||
<Compile Include="DiscUtils\Vfs\IVfsFile.cs" />
|
||||
<Compile Include="DiscUtils\Vfs\IVfsFileWithStreams.cs" />
|
||||
<Compile Include="DiscUtils\Vfs\IVfsSymlink.cs" />
|
||||
<Compile Include="DiscUtils\Vfs\VfsContext.cs" />
|
||||
<Compile Include="DiscUtils\Vfs\VfsDirEntry.cs" />
|
||||
<Compile Include="DiscUtils\Vfs\VfsFileSystem.cs" />
|
||||
<Compile Include="DiscUtils\Vfs\VfsFileSystemFacade.cs" />
|
||||
<Compile Include="DiscUtils\Vfs\VfsFileSystemFactory.cs" />
|
||||
<Compile Include="DiscUtils\Vfs\VfsFileSystemFactoryAttribute.cs" />
|
||||
<Compile Include="DiscUtils\Vfs\VfsFileSystemInfo.cs" />
|
||||
<Compile Include="DiscUtils\Vfs\VfsFileSystemOpener.cs" />
|
||||
<Compile Include="DiscUtils\Vfs\VfsReadOnlyFileSystem.cs" />
|
||||
<Compile Include="DiscUtils\VirtualDisk.cs" />
|
||||
<Compile Include="DiscUtils\VirtualDiskClass.cs" />
|
||||
<Compile Include="DiscUtils\VirtualDiskExtent.cs" />
|
||||
<Compile Include="DiscUtils\VirtualDiskLayer.cs" />
|
||||
<Compile Include="DiscUtils\VirtualDiskManager.cs" />
|
||||
<Compile Include="DiscUtils\VirtualDiskParameters.cs" />
|
||||
<Compile Include="DiscUtils\VirtualDiskTypeInfo.cs" />
|
||||
<Compile Include="DiscUtils\VolumeInfo.cs" />
|
||||
<Compile Include="DiscUtils\VolumeManager.cs" />
|
||||
<Compile Include="DiscUtils\WindowsFileInformation.cs" />
|
||||
<Compile Include="MobyGamesDB.cs" />
|
||||
<Compile Include="Pbp.cs" />
|
||||
<Compile Include="PSXPackager\ApplicationInfo.cs" />
|
||||
<Compile Include="PSXPackager\FileExtensionHelper.cs" />
|
||||
<Compile Include="PSXPackager\GameEntry.cs" />
|
||||
<Compile Include="PSXPackager\MergedBin.cs" />
|
||||
<Compile Include="PSXPackager\PackagePsx.cs" />
|
||||
<Compile Include="POPS\Compression.cs" />
|
||||
<Compile Include="POPS\ConvertIsoInfo.cs" />
|
||||
<Compile Include="POPS\CueFile.cs" />
|
||||
<Compile Include="POPS\CueIndex.cs" />
|
||||
<Compile Include="POPS\CueReader.cs" />
|
||||
<Compile Include="POPS\CueTrack.cs" />
|
||||
<Compile Include="POPS\CueWriter.cs" />
|
||||
<Compile Include="POPS\DiscInfo.cs" />
|
||||
<Compile Include="POPS\ExtractIsoInfo.cs" />
|
||||
<Compile Include="POPS\Helper.cs" />
|
||||
<Compile Include="POPS\IndexPosition.cs" />
|
||||
<Compile Include="POPS\IndexPosition.Operators.cs" />
|
||||
<Compile Include="POPS\IsoIndex.cs" />
|
||||
<Compile Include="POPS\IsoIndexLite.cs" />
|
||||
<Compile Include="POPS\PatchData.cs" />
|
||||
<Compile Include="POPS\PbpStream.cs" />
|
||||
<Compile Include="POPS\Popstation.cs" />
|
||||
<Compile Include="POPS\Popstation.Data.cs" />
|
||||
<Compile Include="POPS\Popstation.Extract.cs" />
|
||||
<Compile Include="POPS\PopstationEventEnum.cs" />
|
||||
<Compile Include="POPS\SFOBuilder.cs" />
|
||||
<Compile Include="POPS\SFOData.cs" />
|
||||
<Compile Include="POPS\SFODir.cs" />
|
||||
<Compile Include="POPS\SFOEntry.cs" />
|
||||
<Compile Include="POPS\SFOKeys.cs" />
|
||||
<Compile Include="POPS\SFOValues.cs" />
|
||||
<Compile Include="POPS\StreamExtensions.cs" />
|
||||
<Compile Include="Program.cs" />
|
||||
<Compile Include="Properties\AssemblyInfo.cs" />
|
||||
<Compile Include="PSVIMGTOOLS\PSVIMGBuilder.cs" />
|
||||
<Compile Include="PSVIMGTOOLS\PSVIMGFileStream.cs" />
|
||||
<Compile Include="PSVIMGTOOLS\PSVIMGStream.cs" />
|
||||
<Compile Include="PSVIMGTOOLS\PSVIMGStructs.cs" />
|
||||
<Compile Include="PSVIMGTOOLS\PSVMDBuilder.cs" />
|
||||
<Compile Include="DataUtils.cs" />
|
||||
<Compile Include="ParamSfo.cs" />
|
||||
<EmbeddedResource Include="CHOVYPspBuilder.resx">
|
||||
<DependentUpon>CHOVYPspBuilder.cs</DependentUpon>
|
||||
</EmbeddedResource>
|
||||
<EmbeddedResource Include="CHOVYCmaSelector.resx">
|
||||
<DependentUpon>CHOVYCmaSelector.cs</DependentUpon>
|
||||
</EmbeddedResource>
|
||||
<EmbeddedResource Include="CHOVYPopsBuilder.resx">
|
||||
<DependentUpon>CHOVYPopsBuilder.cs</DependentUpon>
|
||||
</EmbeddedResource>
|
||||
<EmbeddedResource Include="Properties\Resources.resx">
|
||||
<Generator>ResXFileCodeGenerator</Generator>
|
||||
<LastGenOutput>Resources.Designer.cs</LastGenOutput>
|
||||
<SubType>Designer</SubType>
|
||||
</EmbeddedResource>
|
||||
<Compile Include="Properties\Resources.Designer.cs">
|
||||
<AutoGen>True</AutoGen>
|
||||
<DependentUpon>Resources.resx</DependentUpon>
|
||||
<DesignTime>True</DesignTime>
|
||||
</Compile>
|
||||
<None Include="Properties\Settings.settings">
|
||||
<Generator>SettingsSingleFileGenerator</Generator>
|
||||
<LastGenOutput>Settings.Designer.cs</LastGenOutput>
|
||||
</None>
|
||||
<Compile Include="Properties\Settings.Designer.cs">
|
||||
<AutoGen>True</AutoGen>
|
||||
<DependentUpon>Settings.settings</DependentUpon>
|
||||
<DesignTimeSharedInput>True</DesignTimeSharedInput>
|
||||
</Compile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="App.config" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="Resources\idkbackground.gif" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="Resources\umd.gif" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="Resources\Murica.wav" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="Resources\MINIS.png" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="Resources\ChovyLogo.png" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Content Include="Icon.ico" />
|
||||
<None Include="Resources\PopsDefaultIcon.png" />
|
||||
<None Include="Resources\does_not_protect_from_illegal_copies.gif" />
|
||||
<None Include="Resources\ps1.gif" />
|
||||
<None Include="Resources\POPS.wav" />
|
||||
</ItemGroup>
|
||||
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
|
||||
</Project>
|
|
@ -1,6 +0,0 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)' == 'Debug|x86'">
|
||||
<EnableUnmanagedDebugging>true</EnableUnmanagedDebugging>
|
||||
</PropertyGroup>
|
||||
</Project>
|
|
@ -1,122 +0,0 @@
|
|||
using ParamSfo;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Windows.Forms;
|
||||
|
||||
namespace CHOVY_SIGN
|
||||
{
|
||||
public partial class CHOVYCmaSelector : Form
|
||||
{
|
||||
public bool PSGame = false;
|
||||
public CHOVYCmaSelector(string CMA = "", string AID = "", bool PS1=false)
|
||||
{
|
||||
InitializeComponent();
|
||||
PSGame = PS1;
|
||||
CMADir.Text = CMA;
|
||||
AIDSelector.Text = AID;
|
||||
}
|
||||
|
||||
public string GetSelectedBackup()
|
||||
{
|
||||
try
|
||||
{
|
||||
return BackupList.Text.Substring(0, 9);
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
return "";
|
||||
}
|
||||
}
|
||||
public string GetCmaDir()
|
||||
{
|
||||
return CMADir.Text;
|
||||
}
|
||||
public string GetCmaAid()
|
||||
{
|
||||
return AIDSelector.Text;
|
||||
}
|
||||
|
||||
private void UpdateAidList()
|
||||
{
|
||||
AIDSelector.Items.Clear();
|
||||
try
|
||||
{
|
||||
string CmaDir = CMADir.Text;
|
||||
string BackupPath;
|
||||
if (!PSGame)
|
||||
BackupPath = Path.Combine(CmaDir, "PGAME");
|
||||
else
|
||||
BackupPath = Path.Combine(CmaDir, "PSGAME");
|
||||
foreach (string Dir in Directory.GetDirectories(BackupPath))
|
||||
{
|
||||
AIDSelector.Items.Add(Path.GetFileName(Dir));
|
||||
}
|
||||
AIDSelector.SelectedIndex = 0;
|
||||
}
|
||||
catch (Exception) { }
|
||||
|
||||
}
|
||||
private void UpdateBackupList()
|
||||
{
|
||||
BackupList.Items.Clear();
|
||||
|
||||
try
|
||||
{
|
||||
string CmaDir = CMADir.Text;
|
||||
string Aid = AIDSelector.Text;
|
||||
string BackupPath;
|
||||
if(!PSGame)
|
||||
BackupPath = Path.Combine(CmaDir, "PGAME", Aid);
|
||||
else
|
||||
BackupPath = Path.Combine(CmaDir, "PSGAME", Aid);
|
||||
foreach (string Dir in Directory.GetDirectories(BackupPath))
|
||||
{
|
||||
try
|
||||
{
|
||||
string SfoPath = Path.Combine(BackupPath, Dir, "sce_sys", "param.sfo");
|
||||
FileStream SfoStream = File.OpenRead(SfoPath);
|
||||
Dictionary<string,object> SfoKeys = Sfo.ReadSfo(SfoStream);
|
||||
string Title = (string)SfoKeys["TITLE"];
|
||||
SfoStream.Close();
|
||||
string BackupName = (Path.GetFileName(Dir) + " - " + Title);
|
||||
BackupList.Items.Add(BackupName);
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
BackupList.Items.Add(Path.GetFileName(Dir));
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
catch (Exception) { }
|
||||
|
||||
}
|
||||
|
||||
private void AIDSelector_TextChanged(object sender, EventArgs e)
|
||||
{
|
||||
UpdateBackupList();
|
||||
}
|
||||
|
||||
private void CMADir_TextChanged(object sender, EventArgs e)
|
||||
{
|
||||
UpdateBackupList();
|
||||
UpdateAidList();
|
||||
}
|
||||
|
||||
private void Browse_Click(object sender, EventArgs e)
|
||||
{
|
||||
FolderBrowserDialog fbd = new FolderBrowserDialog();
|
||||
fbd.Description = "CMA Backups Directory";
|
||||
fbd.ShowDialog();
|
||||
|
||||
CMADir.Text = fbd.SelectedPath;
|
||||
}
|
||||
|
||||
private void GitRifAndVerKey_Click(object sender, EventArgs e)
|
||||
{
|
||||
this.Close();
|
||||
}
|
||||
|
||||
}
|
||||
}
|
|
@ -1,658 +0,0 @@
|
|||
namespace CHOVY_SIGN
|
||||
{
|
||||
partial class CHOVYPopsBuilder
|
||||
{
|
||||
/// <summary>
|
||||
/// Required designer variable.
|
||||
/// </summary>
|
||||
private System.ComponentModel.IContainer components = null;
|
||||
|
||||
/// <summary>
|
||||
/// Clean up any resources being used.
|
||||
/// </summary>
|
||||
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
|
||||
protected override void Dispose(bool disposing)
|
||||
{
|
||||
if (disposing && (components != null))
|
||||
{
|
||||
components.Dispose();
|
||||
}
|
||||
base.Dispose(disposing);
|
||||
}
|
||||
|
||||
#region Windows Form Designer generated code
|
||||
|
||||
/// <summary>
|
||||
/// Required method for Designer support - do not modify
|
||||
/// the contents of this method with the code editor.
|
||||
/// </summary>
|
||||
private void InitializeComponent()
|
||||
{
|
||||
System.ComponentModel.ComponentResourceManager resources = new System.ComponentModel.ComponentResourceManager(typeof(CHOVYPopsBuilder));
|
||||
this.groupBox1 = new System.Windows.Forms.GroupBox();
|
||||
this.label6 = new System.Windows.Forms.Label();
|
||||
this.browseDisc5 = new System.Windows.Forms.Button();
|
||||
this.label5 = new System.Windows.Forms.Label();
|
||||
this.Disc5Path = new System.Windows.Forms.TextBox();
|
||||
this.browseDisc4 = new System.Windows.Forms.Button();
|
||||
this.label4 = new System.Windows.Forms.Label();
|
||||
this.Disc4Path = new System.Windows.Forms.TextBox();
|
||||
this.label3 = new System.Windows.Forms.Label();
|
||||
this.browseDisc3 = new System.Windows.Forms.Button();
|
||||
this.Disc3Path = new System.Windows.Forms.TextBox();
|
||||
this.browseDisc2 = new System.Windows.Forms.Button();
|
||||
this.Disc2Path = new System.Windows.Forms.TextBox();
|
||||
this.label2 = new System.Windows.Forms.Label();
|
||||
this.browseDisc1 = new System.Windows.Forms.Button();
|
||||
this.Disc1Path = new System.Windows.Forms.TextBox();
|
||||
this.label1 = new System.Windows.Forms.Label();
|
||||
this.label7 = new System.Windows.Forms.Label();
|
||||
this.groupBox2 = new System.Windows.Forms.GroupBox();
|
||||
this.FindFromCMA = new System.Windows.Forms.Button();
|
||||
this.Versionkey = new System.Windows.Forms.TextBox();
|
||||
this.label8 = new System.Windows.Forms.Label();
|
||||
this.RifPath = new System.Windows.Forms.TextBox();
|
||||
this.groupBox3 = new System.Windows.Forms.GroupBox();
|
||||
this.NtscPal = new System.Windows.Forms.RadioButton();
|
||||
this.Pal = new System.Windows.Forms.RadioButton();
|
||||
this.Ntsc = new System.Windows.Forms.RadioButton();
|
||||
this.label13 = new System.Windows.Forms.Label();
|
||||
this.SaveDescription = new System.Windows.Forms.TextBox();
|
||||
this.DiscId = new System.Windows.Forms.Label();
|
||||
this.label10 = new System.Windows.Forms.Label();
|
||||
this.BubbleIconPath = new System.Windows.Forms.TextBox();
|
||||
this.label9 = new System.Windows.Forms.Label();
|
||||
this.browseIcon = new System.Windows.Forms.Button();
|
||||
this.GameTitle = new System.Windows.Forms.TextBox();
|
||||
this.progressBar1 = new System.Windows.Forms.ProgressBar();
|
||||
this.ProgressStatus = new System.Windows.Forms.Label();
|
||||
this.FREEDOM = new System.Windows.Forms.Button();
|
||||
this.label11 = new System.Windows.Forms.Label();
|
||||
this.label12 = new System.Windows.Forms.Label();
|
||||
this.BubbleIcon = new System.Windows.Forms.PictureBox();
|
||||
this.CoolArtwork = new System.Windows.Forms.PictureBox();
|
||||
this.pictureBox1 = new System.Windows.Forms.PictureBox();
|
||||
this.groupBox1.SuspendLayout();
|
||||
this.groupBox2.SuspendLayout();
|
||||
this.groupBox3.SuspendLayout();
|
||||
((System.ComponentModel.ISupportInitialize)(this.BubbleIcon)).BeginInit();
|
||||
((System.ComponentModel.ISupportInitialize)(this.CoolArtwork)).BeginInit();
|
||||
((System.ComponentModel.ISupportInitialize)(this.pictureBox1)).BeginInit();
|
||||
this.SuspendLayout();
|
||||
//
|
||||
// groupBox1
|
||||
//
|
||||
this.groupBox1.Controls.Add(this.label6);
|
||||
this.groupBox1.Controls.Add(this.browseDisc5);
|
||||
this.groupBox1.Controls.Add(this.label5);
|
||||
this.groupBox1.Controls.Add(this.Disc5Path);
|
||||
this.groupBox1.Controls.Add(this.browseDisc4);
|
||||
this.groupBox1.Controls.Add(this.label4);
|
||||
this.groupBox1.Controls.Add(this.Disc4Path);
|
||||
this.groupBox1.Controls.Add(this.label3);
|
||||
this.groupBox1.Controls.Add(this.browseDisc3);
|
||||
this.groupBox1.Controls.Add(this.Disc3Path);
|
||||
this.groupBox1.Controls.Add(this.browseDisc2);
|
||||
this.groupBox1.Controls.Add(this.Disc2Path);
|
||||
this.groupBox1.Controls.Add(this.label2);
|
||||
this.groupBox1.Controls.Add(this.browseDisc1);
|
||||
this.groupBox1.Controls.Add(this.pictureBox1);
|
||||
this.groupBox1.Controls.Add(this.Disc1Path);
|
||||
this.groupBox1.Controls.Add(this.label1);
|
||||
this.groupBox1.ForeColor = System.Drawing.Color.Lime;
|
||||
this.groupBox1.Location = new System.Drawing.Point(317, 87);
|
||||
this.groupBox1.Name = "groupBox1";
|
||||
this.groupBox1.Size = new System.Drawing.Size(542, 252);
|
||||
this.groupBox1.TabIndex = 0;
|
||||
this.groupBox1.TabStop = false;
|
||||
this.groupBox1.Text = "The PS1 Game.";
|
||||
//
|
||||
// label6
|
||||
//
|
||||
this.label6.AutoSize = true;
|
||||
this.label6.Location = new System.Drawing.Point(3, 233);
|
||||
this.label6.Name = "label6";
|
||||
this.label6.Size = new System.Drawing.Size(107, 13);
|
||||
this.label6.TabIndex = 26;
|
||||
this.label6.Text = "Bin/Cue Disc Images";
|
||||
//
|
||||
// browseDisc5
|
||||
//
|
||||
this.browseDisc5.FlatStyle = System.Windows.Forms.FlatStyle.Flat;
|
||||
this.browseDisc5.ForeColor = System.Drawing.Color.Lime;
|
||||
this.browseDisc5.Location = new System.Drawing.Point(463, 198);
|
||||
this.browseDisc5.Name = "browseDisc5";
|
||||
this.browseDisc5.Size = new System.Drawing.Size(60, 22);
|
||||
this.browseDisc5.TabIndex = 25;
|
||||
this.browseDisc5.Text = "Browse";
|
||||
this.browseDisc5.UseVisualStyleBackColor = true;
|
||||
this.browseDisc5.EnabledChanged += new System.EventHandler(this.browseDisc5_EnabledChanged);
|
||||
this.browseDisc5.Click += new System.EventHandler(this.browseDisc5_Click);
|
||||
//
|
||||
// label5
|
||||
//
|
||||
this.label5.AutoSize = true;
|
||||
this.label5.Location = new System.Drawing.Point(112, 185);
|
||||
this.label5.Name = "label5";
|
||||
this.label5.Size = new System.Drawing.Size(47, 13);
|
||||
this.label5.TabIndex = 24;
|
||||
this.label5.Text = "Disc #5:";
|
||||
//
|
||||
// Disc5Path
|
||||
//
|
||||
this.Disc5Path.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(64)))), ((int)(((byte)(64)))), ((int)(((byte)(64)))));
|
||||
this.Disc5Path.BorderStyle = System.Windows.Forms.BorderStyle.FixedSingle;
|
||||
this.Disc5Path.Enabled = false;
|
||||
this.Disc5Path.ForeColor = System.Drawing.Color.Lime;
|
||||
this.Disc5Path.Location = new System.Drawing.Point(115, 201);
|
||||
this.Disc5Path.Name = "Disc5Path";
|
||||
this.Disc5Path.Size = new System.Drawing.Size(342, 20);
|
||||
this.Disc5Path.TabIndex = 23;
|
||||
//
|
||||
// browseDisc4
|
||||
//
|
||||
this.browseDisc4.FlatStyle = System.Windows.Forms.FlatStyle.Flat;
|
||||
this.browseDisc4.ForeColor = System.Drawing.Color.Lime;
|
||||
this.browseDisc4.Location = new System.Drawing.Point(463, 162);
|
||||
this.browseDisc4.Name = "browseDisc4";
|
||||
this.browseDisc4.Size = new System.Drawing.Size(60, 22);
|
||||
this.browseDisc4.TabIndex = 22;
|
||||
this.browseDisc4.Text = "Browse";
|
||||
this.browseDisc4.UseVisualStyleBackColor = true;
|
||||
this.browseDisc4.EnabledChanged += new System.EventHandler(this.browseDisc4_EnabledChanged);
|
||||
this.browseDisc4.Click += new System.EventHandler(this.browseDisc4_Click);
|
||||
//
|
||||
// label4
|
||||
//
|
||||
this.label4.AutoSize = true;
|
||||
this.label4.Location = new System.Drawing.Point(112, 146);
|
||||
this.label4.Name = "label4";
|
||||
this.label4.Size = new System.Drawing.Size(47, 13);
|
||||
this.label4.TabIndex = 21;
|
||||
this.label4.Text = "Disc #4:";
|
||||
//
|
||||
// Disc4Path
|
||||
//
|
||||
this.Disc4Path.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(64)))), ((int)(((byte)(64)))), ((int)(((byte)(64)))));
|
||||
this.Disc4Path.BorderStyle = System.Windows.Forms.BorderStyle.FixedSingle;
|
||||
this.Disc4Path.Enabled = false;
|
||||
this.Disc4Path.ForeColor = System.Drawing.Color.Lime;
|
||||
this.Disc4Path.Location = new System.Drawing.Point(115, 162);
|
||||
this.Disc4Path.Name = "Disc4Path";
|
||||
this.Disc4Path.Size = new System.Drawing.Size(342, 20);
|
||||
this.Disc4Path.TabIndex = 20;
|
||||
this.Disc4Path.TextChanged += new System.EventHandler(this.Disc4Path_TextChanged);
|
||||
//
|
||||
// label3
|
||||
//
|
||||
this.label3.AutoSize = true;
|
||||
this.label3.Location = new System.Drawing.Point(112, 105);
|
||||
this.label3.Name = "label3";
|
||||
this.label3.Size = new System.Drawing.Size(47, 13);
|
||||
this.label3.TabIndex = 19;
|
||||
this.label3.Text = "Disc #3:";
|
||||
//
|
||||
// browseDisc3
|
||||
//
|
||||
this.browseDisc3.FlatStyle = System.Windows.Forms.FlatStyle.Flat;
|
||||
this.browseDisc3.ForeColor = System.Drawing.Color.Lime;
|
||||
this.browseDisc3.Location = new System.Drawing.Point(463, 123);
|
||||
this.browseDisc3.Name = "browseDisc3";
|
||||
this.browseDisc3.Size = new System.Drawing.Size(60, 22);
|
||||
this.browseDisc3.TabIndex = 18;
|
||||
this.browseDisc3.Text = "Browse";
|
||||
this.browseDisc3.UseVisualStyleBackColor = true;
|
||||
this.browseDisc3.EnabledChanged += new System.EventHandler(this.browseDisc3_EnabledChanged);
|
||||
this.browseDisc3.Click += new System.EventHandler(this.browseDisc3_Click);
|
||||
//
|
||||
// Disc3Path
|
||||
//
|
||||
this.Disc3Path.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(64)))), ((int)(((byte)(64)))), ((int)(((byte)(64)))));
|
||||
this.Disc3Path.BorderStyle = System.Windows.Forms.BorderStyle.FixedSingle;
|
||||
this.Disc3Path.Enabled = false;
|
||||
this.Disc3Path.ForeColor = System.Drawing.Color.Lime;
|
||||
this.Disc3Path.Location = new System.Drawing.Point(115, 123);
|
||||
this.Disc3Path.Name = "Disc3Path";
|
||||
this.Disc3Path.Size = new System.Drawing.Size(342, 20);
|
||||
this.Disc3Path.TabIndex = 17;
|
||||
this.Disc3Path.TextChanged += new System.EventHandler(this.Disc3Path_TextChanged);
|
||||
//
|
||||
// browseDisc2
|
||||
//
|
||||
this.browseDisc2.FlatStyle = System.Windows.Forms.FlatStyle.Flat;
|
||||
this.browseDisc2.ForeColor = System.Drawing.Color.Lime;
|
||||
this.browseDisc2.Location = new System.Drawing.Point(463, 82);
|
||||
this.browseDisc2.Name = "browseDisc2";
|
||||
this.browseDisc2.Size = new System.Drawing.Size(60, 22);
|
||||
this.browseDisc2.TabIndex = 16;
|
||||
this.browseDisc2.Text = "Browse";
|
||||
this.browseDisc2.UseVisualStyleBackColor = true;
|
||||
this.browseDisc2.EnabledChanged += new System.EventHandler(this.browseDisc2_EnabledChanged);
|
||||
this.browseDisc2.Click += new System.EventHandler(this.browseDisc2_Click);
|
||||
//
|
||||
// Disc2Path
|
||||
//
|
||||
this.Disc2Path.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(64)))), ((int)(((byte)(64)))), ((int)(((byte)(64)))));
|
||||
this.Disc2Path.BorderStyle = System.Windows.Forms.BorderStyle.FixedSingle;
|
||||
this.Disc2Path.Enabled = false;
|
||||
this.Disc2Path.ForeColor = System.Drawing.Color.Lime;
|
||||
this.Disc2Path.Location = new System.Drawing.Point(115, 82);
|
||||
this.Disc2Path.Name = "Disc2Path";
|
||||
this.Disc2Path.Size = new System.Drawing.Size(342, 20);
|
||||
this.Disc2Path.TabIndex = 15;
|
||||
this.Disc2Path.TextChanged += new System.EventHandler(this.Disc2Path_TextChanged);
|
||||
//
|
||||
// label2
|
||||
//
|
||||
this.label2.AutoSize = true;
|
||||
this.label2.Location = new System.Drawing.Point(112, 66);
|
||||
this.label2.Name = "label2";
|
||||
this.label2.Size = new System.Drawing.Size(47, 13);
|
||||
this.label2.TabIndex = 14;
|
||||
this.label2.Text = "Disc #2:";
|
||||
//
|
||||
// browseDisc1
|
||||
//
|
||||
this.browseDisc1.FlatStyle = System.Windows.Forms.FlatStyle.Flat;
|
||||
this.browseDisc1.ForeColor = System.Drawing.Color.Lime;
|
||||
this.browseDisc1.Location = new System.Drawing.Point(463, 43);
|
||||
this.browseDisc1.Name = "browseDisc1";
|
||||
this.browseDisc1.Size = new System.Drawing.Size(60, 22);
|
||||
this.browseDisc1.TabIndex = 13;
|
||||
this.browseDisc1.Text = "Browse";
|
||||
this.browseDisc1.UseVisualStyleBackColor = true;
|
||||
this.browseDisc1.EnabledChanged += new System.EventHandler(this.browseDisc1_EnabledChanged);
|
||||
this.browseDisc1.Click += new System.EventHandler(this.browseDisc1_Click);
|
||||
//
|
||||
// Disc1Path
|
||||
//
|
||||
this.Disc1Path.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(64)))), ((int)(((byte)(64)))), ((int)(((byte)(64)))));
|
||||
this.Disc1Path.BorderStyle = System.Windows.Forms.BorderStyle.FixedSingle;
|
||||
this.Disc1Path.ForeColor = System.Drawing.Color.Lime;
|
||||
this.Disc1Path.Location = new System.Drawing.Point(115, 43);
|
||||
this.Disc1Path.Name = "Disc1Path";
|
||||
this.Disc1Path.Size = new System.Drawing.Size(342, 20);
|
||||
this.Disc1Path.TabIndex = 7;
|
||||
this.Disc1Path.TextChanged += new System.EventHandler(this.Disc1Path_TextChanged);
|
||||
//
|
||||
// label1
|
||||
//
|
||||
this.label1.AutoSize = true;
|
||||
this.label1.Location = new System.Drawing.Point(112, 27);
|
||||
this.label1.Name = "label1";
|
||||
this.label1.Size = new System.Drawing.Size(47, 13);
|
||||
this.label1.TabIndex = 0;
|
||||
this.label1.Text = "Disc #1:";
|
||||
//
|
||||
// label7
|
||||
//
|
||||
this.label7.AccessibleRole = System.Windows.Forms.AccessibleRole.None;
|
||||
this.label7.AutoSize = true;
|
||||
this.label7.ForeColor = System.Drawing.Color.Lime;
|
||||
this.label7.Location = new System.Drawing.Point(6, 21);
|
||||
this.label7.Name = "label7";
|
||||
this.label7.Size = new System.Drawing.Size(27, 13);
|
||||
this.label7.TabIndex = 2;
|
||||
this.label7.Text = "RIF:";
|
||||
//
|
||||
// groupBox2
|
||||
//
|
||||
this.groupBox2.Controls.Add(this.FindFromCMA);
|
||||
this.groupBox2.Controls.Add(this.Versionkey);
|
||||
this.groupBox2.Controls.Add(this.label8);
|
||||
this.groupBox2.Controls.Add(this.RifPath);
|
||||
this.groupBox2.Controls.Add(this.label7);
|
||||
this.groupBox2.ForeColor = System.Drawing.Color.Lime;
|
||||
this.groupBox2.Location = new System.Drawing.Point(239, 12);
|
||||
this.groupBox2.Name = "groupBox2";
|
||||
this.groupBox2.Size = new System.Drawing.Size(694, 54);
|
||||
this.groupBox2.TabIndex = 3;
|
||||
this.groupBox2.TabStop = false;
|
||||
this.groupBox2.Text = "Keys to the Kingdom";
|
||||
//
|
||||
// FindFromCMA
|
||||
//
|
||||
this.FindFromCMA.FlatStyle = System.Windows.Forms.FlatStyle.Flat;
|
||||
this.FindFromCMA.ForeColor = System.Drawing.Color.Lime;
|
||||
this.FindFromCMA.Location = new System.Drawing.Point(569, 16);
|
||||
this.FindFromCMA.Name = "FindFromCMA";
|
||||
this.FindFromCMA.Size = new System.Drawing.Size(109, 23);
|
||||
this.FindFromCMA.TabIndex = 6;
|
||||
this.FindFromCMA.Text = "Find from CMA";
|
||||
this.FindFromCMA.UseVisualStyleBackColor = true;
|
||||
this.FindFromCMA.Click += new System.EventHandler(this.FindFromCMA_Click);
|
||||
//
|
||||
// Versionkey
|
||||
//
|
||||
this.Versionkey.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(64)))), ((int)(((byte)(64)))), ((int)(((byte)(64)))));
|
||||
this.Versionkey.BorderStyle = System.Windows.Forms.BorderStyle.FixedSingle;
|
||||
this.Versionkey.ForeColor = System.Drawing.Color.Lime;
|
||||
this.Versionkey.Location = new System.Drawing.Point(338, 19);
|
||||
this.Versionkey.Name = "Versionkey";
|
||||
this.Versionkey.Size = new System.Drawing.Size(225, 20);
|
||||
this.Versionkey.TabIndex = 5;
|
||||
//
|
||||
// label8
|
||||
//
|
||||
this.label8.AccessibleRole = System.Windows.Forms.AccessibleRole.None;
|
||||
this.label8.AutoSize = true;
|
||||
this.label8.ForeColor = System.Drawing.Color.Lime;
|
||||
this.label8.Location = new System.Drawing.Point(270, 21);
|
||||
this.label8.Name = "label8";
|
||||
this.label8.Size = new System.Drawing.Size(63, 13);
|
||||
this.label8.TabIndex = 4;
|
||||
this.label8.Text = "VersionKey:";
|
||||
//
|
||||
// RifPath
|
||||
//
|
||||
this.RifPath.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(64)))), ((int)(((byte)(64)))), ((int)(((byte)(64)))));
|
||||
this.RifPath.BorderStyle = System.Windows.Forms.BorderStyle.FixedSingle;
|
||||
this.RifPath.ForeColor = System.Drawing.Color.Lime;
|
||||
this.RifPath.Location = new System.Drawing.Point(39, 19);
|
||||
this.RifPath.Name = "RifPath";
|
||||
this.RifPath.Size = new System.Drawing.Size(225, 20);
|
||||
this.RifPath.TabIndex = 3;
|
||||
//
|
||||
// groupBox3
|
||||
//
|
||||
this.groupBox3.Controls.Add(this.NtscPal);
|
||||
this.groupBox3.Controls.Add(this.Pal);
|
||||
this.groupBox3.Controls.Add(this.Ntsc);
|
||||
this.groupBox3.Controls.Add(this.label13);
|
||||
this.groupBox3.Controls.Add(this.SaveDescription);
|
||||
this.groupBox3.Controls.Add(this.DiscId);
|
||||
this.groupBox3.Controls.Add(this.label10);
|
||||
this.groupBox3.Controls.Add(this.BubbleIconPath);
|
||||
this.groupBox3.Controls.Add(this.label9);
|
||||
this.groupBox3.Controls.Add(this.browseIcon);
|
||||
this.groupBox3.Controls.Add(this.GameTitle);
|
||||
this.groupBox3.Controls.Add(this.BubbleIcon);
|
||||
this.groupBox3.ForeColor = System.Drawing.Color.Lime;
|
||||
this.groupBox3.Location = new System.Drawing.Point(260, 358);
|
||||
this.groupBox3.Name = "groupBox3";
|
||||
this.groupBox3.Size = new System.Drawing.Size(645, 256);
|
||||
this.groupBox3.TabIndex = 4;
|
||||
this.groupBox3.TabStop = false;
|
||||
this.groupBox3.Text = "Bubble Info";
|
||||
//
|
||||
// NtscPal
|
||||
//
|
||||
this.NtscPal.AutoSize = true;
|
||||
this.NtscPal.FlatStyle = System.Windows.Forms.FlatStyle.Flat;
|
||||
this.NtscPal.Location = new System.Drawing.Point(438, 229);
|
||||
this.NtscPal.Name = "NtscPal";
|
||||
this.NtscPal.Size = new System.Drawing.Size(76, 17);
|
||||
this.NtscPal.TabIndex = 35;
|
||||
this.NtscPal.Text = "NTSC-PAL";
|
||||
this.NtscPal.UseVisualStyleBackColor = true;
|
||||
//
|
||||
// Pal
|
||||
//
|
||||
this.Pal.AutoSize = true;
|
||||
this.Pal.FlatStyle = System.Windows.Forms.FlatStyle.Flat;
|
||||
this.Pal.Location = new System.Drawing.Point(520, 229);
|
||||
this.Pal.Name = "Pal";
|
||||
this.Pal.Size = new System.Drawing.Size(44, 17);
|
||||
this.Pal.TabIndex = 34;
|
||||
this.Pal.Text = "PAL";
|
||||
this.Pal.UseVisualStyleBackColor = true;
|
||||
//
|
||||
// Ntsc
|
||||
//
|
||||
this.Ntsc.AutoSize = true;
|
||||
this.Ntsc.Checked = true;
|
||||
this.Ntsc.FlatStyle = System.Windows.Forms.FlatStyle.Flat;
|
||||
this.Ntsc.Location = new System.Drawing.Point(379, 229);
|
||||
this.Ntsc.Name = "Ntsc";
|
||||
this.Ntsc.Size = new System.Drawing.Size(53, 17);
|
||||
this.Ntsc.TabIndex = 33;
|
||||
this.Ntsc.TabStop = true;
|
||||
this.Ntsc.Text = "NTSC";
|
||||
this.Ntsc.UseVisualStyleBackColor = true;
|
||||
//
|
||||
// label13
|
||||
//
|
||||
this.label13.AutoSize = true;
|
||||
this.label13.Location = new System.Drawing.Point(111, 104);
|
||||
this.label13.Name = "label13";
|
||||
this.label13.Size = new System.Drawing.Size(91, 13);
|
||||
this.label13.TabIndex = 32;
|
||||
this.label13.Text = "Save Description:";
|
||||
//
|
||||
// SaveDescription
|
||||
//
|
||||
this.SaveDescription.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(64)))), ((int)(((byte)(64)))), ((int)(((byte)(64)))));
|
||||
this.SaveDescription.BorderStyle = System.Windows.Forms.BorderStyle.FixedSingle;
|
||||
this.SaveDescription.ForeColor = System.Drawing.Color.Lime;
|
||||
this.SaveDescription.Location = new System.Drawing.Point(114, 120);
|
||||
this.SaveDescription.MaxLength = 80;
|
||||
this.SaveDescription.Multiline = true;
|
||||
this.SaveDescription.Name = "SaveDescription";
|
||||
this.SaveDescription.Size = new System.Drawing.Size(519, 64);
|
||||
this.SaveDescription.TabIndex = 31;
|
||||
this.SaveDescription.Text = "Epiic PS1 Game - Save File";
|
||||
//
|
||||
// DiscId
|
||||
//
|
||||
this.DiscId.AutoSize = true;
|
||||
this.DiscId.Location = new System.Drawing.Point(25, 121);
|
||||
this.DiscId.Name = "DiscId";
|
||||
this.DiscId.Size = new System.Drawing.Size(0, 13);
|
||||
this.DiscId.TabIndex = 30;
|
||||
//
|
||||
// label10
|
||||
//
|
||||
this.label10.AutoSize = true;
|
||||
this.label10.Location = new System.Drawing.Point(111, 187);
|
||||
this.label10.Name = "label10";
|
||||
this.label10.Size = new System.Drawing.Size(105, 13);
|
||||
this.label10.TabIndex = 29;
|
||||
this.label10.Text = "Bubble Icon (80x80):";
|
||||
//
|
||||
// BubbleIconPath
|
||||
//
|
||||
this.BubbleIconPath.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(64)))), ((int)(((byte)(64)))), ((int)(((byte)(64)))));
|
||||
this.BubbleIconPath.BorderStyle = System.Windows.Forms.BorderStyle.FixedSingle;
|
||||
this.BubbleIconPath.ForeColor = System.Drawing.Color.Lime;
|
||||
this.BubbleIconPath.Location = new System.Drawing.Point(114, 203);
|
||||
this.BubbleIconPath.Name = "BubbleIconPath";
|
||||
this.BubbleIconPath.Size = new System.Drawing.Size(450, 20);
|
||||
this.BubbleIconPath.TabIndex = 28;
|
||||
this.BubbleIconPath.Text = "(none)";
|
||||
this.BubbleIconPath.TextChanged += new System.EventHandler(this.BubbleIconPath_TextChanged);
|
||||
//
|
||||
// label9
|
||||
//
|
||||
this.label9.AutoSize = true;
|
||||
this.label9.Location = new System.Drawing.Point(114, 21);
|
||||
this.label9.Name = "label9";
|
||||
this.label9.Size = new System.Drawing.Size(30, 13);
|
||||
this.label9.TabIndex = 27;
|
||||
this.label9.Text = "Title:";
|
||||
//
|
||||
// browseIcon
|
||||
//
|
||||
this.browseIcon.FlatStyle = System.Windows.Forms.FlatStyle.Flat;
|
||||
this.browseIcon.ForeColor = System.Drawing.Color.Lime;
|
||||
this.browseIcon.Location = new System.Drawing.Point(570, 203);
|
||||
this.browseIcon.Name = "browseIcon";
|
||||
this.browseIcon.Size = new System.Drawing.Size(60, 22);
|
||||
this.browseIcon.TabIndex = 26;
|
||||
this.browseIcon.Text = "Browse";
|
||||
this.browseIcon.UseVisualStyleBackColor = true;
|
||||
this.browseIcon.Click += new System.EventHandler(this.browseIcon_Click);
|
||||
//
|
||||
// GameTitle
|
||||
//
|
||||
this.GameTitle.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(64)))), ((int)(((byte)(64)))), ((int)(((byte)(64)))));
|
||||
this.GameTitle.BorderStyle = System.Windows.Forms.BorderStyle.FixedSingle;
|
||||
this.GameTitle.ForeColor = System.Drawing.Color.Lime;
|
||||
this.GameTitle.Location = new System.Drawing.Point(114, 37);
|
||||
this.GameTitle.MaxLength = 80;
|
||||
this.GameTitle.Multiline = true;
|
||||
this.GameTitle.Name = "GameTitle";
|
||||
this.GameTitle.Size = new System.Drawing.Size(516, 64);
|
||||
this.GameTitle.TabIndex = 8;
|
||||
this.GameTitle.Text = "Epic PS1 Game!";
|
||||
//
|
||||
// progressBar1
|
||||
//
|
||||
this.progressBar1.Location = new System.Drawing.Point(260, 659);
|
||||
this.progressBar1.Name = "progressBar1";
|
||||
this.progressBar1.Size = new System.Drawing.Size(564, 23);
|
||||
this.progressBar1.TabIndex = 5;
|
||||
//
|
||||
// ProgressStatus
|
||||
//
|
||||
this.ProgressStatus.AutoSize = true;
|
||||
this.ProgressStatus.ForeColor = System.Drawing.Color.Lime;
|
||||
this.ProgressStatus.Location = new System.Drawing.Point(257, 643);
|
||||
this.ProgressStatus.Name = "ProgressStatus";
|
||||
this.ProgressStatus.Size = new System.Drawing.Size(59, 13);
|
||||
this.ProgressStatus.TabIndex = 6;
|
||||
this.ProgressStatus.Text = "Progress %";
|
||||
//
|
||||
// FREEDOM
|
||||
//
|
||||
this.FREEDOM.FlatStyle = System.Windows.Forms.FlatStyle.Flat;
|
||||
this.FREEDOM.ForeColor = System.Drawing.Color.FromArgb(((int)(((byte)(192)))), ((int)(((byte)(0)))), ((int)(((byte)(0)))));
|
||||
this.FREEDOM.Location = new System.Drawing.Point(830, 659);
|
||||
this.FREEDOM.Name = "FREEDOM";
|
||||
this.FREEDOM.Size = new System.Drawing.Size(75, 23);
|
||||
this.FREEDOM.TabIndex = 16;
|
||||
this.FREEDOM.Text = "FREEDOM";
|
||||
this.FREEDOM.UseVisualStyleBackColor = true;
|
||||
this.FREEDOM.EnabledChanged += new System.EventHandler(this.FREEDOM_EnabledChanged);
|
||||
this.FREEDOM.Click += new System.EventHandler(this.FREEDOM_Click);
|
||||
//
|
||||
// label11
|
||||
//
|
||||
this.label11.AutoSize = true;
|
||||
this.label11.ForeColor = System.Drawing.Color.Lime;
|
||||
this.label11.Location = new System.Drawing.Point(835, 703);
|
||||
this.label11.Name = "label11";
|
||||
this.label11.Size = new System.Drawing.Size(113, 13);
|
||||
this.label11.TabIndex = 17;
|
||||
this.label11.Text = "SilicaAndPina, dots_tb";
|
||||
//
|
||||
// label12
|
||||
//
|
||||
this.label12.AutoSize = true;
|
||||
this.label12.ForeColor = System.Drawing.Color.Lime;
|
||||
this.label12.Location = new System.Drawing.Point(222, 703);
|
||||
this.label12.Name = "label12";
|
||||
this.label12.Size = new System.Drawing.Size(123, 13);
|
||||
this.label12.TabIndex = 18;
|
||||
this.label12.Text = "Made possible by CBPS.";
|
||||
//
|
||||
// BubbleIcon
|
||||
//
|
||||
this.BubbleIcon.BackgroundImage = global::CHOVY_SIGN.Properties.Resources.PopsDefaultIcon;
|
||||
this.BubbleIcon.BackgroundImageLayout = System.Windows.Forms.ImageLayout.None;
|
||||
this.BubbleIcon.Location = new System.Drawing.Point(18, 37);
|
||||
this.BubbleIcon.Name = "BubbleIcon";
|
||||
this.BubbleIcon.Size = new System.Drawing.Size(80, 80);
|
||||
this.BubbleIcon.TabIndex = 0;
|
||||
this.BubbleIcon.TabStop = false;
|
||||
//
|
||||
// CoolArtwork
|
||||
//
|
||||
this.CoolArtwork.Location = new System.Drawing.Point(12, 3);
|
||||
this.CoolArtwork.Name = "CoolArtwork";
|
||||
this.CoolArtwork.Size = new System.Drawing.Size(204, 713);
|
||||
this.CoolArtwork.TabIndex = 1;
|
||||
this.CoolArtwork.TabStop = false;
|
||||
this.CoolArtwork.Click += new System.EventHandler(this.CoolArtwork_Click);
|
||||
//
|
||||
// pictureBox1
|
||||
//
|
||||
this.pictureBox1.BackgroundImage = global::CHOVY_SIGN.Properties.Resources.does_not_protect_from_illegal_copies;
|
||||
this.pictureBox1.BackgroundImageLayout = System.Windows.Forms.ImageLayout.Stretch;
|
||||
this.pictureBox1.Location = new System.Drawing.Point(7, 79);
|
||||
this.pictureBox1.Name = "pictureBox1";
|
||||
this.pictureBox1.Size = new System.Drawing.Size(103, 103);
|
||||
this.pictureBox1.TabIndex = 1;
|
||||
this.pictureBox1.TabStop = false;
|
||||
//
|
||||
// CHOVYPopsBuilder
|
||||
//
|
||||
this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
|
||||
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
|
||||
this.BackColor = System.Drawing.Color.Black;
|
||||
this.ClientSize = new System.Drawing.Size(960, 728);
|
||||
this.Controls.Add(this.label12);
|
||||
this.Controls.Add(this.label11);
|
||||
this.Controls.Add(this.FREEDOM);
|
||||
this.Controls.Add(this.ProgressStatus);
|
||||
this.Controls.Add(this.progressBar1);
|
||||
this.Controls.Add(this.groupBox3);
|
||||
this.Controls.Add(this.groupBox2);
|
||||
this.Controls.Add(this.CoolArtwork);
|
||||
this.Controls.Add(this.groupBox1);
|
||||
this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.FixedSingle;
|
||||
this.Icon = ((System.Drawing.Icon)(resources.GetObject("$this.Icon")));
|
||||
this.MaximizeBox = false;
|
||||
this.Name = "CHOVYPopsBuilder";
|
||||
this.Text = " CHOVY-POPS-SIGN";
|
||||
this.Load += new System.EventHandler(this.CHOVYPopsBuilder_Load);
|
||||
this.groupBox1.ResumeLayout(false);
|
||||
this.groupBox1.PerformLayout();
|
||||
this.groupBox2.ResumeLayout(false);
|
||||
this.groupBox2.PerformLayout();
|
||||
this.groupBox3.ResumeLayout(false);
|
||||
this.groupBox3.PerformLayout();
|
||||
((System.ComponentModel.ISupportInitialize)(this.BubbleIcon)).EndInit();
|
||||
((System.ComponentModel.ISupportInitialize)(this.CoolArtwork)).EndInit();
|
||||
((System.ComponentModel.ISupportInitialize)(this.pictureBox1)).EndInit();
|
||||
this.ResumeLayout(false);
|
||||
this.PerformLayout();
|
||||
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
private System.Windows.Forms.GroupBox groupBox1;
|
||||
private System.Windows.Forms.Label label1;
|
||||
private System.Windows.Forms.PictureBox pictureBox1;
|
||||
private System.Windows.Forms.TextBox Disc1Path;
|
||||
private System.Windows.Forms.TextBox Disc4Path;
|
||||
private System.Windows.Forms.Label label3;
|
||||
private System.Windows.Forms.Button browseDisc3;
|
||||
private System.Windows.Forms.TextBox Disc3Path;
|
||||
private System.Windows.Forms.Button browseDisc2;
|
||||
private System.Windows.Forms.TextBox Disc2Path;
|
||||
private System.Windows.Forms.Label label2;
|
||||
private System.Windows.Forms.Button browseDisc1;
|
||||
private System.Windows.Forms.Label label6;
|
||||
private System.Windows.Forms.Button browseDisc5;
|
||||
private System.Windows.Forms.Label label5;
|
||||
private System.Windows.Forms.TextBox Disc5Path;
|
||||
private System.Windows.Forms.Button browseDisc4;
|
||||
private System.Windows.Forms.Label label4;
|
||||
private System.Windows.Forms.PictureBox CoolArtwork;
|
||||
private System.Windows.Forms.Label label7;
|
||||
private System.Windows.Forms.GroupBox groupBox2;
|
||||
private System.Windows.Forms.TextBox Versionkey;
|
||||
private System.Windows.Forms.Label label8;
|
||||
private System.Windows.Forms.TextBox RifPath;
|
||||
private System.Windows.Forms.Button FindFromCMA;
|
||||
private System.Windows.Forms.GroupBox groupBox3;
|
||||
private System.Windows.Forms.PictureBox BubbleIcon;
|
||||
private System.Windows.Forms.Label label10;
|
||||
private System.Windows.Forms.TextBox BubbleIconPath;
|
||||
private System.Windows.Forms.Label label9;
|
||||
private System.Windows.Forms.Button browseIcon;
|
||||
private System.Windows.Forms.TextBox GameTitle;
|
||||
private System.Windows.Forms.ProgressBar progressBar1;
|
||||
private System.Windows.Forms.Label ProgressStatus;
|
||||
private System.Windows.Forms.Button FREEDOM;
|
||||
private System.Windows.Forms.Label label11;
|
||||
private System.Windows.Forms.Label label12;
|
||||
private System.Windows.Forms.Label DiscId;
|
||||
private System.Windows.Forms.Label label13;
|
||||
private System.Windows.Forms.TextBox SaveDescription;
|
||||
private System.Windows.Forms.RadioButton NtscPal;
|
||||
private System.Windows.Forms.RadioButton Pal;
|
||||
private System.Windows.Forms.RadioButton Ntsc;
|
||||
}
|
||||
}
|
|
@ -1,455 +0,0 @@
|
|||
using Ionic.Zlib;
|
||||
using Microsoft.Win32;
|
||||
using Popstation;
|
||||
using PSVIMGTOOLS;
|
||||
using PSXPackager;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Drawing;
|
||||
using System.Drawing.Imaging;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Net;
|
||||
using System.Threading;
|
||||
using System.Windows.Forms;
|
||||
|
||||
namespace CHOVY_SIGN
|
||||
{
|
||||
public partial class CHOVYPopsBuilder : Form
|
||||
{
|
||||
public CHOVYPopsBuilder()
|
||||
{
|
||||
InitializeComponent();
|
||||
}
|
||||
|
||||
public bool MutedAudio = false;
|
||||
public string ReadSetting(string Setting)
|
||||
{
|
||||
string Value = "";
|
||||
try
|
||||
{
|
||||
|
||||
RegistryKey key;
|
||||
key = Registry.CurrentUser.CreateSubKey(@"Software\CHOVYProject\Chovy-Pops-Sign");
|
||||
Value = key.GetValue(Setting).ToString();
|
||||
key.Close();
|
||||
}
|
||||
catch (Exception) { return ""; }
|
||||
return Value;
|
||||
}
|
||||
|
||||
public void WriteSetting(string Setting, string Value)
|
||||
{
|
||||
try
|
||||
{
|
||||
RegistryKey key;
|
||||
key = Registry.CurrentUser.CreateSubKey(@"Software\CHOVYProject\Chovy-Pops-Sign");
|
||||
key.SetValue(Setting, Value);
|
||||
key.Close();
|
||||
}
|
||||
catch (Exception) { }
|
||||
}
|
||||
|
||||
private void Disc1Path_TextChanged(object sender, EventArgs e)
|
||||
{
|
||||
if (Disc1Path.Text != "")
|
||||
{
|
||||
Disc2Path.Enabled = true;
|
||||
browseDisc2.Enabled = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
Disc2Path.Text = "";
|
||||
Disc2Path.Enabled = false;
|
||||
browseDisc2.Enabled = false;
|
||||
}
|
||||
}
|
||||
|
||||
private void Disc2Path_TextChanged(object sender, EventArgs e)
|
||||
{
|
||||
if (Disc2Path.Text != "")
|
||||
{
|
||||
Disc3Path.Enabled = true;
|
||||
browseDisc3.Enabled = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
Disc3Path.Text = "";
|
||||
Disc3Path.Enabled = false;
|
||||
browseDisc3.Enabled = false;
|
||||
}
|
||||
}
|
||||
|
||||
private void Disc3Path_TextChanged(object sender, EventArgs e)
|
||||
{
|
||||
if (Disc3Path.Text != "")
|
||||
{
|
||||
Disc4Path.Enabled = true;
|
||||
browseDisc4.Enabled = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
Disc4Path.Text = "";
|
||||
Disc4Path.Enabled = false;
|
||||
browseDisc4.Enabled = false;
|
||||
}
|
||||
}
|
||||
|
||||
private void Disc4Path_TextChanged(object sender, EventArgs e)
|
||||
{
|
||||
if (Disc4Path.Text != "")
|
||||
{
|
||||
Disc5Path.Enabled = true;
|
||||
browseDisc5.Enabled = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
Disc5Path.Text = "";
|
||||
Disc5Path.Enabled = false;
|
||||
browseDisc5.Enabled = false;
|
||||
}
|
||||
}
|
||||
|
||||
private void FindFromCMA_Click(object sender, EventArgs e)
|
||||
{
|
||||
this.Hide();
|
||||
string cmaDir = "";
|
||||
string accountId = "0000000000000000";
|
||||
|
||||
try
|
||||
{
|
||||
//try qcma
|
||||
cmaDir = Registry.CurrentUser.OpenSubKey(@"Software\codestation\qcma").GetValue("appsPath").ToString();
|
||||
accountId = Registry.CurrentUser.OpenSubKey(@"Software\codestation\qcma").GetValue("lastAccountId").ToString();
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
try
|
||||
{
|
||||
//try sony cma
|
||||
cmaDir = Registry.CurrentUser.OpenSubKey(@"Software\Sony Corporation\Content Manager Assistant\Settings").GetValue("ApplicationHomePath").ToString();
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
try
|
||||
{
|
||||
//try devkit cma
|
||||
cmaDir = Registry.CurrentUser.OpenSubKey(@"Software\SCE\PSP2\Services\Content Manager Assistant for PlayStation(R)Vita DevKit\Settings").GetValue("ApplicationHomePath").ToString();
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
try
|
||||
{
|
||||
string DefaultDir = Path.Combine(Environment.GetEnvironmentVariable("HOMEDRIVE"), Environment.GetEnvironmentVariable("HOMEPATH"), "Documents", "PS Vita");
|
||||
if (Directory.Exists(DefaultDir))
|
||||
{
|
||||
cmaDir = DefaultDir;
|
||||
}
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
//Do nothing
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
CHOVYCmaSelector ccs = new CHOVYCmaSelector(cmaDir, accountId, true);
|
||||
ccs.FormClosing += Ccs_FormClosing;
|
||||
ccs.ShowDialog();
|
||||
}
|
||||
|
||||
private void Ccs_FormClosing(object sender, FormClosingEventArgs e)
|
||||
{
|
||||
CHOVYCmaSelector ccs = (CHOVYCmaSelector)sender;
|
||||
string CmaDir = ccs.GetCmaDir();
|
||||
string CmaAid = ccs.GetCmaAid();
|
||||
string Backup = ccs.GetSelectedBackup();
|
||||
|
||||
WriteSetting("CmaDir", CmaDir);
|
||||
|
||||
if (Backup == "")
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
string BackupPath = Path.Combine(CmaDir, "PSGAME", CmaAid, Backup, "game", "game.psvimg");
|
||||
if (!File.Exists(BackupPath))
|
||||
{
|
||||
MessageBox.Show("Could not find \n" + BackupPath + "\n Perhaps backup failed?", "License Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
|
||||
ccs.Hide();
|
||||
this.Show();
|
||||
this.Focus();
|
||||
return;
|
||||
}
|
||||
|
||||
byte[] AID = BitConverter.GetBytes(Convert.ToInt64(CmaAid, 16));
|
||||
Array.Reverse(AID);
|
||||
byte[] Key = CmaKeys.GenerateKey(AID);
|
||||
|
||||
PSVIMGStream GamePsvimg = new PSVIMGStream(File.OpenRead(BackupPath), Key);
|
||||
|
||||
BackupPath = Path.Combine(CmaDir, "PSGAME", CmaAid, Backup, "license", "license.psvimg");
|
||||
if (!File.Exists(BackupPath))
|
||||
{
|
||||
MessageBox.Show("Could not find \n" + BackupPath + "\n Perhaps backup failed?", "License Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
|
||||
ccs.Hide();
|
||||
this.Show();
|
||||
this.Focus();
|
||||
return;
|
||||
}
|
||||
|
||||
PSVIMGStream LicensePsvimg = new PSVIMGStream(File.OpenRead(BackupPath), Key);
|
||||
|
||||
PSVIMGFileStream EbootPbp = new PSVIMGFileStream(GamePsvimg, "/EBOOT.PBP");
|
||||
byte[] VersionKey = Pbp.GetVersionKeyPs1(EbootPbp);
|
||||
string VerKey = BitConverter.ToString(VersionKey).Replace("-", "");
|
||||
WriteSetting("VersionKey", VerKey);
|
||||
|
||||
string ContentID = Pbp.GetContentIdPS1(EbootPbp);
|
||||
PSVIMGFileStream LicenseRif = new PSVIMGFileStream(LicensePsvimg, "/" + ContentID + ".rif");
|
||||
byte[] LicenseRifBytes = new byte[LicenseRif.Length];
|
||||
LicenseRif.Read(LicenseRifBytes, 0x00, LicenseRifBytes.Length);
|
||||
|
||||
LicenseRif.Close();
|
||||
LicensePsvimg.Close();
|
||||
EbootPbp.Close();
|
||||
GamePsvimg.Close();
|
||||
|
||||
byte[] zRifBytes = ZlibStream.CompressBuffer(LicenseRifBytes);
|
||||
string Rif = Convert.ToBase64String(zRifBytes);
|
||||
WriteSetting("RifPath", Rif);
|
||||
|
||||
Versionkey.Text = VerKey;
|
||||
RifPath.Text = Rif;
|
||||
|
||||
ccs.Hide();
|
||||
this.Show();
|
||||
this.Focus();
|
||||
|
||||
MessageBox.Show("KEYS HAVE BEEN EXTRACTED FROM CMA, YOU MAY NOW LIBERATE YOURSELF", "SUCCESS", MessageBoxButtons.OK, MessageBoxIcon.Information);
|
||||
}
|
||||
|
||||
private void browseDisc1_EnabledChanged(object sender, EventArgs e)
|
||||
{
|
||||
Color green = Color.Lime;
|
||||
Color black = Color.Black;
|
||||
bool enabled = this.browseDisc1.Enabled;
|
||||
this.browseDisc1.ForeColor = enabled ? green : black;
|
||||
this.browseDisc1.BackColor = enabled ? black : green;
|
||||
|
||||
}
|
||||
|
||||
private void browseDisc2_EnabledChanged(object sender, EventArgs e)
|
||||
{
|
||||
Color green = Color.Lime;
|
||||
Color black = Color.Black;
|
||||
bool enabled = this.browseDisc2.Enabled;
|
||||
this.browseDisc2.ForeColor = enabled ? green : black;
|
||||
this.browseDisc2.BackColor = enabled ? black : green;
|
||||
}
|
||||
|
||||
private void browseDisc3_EnabledChanged(object sender, EventArgs e)
|
||||
{
|
||||
Color green = Color.Lime;
|
||||
Color black = Color.Black;
|
||||
bool enabled = this.browseDisc3.Enabled;
|
||||
this.browseDisc3.ForeColor = enabled ? green : black;
|
||||
this.browseDisc3.BackColor = enabled ? black : green;
|
||||
}
|
||||
|
||||
private void browseDisc4_EnabledChanged(object sender, EventArgs e)
|
||||
{
|
||||
Color green = Color.Lime;
|
||||
Color black = Color.Black;
|
||||
bool enabled = this.browseDisc4.Enabled;
|
||||
this.browseDisc4.ForeColor = enabled ? green : black;
|
||||
this.browseDisc4.BackColor = enabled ? black : green;
|
||||
}
|
||||
|
||||
private void browseDisc5_EnabledChanged(object sender, EventArgs e)
|
||||
{
|
||||
Color green = Color.Lime;
|
||||
Color black = Color.Black;
|
||||
bool enabled = this.browseDisc5.Enabled;
|
||||
this.browseDisc5.ForeColor = enabled ? green : black;
|
||||
this.browseDisc5.BackColor = enabled ? black : green;
|
||||
}
|
||||
|
||||
private void FREEDOM_EnabledChanged(object sender, EventArgs e)
|
||||
{
|
||||
Color red = Color.FromArgb(192, 0, 0);
|
||||
Color black = Color.Black;
|
||||
bool enabled = this.FREEDOM.Enabled;
|
||||
this.FREEDOM.ForeColor = enabled ? red : black;
|
||||
this.FREEDOM.BackColor = enabled ? black : red;
|
||||
|
||||
}
|
||||
|
||||
private void CHOVYPopsBuilder_Load(object sender, EventArgs e)
|
||||
{
|
||||
if (ReadSetting("MuteAudio") == "1")
|
||||
{
|
||||
MutedAudio = true;
|
||||
}
|
||||
|
||||
Versionkey.Text = ReadSetting("VersionKey");
|
||||
RifPath.Text = ReadSetting("RifPath");
|
||||
|
||||
Disc1Path.Enabled = true;
|
||||
browseDisc1.Enabled = true;
|
||||
Disc2Path.Enabled = false;
|
||||
browseDisc2.Enabled = false;
|
||||
Disc3Path.Enabled = false;
|
||||
browseDisc3.Enabled = false;
|
||||
Disc4Path.Enabled = false;
|
||||
browseDisc4.Enabled = false;
|
||||
Disc5Path.Enabled = false;
|
||||
browseDisc5.Enabled = false;
|
||||
}
|
||||
|
||||
private void CoolArtwork_Click(object sender, EventArgs e)
|
||||
{
|
||||
if (!MutedAudio)
|
||||
{
|
||||
MutedAudio = true;
|
||||
WriteSetting("MuteAudio", "1");
|
||||
}
|
||||
else
|
||||
{
|
||||
MutedAudio = false;
|
||||
WriteSetting("MuteAudio", "0");
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private void browseDisc1_Click(object sender, EventArgs e)
|
||||
{
|
||||
OpenFileDialog ofd = new OpenFileDialog();
|
||||
ofd.Title = "Select PS1 Disc image *.cue";
|
||||
ofd.Filter = "Cue Sheet Files (*.cue)|*.cue";
|
||||
ofd.ShowDialog();
|
||||
|
||||
string fileName = ofd.FileName;
|
||||
Disc1Path.Text = fileName;
|
||||
|
||||
string BinFile = CueReader.Read(fileName).First().FileName;
|
||||
string BinFilePath = Path.Combine(Path.GetDirectoryName(fileName), BinFile);
|
||||
|
||||
GameEntry gmEntry = PackagePsx.FindGameInfo(BinFilePath);
|
||||
DiscId.Text = gmEntry.GameID;
|
||||
|
||||
MobyGamesDB.GetGameInformation(gmEntry.GameID);
|
||||
GameTitle.Text = MobyGamesDB.Name;
|
||||
SaveDescription.Text = MobyGamesDB.Name + " - Save Data";
|
||||
|
||||
if (MobyGamesDB.CoverImage != "(none)")
|
||||
{
|
||||
try
|
||||
{
|
||||
BubbleIconPath.Text = MobyGamesDB.CoverImage;
|
||||
|
||||
WebClient wc = new WebClient();
|
||||
byte[] ImageData = wc.DownloadData(MobyGamesDB.CoverImage);
|
||||
MemoryStream ms = new MemoryStream(ImageData);
|
||||
Bitmap bmp = new Bitmap(ms);
|
||||
Bitmap resized = new Bitmap(bmp, new Size(80, 80));
|
||||
|
||||
bmp.Dispose();
|
||||
BubbleIcon.BackgroundImage.Dispose();
|
||||
|
||||
BubbleIcon.BackgroundImage = resized;
|
||||
|
||||
}
|
||||
catch (Exception) { };
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private void browseDisc2_Click(object sender, EventArgs e)
|
||||
{
|
||||
OpenFileDialog ofd = new OpenFileDialog();
|
||||
ofd.Title = "Select PS1 Disc image *.cue";
|
||||
ofd.Filter = "Cue Sheet Files (*.cue)|*.cue";
|
||||
ofd.ShowDialog();
|
||||
Disc2Path.Text = ofd.FileName;
|
||||
}
|
||||
|
||||
private void browseDisc3_Click(object sender, EventArgs e)
|
||||
{
|
||||
OpenFileDialog ofd = new OpenFileDialog();
|
||||
ofd.Title = "Select PS1 Disc image *.cue";
|
||||
ofd.Filter = "Cue Sheet Files (*.cue)|*.cue";
|
||||
ofd.ShowDialog();
|
||||
Disc3Path.Text = ofd.FileName;
|
||||
}
|
||||
|
||||
private void browseDisc4_Click(object sender, EventArgs e)
|
||||
{
|
||||
OpenFileDialog ofd = new OpenFileDialog();
|
||||
ofd.Title = "Select PS1 Disc image *.cue";
|
||||
ofd.Filter = "Cue Sheet Files (*.cue)|*.cue";
|
||||
ofd.ShowDialog();
|
||||
Disc4Path.Text = ofd.FileName;
|
||||
}
|
||||
|
||||
private void browseDisc5_Click(object sender, EventArgs e)
|
||||
{
|
||||
OpenFileDialog ofd = new OpenFileDialog();
|
||||
ofd.Title = "Select PS1 Disc image *.cue";
|
||||
ofd.Filter = "Cue Sheet Files (*.cue)|*.cue";
|
||||
ofd.ShowDialog();
|
||||
Disc5Path.Text = ofd.FileName;
|
||||
}
|
||||
|
||||
private void browseIcon_Click(object sender, EventArgs e)
|
||||
{
|
||||
OpenFileDialog ofd = new OpenFileDialog();
|
||||
ofd.Title = "Select Portable Network Graphics *.png";
|
||||
ofd.Filter = "Portable Network Graphics Files (*.png)|*.png";
|
||||
ofd.ShowDialog();
|
||||
|
||||
try
|
||||
{
|
||||
Bitmap bmp = new Bitmap(BubbleIconPath.Text);
|
||||
if (bmp.Width == 80 && bmp.Height == 80)
|
||||
{
|
||||
BubbleIcon.Dispose();
|
||||
BubbleIcon.Image = bmp;
|
||||
BubbleIconPath.Text = ofd.FileName;
|
||||
}
|
||||
else
|
||||
{
|
||||
MessageBox.Show("Invalid Icon file (not 80x80)", "Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
|
||||
}
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
MessageBox.Show("Invalid PNG File.", "Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private void BubbleIconPath_TextChanged(object sender, EventArgs e)
|
||||
{
|
||||
try
|
||||
{
|
||||
Bitmap bmp = new Bitmap(BubbleIconPath.Text);
|
||||
if (bmp.Width == 80 && bmp.Height == 80)
|
||||
{
|
||||
BubbleIcon.Dispose();
|
||||
BubbleIcon.Image = bmp;
|
||||
}
|
||||
}
|
||||
catch (Exception) { };
|
||||
}
|
||||
private void FREEDOM_Click(object sender, EventArgs e)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
}
|
File diff suppressed because it is too large
Load Diff
|
@ -1,356 +0,0 @@
|
|||
namespace CHOVY_SIGN
|
||||
{
|
||||
partial class CHOVYPspBuilder
|
||||
{
|
||||
/// <summary>
|
||||
/// Required designer variable.
|
||||
/// </summary>
|
||||
private System.ComponentModel.IContainer components = null;
|
||||
|
||||
/// <summary>
|
||||
/// Clean up any resources being used.
|
||||
/// </summary>
|
||||
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
|
||||
protected override void Dispose(bool disposing)
|
||||
{
|
||||
if (disposing && (components != null))
|
||||
{
|
||||
components.Dispose();
|
||||
}
|
||||
base.Dispose(disposing);
|
||||
}
|
||||
|
||||
#region Windows Form Designer generated code
|
||||
|
||||
/// <summary>
|
||||
/// Required method for Designer support - do not modify
|
||||
/// the contents of this method with the code editor.
|
||||
/// </summary>
|
||||
private void InitializeComponent()
|
||||
{
|
||||
System.ComponentModel.ComponentResourceManager resources = new System.ComponentModel.ComponentResourceManager(typeof(CHOVYPspBuilder));
|
||||
this.label1 = new System.Windows.Forms.Label();
|
||||
this.RifPath = new System.Windows.Forms.TextBox();
|
||||
this.Versionkey = new System.Windows.Forms.TextBox();
|
||||
this.label2 = new System.Windows.Forms.Label();
|
||||
this.FindFromCMA = new System.Windows.Forms.Button();
|
||||
this.ISOPath = new System.Windows.Forms.TextBox();
|
||||
this.label3 = new System.Windows.Forms.Label();
|
||||
this.label4 = new System.Windows.Forms.Label();
|
||||
this.label5 = new System.Windows.Forms.Label();
|
||||
this.BrowseButton = new System.Windows.Forms.Button();
|
||||
this.TotalProgress = new System.Windows.Forms.ProgressBar();
|
||||
this.Status = new System.Windows.Forms.Label();
|
||||
this.FREEDOM = new System.Windows.Forms.Button();
|
||||
this.groupBox1 = new System.Windows.Forms.GroupBox();
|
||||
this.groupBox2 = new System.Windows.Forms.GroupBox();
|
||||
this.CompressPBP = new System.Windows.Forms.CheckBox();
|
||||
this.pictureBox2 = new System.Windows.Forms.PictureBox();
|
||||
this.label6 = new System.Windows.Forms.Label();
|
||||
this.Ps1Menu = new System.Windows.Forms.Button();
|
||||
this.DexAidEnabler = new System.Windows.Forms.PictureBox();
|
||||
this.PsmChan = new System.Windows.Forms.PictureBox();
|
||||
this.groupBox1.SuspendLayout();
|
||||
this.groupBox2.SuspendLayout();
|
||||
((System.ComponentModel.ISupportInitialize)(this.pictureBox2)).BeginInit();
|
||||
((System.ComponentModel.ISupportInitialize)(this.DexAidEnabler)).BeginInit();
|
||||
((System.ComponentModel.ISupportInitialize)(this.PsmChan)).BeginInit();
|
||||
this.SuspendLayout();
|
||||
//
|
||||
// label1
|
||||
//
|
||||
this.label1.AutoSize = true;
|
||||
this.label1.ForeColor = System.Drawing.Color.Lime;
|
||||
this.label1.Location = new System.Drawing.Point(6, 19);
|
||||
this.label1.Name = "label1";
|
||||
this.label1.Size = new System.Drawing.Size(27, 13);
|
||||
this.label1.TabIndex = 0;
|
||||
this.label1.Text = "RIF:";
|
||||
//
|
||||
// RifPath
|
||||
//
|
||||
this.RifPath.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(64)))), ((int)(((byte)(64)))), ((int)(((byte)(64)))));
|
||||
this.RifPath.BorderStyle = System.Windows.Forms.BorderStyle.FixedSingle;
|
||||
this.RifPath.ForeColor = System.Drawing.Color.Lime;
|
||||
this.RifPath.Location = new System.Drawing.Point(37, 16);
|
||||
this.RifPath.Name = "RifPath";
|
||||
this.RifPath.Size = new System.Drawing.Size(225, 20);
|
||||
this.RifPath.TabIndex = 1;
|
||||
//
|
||||
// Versionkey
|
||||
//
|
||||
this.Versionkey.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(64)))), ((int)(((byte)(64)))), ((int)(((byte)(64)))));
|
||||
this.Versionkey.BorderStyle = System.Windows.Forms.BorderStyle.FixedSingle;
|
||||
this.Versionkey.ForeColor = System.Drawing.Color.Lime;
|
||||
this.Versionkey.Location = new System.Drawing.Point(337, 16);
|
||||
this.Versionkey.MaxLength = 32;
|
||||
this.Versionkey.Name = "Versionkey";
|
||||
this.Versionkey.Size = new System.Drawing.Size(225, 20);
|
||||
this.Versionkey.TabIndex = 2;
|
||||
//
|
||||
// label2
|
||||
//
|
||||
this.label2.AutoSize = true;
|
||||
this.label2.ForeColor = System.Drawing.Color.Lime;
|
||||
this.label2.Location = new System.Drawing.Point(268, 19);
|
||||
this.label2.Name = "label2";
|
||||
this.label2.Size = new System.Drawing.Size(63, 13);
|
||||
this.label2.TabIndex = 3;
|
||||
this.label2.Text = "VersionKey:";
|
||||
//
|
||||
// FindFromCMA
|
||||
//
|
||||
this.FindFromCMA.FlatStyle = System.Windows.Forms.FlatStyle.Flat;
|
||||
this.FindFromCMA.ForeColor = System.Drawing.Color.Lime;
|
||||
this.FindFromCMA.Location = new System.Drawing.Point(568, 16);
|
||||
this.FindFromCMA.Name = "FindFromCMA";
|
||||
this.FindFromCMA.Size = new System.Drawing.Size(109, 23);
|
||||
this.FindFromCMA.TabIndex = 4;
|
||||
this.FindFromCMA.Text = "Find from CMA";
|
||||
this.FindFromCMA.UseVisualStyleBackColor = true;
|
||||
this.FindFromCMA.Click += new System.EventHandler(this.FindFromCMA_Click);
|
||||
//
|
||||
// ISOPath
|
||||
//
|
||||
this.ISOPath.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(64)))), ((int)(((byte)(64)))), ((int)(((byte)(64)))));
|
||||
this.ISOPath.BorderStyle = System.Windows.Forms.BorderStyle.FixedSingle;
|
||||
this.ISOPath.ForeColor = System.Drawing.Color.Lime;
|
||||
this.ISOPath.Location = new System.Drawing.Point(77, 54);
|
||||
this.ISOPath.Name = "ISOPath";
|
||||
this.ISOPath.Size = new System.Drawing.Size(345, 20);
|
||||
this.ISOPath.TabIndex = 6;
|
||||
//
|
||||
// label3
|
||||
//
|
||||
this.label3.AutoSize = true;
|
||||
this.label3.ForeColor = System.Drawing.Color.Lime;
|
||||
this.label3.Location = new System.Drawing.Point(74, 38);
|
||||
this.label3.Name = "label3";
|
||||
this.label3.Size = new System.Drawing.Size(60, 13);
|
||||
this.label3.TabIndex = 8;
|
||||
this.label3.Text = "ISO Image:";
|
||||
//
|
||||
// label4
|
||||
//
|
||||
this.label4.AutoSize = true;
|
||||
this.label4.ForeColor = System.Drawing.Color.Chartreuse;
|
||||
this.label4.Location = new System.Drawing.Point(132, 280);
|
||||
this.label4.Name = "label4";
|
||||
this.label4.Size = new System.Drawing.Size(145, 13);
|
||||
this.label4.TabIndex = 10;
|
||||
this.label4.Text = "Made Possible by the CBPS! ";
|
||||
//
|
||||
// label5
|
||||
//
|
||||
this.label5.AutoSize = true;
|
||||
this.label5.ForeColor = System.Drawing.Color.Chartreuse;
|
||||
this.label5.Location = new System.Drawing.Point(664, 280);
|
||||
this.label5.Name = "label5";
|
||||
this.label5.Size = new System.Drawing.Size(167, 13);
|
||||
this.label5.TabIndex = 11;
|
||||
this.label5.Text = "SilicaAndPina, dots_tb, Motoharu.";
|
||||
//
|
||||
// BrowseButton
|
||||
//
|
||||
this.BrowseButton.FlatStyle = System.Windows.Forms.FlatStyle.Flat;
|
||||
this.BrowseButton.ForeColor = System.Drawing.Color.Lime;
|
||||
this.BrowseButton.Location = new System.Drawing.Point(428, 52);
|
||||
this.BrowseButton.Name = "BrowseButton";
|
||||
this.BrowseButton.Size = new System.Drawing.Size(60, 22);
|
||||
this.BrowseButton.TabIndex = 12;
|
||||
this.BrowseButton.Text = "Browse";
|
||||
this.BrowseButton.UseVisualStyleBackColor = true;
|
||||
this.BrowseButton.Click += new System.EventHandler(this.BrowseButton_Click);
|
||||
//
|
||||
// TotalProgress
|
||||
//
|
||||
this.TotalProgress.BackColor = System.Drawing.Color.Black;
|
||||
this.TotalProgress.ForeColor = System.Drawing.Color.FromArgb(((int)(((byte)(0)))), ((int)(((byte)(192)))), ((int)(((byte)(0)))));
|
||||
this.TotalProgress.Location = new System.Drawing.Point(209, 227);
|
||||
this.TotalProgress.Name = "TotalProgress";
|
||||
this.TotalProgress.Size = new System.Drawing.Size(443, 23);
|
||||
this.TotalProgress.TabIndex = 13;
|
||||
//
|
||||
// Status
|
||||
//
|
||||
this.Status.AutoSize = true;
|
||||
this.Status.ForeColor = System.Drawing.Color.LawnGreen;
|
||||
this.Status.Location = new System.Drawing.Point(206, 211);
|
||||
this.Status.Name = "Status";
|
||||
this.Status.Size = new System.Drawing.Size(62, 13);
|
||||
this.Status.TabIndex = 14;
|
||||
this.Status.Text = "Progress % ";
|
||||
//
|
||||
// FREEDOM
|
||||
//
|
||||
this.FREEDOM.FlatStyle = System.Windows.Forms.FlatStyle.Flat;
|
||||
this.FREEDOM.ForeColor = System.Drawing.Color.FromArgb(((int)(((byte)(192)))), ((int)(((byte)(0)))), ((int)(((byte)(0)))));
|
||||
this.FREEDOM.Location = new System.Drawing.Point(658, 227);
|
||||
this.FREEDOM.Name = "FREEDOM";
|
||||
this.FREEDOM.Size = new System.Drawing.Size(75, 23);
|
||||
this.FREEDOM.TabIndex = 15;
|
||||
this.FREEDOM.Text = "FREEDOM";
|
||||
this.FREEDOM.UseVisualStyleBackColor = true;
|
||||
this.FREEDOM.EnabledChanged += new System.EventHandler(this.FREEDOM_EnabledChanged);
|
||||
this.FREEDOM.Click += new System.EventHandler(this.FREEDOM_Click);
|
||||
//
|
||||
// groupBox1
|
||||
//
|
||||
this.groupBox1.BackColor = System.Drawing.Color.Black;
|
||||
this.groupBox1.Controls.Add(this.RifPath);
|
||||
this.groupBox1.Controls.Add(this.label1);
|
||||
this.groupBox1.Controls.Add(this.label2);
|
||||
this.groupBox1.Controls.Add(this.Versionkey);
|
||||
this.groupBox1.Controls.Add(this.FindFromCMA);
|
||||
this.groupBox1.FlatStyle = System.Windows.Forms.FlatStyle.Flat;
|
||||
this.groupBox1.ForeColor = System.Drawing.Color.Lime;
|
||||
this.groupBox1.Location = new System.Drawing.Point(135, 12);
|
||||
this.groupBox1.Name = "groupBox1";
|
||||
this.groupBox1.Size = new System.Drawing.Size(696, 47);
|
||||
this.groupBox1.TabIndex = 16;
|
||||
this.groupBox1.TabStop = false;
|
||||
this.groupBox1.Text = "Keys To The Kingdom";
|
||||
//
|
||||
// groupBox2
|
||||
//
|
||||
this.groupBox2.Controls.Add(this.CompressPBP);
|
||||
this.groupBox2.Controls.Add(this.pictureBox2);
|
||||
this.groupBox2.Controls.Add(this.label3);
|
||||
this.groupBox2.Controls.Add(this.ISOPath);
|
||||
this.groupBox2.Controls.Add(this.BrowseButton);
|
||||
this.groupBox2.ForeColor = System.Drawing.Color.Lime;
|
||||
this.groupBox2.Location = new System.Drawing.Point(209, 74);
|
||||
this.groupBox2.Name = "groupBox2";
|
||||
this.groupBox2.Size = new System.Drawing.Size(524, 105);
|
||||
this.groupBox2.TabIndex = 17;
|
||||
this.groupBox2.TabStop = false;
|
||||
this.groupBox2.Text = "The PSP Game";
|
||||
//
|
||||
// CompressPBP
|
||||
//
|
||||
this.CompressPBP.AutoSize = true;
|
||||
this.CompressPBP.FlatStyle = System.Windows.Forms.FlatStyle.Flat;
|
||||
this.CompressPBP.Location = new System.Drawing.Point(15, 80);
|
||||
this.CompressPBP.Name = "CompressPBP";
|
||||
this.CompressPBP.Size = new System.Drawing.Size(93, 17);
|
||||
this.CompressPBP.TabIndex = 18;
|
||||
this.CompressPBP.Text = "Compress PBP";
|
||||
this.CompressPBP.UseVisualStyleBackColor = true;
|
||||
//
|
||||
// pictureBox2
|
||||
//
|
||||
this.pictureBox2.BackgroundImage = global::CHOVY_SIGN.Properties.Resources.UMD;
|
||||
this.pictureBox2.BackgroundImageLayout = System.Windows.Forms.ImageLayout.Zoom;
|
||||
this.pictureBox2.Location = new System.Drawing.Point(15, 31);
|
||||
this.pictureBox2.Name = "pictureBox2";
|
||||
this.pictureBox2.Size = new System.Drawing.Size(53, 43);
|
||||
this.pictureBox2.TabIndex = 9;
|
||||
this.pictureBox2.TabStop = false;
|
||||
//
|
||||
// label6
|
||||
//
|
||||
this.label6.AutoSize = true;
|
||||
this.label6.ForeColor = System.Drawing.Color.Lime;
|
||||
this.label6.Location = new System.Drawing.Point(735, 62);
|
||||
this.label6.Name = "label6";
|
||||
this.label6.Size = new System.Drawing.Size(96, 13);
|
||||
this.label6.TabIndex = 18;
|
||||
this.label6.Text = "100% percent free!\r\n";
|
||||
//
|
||||
// Ps1Menu
|
||||
//
|
||||
this.Ps1Menu.BackgroundImage = global::CHOVY_SIGN.Properties.Resources.ps1;
|
||||
this.Ps1Menu.BackgroundImageLayout = System.Windows.Forms.ImageLayout.Stretch;
|
||||
this.Ps1Menu.FlatStyle = System.Windows.Forms.FlatStyle.Flat;
|
||||
this.Ps1Menu.ForeColor = System.Drawing.Color.Lime;
|
||||
this.Ps1Menu.Location = new System.Drawing.Point(748, 95);
|
||||
this.Ps1Menu.Name = "Ps1Menu";
|
||||
this.Ps1Menu.Size = new System.Drawing.Size(75, 71);
|
||||
this.Ps1Menu.TabIndex = 20;
|
||||
this.Ps1Menu.Text = " ";
|
||||
this.Ps1Menu.UseVisualStyleBackColor = true;
|
||||
this.Ps1Menu.Click += new System.EventHandler(this.Ps1Menu_Click);
|
||||
//
|
||||
// DexAidEnabler
|
||||
//
|
||||
this.DexAidEnabler.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Right)));
|
||||
this.DexAidEnabler.Location = new System.Drawing.Point(829, 1);
|
||||
this.DexAidEnabler.Name = "DexAidEnabler";
|
||||
this.DexAidEnabler.Size = new System.Drawing.Size(15, 15);
|
||||
this.DexAidEnabler.TabIndex = 19;
|
||||
this.DexAidEnabler.TabStop = false;
|
||||
this.DexAidEnabler.Click += new System.EventHandler(this.DexAidEnabler_Click);
|
||||
//
|
||||
// PsmChan
|
||||
//
|
||||
this.PsmChan.BackgroundImage = global::CHOVY_SIGN.Properties.Resources.idkbackground;
|
||||
this.PsmChan.BackgroundImageLayout = System.Windows.Forms.ImageLayout.Stretch;
|
||||
this.PsmChan.Location = new System.Drawing.Point(3, 3);
|
||||
this.PsmChan.Name = "PsmChan";
|
||||
this.PsmChan.Size = new System.Drawing.Size(123, 297);
|
||||
this.PsmChan.TabIndex = 5;
|
||||
this.PsmChan.TabStop = false;
|
||||
this.PsmChan.Click += new System.EventHandler(this.PsmChan_Click);
|
||||
//
|
||||
// CHOVY
|
||||
//
|
||||
this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
|
||||
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
|
||||
this.BackColor = System.Drawing.Color.Black;
|
||||
this.ClientSize = new System.Drawing.Size(843, 302);
|
||||
this.Controls.Add(this.Ps1Menu);
|
||||
this.Controls.Add(this.DexAidEnabler);
|
||||
this.Controls.Add(this.label6);
|
||||
this.Controls.Add(this.groupBox2);
|
||||
this.Controls.Add(this.groupBox1);
|
||||
this.Controls.Add(this.FREEDOM);
|
||||
this.Controls.Add(this.Status);
|
||||
this.Controls.Add(this.TotalProgress);
|
||||
this.Controls.Add(this.label5);
|
||||
this.Controls.Add(this.label4);
|
||||
this.Controls.Add(this.PsmChan);
|
||||
this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.FixedSingle;
|
||||
this.Icon = ((System.Drawing.Icon)(resources.GetObject("$this.Icon")));
|
||||
this.MaximizeBox = false;
|
||||
this.Name = "CHOVY";
|
||||
this.Text = "CHOVY-SIGN";
|
||||
this.FormClosing += new System.Windows.Forms.FormClosingEventHandler(this.CHOVY_FormClosing);
|
||||
this.Load += new System.EventHandler(this.CHOVY_Load);
|
||||
this.groupBox1.ResumeLayout(false);
|
||||
this.groupBox1.PerformLayout();
|
||||
this.groupBox2.ResumeLayout(false);
|
||||
this.groupBox2.PerformLayout();
|
||||
((System.ComponentModel.ISupportInitialize)(this.pictureBox2)).EndInit();
|
||||
((System.ComponentModel.ISupportInitialize)(this.DexAidEnabler)).EndInit();
|
||||
((System.ComponentModel.ISupportInitialize)(this.PsmChan)).EndInit();
|
||||
this.ResumeLayout(false);
|
||||
this.PerformLayout();
|
||||
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
private System.Windows.Forms.Label label1;
|
||||
private System.Windows.Forms.TextBox RifPath;
|
||||
private System.Windows.Forms.TextBox Versionkey;
|
||||
private System.Windows.Forms.Label label2;
|
||||
private System.Windows.Forms.Button FindFromCMA;
|
||||
private System.Windows.Forms.PictureBox PsmChan;
|
||||
private System.Windows.Forms.TextBox ISOPath;
|
||||
private System.Windows.Forms.Label label3;
|
||||
private System.Windows.Forms.PictureBox pictureBox2;
|
||||
private System.Windows.Forms.Label label4;
|
||||
private System.Windows.Forms.Label label5;
|
||||
private System.Windows.Forms.Button BrowseButton;
|
||||
private System.Windows.Forms.ProgressBar TotalProgress;
|
||||
private System.Windows.Forms.Label Status;
|
||||
private System.Windows.Forms.Button FREEDOM;
|
||||
private System.Windows.Forms.GroupBox groupBox1;
|
||||
private System.Windows.Forms.GroupBox groupBox2;
|
||||
private System.Windows.Forms.CheckBox CompressPBP;
|
||||
private System.Windows.Forms.Label label6;
|
||||
private System.Windows.Forms.PictureBox DexAidEnabler;
|
||||
private System.Windows.Forms.Button Ps1Menu;
|
||||
}
|
||||
}
|
||||
|
|
@ -1,634 +0,0 @@
|
|||
using CHOVY_SIGN.Properties;
|
||||
using Ionic.Zlib;
|
||||
using Microsoft.Win32;
|
||||
using ParamSfo;
|
||||
using PSVIMGTOOLS;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Drawing;
|
||||
using System.IO;
|
||||
using System.Media;
|
||||
using System.Text;
|
||||
using System.Threading;
|
||||
using System.Windows.Forms;
|
||||
|
||||
namespace CHOVY_SIGN
|
||||
{
|
||||
public partial class CHOVYPspBuilder : Form
|
||||
{
|
||||
bool MutedAudio = false;
|
||||
|
||||
public static byte[] FromHex(string hex)
|
||||
{
|
||||
hex = hex.Replace("-", "");
|
||||
byte[] raw = new byte[hex.Length / 2];
|
||||
for (int i = 0; i < raw.Length; i++)
|
||||
{
|
||||
raw[i] = Convert.ToByte(hex.Substring(i * 2, 2), 16);
|
||||
}
|
||||
return raw;
|
||||
}
|
||||
|
||||
public byte[] ReadFileFromISO(string ISOFile, string FilePath)
|
||||
{
|
||||
try
|
||||
{
|
||||
FileStream ISO = File.OpenRead(ISOFile);
|
||||
|
||||
DiscUtils.Iso9660.CDReader cdr = new DiscUtils.Iso9660.CDReader(ISO, false);
|
||||
Stream FileStr = cdr.OpenFile(FilePath, FileMode.Open, FileAccess.Read);
|
||||
|
||||
byte[] FileBytes = new byte[FileStr.Length];
|
||||
FileStr.Read(FileBytes, 0x00, (int)FileStr.Length);
|
||||
ISO.Close();
|
||||
|
||||
return FileBytes;
|
||||
}
|
||||
catch(Exception)
|
||||
{
|
||||
return new byte[0x00];
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public static string GetTitleID(string ISOFile)
|
||||
{
|
||||
FileStream ISO = File.OpenRead(ISOFile);
|
||||
DiscUtils.Iso9660.CDReader cdr = new DiscUtils.Iso9660.CDReader(ISO, false);
|
||||
Stream ParamSfo = cdr.OpenFile(@"PSP_GAME\PARAM.SFO", FileMode.Open, FileAccess.Read);
|
||||
|
||||
Dictionary<string,object> SfoKeys = Sfo.ReadSfo(ParamSfo);
|
||||
|
||||
string TitleID = (string)SfoKeys["DISC_ID"];
|
||||
ISO.Close();
|
||||
return TitleID;
|
||||
}
|
||||
|
||||
public static bool isMini(string ISOFile)
|
||||
{
|
||||
FileStream ISO = File.OpenRead(ISOFile);
|
||||
DiscUtils.Iso9660.CDReader cdr = new DiscUtils.Iso9660.CDReader(ISO, false);
|
||||
Stream Icon0 = cdr.OpenFile(@"PSP_GAME\ICON0.PNG", FileMode.Open, FileAccess.Read);
|
||||
|
||||
Bitmap bmp = new Bitmap(Icon0);
|
||||
bool isMini = (bmp.Width == 80 && bmp.Height == 80);
|
||||
bmp.Dispose();
|
||||
ISO.Close();
|
||||
|
||||
return isMini;
|
||||
}
|
||||
|
||||
public string ReadSetting(string Setting)
|
||||
{
|
||||
string Value = "";
|
||||
try
|
||||
{
|
||||
|
||||
RegistryKey key;
|
||||
key = Registry.CurrentUser.CreateSubKey(@"Software\CHOVYProject\Chovy-Sign");
|
||||
Value = key.GetValue(Setting).ToString();
|
||||
key.Close();
|
||||
}
|
||||
catch (Exception) { return ""; }
|
||||
return Value;
|
||||
}
|
||||
|
||||
public void WriteSetting(string Setting,string Value)
|
||||
{
|
||||
try
|
||||
{
|
||||
RegistryKey key;
|
||||
key = Registry.CurrentUser.CreateSubKey(@"Software\CHOVYProject\Chovy-Sign");
|
||||
key.SetValue(Setting, Value);
|
||||
key.Close();
|
||||
}
|
||||
catch (Exception) { }
|
||||
}
|
||||
|
||||
public bool IsDexAidSet()
|
||||
{
|
||||
string isDex = ReadSetting("DexAid");
|
||||
if (isDex == "0")
|
||||
{
|
||||
return false;
|
||||
}
|
||||
else if(isDex == "1")
|
||||
{
|
||||
return true;
|
||||
}
|
||||
else
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
public CHOVYPspBuilder()
|
||||
{
|
||||
InitializeComponent();
|
||||
}
|
||||
private void CHOVY_Load(object sender, EventArgs e)
|
||||
{
|
||||
if (ReadSetting("MuteAudio") == "1")
|
||||
{
|
||||
MutedAudio = true;
|
||||
}
|
||||
|
||||
Versionkey.Text = ReadSetting("VersionKey");
|
||||
RifPath.Text = ReadSetting("RifPath");
|
||||
}
|
||||
|
||||
private void FREEDOM_EnabledChanged(object sender, EventArgs e)
|
||||
{
|
||||
Color red = Color.FromArgb(192, 0, 0);
|
||||
Color black = Color.Black;
|
||||
bool enabled = this.FREEDOM.Enabled;
|
||||
this.FREEDOM.ForeColor = enabled ? red : black;
|
||||
this.FREEDOM.BackColor = enabled ? black : red;
|
||||
}
|
||||
private void FREEDOM_Click(object sender, EventArgs e)
|
||||
{
|
||||
Action enable = () => {
|
||||
this.FREEDOM.Enabled = true;
|
||||
this.Ps1Menu.Enabled = true;
|
||||
this.FindFromCMA.Enabled = true;
|
||||
this.RifPath.ReadOnly = false;
|
||||
this.Versionkey.ReadOnly = false;
|
||||
this.ISOPath.ReadOnly = false;
|
||||
this.CompressPBP.Enabled = true;
|
||||
this.BrowseButton.Enabled = true;
|
||||
};
|
||||
|
||||
Action disable = () => {
|
||||
this.FREEDOM.Enabled = false;
|
||||
this.Ps1Menu.Enabled = false;
|
||||
this.FindFromCMA.Enabled = false;
|
||||
this.RifPath.ReadOnly = true;
|
||||
this.Versionkey.ReadOnly = true;
|
||||
this.ISOPath.ReadOnly = true;
|
||||
this.CompressPBP.Enabled = false;
|
||||
this.BrowseButton.Enabled = false;
|
||||
};
|
||||
|
||||
disable();
|
||||
|
||||
bool isZrif = false;
|
||||
if(RifPath.Text == "" || !File.Exists(RifPath.Text))
|
||||
{
|
||||
// Check if valid 'zRIF'
|
||||
try
|
||||
{
|
||||
ZlibStream.UncompressBuffer(Convert.FromBase64String(RifPath.Text));
|
||||
isZrif = true;
|
||||
}
|
||||
catch(Exception)
|
||||
{
|
||||
MessageBox.Show("INVALID RIF!\nPlease try \"Find from CMA\"", "RIF ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error);
|
||||
enable();
|
||||
return;
|
||||
}
|
||||
|
||||
}
|
||||
if(Versionkey.Text.Length != 32)
|
||||
{
|
||||
MessageBox.Show("INVALID VERSION KEY!\nPlease try \"Find from CMA\"", "VERKEY ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error);
|
||||
enable();
|
||||
return;
|
||||
}
|
||||
if(ISOPath.Text == "" || !File.Exists(ISOPath.Text))
|
||||
{
|
||||
MessageBox.Show("INVALID ISO PATH!", "ISO ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error);
|
||||
enable();
|
||||
return;
|
||||
}
|
||||
|
||||
this.FREEDOM.Enabled = false;
|
||||
string CmaDir = ReadSetting("CmaDir");
|
||||
if(CmaDir == "")
|
||||
{
|
||||
FolderBrowserDialog fbd = new FolderBrowserDialog();
|
||||
fbd.Description = "Select CMA Backups Directory";
|
||||
fbd.ShowDialog();
|
||||
CmaDir = fbd.SelectedPath;
|
||||
}
|
||||
string TitleID = GetTitleID(ISOPath.Text);
|
||||
|
||||
string TmpDir = Path.Combine(Application.StartupPath, "_tmp");
|
||||
string GameWorkDir = Path.Combine(TmpDir, TitleID);
|
||||
string EbootFile = Path.Combine(GameWorkDir, "EBOOT.PBP");
|
||||
string EbootSignature = Path.Combine(GameWorkDir, "__sce_ebootpbp");
|
||||
|
||||
Directory.CreateDirectory(TmpDir);
|
||||
Directory.CreateDirectory(GameWorkDir);
|
||||
|
||||
|
||||
//Read RIF data
|
||||
byte[] ContentId = new byte[0x24];
|
||||
byte[] RifAid = new byte[0x08];
|
||||
Stream rif = null;
|
||||
if (!isZrif)
|
||||
rif = File.OpenRead(RifPath.Text);
|
||||
else
|
||||
rif = new MemoryStream(ZlibStream.UncompressBuffer(Convert.FromBase64String(RifPath.Text)));
|
||||
|
||||
rif.Seek(0x10, SeekOrigin.Begin);
|
||||
rif.Read(ContentId, 0x00, 0x24);
|
||||
rif.Seek(0x08, SeekOrigin.Begin);
|
||||
rif.Read(RifAid, 0x00, 0x08);
|
||||
|
||||
|
||||
string ContentID = Encoding.UTF8.GetString(ContentId);
|
||||
string AidStr = BitConverter.ToString(RifAid).Replace("-", "").ToLower();
|
||||
if(IsDexAidSet())
|
||||
{
|
||||
AidStr = "0000000000000000";
|
||||
}
|
||||
string BackupWorkDir = Path.Combine(CmaDir, "PGAME", AidStr, TitleID);
|
||||
|
||||
TotalProgress.Maximum = 100;
|
||||
Status.Text = "Overthrowing The PSPEMU Monarchy 0%";
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
Thread BuildPbpThread = new Thread(() =>
|
||||
{
|
||||
// Try New System
|
||||
try
|
||||
{
|
||||
FileStream EbootStream = File.OpenWrite(EbootFile);
|
||||
FileStream IsoStream = File.OpenRead(ISOPath.Text);
|
||||
Bitmap BootupImage;
|
||||
if (isMini(ISOPath.Text))
|
||||
BootupImage = Resources.MINIS;
|
||||
else
|
||||
BootupImage = Resources.ChovyLogo;
|
||||
|
||||
byte[] Sfo = ReadFileFromISO(ISOPath.Text, @"PSP_GAME\PARAM.SFO");
|
||||
byte[] Icon0Png = ReadFileFromISO(ISOPath.Text, @"PSP_GAME\ICON0.PNG");
|
||||
byte[] Icon1 = ReadFileFromISO(ISOPath.Text, @"PSP_GAME\ICON1.PMF");
|
||||
byte[] Pic0 = ReadFileFromISO(ISOPath.Text, @"PSP_GAME\PIC0.PNG");
|
||||
byte[] Pic1 = ReadFileFromISO(ISOPath.Text, @"PSP_GAME\PIC1.PNG");
|
||||
byte[] Snd0 = ReadFileFromISO(ISOPath.Text, @"PSP_GAME\SND0.AT3");
|
||||
|
||||
Pbp.BuildPbp(EbootStream, IsoStream, CompressPBP.Checked, FromHex(Versionkey.Text), BootupImage, ContentID, Sfo, Icon0Png, Icon1, Pic0, Pic1, Snd0);
|
||||
IsoStream.Close();
|
||||
EbootStream.Close();
|
||||
}
|
||||
catch (Exception exp)
|
||||
{
|
||||
MessageBox.Show(exp.Message, "Error.", MessageBoxButtons.OK, MessageBoxIcon.Error);
|
||||
}
|
||||
|
||||
});
|
||||
BuildPbpThread.Start();
|
||||
while(BuildPbpThread.IsAlive)
|
||||
{
|
||||
if (Pbp.DoEvents)
|
||||
{
|
||||
TotalProgress.Maximum = Pbp.NumberOfSectors;
|
||||
TotalProgress.Value = Pbp.SectorsDone;
|
||||
if (Pbp.SectorsDone != 0 && Pbp.NumberOfSectors != 0)
|
||||
{
|
||||
decimal progress = Math.Floor(((decimal)Pbp.SectorsDone / (decimal)Pbp.NumberOfSectors) * 100);
|
||||
Status.Text = "Overthrowing The PSPEMU Monarchy " + progress.ToString() + "%";
|
||||
}
|
||||
else
|
||||
Status.Text = "Overthrowing The PSPEMU Monarchy 0%";
|
||||
Application.DoEvents();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
TotalProgress.Value = 0;
|
||||
|
||||
Status.Text = "Signing the Declaration of Independance 0%";
|
||||
UInt64 IntAid = BitConverter.ToUInt64(RifAid,0x00);
|
||||
Thread ChovyGenThread = new Thread(() =>
|
||||
{
|
||||
|
||||
int ChovyGenRes = Pbp.gen__sce_ebootpbp(EbootFile, IntAid, EbootSignature);
|
||||
});
|
||||
ChovyGenThread.Start();
|
||||
while(ChovyGenThread.IsAlive)
|
||||
{
|
||||
Application.DoEvents();
|
||||
}
|
||||
|
||||
/*
|
||||
* BUILD PSVIMG FILE
|
||||
*/
|
||||
|
||||
// Pacakge GAME
|
||||
byte[] CmaKey;
|
||||
if (IsDexAidSet())
|
||||
{
|
||||
CmaKey = CmaKeys.GenerateKey(new byte[0x8] { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 });
|
||||
}
|
||||
else
|
||||
{
|
||||
CmaKey = CmaKeys.GenerateKey(RifAid);
|
||||
}
|
||||
|
||||
|
||||
|
||||
string[] entrys = Directory.GetFileSystemEntries(GameWorkDir, "*", SearchOption.AllDirectories);
|
||||
long noEntrys = entrys.LongLength;
|
||||
string parentPath = "ux0:pspemu/temp/game/PSP/GAME/" + TitleID;
|
||||
int noBlocks = 0;
|
||||
foreach (string fileName in Directory.GetFiles(GameWorkDir,"*",SearchOption.AllDirectories))
|
||||
{
|
||||
noBlocks += Convert.ToInt32(new FileInfo(fileName).Length / PSVIMGConstants.PSVIMG_BLOCK_SIZE);
|
||||
}
|
||||
TotalProgress.Maximum = noBlocks;
|
||||
|
||||
|
||||
string BackupDir = Path.Combine(BackupWorkDir, "game");
|
||||
Directory.CreateDirectory(BackupDir);
|
||||
string psvimgFilepath = Path.Combine(BackupDir, "game.psvimg");
|
||||
FileStream gamePsvimg = File.OpenWrite(psvimgFilepath);
|
||||
gamePsvimg.SetLength(0);
|
||||
PSVIMGBuilder builder = new PSVIMGBuilder(gamePsvimg, CmaKey);
|
||||
|
||||
foreach (string entry in entrys)
|
||||
{
|
||||
string relativePath = entry.Remove(0, GameWorkDir.Length);
|
||||
relativePath = relativePath.Replace('\\', '/');
|
||||
|
||||
bool isDir = File.GetAttributes(entry).HasFlag(FileAttributes.Directory);
|
||||
|
||||
if (isDir)
|
||||
{
|
||||
builder.AddDir(entry, parentPath, relativePath);
|
||||
}
|
||||
else
|
||||
{
|
||||
builder.AddFileAsync(entry, parentPath, relativePath);
|
||||
while(!builder.HasFinished)
|
||||
{
|
||||
try
|
||||
{
|
||||
int tBlocks = builder.BlocksWritten;
|
||||
TotalProgress.Value = tBlocks;
|
||||
decimal progress = Math.Floor(((decimal)tBlocks / (decimal)noBlocks) * 100);
|
||||
Status.Text = "Signing the Declaration of Independance " + progress.ToString() + "%";
|
||||
}
|
||||
catch (Exception) { }
|
||||
|
||||
Application.DoEvents();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
long ContentSize = builder.Finish();
|
||||
gamePsvimg = File.OpenRead(psvimgFilepath);
|
||||
FileStream gamePsvmd = File.OpenWrite(Path.Combine(BackupDir, "game.psvmd"));
|
||||
PSVMDBuilder.CreatePsvmd(gamePsvmd, gamePsvimg, ContentSize, "game", CmaKey);
|
||||
gamePsvmd.Close();
|
||||
gamePsvimg.Close();
|
||||
|
||||
// Package LICENSE
|
||||
|
||||
BackupDir = Path.Combine(BackupWorkDir, "license");
|
||||
psvimgFilepath = Path.Combine(BackupDir, "license.psvimg");
|
||||
|
||||
Directory.CreateDirectory(BackupDir);
|
||||
FileStream licensePsvimg = File.OpenWrite(psvimgFilepath);
|
||||
licensePsvimg.SetLength(0);
|
||||
|
||||
builder = new PSVIMGBuilder(licensePsvimg, CmaKey);
|
||||
if (!isZrif)
|
||||
{
|
||||
builder.AddFile(RifPath.Text, "ux0:pspemu/temp/game/PSP/LICENSE", "/" + ContentID + ".rif");
|
||||
}
|
||||
else
|
||||
{
|
||||
rif.Seek(0x00, SeekOrigin.Begin);
|
||||
builder.AddFileFromStream(rif, "ux0:pspemu/temp/game/PSP/LICENSE", "/" + ContentID + ".rif");
|
||||
}
|
||||
|
||||
rif.Close();
|
||||
ContentSize = builder.Finish();
|
||||
|
||||
licensePsvimg = File.OpenRead(psvimgFilepath);
|
||||
FileStream licensePsvmd = File.OpenWrite(Path.Combine(BackupDir, "license.psvmd"));
|
||||
PSVMDBuilder.CreatePsvmd(licensePsvmd, licensePsvimg, ContentSize, "license", CmaKey);
|
||||
licensePsvmd.Close();
|
||||
licensePsvimg.Close();
|
||||
|
||||
// Write PARAM.SFO & ICON0.PNG
|
||||
string SceSysWorkDir = Path.Combine(BackupWorkDir, "sce_sys");
|
||||
Directory.CreateDirectory(SceSysWorkDir);
|
||||
|
||||
byte[] ParamSfo = ReadFileFromISO(ISOPath.Text, @"PSP_GAME\PARAM.SFO");
|
||||
byte[] Icon0 = ReadFileFromISO(ISOPath.Text, @"PSP_GAME\ICON0.PNG");
|
||||
File.WriteAllBytes(Path.Combine(SceSysWorkDir, "param.sfo"), ParamSfo);
|
||||
File.WriteAllBytes(Path.Combine(SceSysWorkDir, "icon0.png"), Icon0);
|
||||
|
||||
Status.Text = "YOU HAVE MADE A SOCIAL CONTRACT WITH FREEDOM!";
|
||||
TotalProgress.Value = 0;
|
||||
|
||||
try
|
||||
{
|
||||
Directory.Delete(TmpDir, true);
|
||||
}
|
||||
catch (Exception) { };
|
||||
|
||||
if (!MutedAudio)
|
||||
{
|
||||
Stream str = Resources.Murica;
|
||||
SoundPlayer snd = new SoundPlayer(str);
|
||||
snd.Play();
|
||||
}
|
||||
|
||||
enable();
|
||||
MessageBox.Show("YOU HAVE MADE A SOCIAL CONTRACT WITH FREEDOM!", "FREEDOM!", MessageBoxButtons.OK, MessageBoxIcon.Information);
|
||||
}
|
||||
|
||||
private void FindFromCMA_Click(object sender, EventArgs e)
|
||||
{
|
||||
this.Hide();
|
||||
string cmaDir = "";
|
||||
string accountId = "0000000000000000";
|
||||
|
||||
try
|
||||
{
|
||||
//try qcma
|
||||
cmaDir = Registry.CurrentUser.OpenSubKey(@"Software\codestation\qcma").GetValue("appsPath").ToString();
|
||||
accountId = Registry.CurrentUser.OpenSubKey(@"Software\codestation\qcma").GetValue("lastAccountId").ToString();
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
try
|
||||
{
|
||||
//try sony cma
|
||||
cmaDir = Registry.CurrentUser.OpenSubKey(@"Software\Sony Corporation\Content Manager Assistant\Settings").GetValue("ApplicationHomePath").ToString();
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
try
|
||||
{
|
||||
//try devkit cma
|
||||
cmaDir = Registry.CurrentUser.OpenSubKey(@"Software\SCE\PSP2\Services\Content Manager Assistant for PlayStation(R)Vita DevKit\Settings").GetValue("ApplicationHomePath").ToString();
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
try
|
||||
{
|
||||
string DefaultDir = Path.Combine(Environment.GetEnvironmentVariable("HOMEDRIVE"), Environment.GetEnvironmentVariable("HOMEPATH"), "Documents", "PS Vita");
|
||||
if (Directory.Exists(DefaultDir))
|
||||
{
|
||||
cmaDir = DefaultDir;
|
||||
}
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
//Do nothing
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
CHOVYCmaSelector ccs = new CHOVYCmaSelector(cmaDir, accountId);
|
||||
ccs.FormClosing += Ccs_FormClosing;
|
||||
ccs.ShowDialog();
|
||||
|
||||
}
|
||||
|
||||
private void Ccs_FormClosing(object sender, FormClosingEventArgs e)
|
||||
{
|
||||
CHOVYCmaSelector ccs = (CHOVYCmaSelector)sender;
|
||||
string CmaDir = ccs.GetCmaDir();
|
||||
string CmaAid = ccs.GetCmaAid();
|
||||
string Backup = ccs.GetSelectedBackup();
|
||||
|
||||
WriteSetting("CmaDir", CmaDir);
|
||||
|
||||
if (Backup == "")
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
string BackupPath = Path.Combine(CmaDir, "PGAME", CmaAid, Backup, "game", "game.psvimg");
|
||||
if(!File.Exists(BackupPath))
|
||||
{
|
||||
MessageBox.Show("Could not find \n" + BackupPath + "\n Perhaps backup failed?", "License Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
|
||||
ccs.Hide();
|
||||
this.Show();
|
||||
this.Focus();
|
||||
return;
|
||||
}
|
||||
|
||||
byte[] AID = BitConverter.GetBytes(Convert.ToInt64(CmaAid, 16));
|
||||
Array.Reverse(AID);
|
||||
byte[] Key = CmaKeys.GenerateKey(AID);
|
||||
|
||||
PSVIMGStream GamePsvimg = new PSVIMGStream(File.OpenRead(BackupPath), Key);
|
||||
|
||||
BackupPath = Path.Combine(CmaDir, "PGAME", CmaAid, Backup, "license", "license.psvimg");
|
||||
if (!File.Exists(BackupPath))
|
||||
{
|
||||
MessageBox.Show("Could not find \n"+BackupPath+"\n Perhaps backup failed?","License Error",MessageBoxButtons.OK,MessageBoxIcon.Error);
|
||||
ccs.Hide();
|
||||
this.Show();
|
||||
this.Focus();
|
||||
return;
|
||||
}
|
||||
|
||||
PSVIMGStream LicensePsvimg = new PSVIMGStream(File.OpenRead(BackupPath), Key);
|
||||
|
||||
PSVIMGFileStream EbootPbp = new PSVIMGFileStream(GamePsvimg, "/EBOOT.PBP");
|
||||
byte[] VersionKey = Pbp.GetVersionKey(EbootPbp);
|
||||
string VerKey = BitConverter.ToString(VersionKey).Replace("-", "");
|
||||
WriteSetting("VersionKey", VerKey);
|
||||
|
||||
string ContentID = Pbp.GetContentId(EbootPbp);
|
||||
PSVIMGFileStream LicenseRif = new PSVIMGFileStream(LicensePsvimg, "/"+ ContentID+ ".rif");
|
||||
byte[] LicenseRifBytes = new byte[LicenseRif.Length];
|
||||
LicenseRif.Read(LicenseRifBytes, 0x00, LicenseRifBytes.Length);
|
||||
|
||||
LicenseRif.Close();
|
||||
LicensePsvimg.Close();
|
||||
EbootPbp.Close();
|
||||
GamePsvimg.Close();
|
||||
|
||||
byte[] zRifBytes = ZlibStream.CompressBuffer(LicenseRifBytes);
|
||||
string Rif = Convert.ToBase64String(zRifBytes);
|
||||
WriteSetting("RifPath", Rif);
|
||||
|
||||
Versionkey.Text = VerKey;
|
||||
RifPath.Text = Rif;
|
||||
|
||||
ccs.Hide();
|
||||
this.Show();
|
||||
this.Focus();
|
||||
|
||||
MessageBox.Show("KEYS HAVE BEEN EXTRACTED FROM CMA, YOU MAY NOW LIBERATE YOURSELF", "SUCCESS", MessageBoxButtons.OK, MessageBoxIcon.Information);
|
||||
}
|
||||
|
||||
private void BrowseButton_Click(object sender, EventArgs e)
|
||||
{
|
||||
OpenFileDialog ofd = new OpenFileDialog();
|
||||
ofd.Title = "Select PSP UMD image *.iso";
|
||||
ofd.Filter = "ISO9660 Image Files (*.iso)|*.iso";
|
||||
ofd.ShowDialog();
|
||||
ISOPath.Text = ofd.FileName;
|
||||
}
|
||||
|
||||
private void CHOVY_FormClosing(object sender, FormClosingEventArgs e)
|
||||
{
|
||||
Environment.Exit(0);
|
||||
}
|
||||
|
||||
private void PsmChan_Click(object sender, EventArgs e)
|
||||
{
|
||||
if(!MutedAudio)
|
||||
{
|
||||
MutedAudio = true;
|
||||
WriteSetting("MuteAudio", "1");
|
||||
}
|
||||
else
|
||||
{
|
||||
MutedAudio = false;
|
||||
WriteSetting("MuteAudio", "0");
|
||||
}
|
||||
}
|
||||
|
||||
private void DexAidEnabler_Click(object sender, EventArgs e)
|
||||
{
|
||||
if (!IsDexAidSet())
|
||||
{
|
||||
WriteSetting("DexAid", "1");
|
||||
MessageBox.Show("Enabled DEX Aid\n(0x0000000000000000) will be used for CMA Backups.", "Dex Aid", MessageBoxButtons.OK, MessageBoxIcon.Information);
|
||||
}
|
||||
else
|
||||
{
|
||||
WriteSetting("DexAid", "0");
|
||||
MessageBox.Show("Enabled Retail Aid,\nAid From RIF Will be used for CMA Backups.", "Dex Aid", MessageBoxButtons.OK, MessageBoxIcon.Information);
|
||||
}
|
||||
}
|
||||
|
||||
private void Ps1Menu_Click(object sender, EventArgs e)
|
||||
{
|
||||
|
||||
if (!MutedAudio)
|
||||
{
|
||||
Stream str = Resources.POPS;
|
||||
SoundPlayer snd = new SoundPlayer(str);
|
||||
snd.Play();
|
||||
}
|
||||
CHOVYPopsBuilder pops = new CHOVYPopsBuilder();
|
||||
this.Hide();
|
||||
pops.Show();
|
||||
pops.FormClosing += Pops_FormClosing;
|
||||
|
||||
}
|
||||
|
||||
private void Pops_FormClosing(object sender, FormClosingEventArgs e)
|
||||
{
|
||||
this.Show();
|
||||
}
|
||||
}
|
||||
}
|
File diff suppressed because it is too large
Load Diff
|
@ -1,153 +0,0 @@
|
|||
namespace CHOVY_SIGN
|
||||
{
|
||||
partial class CHOVYCmaSelector
|
||||
{
|
||||
/// <summary>
|
||||
/// Required designer variable.
|
||||
/// </summary>
|
||||
private System.ComponentModel.IContainer components = null;
|
||||
|
||||
/// <summary>
|
||||
/// Clean up any resources being used.
|
||||
/// </summary>
|
||||
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
|
||||
protected override void Dispose(bool disposing)
|
||||
{
|
||||
if (disposing && (components != null))
|
||||
{
|
||||
components.Dispose();
|
||||
}
|
||||
base.Dispose(disposing);
|
||||
}
|
||||
|
||||
#region Windows Form Designer generated code
|
||||
|
||||
/// <summary>
|
||||
/// Required method for Designer support - do not modify
|
||||
/// the contents of this method with the code editor.
|
||||
/// </summary>
|
||||
private void InitializeComponent()
|
||||
{
|
||||
System.ComponentModel.ComponentResourceManager resources = new System.ComponentModel.ComponentResourceManager(typeof(CHOVYCmaSelector));
|
||||
this.BackupList = new System.Windows.Forms.ListBox();
|
||||
this.label1 = new System.Windows.Forms.Label();
|
||||
this.CMADir = new System.Windows.Forms.TextBox();
|
||||
this.label2 = new System.Windows.Forms.Label();
|
||||
this.AIDSelector = new System.Windows.Forms.ComboBox();
|
||||
this.Browse = new System.Windows.Forms.Button();
|
||||
this.GitRifAndVerKey = new System.Windows.Forms.Button();
|
||||
this.SuspendLayout();
|
||||
//
|
||||
// BackupList
|
||||
//
|
||||
this.BackupList.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(64)))), ((int)(((byte)(64)))), ((int)(((byte)(64)))));
|
||||
this.BackupList.BorderStyle = System.Windows.Forms.BorderStyle.FixedSingle;
|
||||
this.BackupList.ForeColor = System.Drawing.Color.Lime;
|
||||
this.BackupList.FormattingEnabled = true;
|
||||
this.BackupList.Location = new System.Drawing.Point(12, 40);
|
||||
this.BackupList.Name = "BackupList";
|
||||
this.BackupList.Size = new System.Drawing.Size(617, 262);
|
||||
this.BackupList.TabIndex = 0;
|
||||
//
|
||||
// label1
|
||||
//
|
||||
this.label1.AutoSize = true;
|
||||
this.label1.ForeColor = System.Drawing.Color.Chartreuse;
|
||||
this.label1.Location = new System.Drawing.Point(12, 9);
|
||||
this.label1.Name = "label1";
|
||||
this.label1.Size = new System.Drawing.Size(49, 13);
|
||||
this.label1.TabIndex = 1;
|
||||
this.label1.Text = "CMA Dir:";
|
||||
//
|
||||
// CMADir
|
||||
//
|
||||
this.CMADir.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(64)))), ((int)(((byte)(64)))), ((int)(((byte)(64)))));
|
||||
this.CMADir.BorderStyle = System.Windows.Forms.BorderStyle.FixedSingle;
|
||||
this.CMADir.ForeColor = System.Drawing.Color.Lime;
|
||||
this.CMADir.Location = new System.Drawing.Point(67, 6);
|
||||
this.CMADir.Name = "CMADir";
|
||||
this.CMADir.Size = new System.Drawing.Size(240, 20);
|
||||
this.CMADir.TabIndex = 2;
|
||||
this.CMADir.TextChanged += new System.EventHandler(this.CMADir_TextChanged);
|
||||
//
|
||||
// label2
|
||||
//
|
||||
this.label2.AutoSize = true;
|
||||
this.label2.ForeColor = System.Drawing.Color.Chartreuse;
|
||||
this.label2.Location = new System.Drawing.Point(373, 9);
|
||||
this.label2.Name = "label2";
|
||||
this.label2.Size = new System.Drawing.Size(28, 13);
|
||||
this.label2.TabIndex = 3;
|
||||
this.label2.Text = "AID:";
|
||||
//
|
||||
// AIDSelector
|
||||
//
|
||||
this.AIDSelector.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(64)))), ((int)(((byte)(64)))), ((int)(((byte)(64)))));
|
||||
this.AIDSelector.FlatStyle = System.Windows.Forms.FlatStyle.Popup;
|
||||
this.AIDSelector.ForeColor = System.Drawing.Color.Lime;
|
||||
this.AIDSelector.FormattingEnabled = true;
|
||||
this.AIDSelector.Location = new System.Drawing.Point(407, 6);
|
||||
this.AIDSelector.Name = "AIDSelector";
|
||||
this.AIDSelector.Size = new System.Drawing.Size(222, 21);
|
||||
this.AIDSelector.TabIndex = 4;
|
||||
this.AIDSelector.Text = "0000000000000000";
|
||||
this.AIDSelector.TextChanged += new System.EventHandler(this.AIDSelector_TextChanged);
|
||||
//
|
||||
// Browse
|
||||
//
|
||||
this.Browse.FlatStyle = System.Windows.Forms.FlatStyle.Flat;
|
||||
this.Browse.ForeColor = System.Drawing.Color.Chartreuse;
|
||||
this.Browse.Location = new System.Drawing.Point(313, 6);
|
||||
this.Browse.Name = "Browse";
|
||||
this.Browse.Size = new System.Drawing.Size(54, 21);
|
||||
this.Browse.TabIndex = 5;
|
||||
this.Browse.Text = "Browse";
|
||||
this.Browse.UseVisualStyleBackColor = true;
|
||||
this.Browse.Click += new System.EventHandler(this.Browse_Click);
|
||||
//
|
||||
// GitRifAndVerKey
|
||||
//
|
||||
this.GitRifAndVerKey.FlatStyle = System.Windows.Forms.FlatStyle.Flat;
|
||||
this.GitRifAndVerKey.ForeColor = System.Drawing.Color.Red;
|
||||
this.GitRifAndVerKey.Location = new System.Drawing.Point(12, 308);
|
||||
this.GitRifAndVerKey.Name = "GitRifAndVerKey";
|
||||
this.GitRifAndVerKey.Size = new System.Drawing.Size(617, 25);
|
||||
this.GitRifAndVerKey.TabIndex = 6;
|
||||
this.GitRifAndVerKey.Text = "GO GIT THE RIF AND VERSION KEY!!!!";
|
||||
this.GitRifAndVerKey.UseVisualStyleBackColor = true;
|
||||
this.GitRifAndVerKey.Click += new System.EventHandler(this.GitRifAndVerKey_Click);
|
||||
//
|
||||
// CHOVYCmaSelector
|
||||
//
|
||||
this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
|
||||
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
|
||||
this.BackColor = System.Drawing.Color.Black;
|
||||
this.ClientSize = new System.Drawing.Size(641, 341);
|
||||
this.Controls.Add(this.GitRifAndVerKey);
|
||||
this.Controls.Add(this.Browse);
|
||||
this.Controls.Add(this.AIDSelector);
|
||||
this.Controls.Add(this.label2);
|
||||
this.Controls.Add(this.CMADir);
|
||||
this.Controls.Add(this.label1);
|
||||
this.Controls.Add(this.BackupList);
|
||||
this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.FixedSingle;
|
||||
this.Icon = ((System.Drawing.Icon)(resources.GetObject("$this.Icon")));
|
||||
this.MaximizeBox = false;
|
||||
this.Name = "CHOVYCmaSelector";
|
||||
this.Text = "Chovy-Sign - Find Keys";
|
||||
this.ResumeLayout(false);
|
||||
this.PerformLayout();
|
||||
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
private System.Windows.Forms.ListBox BackupList;
|
||||
private System.Windows.Forms.Label label1;
|
||||
private System.Windows.Forms.TextBox CMADir;
|
||||
private System.Windows.Forms.Label label2;
|
||||
private System.Windows.Forms.ComboBox AIDSelector;
|
||||
private System.Windows.Forms.Button Browse;
|
||||
private System.Windows.Forms.Button GitRifAndVerKey;
|
||||
}
|
||||
}
|
File diff suppressed because it is too large
Load Diff
|
@ -1,210 +0,0 @@
|
|||
using System;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
|
||||
namespace BasicDataTypes
|
||||
{
|
||||
class DataUtils
|
||||
{
|
||||
public static void CopyString(byte[] str, String Text, int Index)
|
||||
{
|
||||
byte[] TextBytes = Encoding.UTF8.GetBytes(Text);
|
||||
Array.ConstrainedCopy(TextBytes, 0, str, Index, TextBytes.Length);
|
||||
}
|
||||
public static void CopyUInt16(byte[] str, UInt16 Value, int Index)
|
||||
{
|
||||
byte[] ValueBytes = BitConverter.GetBytes(Value);
|
||||
Array.ConstrainedCopy(ValueBytes, 0, str, Index, ValueBytes.Length);
|
||||
}
|
||||
public static void CopyInt16(byte[] str, Int16 Value, int Index)
|
||||
{
|
||||
byte[] ValueBytes = BitConverter.GetBytes(Value);
|
||||
Array.ConstrainedCopy(ValueBytes, 0, str, Index, ValueBytes.Length);
|
||||
}
|
||||
public static void CopyUInt64(byte[] str, UInt64 Value, int Index)
|
||||
{
|
||||
byte[] ValueBytes = BitConverter.GetBytes(Value);
|
||||
Array.ConstrainedCopy(ValueBytes, 0, str, Index, ValueBytes.Length);
|
||||
}
|
||||
public static void CopyInt64(byte[] str, Int64 Value, int Index)
|
||||
{
|
||||
byte[] ValueBytes = BitConverter.GetBytes(Value);
|
||||
Array.ConstrainedCopy(ValueBytes, 0, str, Index, ValueBytes.Length);
|
||||
}
|
||||
public static void CopyUInt32(byte[] str, UInt32 Value, int Index)
|
||||
{
|
||||
byte[] ValueBytes = BitConverter.GetBytes(Value);
|
||||
Array.ConstrainedCopy(ValueBytes, 0, str, Index, ValueBytes.Length);
|
||||
}
|
||||
public static void CopyInt32(byte[] str, Int32 Value, int Index)
|
||||
{
|
||||
byte[] ValueBytes = BitConverter.GetBytes(Value);
|
||||
Array.ConstrainedCopy(ValueBytes, 0, str, Index, ValueBytes.Length);
|
||||
}
|
||||
public static void CopyInt32BE(byte[] str, Int32 Value, int Index)
|
||||
{
|
||||
byte[] ValueBytes = BitConverter.GetBytes(Value);
|
||||
byte[] ValueBytesBE = ValueBytes.Reverse().ToArray();
|
||||
Array.ConstrainedCopy(ValueBytesBE, 0, str, Index, ValueBytesBE.Length);
|
||||
}
|
||||
|
||||
// Read From Streams
|
||||
public static UInt32 ReadUInt32(Stream Str)
|
||||
{
|
||||
byte[] IntBytes = new byte[0x4];
|
||||
Str.Read(IntBytes, 0x00, IntBytes.Length);
|
||||
return BitConverter.ToUInt32(IntBytes, 0x00);
|
||||
}
|
||||
public static UInt32 ReadInt32(Stream Str)
|
||||
{
|
||||
byte[] IntBytes = new byte[0x4];
|
||||
Str.Read(IntBytes, 0x00, IntBytes.Length);
|
||||
return BitConverter.ToUInt32(IntBytes, 0x00);
|
||||
}
|
||||
public static UInt64 ReadUInt64(Stream Str)
|
||||
{
|
||||
byte[] IntBytes = new byte[0x8];
|
||||
Str.Read(IntBytes, 0x00, IntBytes.Length);
|
||||
return BitConverter.ToUInt64(IntBytes, 0x00);
|
||||
}
|
||||
public static Int64 ReadInt64(Stream Str)
|
||||
{
|
||||
byte[] IntBytes = new byte[0x8];
|
||||
Str.Read(IntBytes, 0x00, IntBytes.Length);
|
||||
return BitConverter.ToInt64(IntBytes, 0x00);
|
||||
}
|
||||
public static UInt16 ReadUInt16(Stream Str)
|
||||
{
|
||||
byte[] IntBytes = new byte[0x2];
|
||||
Str.Read(IntBytes, 0x00, IntBytes.Length);
|
||||
return BitConverter.ToUInt16(IntBytes, 0x00);
|
||||
}
|
||||
public static Int16 ReadInt16(Stream Str)
|
||||
{
|
||||
byte[] IntBytes = new byte[0x2];
|
||||
Str.Read(IntBytes, 0x00, IntBytes.Length);
|
||||
return BitConverter.ToInt16(IntBytes, 0x00);
|
||||
}
|
||||
|
||||
public static UInt32 ReadUint32At(Stream Str, int location)
|
||||
{
|
||||
long oldPos = Str.Position;
|
||||
Str.Seek(location, SeekOrigin.Begin);
|
||||
UInt32 outp = ReadUInt32(Str);
|
||||
Str.Seek(oldPos, SeekOrigin.Begin);
|
||||
return outp;
|
||||
}
|
||||
|
||||
public static byte[] ReadBytesAt(Stream Str, int location, int length)
|
||||
{
|
||||
long oldPos = Str.Position;
|
||||
Str.Seek(location, SeekOrigin.Begin);
|
||||
byte[] work_buf = new byte[length];
|
||||
Str.Read(work_buf, 0x0, work_buf.Length);
|
||||
Str.Seek(oldPos, SeekOrigin.Begin);
|
||||
return work_buf;
|
||||
}
|
||||
|
||||
public static string ReadStringAt(Stream Str,int location)
|
||||
{
|
||||
long oldPos = Str.Position;
|
||||
Str.Seek(location, SeekOrigin.Begin);
|
||||
string outp = ReadString(Str);
|
||||
Str.Seek(oldPos,SeekOrigin.Begin);
|
||||
return outp;
|
||||
}
|
||||
public static string ReadString(Stream Str)
|
||||
{
|
||||
MemoryStream ms = new MemoryStream();
|
||||
|
||||
while (true)
|
||||
{
|
||||
byte c = (byte)Str.ReadByte();
|
||||
if (c == 0)
|
||||
break;
|
||||
ms.WriteByte(c);
|
||||
}
|
||||
ms.Seek(0x00, SeekOrigin.Begin);
|
||||
string outp = Encoding.UTF8.GetString(ms.ToArray());
|
||||
ms.Dispose();
|
||||
return outp;
|
||||
}
|
||||
|
||||
// Write To Streams
|
||||
|
||||
public static void WriteUInt32(Stream Str, UInt32 Numb)
|
||||
{
|
||||
byte[] IntBytes = BitConverter.GetBytes(Numb);
|
||||
Str.Write(IntBytes, 0x00, IntBytes.Length);
|
||||
}
|
||||
public static void WriteInt32(Stream Str, Int32 Numb)
|
||||
{
|
||||
byte[] IntBytes = BitConverter.GetBytes(Numb);
|
||||
Str.Write(IntBytes, 0x00, IntBytes.Length);
|
||||
}
|
||||
public static void WriteUInt64(Stream dst, UInt64 value)
|
||||
{
|
||||
byte[] ValueBytes = BitConverter.GetBytes(value);
|
||||
dst.Write(ValueBytes, 0x00, 0x8);
|
||||
}
|
||||
public static void WriteInt64(Stream dst, Int64 value)
|
||||
{
|
||||
byte[] ValueBytes = BitConverter.GetBytes(value);
|
||||
dst.Write(ValueBytes, 0x00, 0x8);
|
||||
}
|
||||
public static void WriteUInt16(Stream dst, UInt16 value)
|
||||
{
|
||||
byte[] ValueBytes = BitConverter.GetBytes(value);
|
||||
dst.Write(ValueBytes, 0x00, 0x2);
|
||||
}
|
||||
public static void WriteInt16(Stream dst, Int16 value)
|
||||
{
|
||||
byte[] ValueBytes = BitConverter.GetBytes(value);
|
||||
dst.Write(ValueBytes, 0x00, 0x2);
|
||||
}
|
||||
|
||||
public static void WriteInt32BE(Stream Str, Int32 Numb)
|
||||
{
|
||||
byte[] IntBytes = BitConverter.GetBytes(Numb);
|
||||
byte[] IntBytesBE = IntBytes.Reverse().ToArray();
|
||||
Str.Write(IntBytesBE, 0x00, IntBytesBE.Length);
|
||||
}
|
||||
public static void WriteStringAt(Stream Str, string Text, int location)
|
||||
{
|
||||
long oldPos = Str.Position;
|
||||
Str.Seek(location, SeekOrigin.Begin);
|
||||
WriteString(Str,Text);
|
||||
Str.Seek(oldPos, SeekOrigin.Begin);
|
||||
}
|
||||
public static void WriteBytes(Stream Str, byte[] Bytes, Int64 Size)
|
||||
{
|
||||
Int64 Written = 0;
|
||||
while (Written < Size)
|
||||
{
|
||||
if ((Size - Written) > 2000000000)
|
||||
{
|
||||
Str.Write(Bytes, 0x00, 2000000000);
|
||||
Written += 2000000000;
|
||||
}
|
||||
else
|
||||
{
|
||||
Str.Write(Bytes, 0x00, Convert.ToInt32(Size - Written));
|
||||
Written += (Size - Written);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
public static void WriteString(Stream Str, String Text, int len = -1)
|
||||
{
|
||||
if (len < 0)
|
||||
{
|
||||
len = Text.Length;
|
||||
}
|
||||
|
||||
byte[] TextBytes = Encoding.UTF8.GetBytes(Text);
|
||||
Str.Write(TextBytes, 0x00, len);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
|
@ -1,61 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
using DiscUtils.Streams;
|
||||
|
||||
namespace DiscUtils.ApplePartitionMap
|
||||
{
|
||||
internal sealed class BlockZero : IByteArraySerializable
|
||||
{
|
||||
public uint BlockCount;
|
||||
public ushort BlockSize;
|
||||
public ushort DeviceId;
|
||||
public ushort DeviceType;
|
||||
public ushort DriverCount;
|
||||
public uint DriverData;
|
||||
public ushort Signature;
|
||||
|
||||
public int Size
|
||||
{
|
||||
get { return 512; }
|
||||
}
|
||||
|
||||
public int ReadFrom(byte[] buffer, int offset)
|
||||
{
|
||||
Signature = EndianUtilities.ToUInt16BigEndian(buffer, offset + 0);
|
||||
BlockSize = EndianUtilities.ToUInt16BigEndian(buffer, offset + 2);
|
||||
BlockCount = EndianUtilities.ToUInt32BigEndian(buffer, offset + 4);
|
||||
DeviceType = EndianUtilities.ToUInt16BigEndian(buffer, offset + 8);
|
||||
DeviceId = EndianUtilities.ToUInt16BigEndian(buffer, offset + 10);
|
||||
DriverData = EndianUtilities.ToUInt32BigEndian(buffer, offset + 12);
|
||||
DriverCount = EndianUtilities.ToUInt16LittleEndian(buffer, offset + 16);
|
||||
|
||||
return 512;
|
||||
}
|
||||
|
||||
public void WriteTo(byte[] buffer, int offset)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,153 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
using System.Collections.ObjectModel;
|
||||
using System.IO;
|
||||
using DiscUtils.Partitions;
|
||||
using DiscUtils.Streams;
|
||||
|
||||
namespace DiscUtils.ApplePartitionMap
|
||||
{
|
||||
/// <summary>
|
||||
/// Interprets Apple Partition Map structures that partition a disk.
|
||||
/// </summary>
|
||||
public sealed class PartitionMap : PartitionTable
|
||||
{
|
||||
private readonly PartitionMapEntry[] _partitions;
|
||||
private readonly Stream _stream;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the PartitionMap class.
|
||||
/// </summary>
|
||||
/// <param name="stream">Stream containing the contents of a disk.</param>
|
||||
public PartitionMap(Stream stream)
|
||||
{
|
||||
_stream = stream;
|
||||
|
||||
stream.Position = 0;
|
||||
byte[] initialBytes = StreamUtilities.ReadExact(stream, 1024);
|
||||
|
||||
BlockZero b0 = new BlockZero();
|
||||
b0.ReadFrom(initialBytes, 0);
|
||||
|
||||
PartitionMapEntry initialPart = new PartitionMapEntry(_stream);
|
||||
initialPart.ReadFrom(initialBytes, 512);
|
||||
|
||||
byte[] partTableData = StreamUtilities.ReadExact(stream, (int)(initialPart.MapEntries - 1) * 512);
|
||||
|
||||
_partitions = new PartitionMapEntry[initialPart.MapEntries - 1];
|
||||
for (uint i = 0; i < initialPart.MapEntries - 1; ++i)
|
||||
{
|
||||
_partitions[i] = new PartitionMapEntry(_stream);
|
||||
_partitions[i].ReadFrom(partTableData, (int)(512 * i));
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the GUID of the disk, always returns Guid.Empty.
|
||||
/// </summary>
|
||||
public override Guid DiskGuid
|
||||
{
|
||||
get { return Guid.Empty; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the partitions present on the disk.
|
||||
/// </summary>
|
||||
public override ReadOnlyCollection<PartitionInfo> Partitions
|
||||
{
|
||||
get { return new ReadOnlyCollection<PartitionInfo>(_partitions); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates a new partition that encompasses the entire disk.
|
||||
/// </summary>
|
||||
/// <param name="type">The partition type.</param>
|
||||
/// <param name="active">Whether the partition is active (bootable).</param>
|
||||
/// <returns>The index of the partition.</returns>
|
||||
/// <remarks>The partition table must be empty before this method is called,
|
||||
/// otherwise IOException is thrown.</remarks>
|
||||
public override int Create(WellKnownPartitionType type, bool active)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates a new partition with a target size.
|
||||
/// </summary>
|
||||
/// <param name="size">The target size (in bytes).</param>
|
||||
/// <param name="type">The partition type.</param>
|
||||
/// <param name="active">Whether the partition is active (bootable).</param>
|
||||
/// <returns>The index of the new partition.</returns>
|
||||
public override int Create(long size, WellKnownPartitionType type, bool active)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates a new aligned partition that encompasses the entire disk.
|
||||
/// </summary>
|
||||
/// <param name="type">The partition type.</param>
|
||||
/// <param name="active">Whether the partition is active (bootable).</param>
|
||||
/// <param name="alignment">The alignment (in byte).</param>
|
||||
/// <returns>The index of the partition.</returns>
|
||||
/// <remarks>The partition table must be empty before this method is called,
|
||||
/// otherwise IOException is thrown.</remarks>
|
||||
/// <remarks>
|
||||
/// Traditionally partitions were aligned to the physical structure of the underlying disk,
|
||||
/// however with modern storage greater efficiency is acheived by aligning partitions on
|
||||
/// large values that are a power of two.
|
||||
/// </remarks>
|
||||
public override int CreateAligned(WellKnownPartitionType type, bool active, int alignment)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates a new aligned partition with a target size.
|
||||
/// </summary>
|
||||
/// <param name="size">The target size (in bytes).</param>
|
||||
/// <param name="type">The partition type.</param>
|
||||
/// <param name="active">Whether the partition is active (bootable).</param>
|
||||
/// <param name="alignment">The alignment (in byte).</param>
|
||||
/// <returns>The index of the new partition.</returns>
|
||||
/// <remarks>
|
||||
/// Traditionally partitions were aligned to the physical structure of the underlying disk,
|
||||
/// however with modern storage greater efficiency is achieved by aligning partitions on
|
||||
/// large values that are a power of two.
|
||||
/// </remarks>
|
||||
public override int CreateAligned(long size, WellKnownPartitionType type, bool active, int alignment)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Deletes a partition at a given index.
|
||||
/// </summary>
|
||||
/// <param name="index">The index of the partition.</param>
|
||||
public override void Delete(int index)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,112 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
using System.IO;
|
||||
using DiscUtils.Partitions;
|
||||
using DiscUtils.Streams;
|
||||
|
||||
namespace DiscUtils.ApplePartitionMap
|
||||
{
|
||||
internal sealed class PartitionMapEntry : PartitionInfo, IByteArraySerializable
|
||||
{
|
||||
private readonly Stream _diskStream;
|
||||
public uint BootBlock;
|
||||
public uint BootBytes;
|
||||
public uint Flags;
|
||||
public uint LogicalBlocks;
|
||||
public uint LogicalBlockStart;
|
||||
public uint MapEntries;
|
||||
public string Name;
|
||||
public uint PhysicalBlocks;
|
||||
public uint PhysicalBlockStart;
|
||||
public ushort Signature;
|
||||
public string Type;
|
||||
|
||||
public PartitionMapEntry(Stream diskStream)
|
||||
{
|
||||
_diskStream = diskStream;
|
||||
}
|
||||
|
||||
public override byte BiosType
|
||||
{
|
||||
get { return 0xAF; }
|
||||
}
|
||||
|
||||
public override long FirstSector
|
||||
{
|
||||
get { return PhysicalBlockStart; }
|
||||
}
|
||||
|
||||
public override Guid GuidType
|
||||
{
|
||||
get { return Guid.Empty; }
|
||||
}
|
||||
|
||||
public override long LastSector
|
||||
{
|
||||
get { return PhysicalBlockStart + PhysicalBlocks - 1; }
|
||||
}
|
||||
|
||||
public override string TypeAsString
|
||||
{
|
||||
get { return Type; }
|
||||
}
|
||||
|
||||
internal override PhysicalVolumeType VolumeType
|
||||
{
|
||||
get { return PhysicalVolumeType.ApplePartition; }
|
||||
}
|
||||
|
||||
public int Size
|
||||
{
|
||||
get { return 512; }
|
||||
}
|
||||
|
||||
public int ReadFrom(byte[] buffer, int offset)
|
||||
{
|
||||
Signature = EndianUtilities.ToUInt16BigEndian(buffer, offset + 0);
|
||||
MapEntries = EndianUtilities.ToUInt32BigEndian(buffer, offset + 4);
|
||||
PhysicalBlockStart = EndianUtilities.ToUInt32BigEndian(buffer, offset + 8);
|
||||
PhysicalBlocks = EndianUtilities.ToUInt32BigEndian(buffer, offset + 12);
|
||||
Name = EndianUtilities.BytesToString(buffer, offset + 16, 32).TrimEnd('\0');
|
||||
Type = EndianUtilities.BytesToString(buffer, offset + 48, 32).TrimEnd('\0');
|
||||
LogicalBlockStart = EndianUtilities.ToUInt32BigEndian(buffer, offset + 80);
|
||||
LogicalBlocks = EndianUtilities.ToUInt32BigEndian(buffer, offset + 84);
|
||||
Flags = EndianUtilities.ToUInt32BigEndian(buffer, offset + 88);
|
||||
BootBlock = EndianUtilities.ToUInt32BigEndian(buffer, offset + 92);
|
||||
BootBytes = EndianUtilities.ToUInt32BigEndian(buffer, offset + 96);
|
||||
|
||||
return 512;
|
||||
}
|
||||
|
||||
public void WriteTo(byte[] buffer, int offset)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public override SparseStream Open()
|
||||
{
|
||||
return new SubStream(_diskStream, PhysicalBlockStart * 512, PhysicalBlocks * 512);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,66 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System.IO;
|
||||
using DiscUtils.Partitions;
|
||||
using DiscUtils.Streams;
|
||||
|
||||
namespace DiscUtils.ApplePartitionMap
|
||||
{
|
||||
[PartitionTableFactory]
|
||||
internal sealed class PartitionMapFactory : PartitionTableFactory
|
||||
{
|
||||
public override bool DetectIsPartitioned(Stream s)
|
||||
{
|
||||
if (s.Length < 1024)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
s.Position = 0;
|
||||
|
||||
byte[] initialBytes = StreamUtilities.ReadExact(s, 1024);
|
||||
|
||||
BlockZero b0 = new BlockZero();
|
||||
b0.ReadFrom(initialBytes, 0);
|
||||
if (b0.Signature != 0x4552)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
PartitionMapEntry initialPart = new PartitionMapEntry(s);
|
||||
initialPart.ReadFrom(initialBytes, 512);
|
||||
|
||||
return initialPart.Signature == 0x504d;
|
||||
}
|
||||
|
||||
public override PartitionTable DetectPartitionTable(VirtualDisk disk)
|
||||
{
|
||||
if (!DetectIsPartitioned(disk.Content))
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
return new PartitionMap(disk.Content);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,38 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
namespace DiscUtils.Archives
|
||||
{
|
||||
internal sealed class FileRecord
|
||||
{
|
||||
public long Length;
|
||||
public string Name;
|
||||
public long Start;
|
||||
|
||||
public FileRecord(string name, long start, long length)
|
||||
{
|
||||
Name = name;
|
||||
Start = start;
|
||||
Length = length;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,144 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using DiscUtils.Streams;
|
||||
|
||||
namespace DiscUtils.Archives
|
||||
{
|
||||
/// <summary>
|
||||
/// Minimal tar file format implementation.
|
||||
/// </summary>
|
||||
public sealed class TarFile
|
||||
{
|
||||
private readonly Dictionary<string, FileRecord> _files;
|
||||
private readonly Stream _fileStream;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the TarFile class.
|
||||
/// </summary>
|
||||
/// <param name="fileStream">The Tar file.</param>
|
||||
public TarFile(Stream fileStream)
|
||||
{
|
||||
_fileStream = fileStream;
|
||||
_files = new Dictionary<string, FileRecord>();
|
||||
|
||||
TarHeader hdr = new TarHeader();
|
||||
byte[] hdrBuf = StreamUtilities.ReadExact(_fileStream, TarHeader.Length);
|
||||
hdr.ReadFrom(hdrBuf, 0);
|
||||
while (hdr.FileLength != 0 || !string.IsNullOrEmpty(hdr.FileName))
|
||||
{
|
||||
FileRecord record = new FileRecord(hdr.FileName, _fileStream.Position, hdr.FileLength);
|
||||
_files.Add(record.Name, record);
|
||||
_fileStream.Position += (hdr.FileLength + 511) / 512 * 512;
|
||||
|
||||
hdrBuf = StreamUtilities.ReadExact(_fileStream, TarHeader.Length);
|
||||
hdr.ReadFrom(hdrBuf, 0);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Tries to open a file contained in the archive, if it exists.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to the file within the archive.</param>
|
||||
/// <param name="stream">A stream containing the file contents, or null.</param>
|
||||
/// <returns><c>true</c> if the file could be opened, else <c>false</c>.</returns>
|
||||
public bool TryOpenFile(string path, out Stream stream)
|
||||
{
|
||||
if (_files.ContainsKey(path))
|
||||
{
|
||||
FileRecord file = _files[path];
|
||||
stream = new SubStream(_fileStream, file.Start, file.Length);
|
||||
return true;
|
||||
}
|
||||
|
||||
stream = null;
|
||||
return false;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Open a file contained in the archive.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to the file within the archive.</param>
|
||||
/// <returns>A stream containing the file contents.</returns>
|
||||
/// <exception cref="FileNotFoundException">Thrown if the file is not found.</exception>
|
||||
public Stream OpenFile(string path)
|
||||
{
|
||||
if (_files.ContainsKey(path))
|
||||
{
|
||||
FileRecord file = _files[path];
|
||||
return new SubStream(_fileStream, file.Start, file.Length);
|
||||
}
|
||||
|
||||
throw new FileNotFoundException("File is not in archive", path);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Determines if a given file exists in the archive.
|
||||
/// </summary>
|
||||
/// <param name="path">The file path to test.</param>
|
||||
/// <returns><c>true</c> if the file is present, else <c>false</c>.</returns>
|
||||
public bool FileExists(string path)
|
||||
{
|
||||
return _files.ContainsKey(path);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Determines if a given directory exists in the archive.
|
||||
/// </summary>
|
||||
/// <param name="path">The file path to test.</param>
|
||||
/// <returns><c>true</c> if the directory is present, else <c>false</c>.</returns>
|
||||
public bool DirExists(string path)
|
||||
{
|
||||
string searchStr = path;
|
||||
searchStr = searchStr.Replace(@"\", "/");
|
||||
searchStr = searchStr.EndsWith(@"/", StringComparison.Ordinal) ? searchStr : searchStr + @"/";
|
||||
|
||||
foreach (string filePath in _files.Keys)
|
||||
{
|
||||
if (filePath.StartsWith(searchStr, StringComparison.Ordinal))
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
internal IEnumerable<FileRecord> GetFiles(string dir)
|
||||
{
|
||||
string searchStr = dir;
|
||||
searchStr = searchStr.Replace(@"\", "/");
|
||||
searchStr = searchStr.EndsWith(@"/", StringComparison.Ordinal) ? searchStr : searchStr + @"/";
|
||||
|
||||
foreach (string filePath in _files.Keys)
|
||||
{
|
||||
if (filePath.StartsWith(searchStr, StringComparison.Ordinal))
|
||||
{
|
||||
yield return _files[filePath];
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,122 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using DiscUtils.Streams;
|
||||
|
||||
namespace DiscUtils.Archives
|
||||
{
|
||||
/// <summary>
|
||||
/// Builder to create UNIX Tar archive files.
|
||||
/// </summary>
|
||||
public sealed class TarFileBuilder : StreamBuilder
|
||||
{
|
||||
private readonly List<UnixBuildFileRecord> _files;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="TarFileBuilder"/> class.
|
||||
/// </summary>
|
||||
public TarFileBuilder()
|
||||
{
|
||||
_files = new List<UnixBuildFileRecord>();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Add a file to the tar archive.
|
||||
/// </summary>
|
||||
/// <param name="name">The name of the file.</param>
|
||||
/// <param name="buffer">The file data.</param>
|
||||
public void AddFile(string name, byte[] buffer)
|
||||
{
|
||||
_files.Add(new UnixBuildFileRecord(name, buffer));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Add a file to the tar archive.
|
||||
/// </summary>
|
||||
/// <param name="name">The name of the file.</param>
|
||||
/// <param name="buffer">The file data.</param>
|
||||
/// <param name="fileMode">The access mode of the file.</param>
|
||||
/// <param name="ownerId">The uid of the owner.</param>
|
||||
/// <param name="groupId">The gid of the owner.</param>
|
||||
/// <param name="modificationTime">The modification time for the file.</param>
|
||||
public void AddFile(
|
||||
string name, byte[] buffer, UnixFilePermissions fileMode, int ownerId, int groupId,
|
||||
DateTime modificationTime)
|
||||
{
|
||||
_files.Add(new UnixBuildFileRecord(name, buffer, fileMode, ownerId, groupId, modificationTime));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Add a file to the tar archive.
|
||||
/// </summary>
|
||||
/// <param name="name">The name of the file.</param>
|
||||
/// <param name="stream">The file data.</param>
|
||||
public void AddFile(string name, Stream stream)
|
||||
{
|
||||
_files.Add(new UnixBuildFileRecord(name, stream));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Add a file to the tar archive.
|
||||
/// </summary>
|
||||
/// <param name="name">The name of the file.</param>
|
||||
/// <param name="stream">The file data.</param>
|
||||
/// <param name="fileMode">The access mode of the file.</param>
|
||||
/// <param name="ownerId">The uid of the owner.</param>
|
||||
/// <param name="groupId">The gid of the owner.</param>
|
||||
/// <param name="modificationTime">The modification time for the file.</param>
|
||||
public void AddFile(
|
||||
string name, Stream stream, UnixFilePermissions fileMode, int ownerId, int groupId,
|
||||
DateTime modificationTime)
|
||||
{
|
||||
_files.Add(new UnixBuildFileRecord(name, stream, fileMode, ownerId, groupId, modificationTime));
|
||||
}
|
||||
|
||||
protected override List<BuilderExtent> FixExtents(out long totalLength)
|
||||
{
|
||||
List<BuilderExtent> result = new List<BuilderExtent>(_files.Count * 2 + 2);
|
||||
long pos = 0;
|
||||
|
||||
foreach (UnixBuildFileRecord file in _files)
|
||||
{
|
||||
BuilderExtent fileContentExtent = file.Fix(pos + TarHeader.Length);
|
||||
|
||||
result.Add(new TarHeaderExtent(
|
||||
pos, file.Name, fileContentExtent.Length, file.FileMode, file.OwnerId, file.GroupId,
|
||||
file.ModificationTime));
|
||||
pos += TarHeader.Length;
|
||||
|
||||
result.Add(fileContentExtent);
|
||||
pos += MathUtilities.RoundUp(fileContentExtent.Length, 512);
|
||||
}
|
||||
|
||||
// Two empty 512-byte blocks at end of tar file.
|
||||
result.Add(new BuilderBufferExtent(pos, new byte[1024]));
|
||||
|
||||
totalLength = pos + 1024;
|
||||
return result;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,102 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
using DiscUtils.Streams;
|
||||
|
||||
namespace DiscUtils.Archives
|
||||
{
|
||||
internal sealed class TarHeader
|
||||
{
|
||||
public const int Length = 512;
|
||||
public long FileLength;
|
||||
public UnixFilePermissions FileMode;
|
||||
|
||||
public string FileName;
|
||||
public int GroupId;
|
||||
public DateTime ModificationTime;
|
||||
public int OwnerId;
|
||||
|
||||
public void ReadFrom(byte[] buffer, int offset)
|
||||
{
|
||||
FileName = ReadNullTerminatedString(buffer, offset + 0, 100);
|
||||
FileMode = (UnixFilePermissions)OctalToLong(ReadNullTerminatedString(buffer, offset + 100, 8));
|
||||
OwnerId = (int)OctalToLong(ReadNullTerminatedString(buffer, offset + 108, 8));
|
||||
GroupId = (int)OctalToLong(ReadNullTerminatedString(buffer, offset + 116, 8));
|
||||
FileLength = OctalToLong(ReadNullTerminatedString(buffer, offset + 124, 12));
|
||||
ModificationTime = OctalToLong(ReadNullTerminatedString(buffer, offset + 136, 12)).FromUnixTimeSeconds().DateTime;
|
||||
}
|
||||
|
||||
public void WriteTo(byte[] buffer, int offset)
|
||||
{
|
||||
Array.Clear(buffer, offset, Length);
|
||||
|
||||
EndianUtilities.StringToBytes(FileName, buffer, offset, 99);
|
||||
EndianUtilities.StringToBytes(LongToOctal((long)FileMode, 7), buffer, offset + 100, 7);
|
||||
EndianUtilities.StringToBytes(LongToOctal(OwnerId, 7), buffer, offset + 108, 7);
|
||||
EndianUtilities.StringToBytes(LongToOctal(GroupId, 7), buffer, offset + 116, 7);
|
||||
EndianUtilities.StringToBytes(LongToOctal(FileLength, 11), buffer, offset + 124, 11);
|
||||
EndianUtilities.StringToBytes(LongToOctal(Convert.ToUInt32((new DateTimeOffset(ModificationTime)).ToUnixTimeSeconds()), 11), buffer, offset + 136, 11);
|
||||
|
||||
// Checksum
|
||||
EndianUtilities.StringToBytes(new string(' ', 8), buffer, offset + 148, 8);
|
||||
long checkSum = 0;
|
||||
for (int i = 0; i < 512; ++i)
|
||||
{
|
||||
checkSum += buffer[offset + i];
|
||||
}
|
||||
|
||||
EndianUtilities.StringToBytes(LongToOctal(checkSum, 7), buffer, offset + 148, 7);
|
||||
buffer[155] = 0;
|
||||
}
|
||||
|
||||
private static string ReadNullTerminatedString(byte[] buffer, int offset, int length)
|
||||
{
|
||||
return EndianUtilities.BytesToString(buffer, offset, length).TrimEnd('\0');
|
||||
}
|
||||
|
||||
private static long OctalToLong(string value)
|
||||
{
|
||||
long result = 0;
|
||||
|
||||
for (int i = 0; i < value.Length; ++i)
|
||||
{
|
||||
result = result * 8 + (value[i] - '0');
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
private static string LongToOctal(long value, int length)
|
||||
{
|
||||
string result = string.Empty;
|
||||
|
||||
while (value > 0)
|
||||
{
|
||||
result = (char)('0' + value % 8) + result;
|
||||
value = value / 8;
|
||||
}
|
||||
|
||||
return new string('0', length - result.Length) + result;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,68 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
using DiscUtils.Streams;
|
||||
|
||||
namespace DiscUtils.Archives
|
||||
{
|
||||
internal sealed class TarHeaderExtent : BuilderBufferExtent
|
||||
{
|
||||
private readonly long _fileLength;
|
||||
private readonly string _fileName;
|
||||
private readonly int _groupId;
|
||||
private readonly UnixFilePermissions _mode;
|
||||
private readonly DateTime _modificationTime;
|
||||
private readonly int _ownerId;
|
||||
|
||||
public TarHeaderExtent(long start, string fileName, long fileLength, UnixFilePermissions mode, int ownerId,
|
||||
int groupId, DateTime modificationTime)
|
||||
: base(start, 512)
|
||||
{
|
||||
_fileName = fileName;
|
||||
_fileLength = fileLength;
|
||||
_mode = mode;
|
||||
_ownerId = ownerId;
|
||||
_groupId = groupId;
|
||||
_modificationTime = modificationTime;
|
||||
}
|
||||
|
||||
public TarHeaderExtent(long start, string fileName, long fileLength)
|
||||
: this(start, fileName, fileLength, 0, 0, 0, DateTimeOffsetExtensions.UnixEpoch) {}
|
||||
|
||||
protected override byte[] GetBuffer()
|
||||
{
|
||||
byte[] buffer = new byte[TarHeader.Length];
|
||||
|
||||
TarHeader header = new TarHeader();
|
||||
header.FileName = _fileName;
|
||||
header.FileLength = _fileLength;
|
||||
header.FileMode = _mode;
|
||||
header.OwnerId = _ownerId;
|
||||
header.GroupId = _groupId;
|
||||
header.ModificationTime = _modificationTime;
|
||||
header.WriteTo(buffer, 0);
|
||||
|
||||
return buffer;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,75 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
using System.IO;
|
||||
using DiscUtils.Streams;
|
||||
|
||||
namespace DiscUtils.Archives
|
||||
{
|
||||
internal sealed class UnixBuildFileRecord
|
||||
{
|
||||
private readonly BuilderExtentSource _source;
|
||||
|
||||
public UnixBuildFileRecord(string name, byte[] buffer)
|
||||
: this(name, new BuilderBufferExtentSource(buffer), 0, 0, 0, DateTimeOffsetExtensions.UnixEpoch) {}
|
||||
|
||||
public UnixBuildFileRecord(string name, Stream stream)
|
||||
: this(name, new BuilderStreamExtentSource(stream), 0, 0, 0, DateTimeOffsetExtensions.UnixEpoch) {}
|
||||
|
||||
public UnixBuildFileRecord(
|
||||
string name, byte[] buffer, UnixFilePermissions fileMode, int ownerId, int groupId,
|
||||
DateTime modificationTime)
|
||||
: this(name, new BuilderBufferExtentSource(buffer), fileMode, ownerId, groupId, modificationTime) {}
|
||||
|
||||
public UnixBuildFileRecord(
|
||||
string name, Stream stream, UnixFilePermissions fileMode, int ownerId, int groupId,
|
||||
DateTime modificationTime)
|
||||
: this(name, new BuilderStreamExtentSource(stream), fileMode, ownerId, groupId, modificationTime) {}
|
||||
|
||||
public UnixBuildFileRecord(string name, BuilderExtentSource fileSource, UnixFilePermissions fileMode,
|
||||
int ownerId, int groupId, DateTime modificationTime)
|
||||
{
|
||||
Name = name;
|
||||
_source = fileSource;
|
||||
FileMode = fileMode;
|
||||
OwnerId = ownerId;
|
||||
GroupId = groupId;
|
||||
ModificationTime = modificationTime;
|
||||
}
|
||||
|
||||
public UnixFilePermissions FileMode { get; }
|
||||
|
||||
public int GroupId { get; }
|
||||
|
||||
public DateTime ModificationTime { get; }
|
||||
|
||||
public string Name { get; }
|
||||
|
||||
public int OwnerId { get; }
|
||||
|
||||
public BuilderExtent Fix(long pos)
|
||||
{
|
||||
return _source.Fix(pos);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,99 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Class whose instances represent a CHS (Cylinder, Head, Sector) address on a disk.
|
||||
/// </summary>
|
||||
/// <remarks>Instances of this class are immutable.</remarks>
|
||||
public sealed class ChsAddress
|
||||
{
|
||||
/// <summary>
|
||||
/// The address of the first sector on any disk.
|
||||
/// </summary>
|
||||
public static readonly ChsAddress First = new ChsAddress(0, 0, 1);
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the ChsAddress class.
|
||||
/// </summary>
|
||||
/// <param name="cylinder">The number of cylinders of the disk.</param>
|
||||
/// <param name="head">The number of heads (aka platters) of the disk.</param>
|
||||
/// <param name="sector">The number of sectors per track/cylinder of the disk.</param>
|
||||
public ChsAddress(int cylinder, int head, int sector)
|
||||
{
|
||||
Cylinder = cylinder;
|
||||
Head = head;
|
||||
Sector = sector;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the cylinder number (zero-based).
|
||||
/// </summary>
|
||||
public int Cylinder { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the head (zero-based).
|
||||
/// </summary>
|
||||
public int Head { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the sector number (one-based).
|
||||
/// </summary>
|
||||
public int Sector { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Determines if this object is equivalent to another.
|
||||
/// </summary>
|
||||
/// <param name="obj">The object to test against.</param>
|
||||
/// <returns><c>true</c> if the <paramref name="obj"/> is equivalent, else <c>false</c>.</returns>
|
||||
public override bool Equals(object obj)
|
||||
{
|
||||
if (obj == null || obj.GetType() != GetType())
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
ChsAddress other = (ChsAddress)obj;
|
||||
|
||||
return Cylinder == other.Cylinder && Head == other.Head && Sector == other.Sector;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Calculates the hash code for this object.
|
||||
/// </summary>
|
||||
/// <returns>The hash code.</returns>
|
||||
public override int GetHashCode()
|
||||
{
|
||||
return Cylinder.GetHashCode() ^ Head.GetHashCode() ^ Sector.GetHashCode();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets a string representation of this object, in the form (C/H/S).
|
||||
/// </summary>
|
||||
/// <returns>The string representation.</returns>
|
||||
public override string ToString()
|
||||
{
|
||||
return "(" + Cylinder + "/" + Head + "/" + Sector + ")";
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,75 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Class that identifies the role of each cluster in a file system.
|
||||
/// </summary>
|
||||
public sealed class ClusterMap
|
||||
{
|
||||
private readonly object[] _clusterToFileId;
|
||||
private readonly ClusterRoles[] _clusterToRole;
|
||||
private readonly Dictionary<object, string[]> _fileIdToPaths;
|
||||
|
||||
public ClusterMap(ClusterRoles[] clusterToRole, object[] clusterToFileId,
|
||||
Dictionary<object, string[]> fileIdToPaths)
|
||||
{
|
||||
_clusterToRole = clusterToRole;
|
||||
_clusterToFileId = clusterToFileId;
|
||||
_fileIdToPaths = fileIdToPaths;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the role of a cluster within the file system.
|
||||
/// </summary>
|
||||
/// <param name="cluster">The cluster to inspect.</param>
|
||||
/// <returns>The clusters role (or roles).</returns>
|
||||
public ClusterRoles GetRole(long cluster)
|
||||
{
|
||||
if (_clusterToRole == null || _clusterToRole.Length < cluster)
|
||||
{
|
||||
return ClusterRoles.None;
|
||||
}
|
||||
return _clusterToRole[cluster];
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Converts a cluster to a list of file names.
|
||||
/// </summary>
|
||||
/// <param name="cluster">The cluster to inspect.</param>
|
||||
/// <returns>A list of paths that map to the cluster.</returns>
|
||||
/// <remarks>A list is returned because on file systems with the notion of
|
||||
/// hard links, a cluster may correspond to multiple directory entries.</remarks>
|
||||
public string[] ClusterToPaths(long cluster)
|
||||
{
|
||||
if ((GetRole(cluster) & (ClusterRoles.DataFile | ClusterRoles.SystemFile)) != 0)
|
||||
{
|
||||
object fileId = _clusterToFileId[cluster];
|
||||
return _fileIdToPaths[fileId];
|
||||
}
|
||||
return new string[0];
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,50 +0,0 @@
|
|||
using System;
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Enumeration of possible cluster roles.
|
||||
/// </summary>
|
||||
/// <remarks>A cluster may be in more than one role.</remarks>
|
||||
[Flags]
|
||||
public enum ClusterRoles
|
||||
{
|
||||
/// <summary>
|
||||
/// Unknown, or unspecified role.
|
||||
/// </summary>
|
||||
None = 0x00,
|
||||
|
||||
/// <summary>
|
||||
/// Cluster is free.
|
||||
/// </summary>
|
||||
Free = 0x01,
|
||||
|
||||
/// <summary>
|
||||
/// Cluster is in use by a normal file.
|
||||
/// </summary>
|
||||
DataFile = 0x02,
|
||||
|
||||
/// <summary>
|
||||
/// Cluster is in use by a system file.
|
||||
/// </summary>
|
||||
/// <remarks>This isn't a file marked with the 'system' attribute,
|
||||
/// rather files that form part of the file system namespace but also
|
||||
/// form part of the file system meta-data.</remarks>
|
||||
SystemFile = 0x04,
|
||||
|
||||
/// <summary>
|
||||
/// Cluster is in use for meta-data.
|
||||
/// </summary>
|
||||
Metadata = 0x08,
|
||||
|
||||
/// <summary>
|
||||
/// Cluster contains the boot region.
|
||||
/// </summary>
|
||||
BootArea = 0x10,
|
||||
|
||||
/// <summary>
|
||||
/// Cluster is marked bad.
|
||||
/// </summary>
|
||||
Bad = 0x20
|
||||
}
|
||||
}
|
|
@ -1,93 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
|
||||
namespace DiscUtils.Compression
|
||||
{
|
||||
/// <summary>
|
||||
/// Implementation of the Adler-32 checksum algorithm.
|
||||
/// </summary>
|
||||
public class Adler32
|
||||
{
|
||||
private uint _a;
|
||||
private uint _b;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the Adler32 class.
|
||||
/// </summary>
|
||||
public Adler32()
|
||||
{
|
||||
_a = 1;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the checksum of all data processed so far.
|
||||
/// </summary>
|
||||
public int Value
|
||||
{
|
||||
get { return (int)(_b << 16 | _a); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Provides data that should be checksummed.
|
||||
/// </summary>
|
||||
/// <param name="buffer">Buffer containing the data to checksum.</param>
|
||||
/// <param name="offset">Offset of the first byte to checksum.</param>
|
||||
/// <param name="count">The number of bytes to checksum.</param>
|
||||
/// <remarks>
|
||||
/// Call this method repeatedly until all checksummed
|
||||
/// data has been processed.
|
||||
/// </remarks>
|
||||
public void Process(byte[] buffer, int offset, int count)
|
||||
{
|
||||
if (buffer == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(buffer));
|
||||
}
|
||||
|
||||
if (offset < 0 || offset > buffer.Length)
|
||||
{
|
||||
throw new ArgumentException("Offset outside of array bounds", nameof(offset));
|
||||
}
|
||||
|
||||
if (count < 0 || offset + count > buffer.Length)
|
||||
{
|
||||
throw new ArgumentException("Array index out of bounds", nameof(count));
|
||||
}
|
||||
|
||||
int processed = 0;
|
||||
while (processed < count)
|
||||
{
|
||||
int innerEnd = Math.Min(count, processed + 2000);
|
||||
while (processed < innerEnd)
|
||||
{
|
||||
_a += buffer[processed++];
|
||||
_b += _a;
|
||||
}
|
||||
|
||||
_a %= 65521;
|
||||
_b %= 65521;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,141 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
//
|
||||
// Based on "libbzip2", Copyright (C) 1996-2007 Julian R Seward.
|
||||
//
|
||||
|
||||
using System.IO;
|
||||
|
||||
namespace DiscUtils.Compression
|
||||
{
|
||||
internal class BZip2BlockDecoder
|
||||
{
|
||||
private readonly InverseBurrowsWheeler _inverseBurrowsWheeler;
|
||||
|
||||
public BZip2BlockDecoder(int blockSize)
|
||||
{
|
||||
_inverseBurrowsWheeler = new InverseBurrowsWheeler(blockSize);
|
||||
}
|
||||
|
||||
public uint Crc { get; private set; }
|
||||
|
||||
public int Process(BitStream bitstream, byte[] outputBuffer, int outputBufferOffset)
|
||||
{
|
||||
Crc = 0;
|
||||
for (int i = 0; i < 4; ++i)
|
||||
{
|
||||
Crc = (Crc << 8) | bitstream.Read(8);
|
||||
}
|
||||
|
||||
bool rand = bitstream.Read(1) != 0;
|
||||
int origPtr = (int)bitstream.Read(24);
|
||||
|
||||
int thisBlockSize = ReadBuffer(bitstream, outputBuffer, outputBufferOffset);
|
||||
|
||||
_inverseBurrowsWheeler.OriginalIndex = origPtr;
|
||||
_inverseBurrowsWheeler.Process(outputBuffer, outputBufferOffset, thisBlockSize, outputBuffer,
|
||||
outputBufferOffset);
|
||||
|
||||
if (rand)
|
||||
{
|
||||
BZip2Randomizer randomizer = new BZip2Randomizer();
|
||||
randomizer.Process(outputBuffer, outputBufferOffset, thisBlockSize, outputBuffer, outputBufferOffset);
|
||||
}
|
||||
|
||||
return thisBlockSize;
|
||||
}
|
||||
|
||||
private static int ReadBuffer(BitStream bitstream, byte[] buffer, int offset)
|
||||
{
|
||||
// The MTF state
|
||||
int numInUse = 0;
|
||||
MoveToFront moveFrontTransform = new MoveToFront();
|
||||
bool[] inUseGroups = new bool[16];
|
||||
for (int i = 0; i < 16; ++i)
|
||||
{
|
||||
inUseGroups[i] = bitstream.Read(1) != 0;
|
||||
}
|
||||
|
||||
for (int i = 0; i < 256; ++i)
|
||||
{
|
||||
if (inUseGroups[i / 16])
|
||||
{
|
||||
if (bitstream.Read(1) != 0)
|
||||
{
|
||||
moveFrontTransform.Set(numInUse, (byte)i);
|
||||
numInUse++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Initialize 'virtual' Huffman tree from bitstream
|
||||
BZip2CombinedHuffmanTrees huffmanTree = new BZip2CombinedHuffmanTrees(bitstream, numInUse + 2);
|
||||
|
||||
// Main loop reading data
|
||||
int readBytes = 0;
|
||||
while (true)
|
||||
{
|
||||
uint symbol = huffmanTree.NextSymbol();
|
||||
|
||||
if (symbol < 2)
|
||||
{
|
||||
// RLE, with length stored in a binary-style format
|
||||
uint runLength = 0;
|
||||
int bitShift = 0;
|
||||
while (symbol < 2)
|
||||
{
|
||||
runLength += (symbol + 1) << bitShift;
|
||||
bitShift++;
|
||||
|
||||
symbol = huffmanTree.NextSymbol();
|
||||
}
|
||||
|
||||
byte b = moveFrontTransform.Head;
|
||||
while (runLength > 0)
|
||||
{
|
||||
buffer[offset + readBytes] = b;
|
||||
++readBytes;
|
||||
--runLength;
|
||||
}
|
||||
}
|
||||
|
||||
if (symbol <= numInUse)
|
||||
{
|
||||
// Single byte
|
||||
byte b = moveFrontTransform.GetAndMove((int)symbol - 1);
|
||||
buffer[offset + readBytes] = b;
|
||||
++readBytes;
|
||||
}
|
||||
else if (symbol == numInUse + 1)
|
||||
{
|
||||
// End of block marker
|
||||
return readBytes;
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new InvalidDataException("Invalid symbol from Huffman table");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,134 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
//
|
||||
// Based on "libbzip2", Copyright (C) 1996-2007 Julian R Seward.
|
||||
//
|
||||
|
||||
using System.IO;
|
||||
|
||||
namespace DiscUtils.Compression
|
||||
{
|
||||
/// <summary>
|
||||
/// Represents scheme used by BZip2 where multiple Huffman trees are used as a
|
||||
/// virtual Huffman tree, with a logical selector every 50 bits in the bit stream.
|
||||
/// </summary>
|
||||
internal class BZip2CombinedHuffmanTrees
|
||||
{
|
||||
private HuffmanTree _activeTree;
|
||||
private readonly BitStream _bitstream;
|
||||
private int _nextSelector;
|
||||
private byte[] _selectors;
|
||||
private int _symbolsToNextSelector;
|
||||
private HuffmanTree[] _trees;
|
||||
|
||||
public BZip2CombinedHuffmanTrees(BitStream bitstream, int maxSymbols)
|
||||
{
|
||||
_bitstream = bitstream;
|
||||
|
||||
Initialize(maxSymbols);
|
||||
}
|
||||
|
||||
public uint NextSymbol()
|
||||
{
|
||||
if (_symbolsToNextSelector == 0)
|
||||
{
|
||||
_symbolsToNextSelector = 50;
|
||||
_activeTree = _trees[_selectors[_nextSelector]];
|
||||
_nextSelector++;
|
||||
}
|
||||
|
||||
_symbolsToNextSelector--;
|
||||
|
||||
return _activeTree.NextSymbol(_bitstream);
|
||||
}
|
||||
|
||||
private void Initialize(int maxSymbols)
|
||||
{
|
||||
int numTrees = (int)_bitstream.Read(3);
|
||||
if (numTrees < 2 || numTrees > 6)
|
||||
{
|
||||
throw new InvalidDataException("Invalid number of tables");
|
||||
}
|
||||
|
||||
int numSelectors = (int)_bitstream.Read(15);
|
||||
if (numSelectors < 1)
|
||||
{
|
||||
throw new InvalidDataException("Invalid number of selectors");
|
||||
}
|
||||
|
||||
_selectors = new byte[numSelectors];
|
||||
MoveToFront mtf = new MoveToFront(numTrees, true);
|
||||
for (int i = 0; i < numSelectors; ++i)
|
||||
{
|
||||
_selectors[i] = mtf.GetAndMove(CountSetBits(numTrees));
|
||||
}
|
||||
|
||||
_trees = new HuffmanTree[numTrees];
|
||||
for (int t = 0; t < numTrees; ++t)
|
||||
{
|
||||
uint[] lengths = new uint[maxSymbols];
|
||||
|
||||
uint len = _bitstream.Read(5);
|
||||
for (int i = 0; i < maxSymbols; ++i)
|
||||
{
|
||||
if (len < 1 || len > 20)
|
||||
{
|
||||
throw new InvalidDataException("Invalid length constructing Huffman tree");
|
||||
}
|
||||
|
||||
while (_bitstream.Read(1) != 0)
|
||||
{
|
||||
len = _bitstream.Read(1) == 0 ? len + 1 : len - 1;
|
||||
|
||||
if (len < 1 || len > 20)
|
||||
{
|
||||
throw new InvalidDataException("Invalid length constructing Huffman tree");
|
||||
}
|
||||
}
|
||||
|
||||
lengths[i] = len;
|
||||
}
|
||||
|
||||
_trees[t] = new HuffmanTree(lengths);
|
||||
}
|
||||
|
||||
_symbolsToNextSelector = 0;
|
||||
_nextSelector = 0;
|
||||
}
|
||||
|
||||
private byte CountSetBits(int max)
|
||||
{
|
||||
byte val = 0;
|
||||
while (_bitstream.Read(1) != 0)
|
||||
{
|
||||
val++;
|
||||
if (val >= max)
|
||||
{
|
||||
throw new InvalidDataException("Exceeded max number of consecutive bits");
|
||||
}
|
||||
}
|
||||
|
||||
return val;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,348 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
//
|
||||
// Based on "libbzip2", Copyright (C) 1996-2007 Julian R Seward.
|
||||
//
|
||||
|
||||
using System;
|
||||
using System.IO;
|
||||
using DiscUtils.Internal;
|
||||
using DiscUtils.Streams;
|
||||
|
||||
namespace DiscUtils.Compression
|
||||
{
|
||||
/// <summary>
|
||||
/// Implementation of a BZip2 decoder.
|
||||
/// </summary>
|
||||
public sealed class BZip2DecoderStream : Stream
|
||||
{
|
||||
private readonly BitStream _bitstream;
|
||||
|
||||
private readonly byte[] _blockBuffer;
|
||||
private uint _blockCrc;
|
||||
private readonly BZip2BlockDecoder _blockDecoder;
|
||||
private Crc32 _calcBlockCrc;
|
||||
private uint _calcCompoundCrc;
|
||||
private uint _compoundCrc;
|
||||
private Stream _compressedStream;
|
||||
|
||||
private bool _eof;
|
||||
private readonly Ownership _ownsCompressed;
|
||||
private long _position;
|
||||
private BZip2RleStream _rleStream;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the BZip2DecoderStream class.
|
||||
/// </summary>
|
||||
/// <param name="stream">The compressed input stream.</param>
|
||||
/// <param name="ownsStream">Whether ownership of stream passes to the new instance.</param>
|
||||
public BZip2DecoderStream(Stream stream, Ownership ownsStream)
|
||||
{
|
||||
_compressedStream = stream;
|
||||
_ownsCompressed = ownsStream;
|
||||
|
||||
_bitstream = new BigEndianBitStream(new BufferedStream(stream));
|
||||
|
||||
// The Magic BZh
|
||||
byte[] magic = new byte[3];
|
||||
magic[0] = (byte)_bitstream.Read(8);
|
||||
magic[1] = (byte)_bitstream.Read(8);
|
||||
magic[2] = (byte)_bitstream.Read(8);
|
||||
if (magic[0] != 0x42 || magic[1] != 0x5A || magic[2] != 0x68)
|
||||
{
|
||||
throw new InvalidDataException("Bad magic at start of stream");
|
||||
}
|
||||
|
||||
// The size of the decompression blocks in multiples of 100,000
|
||||
int blockSize = (int)_bitstream.Read(8) - 0x30;
|
||||
if (blockSize < 1 || blockSize > 9)
|
||||
{
|
||||
throw new InvalidDataException("Unexpected block size in header: " + blockSize);
|
||||
}
|
||||
|
||||
blockSize *= 100000;
|
||||
|
||||
_rleStream = new BZip2RleStream();
|
||||
_blockDecoder = new BZip2BlockDecoder(blockSize);
|
||||
_blockBuffer = new byte[blockSize];
|
||||
|
||||
if (ReadBlock() == 0)
|
||||
{
|
||||
_eof = true;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets an indication of whether read access is permitted.
|
||||
/// </summary>
|
||||
public override bool CanRead
|
||||
{
|
||||
get { return true; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets an indication of whether seeking is permitted.
|
||||
/// </summary>
|
||||
public override bool CanSeek
|
||||
{
|
||||
get { return false; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets an indication of whether write access is permitted.
|
||||
/// </summary>
|
||||
public override bool CanWrite
|
||||
{
|
||||
get { return false; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the length of the stream (the capacity of the underlying buffer).
|
||||
/// </summary>
|
||||
public override long Length
|
||||
{
|
||||
get { throw new NotSupportedException(); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets and sets the current position within the stream.
|
||||
/// </summary>
|
||||
public override long Position
|
||||
{
|
||||
get { return _position; }
|
||||
set { throw new NotSupportedException(); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Flushes all data to the underlying storage.
|
||||
/// </summary>
|
||||
public override void Flush()
|
||||
{
|
||||
throw new NotSupportedException();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Reads a number of bytes from the stream.
|
||||
/// </summary>
|
||||
/// <param name="buffer">The destination buffer.</param>
|
||||
/// <param name="offset">The start offset within the destination buffer.</param>
|
||||
/// <param name="count">The number of bytes to read.</param>
|
||||
/// <returns>The number of bytes read.</returns>
|
||||
public override int Read(byte[] buffer, int offset, int count)
|
||||
{
|
||||
if (buffer == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(buffer));
|
||||
}
|
||||
|
||||
if (buffer.Length < offset + count)
|
||||
{
|
||||
throw new ArgumentException("Buffer smaller than declared");
|
||||
}
|
||||
|
||||
if (offset < 0)
|
||||
{
|
||||
throw new ArgumentException("Offset less than zero", nameof(offset));
|
||||
}
|
||||
|
||||
if (count < 0)
|
||||
{
|
||||
throw new ArgumentException("Count less than zero", nameof(count));
|
||||
}
|
||||
|
||||
if (_eof)
|
||||
{
|
||||
throw new IOException("Attempt to read beyond end of stream");
|
||||
}
|
||||
|
||||
if (count == 0)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
int numRead = _rleStream.Read(buffer, offset, count);
|
||||
if (numRead == 0)
|
||||
{
|
||||
// If there was an existing block, check it's crc.
|
||||
if (_calcBlockCrc != null)
|
||||
{
|
||||
if (_blockCrc != _calcBlockCrc.Value)
|
||||
{
|
||||
throw new InvalidDataException("Decompression failed - block CRC mismatch");
|
||||
}
|
||||
|
||||
_calcCompoundCrc = ((_calcCompoundCrc << 1) | (_calcCompoundCrc >> 31)) ^ _blockCrc;
|
||||
}
|
||||
|
||||
// Read a new block (if any), if none - check the overall CRC before returning
|
||||
if (ReadBlock() == 0)
|
||||
{
|
||||
_eof = true;
|
||||
if (_calcCompoundCrc != _compoundCrc)
|
||||
{
|
||||
throw new InvalidDataException("Decompression failed - compound CRC");
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
numRead = _rleStream.Read(buffer, offset, count);
|
||||
}
|
||||
|
||||
_calcBlockCrc.Process(buffer, offset, numRead);
|
||||
|
||||
// Pre-read next block, so a client that knows the decompressed length will still
|
||||
// have the overall CRC calculated.
|
||||
if (_rleStream.AtEof)
|
||||
{
|
||||
// If there was an existing block, check it's crc.
|
||||
if (_calcBlockCrc != null)
|
||||
{
|
||||
if (_blockCrc != _calcBlockCrc.Value)
|
||||
{
|
||||
throw new InvalidDataException("Decompression failed - block CRC mismatch");
|
||||
}
|
||||
}
|
||||
|
||||
_calcCompoundCrc = ((_calcCompoundCrc << 1) | (_calcCompoundCrc >> 31)) ^ _blockCrc;
|
||||
if (ReadBlock() == 0)
|
||||
{
|
||||
_eof = true;
|
||||
if (_calcCompoundCrc != _compoundCrc)
|
||||
{
|
||||
throw new InvalidDataException("Decompression failed - compound CRC mismatch");
|
||||
}
|
||||
|
||||
return numRead;
|
||||
}
|
||||
}
|
||||
|
||||
_position += numRead;
|
||||
return numRead;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Changes the current stream position.
|
||||
/// </summary>
|
||||
/// <param name="offset">The origin-relative stream position.</param>
|
||||
/// <param name="origin">The origin for the stream position.</param>
|
||||
/// <returns>The new stream position.</returns>
|
||||
public override long Seek(long offset, SeekOrigin origin)
|
||||
{
|
||||
throw new NotSupportedException();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Sets the length of the stream (the underlying buffer's capacity).
|
||||
/// </summary>
|
||||
/// <param name="value">The new length of the stream.</param>
|
||||
public override void SetLength(long value)
|
||||
{
|
||||
throw new NotSupportedException();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Writes a buffer to the stream.
|
||||
/// </summary>
|
||||
/// <param name="buffer">The buffer to write.</param>
|
||||
/// <param name="offset">The starting offset within buffer.</param>
|
||||
/// <param name="count">The number of bytes to write.</param>
|
||||
public override void Write(byte[] buffer, int offset, int count)
|
||||
{
|
||||
throw new NotSupportedException();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Releases underlying resources.
|
||||
/// </summary>
|
||||
/// <param name="disposing">Whether this method is called from Dispose.</param>
|
||||
protected override void Dispose(bool disposing)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (disposing)
|
||||
{
|
||||
if (_compressedStream != null && _ownsCompressed == Ownership.Dispose)
|
||||
{
|
||||
_compressedStream.Dispose();
|
||||
}
|
||||
|
||||
_compressedStream = null;
|
||||
|
||||
if (_rleStream != null)
|
||||
{
|
||||
_rleStream.Dispose();
|
||||
_rleStream = null;
|
||||
}
|
||||
}
|
||||
}
|
||||
finally
|
||||
{
|
||||
base.Dispose(disposing);
|
||||
}
|
||||
}
|
||||
|
||||
private int ReadBlock()
|
||||
{
|
||||
ulong marker = ReadMarker();
|
||||
if (marker == 0x314159265359)
|
||||
{
|
||||
int blockSize = _blockDecoder.Process(_bitstream, _blockBuffer, 0);
|
||||
_rleStream.Reset(_blockBuffer, 0, blockSize);
|
||||
_blockCrc = _blockDecoder.Crc;
|
||||
_calcBlockCrc = new Crc32BigEndian(Crc32Algorithm.Common);
|
||||
return blockSize;
|
||||
}
|
||||
if (marker == 0x177245385090)
|
||||
{
|
||||
_compoundCrc = ReadUint();
|
||||
return 0;
|
||||
}
|
||||
throw new InvalidDataException("Found invalid marker in stream");
|
||||
}
|
||||
|
||||
private uint ReadUint()
|
||||
{
|
||||
uint val = 0;
|
||||
|
||||
for (int i = 0; i < 4; ++i)
|
||||
{
|
||||
val = (val << 8) | _bitstream.Read(8);
|
||||
}
|
||||
|
||||
return val;
|
||||
}
|
||||
|
||||
private ulong ReadMarker()
|
||||
{
|
||||
ulong marker = 0;
|
||||
|
||||
for (int i = 0; i < 6; ++i)
|
||||
{
|
||||
marker = (marker << 8) | _bitstream.Read(8);
|
||||
}
|
||||
|
||||
return marker;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,124 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
//
|
||||
// Based on "libbzip2", Copyright (C) 1996-2007 Julian R Seward.
|
||||
//
|
||||
|
||||
using System;
|
||||
|
||||
namespace DiscUtils.Compression
|
||||
{
|
||||
internal class BZip2Randomizer : DataBlockTransform
|
||||
{
|
||||
private static readonly int[] RandomVals =
|
||||
{
|
||||
619, 720, 127, 481, 931, 816, 813, 233, 566, 247,
|
||||
985, 724, 205, 454, 863, 491, 741, 242, 949, 214,
|
||||
733, 859, 335, 708, 621, 574, 73, 654, 730, 472,
|
||||
419, 436, 278, 496, 867, 210, 399, 680, 480, 51,
|
||||
878, 465, 811, 169, 869, 675, 611, 697, 867, 561,
|
||||
862, 687, 507, 283, 482, 129, 807, 591, 733, 623,
|
||||
150, 238, 59, 379, 684, 877, 625, 169, 643, 105,
|
||||
170, 607, 520, 932, 727, 476, 693, 425, 174, 647,
|
||||
73, 122, 335, 530, 442, 853, 695, 249, 445, 515,
|
||||
909, 545, 703, 919, 874, 474, 882, 500, 594, 612,
|
||||
641, 801, 220, 162, 819, 984, 589, 513, 495, 799,
|
||||
161, 604, 958, 533, 221, 400, 386, 867, 600, 782,
|
||||
382, 596, 414, 171, 516, 375, 682, 485, 911, 276,
|
||||
98, 553, 163, 354, 666, 933, 424, 341, 533, 870,
|
||||
227, 730, 475, 186, 263, 647, 537, 686, 600, 224,
|
||||
469, 68, 770, 919, 190, 373, 294, 822, 808, 206,
|
||||
184, 943, 795, 384, 383, 461, 404, 758, 839, 887,
|
||||
715, 67, 618, 276, 204, 918, 873, 777, 604, 560,
|
||||
951, 160, 578, 722, 79, 804, 96, 409, 713, 940,
|
||||
652, 934, 970, 447, 318, 353, 859, 672, 112, 785,
|
||||
645, 863, 803, 350, 139, 93, 354, 99, 820, 908,
|
||||
609, 772, 154, 274, 580, 184, 79, 626, 630, 742,
|
||||
653, 282, 762, 623, 680, 81, 927, 626, 789, 125,
|
||||
411, 521, 938, 300, 821, 78, 343, 175, 128, 250,
|
||||
170, 774, 972, 275, 999, 639, 495, 78, 352, 126,
|
||||
857, 956, 358, 619, 580, 124, 737, 594, 701, 612,
|
||||
669, 112, 134, 694, 363, 992, 809, 743, 168, 974,
|
||||
944, 375, 748, 52, 600, 747, 642, 182, 862, 81,
|
||||
344, 805, 988, 739, 511, 655, 814, 334, 249, 515,
|
||||
897, 955, 664, 981, 649, 113, 974, 459, 893, 228,
|
||||
433, 837, 553, 268, 926, 240, 102, 654, 459, 51,
|
||||
686, 754, 806, 760, 493, 403, 415, 394, 687, 700,
|
||||
946, 670, 656, 610, 738, 392, 760, 799, 887, 653,
|
||||
978, 321, 576, 617, 626, 502, 894, 679, 243, 440,
|
||||
680, 879, 194, 572, 640, 724, 926, 56, 204, 700,
|
||||
707, 151, 457, 449, 797, 195, 791, 558, 945, 679,
|
||||
297, 59, 87, 824, 713, 663, 412, 693, 342, 606,
|
||||
134, 108, 571, 364, 631, 212, 174, 643, 304, 329,
|
||||
343, 97, 430, 751, 497, 314, 983, 374, 822, 928,
|
||||
140, 206, 73, 263, 980, 736, 876, 478, 430, 305,
|
||||
170, 514, 364, 692, 829, 82, 855, 953, 676, 246,
|
||||
369, 970, 294, 750, 807, 827, 150, 790, 288, 923,
|
||||
804, 378, 215, 828, 592, 281, 565, 555, 710, 82,
|
||||
896, 831, 547, 261, 524, 462, 293, 465, 502, 56,
|
||||
661, 821, 976, 991, 658, 869, 905, 758, 745, 193,
|
||||
768, 550, 608, 933, 378, 286, 215, 979, 792, 961,
|
||||
61, 688, 793, 644, 986, 403, 106, 366, 905, 644,
|
||||
372, 567, 466, 434, 645, 210, 389, 550, 919, 135,
|
||||
780, 773, 635, 389, 707, 100, 626, 958, 165, 504,
|
||||
920, 176, 193, 713, 857, 265, 203, 50, 668, 108,
|
||||
645, 990, 626, 197, 510, 357, 358, 850, 858, 364,
|
||||
936, 638
|
||||
};
|
||||
|
||||
protected override bool BuffersMustNotOverlap
|
||||
{
|
||||
get { return false; }
|
||||
}
|
||||
|
||||
protected override int DoProcess(byte[] input, int inputOffset, int inputCount, byte[] output, int outputOffset)
|
||||
{
|
||||
if (input != output || inputOffset != outputOffset)
|
||||
{
|
||||
Array.Copy(input, inputOffset, output, outputOffset, inputCount);
|
||||
}
|
||||
|
||||
int randIndex = 1;
|
||||
int nextByte = RandomVals[0] - 2;
|
||||
|
||||
while (nextByte < inputCount)
|
||||
{
|
||||
output[nextByte] ^= 1;
|
||||
nextByte += RandomVals[randIndex++];
|
||||
randIndex &= 0x1FF;
|
||||
}
|
||||
|
||||
return inputCount;
|
||||
}
|
||||
|
||||
protected override int MaxOutputCount(int inputCount)
|
||||
{
|
||||
return inputCount;
|
||||
}
|
||||
|
||||
protected override int MinOutputCount(int inputCount)
|
||||
{
|
||||
return inputCount;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,157 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
//
|
||||
// Based on "libbzip2", Copyright (C) 1996-2007 Julian R Seward.
|
||||
//
|
||||
|
||||
using System;
|
||||
using System.IO;
|
||||
|
||||
namespace DiscUtils.Compression
|
||||
{
|
||||
internal class BZip2RleStream : Stream
|
||||
{
|
||||
private byte[] _blockBuffer;
|
||||
private int _blockOffset;
|
||||
private int _blockRemaining;
|
||||
private byte _lastByte;
|
||||
|
||||
private int _numSame;
|
||||
private long _position;
|
||||
private int _runBytesOutstanding;
|
||||
|
||||
public bool AtEof
|
||||
{
|
||||
get { return _runBytesOutstanding == 0 && _blockRemaining == 0; }
|
||||
}
|
||||
|
||||
public override bool CanRead
|
||||
{
|
||||
get { return true; }
|
||||
}
|
||||
|
||||
public override bool CanSeek
|
||||
{
|
||||
get { return false; }
|
||||
}
|
||||
|
||||
public override bool CanWrite
|
||||
{
|
||||
get { return false; }
|
||||
}
|
||||
|
||||
public override long Length
|
||||
{
|
||||
get { throw new NotSupportedException(); }
|
||||
}
|
||||
|
||||
public override long Position
|
||||
{
|
||||
get { return _position; }
|
||||
set { throw new NotSupportedException(); }
|
||||
}
|
||||
|
||||
public void Reset(byte[] buffer, int offset, int count)
|
||||
{
|
||||
_position = 0;
|
||||
_blockBuffer = buffer;
|
||||
_blockOffset = offset;
|
||||
_blockRemaining = count;
|
||||
_numSame = -1;
|
||||
_lastByte = 0;
|
||||
_runBytesOutstanding = 0;
|
||||
}
|
||||
|
||||
public override void Flush()
|
||||
{
|
||||
throw new NotSupportedException();
|
||||
}
|
||||
|
||||
public override int Read(byte[] buffer, int offset, int count)
|
||||
{
|
||||
int numRead = 0;
|
||||
|
||||
while (numRead < count && _runBytesOutstanding > 0)
|
||||
{
|
||||
int runCount = Math.Min(_runBytesOutstanding, count);
|
||||
for (int i = 0; i < runCount; ++i)
|
||||
{
|
||||
buffer[offset + numRead] = _lastByte;
|
||||
}
|
||||
|
||||
_runBytesOutstanding -= runCount;
|
||||
numRead += runCount;
|
||||
}
|
||||
|
||||
while (numRead < count && _blockRemaining > 0)
|
||||
{
|
||||
byte b = _blockBuffer[_blockOffset];
|
||||
++_blockOffset;
|
||||
--_blockRemaining;
|
||||
|
||||
if (_numSame == 4)
|
||||
{
|
||||
int runCount = Math.Min(b, count - numRead);
|
||||
for (int i = 0; i < runCount; ++i)
|
||||
{
|
||||
buffer[offset + numRead] = _lastByte;
|
||||
numRead++;
|
||||
}
|
||||
|
||||
_runBytesOutstanding = b - runCount;
|
||||
_numSame = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (b != _lastByte || _numSame <= 0)
|
||||
{
|
||||
_lastByte = b;
|
||||
_numSame = 0;
|
||||
}
|
||||
|
||||
buffer[offset + numRead] = b;
|
||||
numRead++;
|
||||
_numSame++;
|
||||
}
|
||||
}
|
||||
|
||||
_position += numRead;
|
||||
return numRead;
|
||||
}
|
||||
|
||||
public override long Seek(long offset, SeekOrigin origin)
|
||||
{
|
||||
throw new NotSupportedException();
|
||||
}
|
||||
|
||||
public override void SetLength(long value)
|
||||
{
|
||||
throw new NotSupportedException();
|
||||
}
|
||||
|
||||
public override void Write(byte[] buffer, int offset, int count)
|
||||
{
|
||||
throw new NotSupportedException();
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,94 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System.IO;
|
||||
|
||||
namespace DiscUtils.Compression
|
||||
{
|
||||
/// <summary>
|
||||
/// Converts a byte stream into a bit stream.
|
||||
/// </summary>
|
||||
internal class BigEndianBitStream : BitStream
|
||||
{
|
||||
private uint _buffer;
|
||||
private int _bufferAvailable;
|
||||
private readonly Stream _byteStream;
|
||||
|
||||
private readonly byte[] _readBuffer = new byte[2];
|
||||
|
||||
public BigEndianBitStream(Stream byteStream)
|
||||
{
|
||||
_byteStream = byteStream;
|
||||
}
|
||||
|
||||
public override int MaxReadAhead
|
||||
{
|
||||
get { return 16; }
|
||||
}
|
||||
|
||||
public override uint Read(int count)
|
||||
{
|
||||
if (count > 16)
|
||||
{
|
||||
uint result = Read(16) << (count - 16);
|
||||
return result | Read(count - 16);
|
||||
}
|
||||
|
||||
EnsureBufferFilled();
|
||||
|
||||
_bufferAvailable -= count;
|
||||
|
||||
uint mask = (uint)((1 << count) - 1);
|
||||
|
||||
return (_buffer >> _bufferAvailable) & mask;
|
||||
}
|
||||
|
||||
public override uint Peek(int count)
|
||||
{
|
||||
EnsureBufferFilled();
|
||||
|
||||
uint mask = (uint)((1 << count) - 1);
|
||||
|
||||
return (_buffer >> (_bufferAvailable - count)) & mask;
|
||||
}
|
||||
|
||||
public override void Consume(int count)
|
||||
{
|
||||
EnsureBufferFilled();
|
||||
|
||||
_bufferAvailable -= count;
|
||||
}
|
||||
|
||||
private void EnsureBufferFilled()
|
||||
{
|
||||
if (_bufferAvailable < 16)
|
||||
{
|
||||
_readBuffer[0] = 0;
|
||||
_readBuffer[1] = 0;
|
||||
_byteStream.Read(_readBuffer, 0, 2);
|
||||
|
||||
_buffer = _buffer << 16 | (uint)(_readBuffer[0] << 8) | _readBuffer[1];
|
||||
_bufferAvailable += 16;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,60 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
namespace DiscUtils.Compression
|
||||
{
|
||||
/// <summary>
|
||||
/// Base class for bit streams.
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// The rules for conversion of a byte stream to a bit stream vary
|
||||
/// between implementations.
|
||||
/// </remarks>
|
||||
internal abstract class BitStream
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets the maximum number of bits that can be peeked on the stream.
|
||||
/// </summary>
|
||||
public abstract int MaxReadAhead { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Reads bits from the stream.
|
||||
/// </summary>
|
||||
/// <param name="count">The number of bits to read.</param>
|
||||
/// <returns>The bits as a UInt32.</returns>
|
||||
public abstract uint Read(int count);
|
||||
|
||||
/// <summary>
|
||||
/// Queries data from the stream.
|
||||
/// </summary>
|
||||
/// <param name="count">The number of bits to query.</param>
|
||||
/// <returns>The bits as a UInt32.</returns>
|
||||
/// <remarks>This method does not consume the bits (i.e. move the file pointer).</remarks>
|
||||
public abstract uint Peek(int count);
|
||||
|
||||
/// <summary>
|
||||
/// Consumes bits from the stream without returning them.
|
||||
/// </summary>
|
||||
/// <param name="count">The number of bits to consume.</param>
|
||||
public abstract void Consume(int count);
|
||||
}
|
||||
}
|
|
@ -1,64 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
namespace DiscUtils.Compression
|
||||
{
|
||||
/// <summary>
|
||||
/// Base class for block compression algorithms.
|
||||
/// </summary>
|
||||
public abstract class BlockCompressor
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets or sets the block size parameter to the algorithm.
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// Some algorithms may use this to control both compression and decompression, others may
|
||||
/// only use it to control compression. Some may ignore it entirely.
|
||||
/// </remarks>
|
||||
public int BlockSize { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Compresses some data.
|
||||
/// </summary>
|
||||
/// <param name="source">The uncompressed input.</param>
|
||||
/// <param name="sourceOffset">Offset of the input data in <c>source</c>.</param>
|
||||
/// <param name="sourceLength">The amount of uncompressed data.</param>
|
||||
/// <param name="compressed">The destination for the output compressed data.</param>
|
||||
/// <param name="compressedOffset">Offset for the output data in <c>compressed</c>.</param>
|
||||
/// <param name="compressedLength">The maximum size of the compressed data on input, and the actual size on output.</param>
|
||||
/// <returns>Indication of success, or indication the data could not compress into the requested space.</returns>
|
||||
public abstract CompressionResult Compress(byte[] source, int sourceOffset, int sourceLength, byte[] compressed,
|
||||
int compressedOffset, ref int compressedLength);
|
||||
|
||||
/// <summary>
|
||||
/// Decompresses some data.
|
||||
/// </summary>
|
||||
/// <param name="source">The compressed input.</param>
|
||||
/// <param name="sourceOffset">Offset of the input data in <c>source</c>.</param>
|
||||
/// <param name="sourceLength">The amount of compressed data.</param>
|
||||
/// <param name="decompressed">The destination for the output decompressed data.</param>
|
||||
/// <param name="decompressedOffset">Offset for the output data in <c>decompressed</c>.</param>
|
||||
/// <returns>The amount of decompressed data.</returns>
|
||||
public abstract int Decompress(byte[] source, int sourceOffset, int sourceLength, byte[] decompressed,
|
||||
int decompressedOffset);
|
||||
}
|
||||
}
|
|
@ -1,50 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
namespace DiscUtils.Compression
|
||||
{
|
||||
/// <summary>
|
||||
/// Possible results of attempting to compress data.
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// A compression routine <i>may</i> return <c>Compressed</c>, even if the data
|
||||
/// was 'all zeros' or increased in size. The <c>AllZeros</c> and <c>Incompressible</c>
|
||||
/// values are for algorithms that include special detection for these cases.
|
||||
/// </remarks>
|
||||
public enum CompressionResult
|
||||
{
|
||||
/// <summary>
|
||||
/// The data compressed succesfully.
|
||||
/// </summary>
|
||||
Compressed,
|
||||
|
||||
/// <summary>
|
||||
/// The data was all-zero's.
|
||||
/// </summary>
|
||||
AllZeros,
|
||||
|
||||
/// <summary>
|
||||
/// The data was incompressible (could not fit into destination buffer).
|
||||
/// </summary>
|
||||
Incompressible
|
||||
}
|
||||
}
|
|
@ -1,70 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
using System.Globalization;
|
||||
|
||||
namespace DiscUtils.Compression
|
||||
{
|
||||
internal abstract class DataBlockTransform
|
||||
{
|
||||
protected abstract bool BuffersMustNotOverlap { get; }
|
||||
|
||||
public int Process(byte[] input, int inputOffset, int inputCount, byte[] output, int outputOffset)
|
||||
{
|
||||
if (output.Length < outputOffset + (long)MinOutputCount(inputCount))
|
||||
{
|
||||
throw new ArgumentException(
|
||||
string.Format(
|
||||
CultureInfo.InvariantCulture,
|
||||
"Output buffer to small, must be at least {0} bytes may need to be {1} bytes",
|
||||
MinOutputCount(inputCount),
|
||||
MaxOutputCount(inputCount)));
|
||||
}
|
||||
|
||||
if (BuffersMustNotOverlap)
|
||||
{
|
||||
int maxOut = MaxOutputCount(inputCount);
|
||||
|
||||
if (input == output
|
||||
&& (inputOffset + (long)inputCount > outputOffset)
|
||||
&& (inputOffset <= outputOffset + (long)maxOut))
|
||||
{
|
||||
byte[] tempBuffer = new byte[maxOut];
|
||||
|
||||
int outCount = DoProcess(input, inputOffset, inputCount, tempBuffer, 0);
|
||||
Array.Copy(tempBuffer, 0, output, outputOffset, outCount);
|
||||
|
||||
return outCount;
|
||||
}
|
||||
}
|
||||
|
||||
return DoProcess(input, inputOffset, inputCount, output, outputOffset);
|
||||
}
|
||||
|
||||
protected abstract int DoProcess(byte[] input, int inputOffset, int inputCount, byte[] output, int outputOffset);
|
||||
|
||||
protected abstract int MaxOutputCount(int inputCount);
|
||||
|
||||
protected abstract int MinOutputCount(int inputCount);
|
||||
}
|
||||
}
|
|
@ -1,102 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
namespace DiscUtils.Compression
|
||||
{
|
||||
/// <summary>
|
||||
/// A canonical Huffman tree implementation.
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// A lookup table is created that will take any bit sequence (max tree depth in length),
|
||||
/// indicating the output symbol. In WIM files, in practice, no chunk exceeds 32768 bytes
|
||||
/// in length, so we often end up generating a bigger lookup table than the data it's
|
||||
/// encoding. This makes for exceptionally fast symbol lookups O(1), but is inefficient
|
||||
/// overall.
|
||||
/// </remarks>
|
||||
internal sealed class HuffmanTree
|
||||
{
|
||||
private readonly uint[] _buffer;
|
||||
private readonly int _numBits; // Max bits per symbol
|
||||
private readonly int _numSymbols; // Max symbols
|
||||
|
||||
public HuffmanTree(uint[] lengths)
|
||||
{
|
||||
Lengths = lengths;
|
||||
_numSymbols = lengths.Length;
|
||||
|
||||
uint maxLength = 0;
|
||||
for (int i = 0; i < Lengths.Length; ++i)
|
||||
{
|
||||
if (Lengths[i] > maxLength)
|
||||
{
|
||||
maxLength = Lengths[i];
|
||||
}
|
||||
}
|
||||
|
||||
_numBits = (int)maxLength;
|
||||
_buffer = new uint[1 << _numBits];
|
||||
|
||||
Build();
|
||||
}
|
||||
|
||||
public uint[] Lengths { get; }
|
||||
|
||||
public uint NextSymbol(BitStream bitStream)
|
||||
{
|
||||
uint symbol = _buffer[bitStream.Peek(_numBits)];
|
||||
|
||||
// We may have over-read, reset bitstream position
|
||||
bitStream.Consume((int)Lengths[symbol]);
|
||||
|
||||
return symbol;
|
||||
}
|
||||
|
||||
private void Build()
|
||||
{
|
||||
int position = 0;
|
||||
|
||||
// For each bit-length...
|
||||
for (int i = 1; i <= _numBits; ++i)
|
||||
{
|
||||
// Check each symbol
|
||||
for (uint symbol = 0; symbol < _numSymbols; ++symbol)
|
||||
{
|
||||
if (Lengths[symbol] == i)
|
||||
{
|
||||
int numToFill = 1 << (_numBits - i);
|
||||
for (int n = 0; n < numToFill; ++n)
|
||||
{
|
||||
_buffer[position + n] = symbol;
|
||||
}
|
||||
|
||||
position += numToFill;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (int i = position; i < _buffer.Length; ++i)
|
||||
{
|
||||
_buffer[i] = uint.MaxValue;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,97 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
|
||||
namespace DiscUtils.Compression
|
||||
{
|
||||
internal sealed class InverseBurrowsWheeler : DataBlockTransform
|
||||
{
|
||||
private readonly int[] _nextPos;
|
||||
private readonly int[] _pointers;
|
||||
|
||||
public InverseBurrowsWheeler(int bufferSize)
|
||||
{
|
||||
_pointers = new int[bufferSize];
|
||||
_nextPos = new int[256];
|
||||
}
|
||||
|
||||
protected override bool BuffersMustNotOverlap
|
||||
{
|
||||
get { return true; }
|
||||
}
|
||||
|
||||
public int OriginalIndex { get; set; }
|
||||
|
||||
protected override int DoProcess(byte[] input, int inputOffset, int inputCount, byte[] output, int outputOffset)
|
||||
{
|
||||
int outputCount = inputCount;
|
||||
|
||||
// First find the frequency of each value
|
||||
Array.Clear(_nextPos, 0, _nextPos.Length);
|
||||
for (int i = inputOffset; i < inputOffset + inputCount; ++i)
|
||||
{
|
||||
_nextPos[input[i]]++;
|
||||
}
|
||||
|
||||
// We know they're 'sorted' in the first column, so now can figure
|
||||
// out the position of the first instance of each.
|
||||
int sum = 0;
|
||||
for (int i = 0; i < 256; ++i)
|
||||
{
|
||||
int tempSum = sum;
|
||||
sum += _nextPos[i];
|
||||
_nextPos[i] = tempSum;
|
||||
}
|
||||
|
||||
// For each value in the final column, put a pointer to to the
|
||||
// 'next' character in the first (sorted) column.
|
||||
for (int i = 0; i < inputCount; ++i)
|
||||
{
|
||||
_pointers[_nextPos[input[inputOffset + i]]++] = i;
|
||||
}
|
||||
|
||||
// The 'next' character after the end of the original string is the
|
||||
// first character of the original string.
|
||||
int focus = _pointers[OriginalIndex];
|
||||
|
||||
// We can now just walk the pointers to reconstruct the original string
|
||||
for (int i = 0; i < outputCount; ++i)
|
||||
{
|
||||
output[outputOffset + i] = input[inputOffset + focus];
|
||||
focus = _pointers[focus];
|
||||
}
|
||||
|
||||
return outputCount;
|
||||
}
|
||||
|
||||
protected override int MaxOutputCount(int inputCount)
|
||||
{
|
||||
return inputCount;
|
||||
}
|
||||
|
||||
protected override int MinOutputCount(int inputCount)
|
||||
{
|
||||
return inputCount;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,68 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
namespace DiscUtils.Compression
|
||||
{
|
||||
internal class MoveToFront
|
||||
{
|
||||
private readonly byte[] _buffer;
|
||||
|
||||
public MoveToFront()
|
||||
: this(256, false) {}
|
||||
|
||||
public MoveToFront(int size, bool autoInit)
|
||||
{
|
||||
_buffer = new byte[size];
|
||||
|
||||
if (autoInit)
|
||||
{
|
||||
for (byte i = 0; i < size; ++i)
|
||||
{
|
||||
_buffer[i] = i;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public byte Head
|
||||
{
|
||||
get { return _buffer[0]; }
|
||||
}
|
||||
|
||||
public void Set(int pos, byte val)
|
||||
{
|
||||
_buffer[pos] = val;
|
||||
}
|
||||
|
||||
public byte GetAndMove(int pos)
|
||||
{
|
||||
byte val = _buffer[pos];
|
||||
|
||||
for (int i = pos; i > 0; --i)
|
||||
{
|
||||
_buffer[i] = _buffer[i - 1];
|
||||
}
|
||||
|
||||
_buffer[0] = val;
|
||||
return val;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,64 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2014, Quamotion
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.IO.Compression;
|
||||
|
||||
namespace DiscUtils.Compression
|
||||
{
|
||||
internal class SizedDeflateStream : DeflateStream
|
||||
{
|
||||
private readonly int _length;
|
||||
private int _position;
|
||||
|
||||
public SizedDeflateStream(Stream stream, CompressionMode mode, bool leaveOpen, int length)
|
||||
: base(stream, mode, leaveOpen)
|
||||
{
|
||||
_length = length;
|
||||
}
|
||||
|
||||
public override long Length
|
||||
{
|
||||
get { return _length; }
|
||||
}
|
||||
|
||||
public override long Position
|
||||
{
|
||||
get { return _position; }
|
||||
set
|
||||
{
|
||||
if (value != Position)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public override int Read(byte[] array, int offset, int count)
|
||||
{
|
||||
int read = base.Read(array, offset, count);
|
||||
_position += read;
|
||||
return read;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,86 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2014, Quamotion
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using DiscUtils.Streams;
|
||||
using Buffer=DiscUtils.Streams.Buffer;
|
||||
|
||||
namespace DiscUtils.Compression
|
||||
{
|
||||
internal class ZlibBuffer : Buffer
|
||||
{
|
||||
private Ownership _ownership;
|
||||
private readonly Stream _stream;
|
||||
private int position;
|
||||
|
||||
public ZlibBuffer(Stream stream, Ownership ownership)
|
||||
{
|
||||
_stream = stream;
|
||||
_ownership = ownership;
|
||||
position = 0;
|
||||
}
|
||||
|
||||
public override bool CanRead
|
||||
{
|
||||
get { return _stream.CanRead; }
|
||||
}
|
||||
|
||||
public override bool CanWrite
|
||||
{
|
||||
get { return _stream.CanWrite; }
|
||||
}
|
||||
|
||||
public override long Capacity
|
||||
{
|
||||
get { return _stream.Length; }
|
||||
}
|
||||
|
||||
public override int Read(long pos, byte[] buffer, int offset, int count)
|
||||
{
|
||||
if (pos != position)
|
||||
{
|
||||
throw new NotSupportedException();
|
||||
}
|
||||
|
||||
int read = _stream.Read(buffer, offset, count);
|
||||
position += read;
|
||||
return read;
|
||||
}
|
||||
|
||||
public override void Write(long pos, byte[] buffer, int offset, int count)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public override void SetCapacity(long value)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public override IEnumerable<StreamExtent> GetExtentsInRange(long start, long count)
|
||||
{
|
||||
yield return new StreamExtent(0, _stream.Length);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,240 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.IO.Compression;
|
||||
using DiscUtils.Streams;
|
||||
|
||||
namespace DiscUtils.Compression
|
||||
{
|
||||
/// <summary>
|
||||
/// Implementation of the Zlib compression algorithm.
|
||||
/// </summary>
|
||||
/// <remarks>Only decompression is currently implemented.</remarks>
|
||||
public class ZlibStream : Stream
|
||||
{
|
||||
private readonly Adler32 _adler32;
|
||||
private readonly DeflateStream _deflateStream;
|
||||
private readonly CompressionMode _mode;
|
||||
private readonly Stream _stream;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the ZlibStream class.
|
||||
/// </summary>
|
||||
/// <param name="stream">The stream to compress of decompress.</param>
|
||||
/// <param name="mode">Whether to compress or decompress.</param>
|
||||
/// <param name="leaveOpen">Whether closing this stream should leave <c>stream</c> open.</param>
|
||||
public ZlibStream(Stream stream, CompressionMode mode, bool leaveOpen)
|
||||
{
|
||||
_stream = stream;
|
||||
_mode = mode;
|
||||
|
||||
if (mode == CompressionMode.Decompress)
|
||||
{
|
||||
// We just sanity check against expected header values...
|
||||
byte[] headerBuffer = StreamUtilities.ReadExact(stream, 2);
|
||||
ushort header = EndianUtilities.ToUInt16BigEndian(headerBuffer, 0);
|
||||
|
||||
if (header % 31 != 0)
|
||||
{
|
||||
throw new IOException("Invalid Zlib header found");
|
||||
}
|
||||
|
||||
if ((header & 0x0F00) != 8 << 8)
|
||||
{
|
||||
throw new NotSupportedException("Zlib compression not using DEFLATE algorithm");
|
||||
}
|
||||
|
||||
if ((header & 0x0020) != 0)
|
||||
{
|
||||
throw new NotSupportedException("Zlib compression using preset dictionary");
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
ushort header =
|
||||
(8 << 8) // DEFLATE
|
||||
| (7 << 12) // 32K window size
|
||||
| 0x80; // Default algorithm
|
||||
header |= (ushort)(31 - header % 31);
|
||||
|
||||
byte[] headerBuffer = new byte[2];
|
||||
EndianUtilities.WriteBytesBigEndian(header, headerBuffer, 0);
|
||||
stream.Write(headerBuffer, 0, 2);
|
||||
}
|
||||
|
||||
_deflateStream = new DeflateStream(stream, mode, leaveOpen);
|
||||
_adler32 = new Adler32();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets whether the stream can be read.
|
||||
/// </summary>
|
||||
public override bool CanRead
|
||||
{
|
||||
get { return _deflateStream.CanRead; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets whether the stream pointer can be changed.
|
||||
/// </summary>
|
||||
public override bool CanSeek
|
||||
{
|
||||
get { return false; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets whether the stream can be written to.
|
||||
/// </summary>
|
||||
public override bool CanWrite
|
||||
{
|
||||
get { return _deflateStream.CanWrite; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the length of the stream.
|
||||
/// </summary>
|
||||
public override long Length
|
||||
{
|
||||
get { throw new NotSupportedException(); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets and sets the stream position.
|
||||
/// </summary>
|
||||
public override long Position
|
||||
{
|
||||
get { throw new NotSupportedException(); }
|
||||
set { throw new NotSupportedException(); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Closes the stream.
|
||||
/// </summary>
|
||||
protected override void Dispose(bool disposing)
|
||||
{
|
||||
if (_mode == CompressionMode.Decompress)
|
||||
{
|
||||
// Can only check Adler checksum on seekable streams. Since DeflateStream
|
||||
// aggresively caches input, it normally has already consumed the footer.
|
||||
if (_stream.CanSeek)
|
||||
{
|
||||
_stream.Seek(-4, SeekOrigin.End);
|
||||
byte[] footerBuffer = StreamUtilities.ReadExact(_stream, 4);
|
||||
if (EndianUtilities.ToInt32BigEndian(footerBuffer, 0) != _adler32.Value)
|
||||
{
|
||||
throw new InvalidDataException("Corrupt decompressed data detected");
|
||||
}
|
||||
}
|
||||
|
||||
_deflateStream.Dispose();
|
||||
}
|
||||
else
|
||||
{
|
||||
_deflateStream.Dispose();
|
||||
|
||||
byte[] footerBuffer = new byte[4];
|
||||
EndianUtilities.WriteBytesBigEndian(_adler32.Value, footerBuffer, 0);
|
||||
_stream.Write(footerBuffer, 0, 4);
|
||||
}
|
||||
|
||||
base.Dispose(disposing);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Flushes the stream.
|
||||
/// </summary>
|
||||
public override void Flush()
|
||||
{
|
||||
_deflateStream.Flush();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Reads data from the stream.
|
||||
/// </summary>
|
||||
/// <param name="buffer">The buffer to populate.</param>
|
||||
/// <param name="offset">The first byte to write.</param>
|
||||
/// <param name="count">The number of bytes requested.</param>
|
||||
/// <returns>The number of bytes read.</returns>
|
||||
public override int Read(byte[] buffer, int offset, int count)
|
||||
{
|
||||
CheckParams(buffer, offset, count);
|
||||
|
||||
int numRead = _deflateStream.Read(buffer, offset, count);
|
||||
_adler32.Process(buffer, offset, numRead);
|
||||
return numRead;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Seeks to a new position.
|
||||
/// </summary>
|
||||
/// <param name="offset">Relative position to seek to.</param>
|
||||
/// <param name="origin">The origin of the seek.</param>
|
||||
/// <returns>The new position.</returns>
|
||||
public override long Seek(long offset, SeekOrigin origin)
|
||||
{
|
||||
throw new NotSupportedException();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Changes the length of the stream.
|
||||
/// </summary>
|
||||
/// <param name="value">The new desired length of the stream.</param>
|
||||
public override void SetLength(long value)
|
||||
{
|
||||
throw new NotSupportedException();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Writes data to the stream.
|
||||
/// </summary>
|
||||
/// <param name="buffer">Buffer containing the data to write.</param>
|
||||
/// <param name="offset">Offset of the first byte to write.</param>
|
||||
/// <param name="count">Number of bytes to write.</param>
|
||||
public override void Write(byte[] buffer, int offset, int count)
|
||||
{
|
||||
CheckParams(buffer, offset, count);
|
||||
|
||||
_adler32.Process(buffer, offset, count);
|
||||
_deflateStream.Write(buffer, offset, count);
|
||||
}
|
||||
|
||||
private static void CheckParams(byte[] buffer, int offset, int count)
|
||||
{
|
||||
if (buffer == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(buffer));
|
||||
}
|
||||
|
||||
if (offset < 0 || offset > buffer.Length)
|
||||
{
|
||||
throw new ArgumentException("Offset outside of array bounds", nameof(offset));
|
||||
}
|
||||
|
||||
if (count < 0 || offset + count > buffer.Length)
|
||||
{
|
||||
throw new ArgumentException("Array index out of bounds", nameof(count));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,23 +0,0 @@
|
|||
#if NETSTANDARD
|
||||
using System.Text;
|
||||
#endif
|
||||
|
||||
namespace DiscUtils.CoreCompat
|
||||
{
|
||||
internal static class EncodingHelper
|
||||
{
|
||||
private static bool _registered;
|
||||
|
||||
public static void RegisterEncodings()
|
||||
{
|
||||
if (_registered)
|
||||
return;
|
||||
|
||||
_registered = true;
|
||||
|
||||
#if NETSTANDARD
|
||||
Encoding.RegisterProvider(CodePagesEncodingProvider.Instance);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,91 +0,0 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Reflection;
|
||||
using System.Runtime.InteropServices;
|
||||
|
||||
namespace DiscUtils.CoreCompat
|
||||
{
|
||||
internal static class ReflectionHelper
|
||||
{
|
||||
public static bool IsEnum(Type type)
|
||||
{
|
||||
#if NETSTANDARD1_5
|
||||
return type.GetTypeInfo().IsEnum;
|
||||
#else
|
||||
return type.IsEnum;
|
||||
#endif
|
||||
}
|
||||
|
||||
public static Attribute GetCustomAttribute(PropertyInfo property, Type attributeType)
|
||||
{
|
||||
#if NETSTANDARD1_5
|
||||
return property.GetCustomAttribute(attributeType);
|
||||
#else
|
||||
return Attribute.GetCustomAttribute(property, attributeType);
|
||||
#endif
|
||||
}
|
||||
|
||||
public static Attribute GetCustomAttribute(PropertyInfo property, Type attributeType, bool inherit)
|
||||
{
|
||||
#if NETSTANDARD1_5
|
||||
return property.GetCustomAttribute(attributeType, inherit);
|
||||
#else
|
||||
return Attribute.GetCustomAttribute(property, attributeType, inherit);
|
||||
#endif
|
||||
}
|
||||
|
||||
public static Attribute GetCustomAttribute(FieldInfo field, Type attributeType)
|
||||
{
|
||||
#if NETSTANDARD1_5
|
||||
return field.GetCustomAttribute(attributeType);
|
||||
#else
|
||||
return Attribute.GetCustomAttribute(field, attributeType);
|
||||
#endif
|
||||
}
|
||||
|
||||
public static Attribute GetCustomAttribute(Type type, Type attributeType)
|
||||
{
|
||||
#if NETSTANDARD1_5
|
||||
return type.GetTypeInfo().GetCustomAttribute(attributeType);
|
||||
#else
|
||||
return Attribute.GetCustomAttribute(type, attributeType);
|
||||
#endif
|
||||
}
|
||||
|
||||
public static Attribute GetCustomAttribute(Type type, Type attributeType, bool inherit)
|
||||
{
|
||||
#if NETSTANDARD1_5
|
||||
return type.GetTypeInfo().GetCustomAttribute(attributeType, inherit);
|
||||
#else
|
||||
return Attribute.GetCustomAttribute(type, attributeType);
|
||||
#endif
|
||||
}
|
||||
|
||||
public static IEnumerable<Attribute> GetCustomAttributes(Type type, Type attributeType, bool inherit)
|
||||
{
|
||||
#if NETSTANDARD1_5
|
||||
return type.GetTypeInfo().GetCustomAttributes(attributeType, inherit);
|
||||
#else
|
||||
return Attribute.GetCustomAttributes(type, attributeType);
|
||||
#endif
|
||||
}
|
||||
|
||||
public static Assembly GetAssembly(Type type)
|
||||
{
|
||||
#if NETSTANDARD1_5
|
||||
return type.GetTypeInfo().Assembly;
|
||||
#else
|
||||
return type.Assembly;
|
||||
#endif
|
||||
}
|
||||
|
||||
public static int SizeOf<T>()
|
||||
{
|
||||
#if NETSTANDARD1_5
|
||||
return Marshal.SizeOf<T>();
|
||||
#else
|
||||
return Marshal.SizeOf(typeof(T));
|
||||
#endif
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,15 +0,0 @@
|
|||
#if NETSTANDARD1_5
|
||||
using System.Globalization;
|
||||
|
||||
namespace DiscUtils.CoreCompat
|
||||
{
|
||||
internal static class StringExtensions
|
||||
{
|
||||
public static string ToUpper(this string value, CultureInfo culture)
|
||||
{
|
||||
return value.ToUpper();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
|
@ -1,190 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System.IO;
|
||||
using DiscUtils.Internal;
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Provides information about a directory on a disc.
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// This class allows navigation of the disc directory/file hierarchy.
|
||||
/// </remarks>
|
||||
public sealed class DiscDirectoryInfo : DiscFileSystemInfo
|
||||
{
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the DiscDirectoryInfo class.
|
||||
/// </summary>
|
||||
/// <param name="fileSystem">The file system the directory info relates to.</param>
|
||||
/// <param name="path">The path within the file system of the directory.</param>
|
||||
internal DiscDirectoryInfo(DiscFileSystem fileSystem, string path)
|
||||
: base(fileSystem, path) {}
|
||||
|
||||
/// <summary>
|
||||
/// Gets a value indicating whether the directory exists.
|
||||
/// </summary>
|
||||
public override bool Exists
|
||||
{
|
||||
get { return FileSystem.DirectoryExists(Path); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the full path of the directory.
|
||||
/// </summary>
|
||||
public override string FullName
|
||||
{
|
||||
get { return base.FullName + @"\"; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates a directory.
|
||||
/// </summary>
|
||||
public void Create()
|
||||
{
|
||||
FileSystem.CreateDirectory(Path);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Deletes a directory, even if it's not empty.
|
||||
/// </summary>
|
||||
public override void Delete()
|
||||
{
|
||||
FileSystem.DeleteDirectory(Path, false);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Deletes a directory, with the caller choosing whether to recurse.
|
||||
/// </summary>
|
||||
/// <param name="recursive"><c>true</c> to delete all child node, <c>false</c> to fail if the directory is not empty.</param>
|
||||
public void Delete(bool recursive)
|
||||
{
|
||||
FileSystem.DeleteDirectory(Path, recursive);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Moves a directory and it's contents to a new path.
|
||||
/// </summary>
|
||||
/// <param name="destinationDirName">The destination directory name.</param>
|
||||
public void MoveTo(string destinationDirName)
|
||||
{
|
||||
FileSystem.MoveDirectory(Path, destinationDirName);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets all child directories.
|
||||
/// </summary>
|
||||
/// <returns>An array of child directories.</returns>
|
||||
public DiscDirectoryInfo[] GetDirectories()
|
||||
{
|
||||
return Utilities.Map(FileSystem.GetDirectories(Path),
|
||||
p => new DiscDirectoryInfo(FileSystem, p));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets all child directories matching a search pattern.
|
||||
/// </summary>
|
||||
/// <param name="pattern">The search pattern.</param>
|
||||
/// <returns>An array of child directories, or empty if none match.</returns>
|
||||
/// <remarks>The search pattern can include the wildcards * (matching 0 or more characters)
|
||||
/// and ? (matching 1 character).</remarks>
|
||||
public DiscDirectoryInfo[] GetDirectories(string pattern)
|
||||
{
|
||||
return GetDirectories(pattern, SearchOption.TopDirectoryOnly);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets all descendant directories matching a search pattern.
|
||||
/// </summary>
|
||||
/// <param name="pattern">The search pattern.</param>
|
||||
/// <param name="searchOption">Whether to search just this directory, or all children.</param>
|
||||
/// <returns>An array of descendant directories, or empty if none match.</returns>
|
||||
/// <remarks>The search pattern can include the wildcards * (matching 0 or more characters)
|
||||
/// and ? (matching 1 character). The option parameter determines whether only immediate
|
||||
/// children, or all children are returned.</remarks>
|
||||
public DiscDirectoryInfo[] GetDirectories(string pattern, SearchOption searchOption)
|
||||
{
|
||||
return Utilities.Map(FileSystem.GetDirectories(Path, pattern, searchOption),
|
||||
p => new DiscDirectoryInfo(FileSystem, p));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets all files.
|
||||
/// </summary>
|
||||
/// <returns>An array of files.</returns>
|
||||
public DiscFileInfo[] GetFiles()
|
||||
{
|
||||
return Utilities.Map(FileSystem.GetFiles(Path), p => new DiscFileInfo(FileSystem, p));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets all files matching a search pattern.
|
||||
/// </summary>
|
||||
/// <param name="pattern">The search pattern.</param>
|
||||
/// <returns>An array of files, or empty if none match.</returns>
|
||||
/// <remarks>The search pattern can include the wildcards * (matching 0 or more characters)
|
||||
/// and ? (matching 1 character).</remarks>
|
||||
public DiscFileInfo[] GetFiles(string pattern)
|
||||
{
|
||||
return GetFiles(pattern, SearchOption.TopDirectoryOnly);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets all descendant files matching a search pattern.
|
||||
/// </summary>
|
||||
/// <param name="pattern">The search pattern.</param>
|
||||
/// <param name="searchOption">Whether to search just this directory, or all children.</param>
|
||||
/// <returns>An array of descendant files, or empty if none match.</returns>
|
||||
/// <remarks>The search pattern can include the wildcards * (matching 0 or more characters)
|
||||
/// and ? (matching 1 character). The option parameter determines whether only immediate
|
||||
/// children, or all children are returned.</remarks>
|
||||
public DiscFileInfo[] GetFiles(string pattern, SearchOption searchOption)
|
||||
{
|
||||
return Utilities.Map(FileSystem.GetFiles(Path, pattern, searchOption),
|
||||
p => new DiscFileInfo(FileSystem, p));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets all files and directories in this directory.
|
||||
/// </summary>
|
||||
/// <returns>An array of files and directories.</returns>
|
||||
public DiscFileSystemInfo[] GetFileSystemInfos()
|
||||
{
|
||||
return Utilities.Map(FileSystem.GetFileSystemEntries(Path),
|
||||
p => new DiscFileSystemInfo(FileSystem, p));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets all files and directories in this directory.
|
||||
/// </summary>
|
||||
/// <param name="pattern">The search pattern.</param>
|
||||
/// <returns>An array of files and directories.</returns>
|
||||
/// <remarks>The search pattern can include the wildcards * (matching 0 or more characters)
|
||||
/// and ? (matching 1 character).</remarks>
|
||||
public DiscFileSystemInfo[] GetFileSystemInfos(string pattern)
|
||||
{
|
||||
return Utilities.Map(FileSystem.GetFileSystemEntries(Path, pattern),
|
||||
p => new DiscFileSystemInfo(FileSystem, p));
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,200 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System.IO;
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Provides information about a file on a disc.
|
||||
/// </summary>
|
||||
public sealed class DiscFileInfo : DiscFileSystemInfo
|
||||
{
|
||||
internal DiscFileInfo(DiscFileSystem fileSystem, string path)
|
||||
: base(fileSystem, path) {}
|
||||
|
||||
/// <summary>
|
||||
/// Gets an instance of the parent directory.
|
||||
/// </summary>
|
||||
public DiscDirectoryInfo Directory
|
||||
{
|
||||
get { return Parent; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets a string representing the directory's full path.
|
||||
/// </summary>
|
||||
public string DirectoryName
|
||||
{
|
||||
get { return Directory.FullName; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets a value indicating whether the file exists.
|
||||
/// </summary>
|
||||
public override bool Exists
|
||||
{
|
||||
get { return FileSystem.FileExists(Path); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets a value indicating whether the file is read-only.
|
||||
/// </summary>
|
||||
public bool IsReadOnly
|
||||
{
|
||||
get { return (Attributes & FileAttributes.ReadOnly) != 0; }
|
||||
|
||||
set
|
||||
{
|
||||
if (value)
|
||||
{
|
||||
Attributes = Attributes | FileAttributes.ReadOnly;
|
||||
}
|
||||
else
|
||||
{
|
||||
Attributes = Attributes & ~FileAttributes.ReadOnly;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the length of the current file in bytes.
|
||||
/// </summary>
|
||||
public long Length
|
||||
{
|
||||
get { return FileSystem.GetFileLength(Path); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Deletes a file.
|
||||
/// </summary>
|
||||
public override void Delete()
|
||||
{
|
||||
FileSystem.DeleteFile(Path);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates a <see cref="StreamWriter" /> that appends text to the file represented by this <see cref="DiscFileInfo"/>.
|
||||
/// </summary>
|
||||
/// <returns>The newly created writer.</returns>
|
||||
public StreamWriter AppendText()
|
||||
{
|
||||
return new StreamWriter(Open(FileMode.Append));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Copies an existing file to a new file.
|
||||
/// </summary>
|
||||
/// <param name="destinationFileName">The destination file.</param>
|
||||
public void CopyTo(string destinationFileName)
|
||||
{
|
||||
CopyTo(destinationFileName, false);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Copies an existing file to a new file, allowing overwriting of an existing file.
|
||||
/// </summary>
|
||||
/// <param name="destinationFileName">The destination file.</param>
|
||||
/// <param name="overwrite">Whether to permit over-writing of an existing file.</param>
|
||||
public void CopyTo(string destinationFileName, bool overwrite)
|
||||
{
|
||||
FileSystem.CopyFile(Path, destinationFileName, overwrite);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates a new file for reading and writing.
|
||||
/// </summary>
|
||||
/// <returns>The newly created stream.</returns>
|
||||
public Stream Create()
|
||||
{
|
||||
return Open(FileMode.Create);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates a new <see cref="StreamWriter"/> that writes a new text file.
|
||||
/// </summary>
|
||||
/// <returns>A new stream writer that can write to the file contents.</returns>
|
||||
public StreamWriter CreateText()
|
||||
{
|
||||
return new StreamWriter(Open(FileMode.Create));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Moves a file to a new location.
|
||||
/// </summary>
|
||||
/// <param name="destinationFileName">The new name of the file.</param>
|
||||
public void MoveTo(string destinationFileName)
|
||||
{
|
||||
FileSystem.MoveFile(Path, destinationFileName);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Opens the current file.
|
||||
/// </summary>
|
||||
/// <param name="mode">The file mode for the created stream.</param>
|
||||
/// <returns>The newly created stream.</returns>
|
||||
/// <remarks>Read-only file systems only support <c>FileMode.Open</c>.</remarks>
|
||||
public Stream Open(FileMode mode)
|
||||
{
|
||||
return FileSystem.OpenFile(Path, mode);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Opens the current file.
|
||||
/// </summary>
|
||||
/// <param name="mode">The file mode for the created stream.</param>
|
||||
/// <param name="access">The access permissions for the created stream.</param>
|
||||
/// <returns>The newly created stream.</returns>
|
||||
/// <remarks>Read-only file systems only support <c>FileMode.Open</c> and <c>FileAccess.Read</c>.</remarks>
|
||||
public Stream Open(FileMode mode, FileAccess access)
|
||||
{
|
||||
return FileSystem.OpenFile(Path, mode, access);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Opens an existing file for read-only access.
|
||||
/// </summary>
|
||||
/// <returns>The newly created stream.</returns>
|
||||
public Stream OpenRead()
|
||||
{
|
||||
return Open(FileMode.Open, FileAccess.Read);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Opens an existing file for reading as UTF-8 text.
|
||||
/// </summary>
|
||||
/// <returns>The newly created reader.</returns>
|
||||
public StreamReader OpenText()
|
||||
{
|
||||
return new StreamReader(OpenRead());
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Opens a file for writing.
|
||||
/// </summary>
|
||||
/// <returns>The newly created stream.</returns>
|
||||
public Stream OpenWrite()
|
||||
{
|
||||
return Open(FileMode.Open, FileAccess.Write);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,93 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
using System.IO;
|
||||
using DiscUtils.Internal;
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
internal sealed class DiscFileLocator : FileLocator
|
||||
{
|
||||
private readonly string _basePath;
|
||||
private readonly DiscFileSystem _fileSystem;
|
||||
|
||||
public DiscFileLocator(DiscFileSystem fileSystem, string basePath)
|
||||
{
|
||||
_fileSystem = fileSystem;
|
||||
_basePath = basePath;
|
||||
}
|
||||
|
||||
public override bool Exists(string fileName)
|
||||
{
|
||||
return _fileSystem.FileExists(Utilities.CombinePaths(_basePath, fileName));
|
||||
}
|
||||
|
||||
protected override Stream OpenFile(string fileName, FileMode mode, FileAccess access, FileShare share)
|
||||
{
|
||||
return _fileSystem.OpenFile(Utilities.CombinePaths(_basePath, fileName), mode, access);
|
||||
}
|
||||
|
||||
public override FileLocator GetRelativeLocator(string path)
|
||||
{
|
||||
return new DiscFileLocator(_fileSystem, Utilities.CombinePaths(_basePath, path));
|
||||
}
|
||||
|
||||
public override string GetFullPath(string path)
|
||||
{
|
||||
return Utilities.CombinePaths(_basePath, path);
|
||||
}
|
||||
|
||||
public override string GetDirectoryFromPath(string path)
|
||||
{
|
||||
return Utilities.GetDirectoryFromPath(path);
|
||||
}
|
||||
|
||||
public override string GetFileFromPath(string path)
|
||||
{
|
||||
return Utilities.GetFileFromPath(path);
|
||||
}
|
||||
|
||||
public override DateTime GetLastWriteTimeUtc(string path)
|
||||
{
|
||||
return _fileSystem.GetLastWriteTimeUtc(Utilities.CombinePaths(_basePath, path));
|
||||
}
|
||||
|
||||
public override bool HasCommonRoot(FileLocator other)
|
||||
{
|
||||
DiscFileLocator otherDiscLocator = other as DiscFileLocator;
|
||||
|
||||
if (otherDiscLocator == null)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
// Common root if the same file system instance.
|
||||
return ReferenceEquals(otherDiscLocator._fileSystem, _fileSystem);
|
||||
}
|
||||
|
||||
public override string ResolveRelativePath(string path)
|
||||
{
|
||||
return Utilities.ResolveRelativePath(_basePath, path);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,509 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
using System.IO;
|
||||
using DiscUtils.Streams;
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Provides the base class for all file systems.
|
||||
/// </summary>
|
||||
public abstract class DiscFileSystem :
|
||||
#if !NETSTANDARD
|
||||
MarshalByRefObject,
|
||||
#endif
|
||||
IFileSystem, IDisposable
|
||||
{
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the DiscFileSystem class.
|
||||
/// </summary>
|
||||
protected DiscFileSystem()
|
||||
{
|
||||
Options = new DiscFileSystemOptions();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the DiscFileSystem class.
|
||||
/// </summary>
|
||||
/// <param name="defaultOptions">The options instance to use for this file system instance.</param>
|
||||
protected DiscFileSystem(DiscFileSystemOptions defaultOptions)
|
||||
{
|
||||
Options = defaultOptions;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Finalizes an instance of the DiscFileSystem class.
|
||||
/// </summary>
|
||||
~DiscFileSystem()
|
||||
{
|
||||
Dispose(false);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the file system options, which can be modified.
|
||||
/// </summary>
|
||||
public virtual DiscFileSystemOptions Options { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets a friendly description of the file system type.
|
||||
/// </summary>
|
||||
public abstract string FriendlyName { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets a value indicating whether the file system is read-only or read-write.
|
||||
/// </summary>
|
||||
/// <returns>true if the file system is read-write.</returns>
|
||||
public abstract bool CanWrite { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the root directory of the file system.
|
||||
/// </summary>
|
||||
public virtual DiscDirectoryInfo Root
|
||||
{
|
||||
get { return new DiscDirectoryInfo(this, string.Empty); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the volume label.
|
||||
/// </summary>
|
||||
public virtual string VolumeLabel
|
||||
{
|
||||
get { return string.Empty; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets a value indicating whether the file system is thread-safe.
|
||||
/// </summary>
|
||||
public virtual bool IsThreadSafe
|
||||
{
|
||||
get { return false; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Copies an existing file to a new file.
|
||||
/// </summary>
|
||||
/// <param name="sourceFile">The source file.</param>
|
||||
/// <param name="destinationFile">The destination file.</param>
|
||||
public virtual void CopyFile(string sourceFile, string destinationFile)
|
||||
{
|
||||
CopyFile(sourceFile, destinationFile, false);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Copies an existing file to a new file, allowing overwriting of an existing file.
|
||||
/// </summary>
|
||||
/// <param name="sourceFile">The source file.</param>
|
||||
/// <param name="destinationFile">The destination file.</param>
|
||||
/// <param name="overwrite">Whether to permit over-writing of an existing file.</param>
|
||||
public abstract void CopyFile(string sourceFile, string destinationFile, bool overwrite);
|
||||
|
||||
/// <summary>
|
||||
/// Creates a directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the new directory.</param>
|
||||
public abstract void CreateDirectory(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Deletes a directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the directory to delete.</param>
|
||||
public abstract void DeleteDirectory(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Deletes a directory, optionally with all descendants.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the directory to delete.</param>
|
||||
/// <param name="recursive">Determines if the all descendants should be deleted.</param>
|
||||
public virtual void DeleteDirectory(string path, bool recursive)
|
||||
{
|
||||
if (recursive)
|
||||
{
|
||||
foreach (string dir in GetDirectories(path))
|
||||
{
|
||||
DeleteDirectory(dir, true);
|
||||
}
|
||||
|
||||
foreach (string file in GetFiles(path))
|
||||
{
|
||||
DeleteFile(file);
|
||||
}
|
||||
}
|
||||
|
||||
DeleteDirectory(path);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Deletes a file.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file to delete.</param>
|
||||
public abstract void DeleteFile(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Indicates if a directory exists.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to test.</param>
|
||||
/// <returns>true if the directory exists.</returns>
|
||||
public abstract bool DirectoryExists(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Indicates if a file exists.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to test.</param>
|
||||
/// <returns>true if the file exists.</returns>
|
||||
public abstract bool FileExists(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Indicates if a file or directory exists.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to test.</param>
|
||||
/// <returns>true if the file or directory exists.</returns>
|
||||
public virtual bool Exists(string path)
|
||||
{
|
||||
return FileExists(path) || DirectoryExists(path);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the names of subdirectories in a specified directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to search.</param>
|
||||
/// <returns>Array of directories.</returns>
|
||||
public virtual string[] GetDirectories(string path)
|
||||
{
|
||||
return GetDirectories(path, "*.*", SearchOption.TopDirectoryOnly);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the names of subdirectories in a specified directory matching a specified
|
||||
/// search pattern.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to search.</param>
|
||||
/// <param name="searchPattern">The search string to match against.</param>
|
||||
/// <returns>Array of directories matching the search pattern.</returns>
|
||||
public virtual string[] GetDirectories(string path, string searchPattern)
|
||||
{
|
||||
return GetDirectories(path, searchPattern, SearchOption.TopDirectoryOnly);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the names of subdirectories in a specified directory matching a specified
|
||||
/// search pattern, using a value to determine whether to search subdirectories.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to search.</param>
|
||||
/// <param name="searchPattern">The search string to match against.</param>
|
||||
/// <param name="searchOption">Indicates whether to search subdirectories.</param>
|
||||
/// <returns>Array of directories matching the search pattern.</returns>
|
||||
public abstract string[] GetDirectories(string path, string searchPattern, SearchOption searchOption);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the names of files in a specified directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to search.</param>
|
||||
/// <returns>Array of files.</returns>
|
||||
public virtual string[] GetFiles(string path)
|
||||
{
|
||||
return GetFiles(path, "*.*", SearchOption.TopDirectoryOnly);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the names of files in a specified directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to search.</param>
|
||||
/// <param name="searchPattern">The search string to match against.</param>
|
||||
/// <returns>Array of files matching the search pattern.</returns>
|
||||
public virtual string[] GetFiles(string path, string searchPattern)
|
||||
{
|
||||
return GetFiles(path, searchPattern, SearchOption.TopDirectoryOnly);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the names of files in a specified directory matching a specified
|
||||
/// search pattern, using a value to determine whether to search subdirectories.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to search.</param>
|
||||
/// <param name="searchPattern">The search string to match against.</param>
|
||||
/// <param name="searchOption">Indicates whether to search subdirectories.</param>
|
||||
/// <returns>Array of files matching the search pattern.</returns>
|
||||
public abstract string[] GetFiles(string path, string searchPattern, SearchOption searchOption);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the names of all files and subdirectories in a specified directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to search.</param>
|
||||
/// <returns>Array of files and subdirectories matching the search pattern.</returns>
|
||||
public abstract string[] GetFileSystemEntries(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the names of files and subdirectories in a specified directory matching a specified
|
||||
/// search pattern.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to search.</param>
|
||||
/// <param name="searchPattern">The search string to match against.</param>
|
||||
/// <returns>Array of files and subdirectories matching the search pattern.</returns>
|
||||
public abstract string[] GetFileSystemEntries(string path, string searchPattern);
|
||||
|
||||
/// <summary>
|
||||
/// Moves a directory.
|
||||
/// </summary>
|
||||
/// <param name="sourceDirectoryName">The directory to move.</param>
|
||||
/// <param name="destinationDirectoryName">The target directory name.</param>
|
||||
public abstract void MoveDirectory(string sourceDirectoryName, string destinationDirectoryName);
|
||||
|
||||
/// <summary>
|
||||
/// Moves a file.
|
||||
/// </summary>
|
||||
/// <param name="sourceName">The file to move.</param>
|
||||
/// <param name="destinationName">The target file name.</param>
|
||||
public virtual void MoveFile(string sourceName, string destinationName)
|
||||
{
|
||||
MoveFile(sourceName, destinationName, false);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Moves a file, allowing an existing file to be overwritten.
|
||||
/// </summary>
|
||||
/// <param name="sourceName">The file to move.</param>
|
||||
/// <param name="destinationName">The target file name.</param>
|
||||
/// <param name="overwrite">Whether to permit a destination file to be overwritten.</param>
|
||||
public abstract void MoveFile(string sourceName, string destinationName, bool overwrite);
|
||||
|
||||
/// <summary>
|
||||
/// Opens the specified file.
|
||||
/// </summary>
|
||||
/// <param name="path">The full path of the file to open.</param>
|
||||
/// <param name="mode">The file mode for the created stream.</param>
|
||||
/// <returns>The new stream.</returns>
|
||||
public virtual SparseStream OpenFile(string path, FileMode mode)
|
||||
{
|
||||
return OpenFile(path, mode, FileAccess.ReadWrite);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Opens the specified file.
|
||||
/// </summary>
|
||||
/// <param name="path">The full path of the file to open.</param>
|
||||
/// <param name="mode">The file mode for the created stream.</param>
|
||||
/// <param name="access">The access permissions for the created stream.</param>
|
||||
/// <returns>The new stream.</returns>
|
||||
public abstract SparseStream OpenFile(string path, FileMode mode, FileAccess access);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the attributes of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The file or directory to inspect.</param>
|
||||
/// <returns>The attributes of the file or directory.</returns>
|
||||
public abstract FileAttributes GetAttributes(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Sets the attributes of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The file or directory to change.</param>
|
||||
/// <param name="newValue">The new attributes of the file or directory.</param>
|
||||
public abstract void SetAttributes(string path, FileAttributes newValue);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the creation time (in local time) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <returns>The creation time.</returns>
|
||||
public virtual DateTime GetCreationTime(string path)
|
||||
{
|
||||
return GetCreationTimeUtc(path).ToLocalTime();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Sets the creation time (in local time) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <param name="newTime">The new time to set.</param>
|
||||
public virtual void SetCreationTime(string path, DateTime newTime)
|
||||
{
|
||||
SetCreationTimeUtc(path, newTime.ToUniversalTime());
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the creation time (in UTC) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <returns>The creation time.</returns>
|
||||
public abstract DateTime GetCreationTimeUtc(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Sets the creation time (in UTC) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <param name="newTime">The new time to set.</param>
|
||||
public abstract void SetCreationTimeUtc(string path, DateTime newTime);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the last access time (in local time) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <returns>The last access time.</returns>
|
||||
public virtual DateTime GetLastAccessTime(string path)
|
||||
{
|
||||
return GetLastAccessTimeUtc(path).ToLocalTime();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Sets the last access time (in local time) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <param name="newTime">The new time to set.</param>
|
||||
public virtual void SetLastAccessTime(string path, DateTime newTime)
|
||||
{
|
||||
SetLastAccessTimeUtc(path, newTime.ToUniversalTime());
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the last access time (in UTC) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <returns>The last access time.</returns>
|
||||
public abstract DateTime GetLastAccessTimeUtc(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Sets the last access time (in UTC) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <param name="newTime">The new time to set.</param>
|
||||
public abstract void SetLastAccessTimeUtc(string path, DateTime newTime);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the last modification time (in local time) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <returns>The last write time.</returns>
|
||||
public virtual DateTime GetLastWriteTime(string path)
|
||||
{
|
||||
return GetLastWriteTimeUtc(path).ToLocalTime();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Sets the last modification time (in local time) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <param name="newTime">The new time to set.</param>
|
||||
public virtual void SetLastWriteTime(string path, DateTime newTime)
|
||||
{
|
||||
SetLastWriteTimeUtc(path, newTime.ToUniversalTime());
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the last modification time (in UTC) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <returns>The last write time.</returns>
|
||||
public abstract DateTime GetLastWriteTimeUtc(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Sets the last modification time (in UTC) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <param name="newTime">The new time to set.</param>
|
||||
public abstract void SetLastWriteTimeUtc(string path, DateTime newTime);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the length of a file.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to the file.</param>
|
||||
/// <returns>The length in bytes.</returns>
|
||||
public abstract long GetFileLength(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Gets an object representing a possible file.
|
||||
/// </summary>
|
||||
/// <param name="path">The file path.</param>
|
||||
/// <returns>The representing object.</returns>
|
||||
/// <remarks>The file does not need to exist.</remarks>
|
||||
public virtual DiscFileInfo GetFileInfo(string path)
|
||||
{
|
||||
return new DiscFileInfo(this, path);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets an object representing a possible directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The directory path.</param>
|
||||
/// <returns>The representing object.</returns>
|
||||
/// <remarks>The directory does not need to exist.</remarks>
|
||||
public virtual DiscDirectoryInfo GetDirectoryInfo(string path)
|
||||
{
|
||||
return new DiscDirectoryInfo(this, path);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets an object representing a possible file system object (file or directory).
|
||||
/// </summary>
|
||||
/// <param name="path">The file system path.</param>
|
||||
/// <returns>The representing object.</returns>
|
||||
/// <remarks>The file system object does not need to exist.</remarks>
|
||||
public virtual DiscFileSystemInfo GetFileSystemInfo(string path)
|
||||
{
|
||||
return new DiscFileSystemInfo(this, path);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Reads the boot code of the file system into a byte array.
|
||||
/// </summary>
|
||||
/// <returns>The boot code, or <c>null</c> if not available.</returns>
|
||||
public virtual byte[] ReadBootCode()
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Size of the Filesystem in bytes
|
||||
/// </summary>
|
||||
public abstract long Size { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Used space of the Filesystem in bytes
|
||||
/// </summary>
|
||||
public abstract long UsedSpace { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Available space of the Filesystem in bytes
|
||||
/// </summary>
|
||||
public abstract long AvailableSpace { get; }
|
||||
|
||||
#region IDisposable Members
|
||||
|
||||
/// <summary>
|
||||
/// Disposes of this instance, releasing all resources.
|
||||
/// </summary>
|
||||
public void Dispose()
|
||||
{
|
||||
Dispose(true);
|
||||
GC.SuppressFinalize(this);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Disposes of this instance.
|
||||
/// </summary>
|
||||
/// <param name="disposing">The value <c>true</c> if Disposing.</param>
|
||||
protected virtual void Dispose(bool disposing) {}
|
||||
|
||||
#endregion
|
||||
}
|
||||
}
|
|
@ -1,43 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System.IO;
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Base class for objects that validate file system integrity.
|
||||
/// </summary>
|
||||
/// <remarks>Instances of this class do not offer the ability to fix/correct
|
||||
/// file system issues, just to perform a limited number of checks on
|
||||
/// integrity of the file system.</remarks>
|
||||
public abstract class DiscFileSystemChecker
|
||||
{
|
||||
/// <summary>
|
||||
/// Checks the integrity of a file system held in a stream.
|
||||
/// </summary>
|
||||
/// <param name="reportOutput">A report on issues found.</param>
|
||||
/// <param name="levels">The amount of detail to report.</param>
|
||||
/// <returns><c>true</c> if the file system appears valid, else <c>false</c>.</returns>
|
||||
public abstract bool Check(TextWriter reportOutput, ReportLevels levels);
|
||||
}
|
||||
}
|
|
@ -1,219 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
using System.IO;
|
||||
using DiscUtils.Internal;
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Provides the base class for both <see cref="DiscFileInfo"/> and <see cref="DiscDirectoryInfo"/> objects.
|
||||
/// </summary>
|
||||
public class DiscFileSystemInfo
|
||||
{
|
||||
internal DiscFileSystemInfo(DiscFileSystem fileSystem, string path)
|
||||
{
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
FileSystem = fileSystem;
|
||||
Path = path.Trim('\\');
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the <see cref="System.IO.FileAttributes"/> of the current <see cref="DiscFileSystemInfo"/> object.
|
||||
/// </summary>
|
||||
public virtual FileAttributes Attributes
|
||||
{
|
||||
get { return FileSystem.GetAttributes(Path); }
|
||||
set { FileSystem.SetAttributes(Path, value); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the creation time (in local time) of the current <see cref="DiscFileSystemInfo"/> object.
|
||||
/// </summary>
|
||||
public virtual DateTime CreationTime
|
||||
{
|
||||
get { return CreationTimeUtc.ToLocalTime(); }
|
||||
set { CreationTimeUtc = value.ToUniversalTime(); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the creation time (in UTC) of the current <see cref="DiscFileSystemInfo"/> object.
|
||||
/// </summary>
|
||||
public virtual DateTime CreationTimeUtc
|
||||
{
|
||||
get { return FileSystem.GetCreationTimeUtc(Path); }
|
||||
set { FileSystem.SetCreationTimeUtc(Path, value); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets a value indicating whether the file system object exists.
|
||||
/// </summary>
|
||||
public virtual bool Exists
|
||||
{
|
||||
get { return FileSystem.Exists(Path); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the extension part of the file or directory name.
|
||||
/// </summary>
|
||||
public virtual string Extension
|
||||
{
|
||||
get
|
||||
{
|
||||
string name = Name;
|
||||
int sepIdx = name.LastIndexOf('.');
|
||||
if (sepIdx >= 0)
|
||||
{
|
||||
return name.Substring(sepIdx + 1);
|
||||
}
|
||||
|
||||
return string.Empty;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the file system the referenced file or directory exists on.
|
||||
/// </summary>
|
||||
public DiscFileSystem FileSystem { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the full path of the file or directory.
|
||||
/// </summary>
|
||||
public virtual string FullName
|
||||
{
|
||||
get { return Path; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the last time (in local time) the file or directory was accessed.
|
||||
/// </summary>
|
||||
/// <remarks>Read-only file systems will never update this value, it will remain at a fixed value.</remarks>
|
||||
public virtual DateTime LastAccessTime
|
||||
{
|
||||
get { return LastAccessTimeUtc.ToLocalTime(); }
|
||||
set { LastAccessTimeUtc = value.ToUniversalTime(); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the last time (in UTC) the file or directory was accessed.
|
||||
/// </summary>
|
||||
/// <remarks>Read-only file systems will never update this value, it will remain at a fixed value.</remarks>
|
||||
public virtual DateTime LastAccessTimeUtc
|
||||
{
|
||||
get { return FileSystem.GetLastAccessTimeUtc(Path); }
|
||||
set { FileSystem.SetLastAccessTimeUtc(Path, value); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the last time (in local time) the file or directory was written to.
|
||||
/// </summary>
|
||||
public virtual DateTime LastWriteTime
|
||||
{
|
||||
get { return LastWriteTimeUtc.ToLocalTime(); }
|
||||
set { LastWriteTimeUtc = value.ToUniversalTime(); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the last time (in UTC) the file or directory was written to.
|
||||
/// </summary>
|
||||
public virtual DateTime LastWriteTimeUtc
|
||||
{
|
||||
get { return FileSystem.GetLastWriteTimeUtc(Path); }
|
||||
set { FileSystem.SetLastWriteTimeUtc(Path, value); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the name of the file or directory.
|
||||
/// </summary>
|
||||
public virtual string Name
|
||||
{
|
||||
get { return Utilities.GetFileFromPath(Path); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the <see cref="DiscDirectoryInfo"/> of the directory containing the current <see cref="DiscFileSystemInfo"/> object.
|
||||
/// </summary>
|
||||
public virtual DiscDirectoryInfo Parent
|
||||
{
|
||||
get
|
||||
{
|
||||
if (string.IsNullOrEmpty(Path))
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
return new DiscDirectoryInfo(FileSystem, Utilities.GetDirectoryFromPath(Path));
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the path to the referenced file.
|
||||
/// </summary>
|
||||
protected string Path { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Deletes a file or directory.
|
||||
/// </summary>
|
||||
public virtual void Delete()
|
||||
{
|
||||
if ((Attributes & FileAttributes.Directory) != 0)
|
||||
{
|
||||
FileSystem.DeleteDirectory(Path);
|
||||
}
|
||||
else
|
||||
{
|
||||
FileSystem.DeleteFile(Path);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Indicates if <paramref name="obj"/> is equivalent to this object.
|
||||
/// </summary>
|
||||
/// <param name="obj">The object to compare.</param>
|
||||
/// <returns><c>true</c> if <paramref name="obj"/> is equivalent, else <c>false</c>.</returns>
|
||||
public override bool Equals(object obj)
|
||||
{
|
||||
DiscFileSystemInfo asInfo = obj as DiscFileSystemInfo;
|
||||
if (obj == null)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return string.Compare(Path, asInfo.Path, StringComparison.Ordinal) == 0 &&
|
||||
Equals(FileSystem, asInfo.FileSystem);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the hash code for this object.
|
||||
/// </summary>
|
||||
/// <returns>The hash code.</returns>
|
||||
public override int GetHashCode()
|
||||
{
|
||||
return Path.GetHashCode() ^ FileSystem.GetHashCode();
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,41 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Common file system options.
|
||||
/// </summary>
|
||||
/// <remarks>Not all options are honoured by all file systems.</remarks>
|
||||
public class DiscFileSystemOptions
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets or sets the random number generator the file system should use.
|
||||
/// </summary>
|
||||
/// <remarks>This option is normally <c>null</c>, which is fine for most purposes.
|
||||
/// Use this option when you need to finely control the filesystem for
|
||||
/// reproducibility of behaviour (for example in a test harness).</remarks>
|
||||
public Random RandomNumberGenerator { get; set; }
|
||||
}
|
||||
}
|
|
@ -1,126 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Globalization;
|
||||
using DiscUtils.CoreCompat;
|
||||
using DiscUtils.Internal;
|
||||
using DiscUtils.Streams;
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Base class for all disk image builders.
|
||||
/// </summary>
|
||||
public abstract class DiskImageBuilder
|
||||
{
|
||||
private static Dictionary<string, VirtualDiskFactory> _typeMap;
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the geometry of this disk, as reported by the BIOS, will be implied from the content stream if not set.
|
||||
/// </summary>
|
||||
public Geometry BiosGeometry { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the content for this disk, implying the size of the disk.
|
||||
/// </summary>
|
||||
public SparseStream Content { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the adapter type for created virtual disk, for file formats that encode this information.
|
||||
/// </summary>
|
||||
public virtual GenericDiskAdapterType GenericAdapterType { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the geometry of this disk, will be implied from the content stream if not set.
|
||||
/// </summary>
|
||||
public Geometry Geometry { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets a value indicating whether this file format preserves BIOS geometry information.
|
||||
/// </summary>
|
||||
public virtual bool PreservesBiosGeometry
|
||||
{
|
||||
get { return false; }
|
||||
}
|
||||
|
||||
private static Dictionary<string, VirtualDiskFactory> TypeMap
|
||||
{
|
||||
get
|
||||
{
|
||||
if (_typeMap == null)
|
||||
{
|
||||
InitializeMaps();
|
||||
}
|
||||
|
||||
return _typeMap;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets an instance that constructs the specified type (and variant) of virtual disk image.
|
||||
/// </summary>
|
||||
/// <param name="type">The type of image to build (VHD, VMDK, etc).</param>
|
||||
/// <param name="variant">The variant type (differencing/dynamic, fixed/static, etc).</param>
|
||||
/// <returns>The builder instance.</returns>
|
||||
public static DiskImageBuilder GetBuilder(string type, string variant)
|
||||
{
|
||||
VirtualDiskFactory factory;
|
||||
if (!TypeMap.TryGetValue(type, out factory))
|
||||
{
|
||||
throw new ArgumentException(string.Format(CultureInfo.InvariantCulture, "Unknown disk type '{0}'", type), nameof(type));
|
||||
}
|
||||
|
||||
return factory.GetImageBuilder(variant);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Initiates the construction of the disk image.
|
||||
/// </summary>
|
||||
/// <param name="baseName">The base name for the disk images.</param>
|
||||
/// <returns>A set of one or more logical files that constitute the
|
||||
/// disk image. The first file is the 'primary' file that is normally attached to VMs.</returns>
|
||||
/// <remarks>The supplied <c>baseName</c> is the start of the file name, with no file
|
||||
/// extension. The set of file specifications will indicate the actual name corresponding
|
||||
/// to each logical file that comprises the disk image. For example, given a base name
|
||||
/// 'foo', the files 'foo.vmdk' and 'foo-flat.vmdk' could be returned.</remarks>
|
||||
public abstract DiskImageFileSpecification[] Build(string baseName);
|
||||
|
||||
private static void InitializeMaps()
|
||||
{
|
||||
Dictionary<string, VirtualDiskFactory> typeMap = new Dictionary<string, VirtualDiskFactory>();
|
||||
|
||||
foreach (Type type in ReflectionHelper.GetAssembly(typeof(VirtualDisk)).GetTypes())
|
||||
{
|
||||
VirtualDiskFactoryAttribute attr = (VirtualDiskFactoryAttribute)ReflectionHelper.GetCustomAttribute(type, typeof(VirtualDiskFactoryAttribute), false);
|
||||
if (attr != null)
|
||||
{
|
||||
VirtualDiskFactory factory = (VirtualDiskFactory)Activator.CreateInstance(type);
|
||||
typeMap.Add(attr.Type, factory);
|
||||
}
|
||||
}
|
||||
|
||||
_typeMap = typeMap;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,54 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using DiscUtils.Streams;
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Describes a particular file that is a constituent part of a virtual disk.
|
||||
/// </summary>
|
||||
public sealed class DiskImageFileSpecification
|
||||
{
|
||||
private readonly StreamBuilder _builder;
|
||||
|
||||
internal DiskImageFileSpecification(string name, StreamBuilder builder)
|
||||
{
|
||||
Name = name;
|
||||
_builder = builder;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets name of the file.
|
||||
/// </summary>
|
||||
public string Name { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the object that provides access to the file's content.
|
||||
/// </summary>
|
||||
/// <returns>A stream object that contains the file's content.</returns>
|
||||
public SparseStream OpenStream()
|
||||
{
|
||||
return _builder.Build();
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,72 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
using System.IO;
|
||||
using DiscUtils.Internal;
|
||||
using DiscUtils.Setup;
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
public abstract class FileLocator
|
||||
{
|
||||
public abstract bool Exists(string fileName);
|
||||
|
||||
public Stream Open(string fileName, FileMode mode, FileAccess access, FileShare share)
|
||||
{
|
||||
var args = new FileOpenEventArgs(fileName, mode, access, share, OpenFile);
|
||||
SetupHelper.OnOpeningFile(this, args);
|
||||
if (args.Result != null)
|
||||
return args.Result;
|
||||
return OpenFile(args.FileName, args.FileMode, args.FileAccess, args.FileShare);
|
||||
}
|
||||
|
||||
protected abstract Stream OpenFile(string fileName, FileMode mode, FileAccess access, FileShare share);
|
||||
|
||||
public abstract FileLocator GetRelativeLocator(string path);
|
||||
|
||||
public abstract string GetFullPath(string path);
|
||||
|
||||
public abstract string GetDirectoryFromPath(string path);
|
||||
|
||||
public abstract string GetFileFromPath(string path);
|
||||
|
||||
public abstract DateTime GetLastWriteTimeUtc(string path);
|
||||
|
||||
public abstract bool HasCommonRoot(FileLocator other);
|
||||
|
||||
public abstract string ResolveRelativePath(string path);
|
||||
|
||||
internal string MakeRelativePath(FileLocator fileLocator, string path)
|
||||
{
|
||||
if (!HasCommonRoot(fileLocator))
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
string ourFullPath = GetFullPath(string.Empty) + @"\";
|
||||
string otherFullPath = fileLocator.GetFullPath(path);
|
||||
|
||||
return Utilities.MakeRelativePath(otherFullPath, ourFullPath);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,90 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System.IO;
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Base class holding information about a file system.
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// File system implementations derive from this class, to provide information about the file system.
|
||||
/// </remarks>
|
||||
public abstract class FileSystemInfo
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets a one-line description of the file system.
|
||||
/// </summary>
|
||||
public abstract string Description { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the name of the file system.
|
||||
/// </summary>
|
||||
public abstract string Name { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Opens a volume using the file system.
|
||||
/// </summary>
|
||||
/// <param name="volume">The volume to access.</param>
|
||||
/// <returns>A file system instance.</returns>
|
||||
public DiscFileSystem Open(VolumeInfo volume)
|
||||
{
|
||||
return Open(volume, null);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Opens a stream using the file system.
|
||||
/// </summary>
|
||||
/// <param name="stream">The stream to access.</param>
|
||||
/// <returns>A file system instance.</returns>
|
||||
public DiscFileSystem Open(Stream stream)
|
||||
{
|
||||
return Open(stream, null);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Opens a volume using the file system.
|
||||
/// </summary>
|
||||
/// <param name="volume">The volume to access.</param>
|
||||
/// <param name="parameters">Parameters for the file system.</param>
|
||||
/// <returns>A file system instance.</returns>
|
||||
public abstract DiscFileSystem Open(VolumeInfo volume, FileSystemParameters parameters);
|
||||
|
||||
/// <summary>
|
||||
/// Opens a stream using the file system.
|
||||
/// </summary>
|
||||
/// <param name="stream">The stream to access.</param>
|
||||
/// <param name="parameters">Parameters for the file system.</param>
|
||||
/// <returns>A file system instance.</returns>
|
||||
public abstract DiscFileSystem Open(Stream stream, FileSystemParameters parameters);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the name of the file system.
|
||||
/// </summary>
|
||||
/// <returns>The file system name.</returns>
|
||||
public override string ToString()
|
||||
{
|
||||
return Name;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,121 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Reflection;
|
||||
using DiscUtils.CoreCompat;
|
||||
using DiscUtils.Vfs;
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// FileSystemManager determines which file systems are present on a volume.
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// The static detection methods detect default file systems. To plug in additional
|
||||
/// file systems, create an instance of this class and call RegisterFileSystems.
|
||||
/// </remarks>
|
||||
public static class FileSystemManager
|
||||
{
|
||||
private static readonly List<VfsFileSystemFactory> _factories;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the FileSystemManager class.
|
||||
/// </summary>
|
||||
static FileSystemManager()
|
||||
{
|
||||
_factories = new List<VfsFileSystemFactory>();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Registers new file systems with an instance of this class.
|
||||
/// </summary>
|
||||
/// <param name="factory">The detector for the new file systems.</param>
|
||||
public static void RegisterFileSystems(VfsFileSystemFactory factory)
|
||||
{
|
||||
_factories.Add(factory);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Registers new file systems detected in an assembly.
|
||||
/// </summary>
|
||||
/// <param name="assembly">The assembly to inspect.</param>
|
||||
/// <remarks>
|
||||
/// To be detected, the <c>VfsFileSystemFactory</c> instances must be marked with the
|
||||
/// <c>VfsFileSystemFactoryAttribute</c>> attribute.
|
||||
/// </remarks>
|
||||
public static void RegisterFileSystems(Assembly assembly)
|
||||
{
|
||||
_factories.AddRange(DetectFactories(assembly));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Detect which file systems are present on a volume.
|
||||
/// </summary>
|
||||
/// <param name="volume">The volume to inspect.</param>
|
||||
/// <returns>The list of file systems detected.</returns>
|
||||
public static FileSystemInfo[] DetectFileSystems(VolumeInfo volume)
|
||||
{
|
||||
using (Stream s = volume.Open())
|
||||
{
|
||||
return DoDetect(s, volume);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Detect which file systems are present in a stream.
|
||||
/// </summary>
|
||||
/// <param name="stream">The stream to inspect.</param>
|
||||
/// <returns>The list of file systems detected.</returns>
|
||||
public static FileSystemInfo[] DetectFileSystems(Stream stream)
|
||||
{
|
||||
return DoDetect(stream, null);
|
||||
}
|
||||
|
||||
private static IEnumerable<VfsFileSystemFactory> DetectFactories(Assembly assembly)
|
||||
{
|
||||
foreach (Type type in assembly.GetTypes())
|
||||
{
|
||||
Attribute attrib = ReflectionHelper.GetCustomAttribute(type, typeof(VfsFileSystemFactoryAttribute), false);
|
||||
if (attrib == null)
|
||||
continue;
|
||||
|
||||
yield return (VfsFileSystemFactory)Activator.CreateInstance(type);
|
||||
}
|
||||
}
|
||||
|
||||
private static FileSystemInfo[] DoDetect(Stream stream, VolumeInfo volume)
|
||||
{
|
||||
BufferedStream detectStream = new BufferedStream(stream);
|
||||
List<FileSystemInfo> detected = new List<FileSystemInfo>();
|
||||
|
||||
foreach (VfsFileSystemFactory factory in _factories)
|
||||
{
|
||||
detected.AddRange(factory.Detect(detectStream, volume));
|
||||
}
|
||||
|
||||
return detected.ToArray();
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,49 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System.Text;
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Class with generic file system parameters.
|
||||
/// </summary>
|
||||
/// <remarks>Note - not all parameters apply to all types of file system.</remarks>
|
||||
public sealed class FileSystemParameters
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets or sets the character encoding for file names, or <c>null</c> for default.
|
||||
/// </summary>
|
||||
/// <remarks>Some file systems, such as FAT, don't specify a particular character set for
|
||||
/// file names. This parameter determines the character set that will be used for such
|
||||
/// file systems.</remarks>
|
||||
public Encoding FileNameEncoding { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the algorithm to convert file system time to UTC.
|
||||
/// </summary>
|
||||
/// <remarks>Some file system, such as FAT, don't have a defined way to convert from file system
|
||||
/// time (local time where the file system is authored) to UTC time. This parameter determines
|
||||
/// the algorithm to use.</remarks>
|
||||
public TimeConverter TimeConverter { get; set; }
|
||||
}
|
||||
}
|
|
@ -1,73 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
using System.Globalization;
|
||||
using System.IO;
|
||||
using DiscUtils.Internal;
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
[VirtualDiskTransport("file")]
|
||||
internal sealed class FileTransport : VirtualDiskTransport
|
||||
{
|
||||
private string _extraInfo;
|
||||
private string _path;
|
||||
|
||||
public override bool IsRawDisk
|
||||
{
|
||||
get { return false; }
|
||||
}
|
||||
|
||||
public override void Connect(Uri uri, string username, string password)
|
||||
{
|
||||
_path = uri.LocalPath;
|
||||
_extraInfo = uri.Fragment.TrimStart('#');
|
||||
|
||||
if (!Directory.Exists(Path.GetDirectoryName(_path)))
|
||||
{
|
||||
throw new FileNotFoundException(
|
||||
string.Format(CultureInfo.InvariantCulture, "No such file '{0}'", uri.OriginalString), _path);
|
||||
}
|
||||
}
|
||||
|
||||
public override VirtualDisk OpenDisk(FileAccess access)
|
||||
{
|
||||
throw new NotSupportedException();
|
||||
}
|
||||
|
||||
public override FileLocator GetFileLocator()
|
||||
{
|
||||
return new LocalFileLocator(Path.GetDirectoryName(_path) + @"\");
|
||||
}
|
||||
|
||||
public override string GetFileName()
|
||||
{
|
||||
return Path.GetFileName(_path);
|
||||
}
|
||||
|
||||
public override string GetExtraInfo()
|
||||
{
|
||||
return _extraInfo;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,45 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// The supported Floppy Disk logical formats.
|
||||
/// </summary>
|
||||
public enum FloppyDiskType
|
||||
{
|
||||
/// <summary>
|
||||
/// 720KiB capacity disk.
|
||||
/// </summary>
|
||||
DoubleDensity = 0,
|
||||
|
||||
/// <summary>
|
||||
/// 1440KiB capacity disk.
|
||||
/// </summary>
|
||||
HighDensity = 1,
|
||||
|
||||
/// <summary>
|
||||
/// 2880KiB capacity disk.
|
||||
/// </summary>
|
||||
Extended = 2
|
||||
}
|
||||
}
|
|
@ -1,40 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Well known hard disk adaptor types.
|
||||
/// </summary>
|
||||
public enum GenericDiskAdapterType
|
||||
{
|
||||
/// <summary>
|
||||
/// IDE adaptor.
|
||||
/// </summary>
|
||||
Ide = 0,
|
||||
|
||||
/// <summary>
|
||||
/// SCSI adaptor.
|
||||
/// </summary>
|
||||
Scsi = 1
|
||||
}
|
||||
}
|
|
@ -1,477 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
using System.Globalization;
|
||||
using DiscUtils.Streams;
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Class whose instances represent disk geometries.
|
||||
/// </summary>
|
||||
/// <remarks>Instances of this class are immutable.</remarks>
|
||||
public sealed class Geometry
|
||||
{
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the Geometry class. The default 512 bytes per sector is assumed.
|
||||
/// </summary>
|
||||
/// <param name="cylinders">The number of cylinders of the disk.</param>
|
||||
/// <param name="headsPerCylinder">The number of heads (aka platters) of the disk.</param>
|
||||
/// <param name="sectorsPerTrack">The number of sectors per track/cylinder of the disk.</param>
|
||||
public Geometry(int cylinders, int headsPerCylinder, int sectorsPerTrack)
|
||||
{
|
||||
Cylinders = cylinders;
|
||||
HeadsPerCylinder = headsPerCylinder;
|
||||
SectorsPerTrack = sectorsPerTrack;
|
||||
BytesPerSector = 512;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the Geometry class.
|
||||
/// </summary>
|
||||
/// <param name="cylinders">The number of cylinders of the disk.</param>
|
||||
/// <param name="headsPerCylinder">The number of heads (aka platters) of the disk.</param>
|
||||
/// <param name="sectorsPerTrack">The number of sectors per track/cylinder of the disk.</param>
|
||||
/// <param name="bytesPerSector">The number of bytes per sector of the disk.</param>
|
||||
public Geometry(int cylinders, int headsPerCylinder, int sectorsPerTrack, int bytesPerSector)
|
||||
{
|
||||
Cylinders = cylinders;
|
||||
HeadsPerCylinder = headsPerCylinder;
|
||||
SectorsPerTrack = sectorsPerTrack;
|
||||
BytesPerSector = bytesPerSector;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the Geometry class.
|
||||
/// </summary>
|
||||
/// <param name="capacity">The total capacity of the disk.</param>
|
||||
/// <param name="headsPerCylinder">The number of heads (aka platters) of the disk.</param>
|
||||
/// <param name="sectorsPerTrack">The number of sectors per track/cylinder of the disk.</param>
|
||||
/// <param name="bytesPerSector">The number of bytes per sector of the disk.</param>
|
||||
public Geometry(long capacity, int headsPerCylinder, int sectorsPerTrack, int bytesPerSector)
|
||||
{
|
||||
Cylinders = (int)(capacity / (headsPerCylinder * (long)sectorsPerTrack * bytesPerSector));
|
||||
HeadsPerCylinder = headsPerCylinder;
|
||||
SectorsPerTrack = sectorsPerTrack;
|
||||
BytesPerSector = bytesPerSector;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the number of bytes in each sector.
|
||||
/// </summary>
|
||||
public int BytesPerSector { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the total capacity of the disk (in bytes).
|
||||
/// </summary>
|
||||
public long Capacity
|
||||
{
|
||||
get { return TotalSectorsLong * BytesPerSector; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the number of cylinders.
|
||||
/// </summary>
|
||||
public int Cylinders { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the number of heads (aka platters).
|
||||
/// </summary>
|
||||
public int HeadsPerCylinder { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets a value indicating whether the Geometry is representable both by the BIOS and by IDE.
|
||||
/// </summary>
|
||||
public bool IsBiosAndIdeSafe
|
||||
{
|
||||
get { return Cylinders <= 1024 && HeadsPerCylinder <= 16 && SectorsPerTrack <= 63; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets a value indicating whether the Geometry is consistent with the values a BIOS can support.
|
||||
/// </summary>
|
||||
public bool IsBiosSafe
|
||||
{
|
||||
get { return Cylinders <= 1024 && HeadsPerCylinder <= 255 && SectorsPerTrack <= 63; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets a value indicating whether the Geometry is consistent with the values IDE can represent.
|
||||
/// </summary>
|
||||
public bool IsIdeSafe
|
||||
{
|
||||
get { return Cylinders <= 65536 && HeadsPerCylinder <= 16 && SectorsPerTrack <= 255; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the address of the last sector on the disk.
|
||||
/// </summary>
|
||||
public ChsAddress LastSector
|
||||
{
|
||||
get { return new ChsAddress(Cylinders - 1, HeadsPerCylinder - 1, SectorsPerTrack); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets a null geometry, which has 512-byte sectors but zero sectors, tracks or cylinders.
|
||||
/// </summary>
|
||||
public static Geometry Null
|
||||
{
|
||||
get { return new Geometry(0, 0, 0, 512); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the number of sectors per track.
|
||||
/// </summary>
|
||||
public int SectorsPerTrack { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the total size of the disk (in sectors).
|
||||
/// </summary>
|
||||
[Obsolete("Use TotalSectorsLong instead, to support very large disks.")]
|
||||
public int TotalSectors
|
||||
{
|
||||
get { return Cylinders * HeadsPerCylinder * SectorsPerTrack; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the total size of the disk (in sectors).
|
||||
/// </summary>
|
||||
public long TotalSectorsLong
|
||||
{
|
||||
get { return Cylinders * (long)HeadsPerCylinder * SectorsPerTrack; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the 'Large' BIOS geometry for a disk, given it's physical geometry.
|
||||
/// </summary>
|
||||
/// <param name="ideGeometry">The physical (aka IDE) geometry of the disk.</param>
|
||||
/// <returns>The geometry a BIOS using the 'Large' method for calculating disk geometry will indicate for the disk.</returns>
|
||||
public static Geometry LargeBiosGeometry(Geometry ideGeometry)
|
||||
{
|
||||
int cylinders = ideGeometry.Cylinders;
|
||||
int heads = ideGeometry.HeadsPerCylinder;
|
||||
int sectors = ideGeometry.SectorsPerTrack;
|
||||
|
||||
while (cylinders > 1024 && heads <= 127)
|
||||
{
|
||||
cylinders >>= 1;
|
||||
heads <<= 1;
|
||||
}
|
||||
|
||||
return new Geometry(cylinders, heads, sectors);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the 'LBA Assisted' BIOS geometry for a disk, given it's capacity.
|
||||
/// </summary>
|
||||
/// <param name="capacity">The capacity of the disk.</param>
|
||||
/// <returns>The geometry a BIOS using the 'LBA Assisted' method for calculating disk geometry will indicate for the disk.</returns>
|
||||
public static Geometry LbaAssistedBiosGeometry(long capacity)
|
||||
{
|
||||
int heads;
|
||||
if (capacity <= 504 * Sizes.OneMiB)
|
||||
{
|
||||
heads = 16;
|
||||
}
|
||||
else if (capacity <= 1008 * Sizes.OneMiB)
|
||||
{
|
||||
heads = 32;
|
||||
}
|
||||
else if (capacity <= 2016 * Sizes.OneMiB)
|
||||
{
|
||||
heads = 64;
|
||||
}
|
||||
else if (capacity <= 4032 * Sizes.OneMiB)
|
||||
{
|
||||
heads = 128;
|
||||
}
|
||||
else
|
||||
{
|
||||
heads = 255;
|
||||
}
|
||||
|
||||
int sectors = 63;
|
||||
int cylinders = (int)Math.Min(1024, capacity / (sectors * (long)heads * Sizes.Sector));
|
||||
return new Geometry(cylinders, heads, sectors, Sizes.Sector);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Converts a geometry into one that is BIOS-safe, if not already.
|
||||
/// </summary>
|
||||
/// <param name="geometry">The geometry to make BIOS-safe.</param>
|
||||
/// <param name="capacity">The capacity of the disk.</param>
|
||||
/// <returns>The new geometry.</returns>
|
||||
/// <remarks>This method returns the LBA-Assisted geometry if the given geometry isn't BIOS-safe.</remarks>
|
||||
public static Geometry MakeBiosSafe(Geometry geometry, long capacity)
|
||||
{
|
||||
if (geometry == null)
|
||||
{
|
||||
return LbaAssistedBiosGeometry(capacity);
|
||||
}
|
||||
if (geometry.IsBiosSafe)
|
||||
{
|
||||
return geometry;
|
||||
}
|
||||
return LbaAssistedBiosGeometry(capacity);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Calculates a sensible disk geometry for a disk capacity using the VHD algorithm (errs under).
|
||||
/// </summary>
|
||||
/// <param name="capacity">The desired capacity of the disk.</param>
|
||||
/// <returns>The appropriate disk geometry.</returns>
|
||||
/// <remarks>The geometry returned tends to produce a disk with less capacity
|
||||
/// than requested (an exact capacity is not always possible). The geometry returned is the IDE
|
||||
/// (aka Physical) geometry of the disk, not necessarily the geometry used by the BIOS.</remarks>
|
||||
public static Geometry FromCapacity(long capacity)
|
||||
{
|
||||
return FromCapacity(capacity, Sizes.Sector);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Calculates a sensible disk geometry for a disk capacity using the VHD algorithm (errs under).
|
||||
/// </summary>
|
||||
/// <param name="capacity">The desired capacity of the disk.</param>
|
||||
/// <param name="sectorSize">The logical sector size of the disk.</param>
|
||||
/// <returns>The appropriate disk geometry.</returns>
|
||||
/// <remarks>The geometry returned tends to produce a disk with less capacity
|
||||
/// than requested (an exact capacity is not always possible). The geometry returned is the IDE
|
||||
/// (aka Physical) geometry of the disk, not necessarily the geometry used by the BIOS.</remarks>
|
||||
public static Geometry FromCapacity(long capacity, int sectorSize)
|
||||
{
|
||||
int totalSectors;
|
||||
int cylinders;
|
||||
int headsPerCylinder;
|
||||
int sectorsPerTrack;
|
||||
|
||||
// If more than ~128GB truncate at ~128GB
|
||||
if (capacity > 65535 * (long)16 * 255 * sectorSize)
|
||||
{
|
||||
totalSectors = 65535 * 16 * 255;
|
||||
}
|
||||
else
|
||||
{
|
||||
totalSectors = (int)(capacity / sectorSize);
|
||||
}
|
||||
|
||||
// If more than ~32GB, break partition table compatibility.
|
||||
// Partition table has max 63 sectors per track. Otherwise
|
||||
// we're looking for a geometry that's valid for both BIOS
|
||||
// and ATA.
|
||||
if (totalSectors > 65535 * 16 * 63)
|
||||
{
|
||||
sectorsPerTrack = 255;
|
||||
headsPerCylinder = 16;
|
||||
}
|
||||
else
|
||||
{
|
||||
sectorsPerTrack = 17;
|
||||
int cylindersTimesHeads = totalSectors / sectorsPerTrack;
|
||||
headsPerCylinder = (cylindersTimesHeads + 1023) / 1024;
|
||||
|
||||
if (headsPerCylinder < 4)
|
||||
{
|
||||
headsPerCylinder = 4;
|
||||
}
|
||||
|
||||
// If we need more than 1023 cylinders, or 16 heads, try more sectors per track
|
||||
if (cylindersTimesHeads >= headsPerCylinder * 1024U || headsPerCylinder > 16)
|
||||
{
|
||||
sectorsPerTrack = 31;
|
||||
headsPerCylinder = 16;
|
||||
cylindersTimesHeads = totalSectors / sectorsPerTrack;
|
||||
}
|
||||
|
||||
// We need 63 sectors per track to keep the cylinder count down
|
||||
if (cylindersTimesHeads >= headsPerCylinder * 1024U)
|
||||
{
|
||||
sectorsPerTrack = 63;
|
||||
headsPerCylinder = 16;
|
||||
}
|
||||
}
|
||||
|
||||
cylinders = totalSectors / sectorsPerTrack / headsPerCylinder;
|
||||
|
||||
return new Geometry(cylinders, headsPerCylinder, sectorsPerTrack, sectorSize);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Converts a CHS (Cylinder,Head,Sector) address to a LBA (Logical Block Address).
|
||||
/// </summary>
|
||||
/// <param name="chsAddress">The CHS address to convert.</param>
|
||||
/// <returns>The Logical Block Address (in sectors).</returns>
|
||||
public long ToLogicalBlockAddress(ChsAddress chsAddress)
|
||||
{
|
||||
return ToLogicalBlockAddress(chsAddress.Cylinder, chsAddress.Head, chsAddress.Sector);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Converts a CHS (Cylinder,Head,Sector) address to a LBA (Logical Block Address).
|
||||
/// </summary>
|
||||
/// <param name="cylinder">The cylinder of the address.</param>
|
||||
/// <param name="head">The head of the address.</param>
|
||||
/// <param name="sector">The sector of the address.</param>
|
||||
/// <returns>The Logical Block Address (in sectors).</returns>
|
||||
public long ToLogicalBlockAddress(int cylinder, int head, int sector)
|
||||
{
|
||||
if (cylinder < 0)
|
||||
{
|
||||
throw new ArgumentOutOfRangeException(nameof(cylinder), cylinder, "cylinder number is negative");
|
||||
}
|
||||
|
||||
if (head >= HeadsPerCylinder)
|
||||
{
|
||||
throw new ArgumentOutOfRangeException(nameof(head), head, "head number is larger than disk geometry");
|
||||
}
|
||||
|
||||
if (head < 0)
|
||||
{
|
||||
throw new ArgumentOutOfRangeException(nameof(head), head, "head number is negative");
|
||||
}
|
||||
|
||||
if (sector > SectorsPerTrack)
|
||||
{
|
||||
throw new ArgumentOutOfRangeException(nameof(sector), sector,
|
||||
"sector number is larger than disk geometry");
|
||||
}
|
||||
|
||||
if (sector < 1)
|
||||
{
|
||||
throw new ArgumentOutOfRangeException(nameof(sector), sector,
|
||||
"sector number is less than one (sectors are 1-based)");
|
||||
}
|
||||
|
||||
return (cylinder * (long)HeadsPerCylinder + head) * SectorsPerTrack + sector - 1;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Converts a LBA (Logical Block Address) to a CHS (Cylinder, Head, Sector) address.
|
||||
/// </summary>
|
||||
/// <param name="logicalBlockAddress">The logical block address (in sectors).</param>
|
||||
/// <returns>The address in CHS form.</returns>
|
||||
public ChsAddress ToChsAddress(long logicalBlockAddress)
|
||||
{
|
||||
if (logicalBlockAddress < 0)
|
||||
{
|
||||
throw new ArgumentOutOfRangeException(nameof(logicalBlockAddress), logicalBlockAddress,
|
||||
"Logical Block Address is negative");
|
||||
}
|
||||
|
||||
int cylinder = (int)(logicalBlockAddress / (HeadsPerCylinder * SectorsPerTrack));
|
||||
int temp = (int)(logicalBlockAddress % (HeadsPerCylinder * SectorsPerTrack));
|
||||
int head = temp / SectorsPerTrack;
|
||||
int sector = temp % SectorsPerTrack + 1;
|
||||
|
||||
return new ChsAddress(cylinder, head, sector);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Translates an IDE (aka Physical) geometry to a BIOS (aka Logical) geometry.
|
||||
/// </summary>
|
||||
/// <param name="translation">The translation to perform.</param>
|
||||
/// <returns>The translated disk geometry.</returns>
|
||||
public Geometry TranslateToBios(GeometryTranslation translation)
|
||||
{
|
||||
return TranslateToBios(0, translation);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Translates an IDE (aka Physical) geometry to a BIOS (aka Logical) geometry.
|
||||
/// </summary>
|
||||
/// <param name="capacity">The capacity of the disk, required if the geometry is an approximation on the actual disk size.</param>
|
||||
/// <param name="translation">The translation to perform.</param>
|
||||
/// <returns>The translated disk geometry.</returns>
|
||||
public Geometry TranslateToBios(long capacity, GeometryTranslation translation)
|
||||
{
|
||||
if (capacity <= 0)
|
||||
{
|
||||
capacity = TotalSectorsLong * 512L;
|
||||
}
|
||||
|
||||
switch (translation)
|
||||
{
|
||||
case GeometryTranslation.None:
|
||||
return this;
|
||||
|
||||
case GeometryTranslation.Auto:
|
||||
if (IsBiosSafe)
|
||||
{
|
||||
return this;
|
||||
}
|
||||
return LbaAssistedBiosGeometry(capacity);
|
||||
|
||||
case GeometryTranslation.Lba:
|
||||
return LbaAssistedBiosGeometry(capacity);
|
||||
|
||||
case GeometryTranslation.Large:
|
||||
return LargeBiosGeometry(this);
|
||||
|
||||
default:
|
||||
throw new ArgumentException(
|
||||
string.Format(CultureInfo.InvariantCulture, "Translation mode '{0}' not yet implemented",
|
||||
translation), nameof(translation));
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Determines if this object is equivalent to another.
|
||||
/// </summary>
|
||||
/// <param name="obj">The object to test against.</param>
|
||||
/// <returns><c>true</c> if the <paramref name="obj"/> is equivalent, else <c>false</c>.</returns>
|
||||
public override bool Equals(object obj)
|
||||
{
|
||||
if (obj == null || obj.GetType() != GetType())
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
Geometry other = (Geometry)obj;
|
||||
|
||||
return Cylinders == other.Cylinders && HeadsPerCylinder == other.HeadsPerCylinder
|
||||
&& SectorsPerTrack == other.SectorsPerTrack && BytesPerSector == other.BytesPerSector;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Calculates the hash code for this object.
|
||||
/// </summary>
|
||||
/// <returns>The hash code.</returns>
|
||||
public override int GetHashCode()
|
||||
{
|
||||
return Cylinders.GetHashCode() ^ HeadsPerCylinder.GetHashCode()
|
||||
^ SectorsPerTrack.GetHashCode() ^ BytesPerSector.GetHashCode();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets a string representation of this object, in the form (C/H/S).
|
||||
/// </summary>
|
||||
/// <returns>The string representation.</returns>
|
||||
public override string ToString()
|
||||
{
|
||||
if (BytesPerSector == 512)
|
||||
{
|
||||
return "(" + Cylinders + "/" + HeadsPerCylinder + "/" + SectorsPerTrack + ")";
|
||||
}
|
||||
return "(" + Cylinders + "/" + HeadsPerCylinder + "/" + SectorsPerTrack + ":" + BytesPerSector + ")";
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,9 +0,0 @@
|
|||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Delegate for calculating a disk geometry from a capacity.
|
||||
/// </summary>
|
||||
/// <param name="capacity">The disk capacity to convert.</param>
|
||||
/// <returns>The appropriate geometry for the disk.</returns>
|
||||
public delegate Geometry GeometryCalculation(long capacity);
|
||||
}
|
|
@ -1,50 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Enumeration of standard BIOS disk geometry translation methods.
|
||||
/// </summary>
|
||||
public enum GeometryTranslation
|
||||
{
|
||||
/// <summary>
|
||||
/// Apply no translation.
|
||||
/// </summary>
|
||||
None = 0,
|
||||
|
||||
/// <summary>
|
||||
/// Automatic, based on the physical geometry select the most appropriate translation.
|
||||
/// </summary>
|
||||
Auto = 1,
|
||||
|
||||
/// <summary>
|
||||
/// LBA assisted translation, based on just the disk capacity.
|
||||
/// </summary>
|
||||
Lba = 2,
|
||||
|
||||
/// <summary>
|
||||
/// Bit-shifting translation, based on the physical geometry of the disk.
|
||||
/// </summary>
|
||||
Large = 3
|
||||
}
|
||||
}
|
|
@ -1,81 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using DiscUtils.Streams;
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Base class for all file systems based on a cluster model.
|
||||
/// </summary>
|
||||
public interface IClusterBasedFileSystem : IFileSystem
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets the size (in bytes) of each cluster.
|
||||
/// </summary>
|
||||
long ClusterSize { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the total number of clusters managed by the file system.
|
||||
/// </summary>
|
||||
long TotalClusters { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Converts a cluster (index) into an absolute byte position in the underlying stream.
|
||||
/// </summary>
|
||||
/// <param name="cluster">The cluster to convert.</param>
|
||||
/// <returns>The corresponding absolute byte position.</returns>
|
||||
long ClusterToOffset(long cluster);
|
||||
|
||||
/// <summary>
|
||||
/// Converts an absolute byte position in the underlying stream to a cluster (index).
|
||||
/// </summary>
|
||||
/// <param name="offset">The byte position to convert.</param>
|
||||
/// <returns>The cluster containing the specified byte.</returns>
|
||||
long OffsetToCluster(long offset);
|
||||
|
||||
/// <summary>
|
||||
/// Converts a file name to the list of clusters occupied by the file's data.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to inspect.</param>
|
||||
/// <returns>The clusters.</returns>
|
||||
/// <remarks>Note that in some file systems, small files may not have dedicated
|
||||
/// clusters. Only dedicated clusters will be returned.</remarks>
|
||||
Range<long, long>[] PathToClusters(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Converts a file name to the extents containing its data.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to inspect.</param>
|
||||
/// <returns>The file extents, as absolute byte positions in the underlying stream.</returns>
|
||||
/// <remarks>Use this method with caution - not all file systems will store all bytes
|
||||
/// directly in extents. Files may be compressed, sparse or encrypted. This method
|
||||
/// merely indicates where file data is stored, not what's stored.</remarks>
|
||||
StreamExtent[] PathToExtents(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Gets an object that can convert between clusters and files.
|
||||
/// </summary>
|
||||
/// <returns>The cluster map.</returns>
|
||||
ClusterMap BuildClusterMap();
|
||||
}
|
||||
}
|
|
@ -1,39 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System.IO;
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Interface exposed by objects that can provide a structured trace of their content.
|
||||
/// </summary>
|
||||
public interface IDiagnosticTraceable
|
||||
{
|
||||
/// <summary>
|
||||
/// Writes a diagnostic report about the state of the object to a writer.
|
||||
/// </summary>
|
||||
/// <param name="writer">The writer to send the report to.</param>
|
||||
/// <param name="linePrefix">The prefix to place at the start of each line.</param>
|
||||
void Dump(TextWriter writer, string linePrefix);
|
||||
}
|
||||
}
|
|
@ -1,367 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System;
|
||||
using System.IO;
|
||||
using DiscUtils.Streams;
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Common interface for all file systems.
|
||||
/// </summary>
|
||||
public interface IFileSystem
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets a value indicating whether the file system is read-only or read-write.
|
||||
/// </summary>
|
||||
/// <returns>true if the file system is read-write.</returns>
|
||||
bool CanWrite { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets a value indicating whether the file system is thread-safe.
|
||||
/// </summary>
|
||||
bool IsThreadSafe { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the root directory of the file system.
|
||||
/// </summary>
|
||||
DiscDirectoryInfo Root { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Copies an existing file to a new file.
|
||||
/// </summary>
|
||||
/// <param name="sourceFile">The source file.</param>
|
||||
/// <param name="destinationFile">The destination file.</param>
|
||||
void CopyFile(string sourceFile, string destinationFile);
|
||||
|
||||
/// <summary>
|
||||
/// Copies an existing file to a new file, allowing overwriting of an existing file.
|
||||
/// </summary>
|
||||
/// <param name="sourceFile">The source file.</param>
|
||||
/// <param name="destinationFile">The destination file.</param>
|
||||
/// <param name="overwrite">Whether to permit over-writing of an existing file.</param>
|
||||
void CopyFile(string sourceFile, string destinationFile, bool overwrite);
|
||||
|
||||
/// <summary>
|
||||
/// Creates a directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the new directory.</param>
|
||||
void CreateDirectory(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Deletes a directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the directory to delete.</param>
|
||||
void DeleteDirectory(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Deletes a directory, optionally with all descendants.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the directory to delete.</param>
|
||||
/// <param name="recursive">Determines if the all descendants should be deleted.</param>
|
||||
void DeleteDirectory(string path, bool recursive);
|
||||
|
||||
/// <summary>
|
||||
/// Deletes a file.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file to delete.</param>
|
||||
void DeleteFile(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Indicates if a directory exists.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to test.</param>
|
||||
/// <returns>true if the directory exists.</returns>
|
||||
bool DirectoryExists(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Indicates if a file exists.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to test.</param>
|
||||
/// <returns>true if the file exists.</returns>
|
||||
bool FileExists(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Indicates if a file or directory exists.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to test.</param>
|
||||
/// <returns>true if the file or directory exists.</returns>
|
||||
bool Exists(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the names of subdirectories in a specified directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to search.</param>
|
||||
/// <returns>Array of directories.</returns>
|
||||
string[] GetDirectories(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the names of subdirectories in a specified directory matching a specified
|
||||
/// search pattern.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to search.</param>
|
||||
/// <param name="searchPattern">The search string to match against.</param>
|
||||
/// <returns>Array of directories matching the search pattern.</returns>
|
||||
string[] GetDirectories(string path, string searchPattern);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the names of subdirectories in a specified directory matching a specified
|
||||
/// search pattern, using a value to determine whether to search subdirectories.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to search.</param>
|
||||
/// <param name="searchPattern">The search string to match against.</param>
|
||||
/// <param name="searchOption">Indicates whether to search subdirectories.</param>
|
||||
/// <returns>Array of directories matching the search pattern.</returns>
|
||||
string[] GetDirectories(string path, string searchPattern, SearchOption searchOption);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the names of files in a specified directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to search.</param>
|
||||
/// <returns>Array of files.</returns>
|
||||
string[] GetFiles(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the names of files in a specified directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to search.</param>
|
||||
/// <param name="searchPattern">The search string to match against.</param>
|
||||
/// <returns>Array of files matching the search pattern.</returns>
|
||||
string[] GetFiles(string path, string searchPattern);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the names of files in a specified directory matching a specified
|
||||
/// search pattern, using a value to determine whether to search subdirectories.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to search.</param>
|
||||
/// <param name="searchPattern">The search string to match against.</param>
|
||||
/// <param name="searchOption">Indicates whether to search subdirectories.</param>
|
||||
/// <returns>Array of files matching the search pattern.</returns>
|
||||
string[] GetFiles(string path, string searchPattern, SearchOption searchOption);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the names of all files and subdirectories in a specified directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to search.</param>
|
||||
/// <returns>Array of files and subdirectories matching the search pattern.</returns>
|
||||
string[] GetFileSystemEntries(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the names of files and subdirectories in a specified directory matching a specified
|
||||
/// search pattern.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to search.</param>
|
||||
/// <param name="searchPattern">The search string to match against.</param>
|
||||
/// <returns>Array of files and subdirectories matching the search pattern.</returns>
|
||||
string[] GetFileSystemEntries(string path, string searchPattern);
|
||||
|
||||
/// <summary>
|
||||
/// Moves a directory.
|
||||
/// </summary>
|
||||
/// <param name="sourceDirectoryName">The directory to move.</param>
|
||||
/// <param name="destinationDirectoryName">The target directory name.</param>
|
||||
void MoveDirectory(string sourceDirectoryName, string destinationDirectoryName);
|
||||
|
||||
/// <summary>
|
||||
/// Moves a file.
|
||||
/// </summary>
|
||||
/// <param name="sourceName">The file to move.</param>
|
||||
/// <param name="destinationName">The target file name.</param>
|
||||
void MoveFile(string sourceName, string destinationName);
|
||||
|
||||
/// <summary>
|
||||
/// Moves a file, allowing an existing file to be overwritten.
|
||||
/// </summary>
|
||||
/// <param name="sourceName">The file to move.</param>
|
||||
/// <param name="destinationName">The target file name.</param>
|
||||
/// <param name="overwrite">Whether to permit a destination file to be overwritten.</param>
|
||||
void MoveFile(string sourceName, string destinationName, bool overwrite);
|
||||
|
||||
/// <summary>
|
||||
/// Opens the specified file.
|
||||
/// </summary>
|
||||
/// <param name="path">The full path of the file to open.</param>
|
||||
/// <param name="mode">The file mode for the created stream.</param>
|
||||
/// <returns>The new stream.</returns>
|
||||
SparseStream OpenFile(string path, FileMode mode);
|
||||
|
||||
/// <summary>
|
||||
/// Opens the specified file.
|
||||
/// </summary>
|
||||
/// <param name="path">The full path of the file to open.</param>
|
||||
/// <param name="mode">The file mode for the created stream.</param>
|
||||
/// <param name="access">The access permissions for the created stream.</param>
|
||||
/// <returns>The new stream.</returns>
|
||||
SparseStream OpenFile(string path, FileMode mode, FileAccess access);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the attributes of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The file or directory to inspect.</param>
|
||||
/// <returns>The attributes of the file or directory.</returns>
|
||||
FileAttributes GetAttributes(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Sets the attributes of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The file or directory to change.</param>
|
||||
/// <param name="newValue">The new attributes of the file or directory.</param>
|
||||
void SetAttributes(string path, FileAttributes newValue);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the creation time (in local time) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <returns>The creation time.</returns>
|
||||
DateTime GetCreationTime(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Sets the creation time (in local time) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <param name="newTime">The new time to set.</param>
|
||||
void SetCreationTime(string path, DateTime newTime);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the creation time (in UTC) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <returns>The creation time.</returns>
|
||||
DateTime GetCreationTimeUtc(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Sets the creation time (in UTC) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <param name="newTime">The new time to set.</param>
|
||||
void SetCreationTimeUtc(string path, DateTime newTime);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the last access time (in local time) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <returns>The last access time.</returns>
|
||||
DateTime GetLastAccessTime(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Sets the last access time (in local time) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <param name="newTime">The new time to set.</param>
|
||||
void SetLastAccessTime(string path, DateTime newTime);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the last access time (in UTC) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <returns>The last access time.</returns>
|
||||
DateTime GetLastAccessTimeUtc(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Sets the last access time (in UTC) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <param name="newTime">The new time to set.</param>
|
||||
void SetLastAccessTimeUtc(string path, DateTime newTime);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the last modification time (in local time) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <returns>The last write time.</returns>
|
||||
DateTime GetLastWriteTime(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Sets the last modification time (in local time) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <param name="newTime">The new time to set.</param>
|
||||
void SetLastWriteTime(string path, DateTime newTime);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the last modification time (in UTC) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <returns>The last write time.</returns>
|
||||
DateTime GetLastWriteTimeUtc(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Sets the last modification time (in UTC) of a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the file or directory.</param>
|
||||
/// <param name="newTime">The new time to set.</param>
|
||||
void SetLastWriteTimeUtc(string path, DateTime newTime);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the length of a file.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to the file.</param>
|
||||
/// <returns>The length in bytes.</returns>
|
||||
long GetFileLength(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Gets an object representing a possible file.
|
||||
/// </summary>
|
||||
/// <param name="path">The file path.</param>
|
||||
/// <returns>The representing object.</returns>
|
||||
/// <remarks>The file does not need to exist.</remarks>
|
||||
DiscFileInfo GetFileInfo(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Gets an object representing a possible directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The directory path.</param>
|
||||
/// <returns>The representing object.</returns>
|
||||
/// <remarks>The directory does not need to exist.</remarks>
|
||||
DiscDirectoryInfo GetDirectoryInfo(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Gets an object representing a possible file system object (file or directory).
|
||||
/// </summary>
|
||||
/// <param name="path">The file system path.</param>
|
||||
/// <returns>The representing object.</returns>
|
||||
/// <remarks>The file system object does not need to exist.</remarks>
|
||||
DiscFileSystemInfo GetFileSystemInfo(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Reads the boot code of the file system into a byte array.
|
||||
/// </summary>
|
||||
/// <returns>The boot code, or <c>null</c> if not available.</returns>
|
||||
byte[] ReadBootCode();
|
||||
|
||||
/// <summary>
|
||||
/// Size of the Filesystem in bytes
|
||||
/// </summary>
|
||||
long Size { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Used space of the Filesystem in bytes
|
||||
/// </summary>
|
||||
long UsedSpace { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Available space of the Filesystem in bytes
|
||||
/// </summary>
|
||||
long AvailableSpace { get; }
|
||||
}
|
||||
}
|
|
@ -1,38 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Provides the base class for all file systems that support Unix semantics.
|
||||
/// </summary>
|
||||
public interface IUnixFileSystem : IFileSystem
|
||||
{
|
||||
/// <summary>
|
||||
/// Retrieves Unix-specific information about a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">Path to the file or directory.</param>
|
||||
/// <returns>Information about the owner, group, permissions and type of the
|
||||
/// file or directory.</returns>
|
||||
UnixFileSystemInfo GetUnixFileInfo(string path);
|
||||
}
|
||||
}
|
|
@ -1,129 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
using System.Security.AccessControl;
|
||||
|
||||
namespace DiscUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Provides the base class for all file systems that support Windows semantics.
|
||||
/// </summary>
|
||||
public interface IWindowsFileSystem : IFileSystem
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets the security descriptor associated with the file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The file or directory to inspect.</param>
|
||||
/// <returns>The security descriptor.</returns>
|
||||
RawSecurityDescriptor GetSecurity(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Sets the security descriptor associated with the file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The file or directory to change.</param>
|
||||
/// <param name="securityDescriptor">The new security descriptor.</param>
|
||||
void SetSecurity(string path, RawSecurityDescriptor securityDescriptor);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the reparse point data associated with a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The file to query.</param>
|
||||
/// <returns>The reparse point information.</returns>
|
||||
ReparsePoint GetReparsePoint(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Sets the reparse point data on a file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The file to set the reparse point on.</param>
|
||||
/// <param name="reparsePoint">The new reparse point.</param>
|
||||
void SetReparsePoint(string path, ReparsePoint reparsePoint);
|
||||
|
||||
/// <summary>
|
||||
/// Removes a reparse point from a file or directory, without deleting the file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to the file or directory to remove the reparse point from.</param>
|
||||
void RemoveReparsePoint(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the short name for a given path.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to convert.</param>
|
||||
/// <returns>The short name.</returns>
|
||||
/// <remarks>
|
||||
/// This method only gets the short name for the final part of the path, to
|
||||
/// convert a complete path, call this method repeatedly, once for each path
|
||||
/// segment. If there is no short name for the given path,<c>null</c> is
|
||||
/// returned.
|
||||
/// </remarks>
|
||||
string GetShortName(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Sets the short name for a given file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">The full path to the file or directory to change.</param>
|
||||
/// <param name="shortName">The shortName, which should not include a path.</param>
|
||||
void SetShortName(string path, string shortName);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the standard file information for a file.
|
||||
/// </summary>
|
||||
/// <param name="path">The full path to the file or directory to query.</param>
|
||||
/// <returns>The standard file information.</returns>
|
||||
WindowsFileInformation GetFileStandardInformation(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Sets the standard file information for a file.
|
||||
/// </summary>
|
||||
/// <param name="path">The full path to the file or directory to query.</param>
|
||||
/// <param name="info">The standard file information.</param>
|
||||
void SetFileStandardInformation(string path, WindowsFileInformation info);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the names of the alternate data streams for a file.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to the file.</param>
|
||||
/// <returns>
|
||||
/// The list of alternate data streams (or empty, if none). To access the contents
|
||||
/// of the alternate streams, use OpenFile(path + ":" + name, ...).
|
||||
/// </returns>
|
||||
string[] GetAlternateDataStreams(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the file id for a given path.
|
||||
/// </summary>
|
||||
/// <param name="path">The path to get the id of.</param>
|
||||
/// <returns>The file id, or -1.</returns>
|
||||
/// <remarks>
|
||||
/// The returned file id uniquely identifies the file, and is shared by all hard
|
||||
/// links to the same file. The value -1 indicates no unique identifier is
|
||||
/// available, and so it can be assumed the file has no hard links.
|
||||
/// </remarks>
|
||||
long GetFileId(string path);
|
||||
|
||||
/// <summary>
|
||||
/// Indicates whether the file is known by other names.
|
||||
/// </summary>
|
||||
/// <param name="path">The file to inspect.</param>
|
||||
/// <returns><c>true</c> if the file has other names, else <c>false</c>.</returns>
|
||||
bool HasHardLinks(string path);
|
||||
}
|
||||
}
|
|
@ -1,43 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
namespace DiscUtils.Internal
|
||||
{
|
||||
internal abstract class Crc32
|
||||
{
|
||||
protected readonly uint[] Table;
|
||||
protected uint _value;
|
||||
|
||||
protected Crc32(uint[] table)
|
||||
{
|
||||
Table = table;
|
||||
_value = 0xFFFFFFFF;
|
||||
}
|
||||
|
||||
public uint Value
|
||||
{
|
||||
get { return _value ^ 0xFFFFFFFF; }
|
||||
}
|
||||
|
||||
public abstract void Process(byte[] buffer, int offset, int count);
|
||||
}
|
||||
}
|
|
@ -1,47 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
namespace DiscUtils.Internal
|
||||
{
|
||||
internal enum Crc32Algorithm
|
||||
{
|
||||
/// <summary>
|
||||
/// Used in Ethernet, PKZIP, BZIP2, Gzip, PNG, etc. (aka CRC32).
|
||||
/// </summary>
|
||||
Common = 0,
|
||||
|
||||
/// <summary>
|
||||
/// Used in iSCSI, SCTP, Btrfs, Vhdx. (aka CRC32C).
|
||||
/// </summary>
|
||||
Castagnoli = 1,
|
||||
|
||||
/// <summary>
|
||||
/// Unknown usage. (aka CRC32K).
|
||||
/// </summary>
|
||||
Koopman = 2,
|
||||
|
||||
/// <summary>
|
||||
/// Used in AIXM. (aka CRC32Q).
|
||||
/// </summary>
|
||||
Aeronautical = 3
|
||||
}
|
||||
}
|
|
@ -1,94 +0,0 @@
|
|||
//
|
||||
// Copyright (c) 2008-2011, Kenneth Bell
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
//
|
||||
|
||||
namespace DiscUtils.Internal
|
||||
{
|
||||
/// <summary>
|
||||
/// Calculates CRC32 of buffers.
|
||||
/// </summary>
|
||||
internal sealed class Crc32BigEndian : Crc32
|
||||
{
|
||||
private static readonly uint[][] Tables;
|
||||
|
||||
static Crc32BigEndian()
|
||||
{
|
||||
Tables = new uint[4][];
|
||||
|
||||
Tables[(int)Crc32Algorithm.Common] = CalcTable(0x04C11DB7);
|
||||
Tables[(int)Crc32Algorithm.Castagnoli] = CalcTable(0x1EDC6F41);
|
||||
Tables[(int)Crc32Algorithm.Koopman] = CalcTable(0x741B8CD7);
|
||||
Tables[(int)Crc32Algorithm.Aeronautical] = CalcTable(0x814141AB);
|
||||
}
|
||||
|
||||
public Crc32BigEndian(Crc32Algorithm algorithm)
|
||||
: base(Tables[(int)algorithm]) {}
|
||||
|
||||
public static uint Compute(Crc32Algorithm algorithm, byte[] buffer, int offset, int count)
|
||||
{
|
||||
return Process(Tables[(int)algorithm], 0xFFFFFFFF, buffer, offset, count) ^ 0xFFFFFFFF;
|
||||
}
|
||||
|
||||
public override void Process(byte[] buffer, int offset, int count)
|
||||
{
|
||||
_value = Process(Table, _value, buffer, offset, count);
|
||||
}
|
||||
|
||||
private static uint[] CalcTable(uint polynomial)
|
||||
{
|
||||
uint[] table = new uint[256];
|
||||
|
||||
for (uint i = 0; i < 256; ++i)
|
||||
{
|
||||
uint crc = i << 24;
|
||||
|
||||
for (int j = 8; j > 0; --j)
|
||||
{
|
||||
if ((crc & 0x80000000) != 0)
|
||||
{
|
||||
crc = (crc << 1) ^ polynomial;
|
||||
}
|
||||
else
|
||||
{
|
||||
crc <<= 1;
|
||||
}
|
||||
}
|
||||
|
||||
table[i] = crc;
|
||||
}
|
||||
|
||||
return table;
|
||||
}
|
||||
|
||||
private static uint Process(uint[] table, uint accumulator, byte[] buffer, int offset, int count)
|
||||
{
|
||||
uint value = accumulator;
|
||||
|
||||
for (int i = 0; i < count; ++i)
|
||||
{
|
||||
byte b = buffer[offset + i];
|
||||
value = table[(value >> 24) ^ b] ^ (value << 8);
|
||||
}
|
||||
|
||||
return value;
|
||||
}
|
||||
}
|
||||
}
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue