Implement support for reading file format header version 2.

This commit is contained in:
2025-08-02 20:23:32 +01:00
parent 9a5a994702
commit b504c8392d
10 changed files with 71 additions and 46 deletions

View File

@@ -30,7 +30,15 @@
#define AARU_MAGIC 0x544D524655524141 #define AARU_MAGIC 0x544D524655524141
/** Image format version. A change in this number indicates an incompatible change to the format that prevents older /** Image format version. A change in this number indicates an incompatible change to the format that prevents older
* implementations from reading it correctly, if at all. */ * implementations from reading it correctly, if at all. */
#define AARUF_VERSION 1 #define AARUF_VERSION 2
/** First version of AaruFormat, created in C#.
* CRC64 was byte-swapped
*/
#define AARUF_VERSION_V1 1
/** Second version of AaruFormat, created in C.
* Introduced new header, many new features, and blocks.
*/
#define AARUF_VERSION_V2 2
/** Maximum read cache size, 512MiB. */ /** Maximum read cache size, 512MiB. */
#define MAX_CACHE_SIZE 536870912 #define MAX_CACHE_SIZE 536870912
/** Size in bytes of LZMA properties. */ /** Size in bytes of LZMA properties. */

View File

@@ -34,13 +34,15 @@
#define SHA256_DIGEST_LENGTH 32 #define SHA256_DIGEST_LENGTH 32
#endif #endif
typedef struct Crc64Context { typedef struct Crc64Context
{
uint64_t finalSeed; uint64_t finalSeed;
uint64_t table[256]; uint64_t table[256];
uint64_t hashInt; uint64_t hashInt;
} Crc64Context; } Crc64Context;
typedef struct CdEccContext { typedef struct CdEccContext
{
bool initedEdc; bool initedEdc;
uint8_t *eccBTable; uint8_t *eccBTable;
uint8_t *eccFTable; uint8_t *eccFTable;
@@ -73,7 +75,7 @@ typedef struct aaruformatContext
uint8_t libraryMajorVersion; uint8_t libraryMajorVersion;
uint8_t libraryMinorVersion; uint8_t libraryMinorVersion;
FILE *imageStream; FILE *imageStream;
AaruHeader header; AaruHeaderV2 header;
uint8_t *sectorPrefix; uint8_t *sectorPrefix;
uint8_t *sectorPrefixCorrected; uint8_t *sectorPrefixCorrected;
uint8_t *sectorSuffix; uint8_t *sectorSuffix;

View File

@@ -219,7 +219,7 @@ int32_t process_data_block(aaruformatContext *ctx, IndexEntry *entry)
crc64 = aaruf_crc64_data(data, blockHeader.length); crc64 = aaruf_crc64_data(data, blockHeader.length);
// Due to how C# wrote it, it is effectively reversed // Due to how C# wrote it, it is effectively reversed
if(ctx->header.imageMajorVersion <= AARUF_VERSION) crc64 = bswap_64(crc64); if(ctx->header.imageMajorVersion <= AARUF_VERSION_V1) crc64 = bswap_64(crc64);
if(crc64 != blockHeader.crc64) if(crc64 != blockHeader.crc64)
{ {

View File

@@ -79,7 +79,7 @@ void process_dumphw_block(aaruformatContext *ctx, const IndexEntry *entry)
crc64 = aaruf_crc64_data(data, ctx->dumpHardwareHeader.length); crc64 = aaruf_crc64_data(data, ctx->dumpHardwareHeader.length);
// Due to how C# wrote it, it is effectively reversed // Due to how C# wrote it, it is effectively reversed
if(ctx->header.imageMajorVersion <= AARUF_VERSION) crc64 = bswap_64(crc64); if(ctx->header.imageMajorVersion <= AARUF_VERSION_V1) crc64 = bswap_64(crc64);
if(crc64 != ctx->dumpHardwareHeader.crc64) if(crc64 != ctx->dumpHardwareHeader.crc64)
{ {

View File

@@ -87,7 +87,7 @@ void process_tracks_block(aaruformatContext *ctx, const IndexEntry *entry)
crc64 = aaruf_crc64_data((const uint8_t *)ctx->trackEntries, ctx->tracksHeader.entries * sizeof(TrackEntry)); crc64 = aaruf_crc64_data((const uint8_t *)ctx->trackEntries, ctx->tracksHeader.entries * sizeof(TrackEntry));
// Due to how C# wrote it, it is effectively reversed // Due to how C# wrote it, it is effectively reversed
if(ctx->header.imageMajorVersion <= AARUF_VERSION) crc64 = bswap_64(crc64); if(ctx->header.imageMajorVersion <= AARUF_VERSION_V1) crc64 = bswap_64(crc64);
if(crc64 != ctx->tracksHeader.crc64) if(crc64 != ctx->tracksHeader.crc64)
{ {

View File

@@ -107,7 +107,7 @@ int32_t verify_index_v1(aaruformatContext *ctx)
crc64 = aaruf_crc64_data((const uint8_t *)index_entries, sizeof(IndexEntry) * index_header.entries); crc64 = aaruf_crc64_data((const uint8_t *)index_entries, sizeof(IndexEntry) * index_header.entries);
// Due to how C# wrote it, it is effectively reversed // Due to how C# wrote it, it is effectively reversed
if(ctx->header.imageMajorVersion <= AARUF_VERSION) crc64 = bswap_64(crc64); if(ctx->header.imageMajorVersion <= AARUF_VERSION_V1) crc64 = bswap_64(crc64);
if(crc64 != index_header.crc64) if(crc64 != index_header.crc64)
{ {

View File

@@ -107,7 +107,7 @@ int32_t verify_index_v2(aaruformatContext *ctx)
crc64 = aaruf_crc64_data((const uint8_t *)index_entries, sizeof(IndexEntry) * index_header.entries); crc64 = aaruf_crc64_data((const uint8_t *)index_entries, sizeof(IndexEntry) * index_header.entries);
// Due to how C# wrote it, it is effectively reversed // Due to how C# wrote it, it is effectively reversed
if(ctx->header.imageMajorVersion <= AARUF_VERSION) crc64 = bswap_64(crc64); if(ctx->header.imageMajorVersion <= AARUF_VERSION_V1) crc64 = bswap_64(crc64);
if(crc64 != index_header.crc64) if(crc64 != index_header.crc64)
{ {

View File

@@ -76,6 +76,21 @@ void *aaruf_open(const char *filepath)
return NULL; return NULL;
} }
// Read new header version
if(ctx->header.imageMajorVersion >= AARUF_VERSION_V2)
{
fseek(ctx->imageStream, 0, SEEK_SET);
readBytes = fread(&ctx->header, 1, sizeof(AaruHeaderV2), ctx->imageStream);
if(readBytes != sizeof(AaruHeaderV2))
{
free(ctx);
errno = AARUF_ERROR_FILE_TOO_SMALL;
return NULL;
}
}
if(ctx->header.imageMajorVersion > AARUF_VERSION) if(ctx->header.imageMajorVersion > AARUF_VERSION)
{ {
free(ctx); free(ctx);

View File

@@ -137,7 +137,7 @@ int32_t aaruf_verify_image(void *context)
aaruf_crc64_final(crc64_context, &crc64); aaruf_crc64_final(crc64_context, &crc64);
// Due to how C# wrote it, it is effectively reversed // Due to how C# wrote it, it is effectively reversed
if(ctx->header.imageMajorVersion <= AARUF_VERSION) crc64 = bswap_64(crc64); if(ctx->header.imageMajorVersion <= AARUF_VERSION_V1) crc64 = bswap_64(crc64);
if(crc64 != block_header.cmpCrc64) if(crc64 != block_header.cmpCrc64)
{ {
@@ -180,7 +180,7 @@ int32_t aaruf_verify_image(void *context)
aaruf_crc64_final(crc64_context, &crc64); aaruf_crc64_final(crc64_context, &crc64);
// Due to how C# wrote it, it is effectively reversed // Due to how C# wrote it, it is effectively reversed
if(ctx->header.imageMajorVersion <= AARUF_VERSION) crc64 = bswap_64(crc64); if(ctx->header.imageMajorVersion <= AARUF_VERSION_V1) crc64 = bswap_64(crc64);
if(crc64 != ddt_header.cmpCrc64) if(crc64 != ddt_header.cmpCrc64)
{ {
@@ -214,7 +214,7 @@ int32_t aaruf_verify_image(void *context)
aaruf_crc64_final(crc64_context, &crc64); aaruf_crc64_final(crc64_context, &crc64);
// Due to how C# wrote it, it is effectively reversed // Due to how C# wrote it, it is effectively reversed
if(ctx->header.imageMajorVersion <= AARUF_VERSION) crc64 = bswap_64(crc64); if(ctx->header.imageMajorVersion <= AARUF_VERSION_V1) crc64 = bswap_64(crc64);
if(crc64 != tracks_header.crc64) if(crc64 != tracks_header.crc64)
{ {

View File

@@ -59,7 +59,7 @@ int info(char *path)
printf("\tApplication version: %d.%d\n", ctx->header.applicationMajorVersion, ctx->header.applicationMinorVersion); printf("\tApplication version: %d.%d\n", ctx->header.applicationMajorVersion, ctx->header.applicationMinorVersion);
printf("\tImage format version: %d.%d\n", ctx->header.imageMajorVersion, ctx->header.imageMinorVersion); printf("\tImage format version: %d.%d\n", ctx->header.imageMajorVersion, ctx->header.imageMinorVersion);
printf("\tMedia type: %d\n", ctx->header.mediaType); printf("\tMedia type: %u\n", ctx->header.mediaType);
printf("\tIndex offset: %llu\n", ctx->header.indexOffset); printf("\tIndex offset: %llu\n", ctx->header.indexOffset);
printf("\tCreation time: %lld\n", ctx->header.creationTime); printf("\tCreation time: %lld\n", ctx->header.creationTime);
printf("\tLast written time: %lld\n", ctx->header.lastWrittenTime); printf("\tLast written time: %lld\n", ctx->header.lastWrittenTime);