int T64Archive::getNumberOfItems() { int noOfItems; // Get number of files from the file header... noOfItems = LO_HI(data[0x24], data[0x25]); if (noOfItems == 0) { // Note: Some archives don't store this value properly. // In this case, we can determine the number of files // by iterating through the directory area... while (directoryItemIsPresent(noOfItems)) noOfItems++; } return noOfItems; }
bool T64File::repair() { unsigned i, n; uint16_t noOfItems = numberOfItems(); // // 1. Repair number of items, if this value is zero // if (noOfItems == 0) { while (directoryItemIsPresent(noOfItems)) noOfItems++; uint16_t noOfItemsStatedInHeader = numberOfItems(); if (noOfItems != noOfItemsStatedInHeader) { debug(1, "Repairing corrupted T64 archive: Changing number of items from %d to %d.\n", noOfItemsStatedInHeader, noOfItems); data[0x24] = LO_BYTE(noOfItems); data[0x25] = HI_BYTE(noOfItems); } assert(noOfItems == numberOfItems()); } for (i = 0; i < noOfItems; i++) { // // 2. Check relative offset information for each item // // Compute start address in file n = 0x48 + (i * 0x20); uint16_t startAddrInContainer = LO_LO_HI_HI(data[n], data[n+1], data[n+2], data[n+3]); if (startAddrInContainer >= size) { warn("T64 archive is corrupt (offset mismatch). Sorry, can't repair.\n"); return false; } // // 3. Check for file end address mismatches (as created by CONVC64) // // Compute start address in memory n = 0x42 + (i * 0x20); uint16_t startAddrInMemory = LO_HI(data[n], data[n+1]); // Compute end address in memory n = 0x44 + (i * 0x20); uint16_t endAddrInMemory = LO_HI(data[n], data[n+1]); if (endAddrInMemory == 0xC3C6) { // Let's assume that the rest of the file data belongs to this file ... uint16_t fixedEndAddrInMemory = startAddrInMemory + (size - startAddrInContainer); debug(1, "Repairing corrupted T64 archive: Changing end address of item %d from %04X to %04X.\n", i, endAddrInMemory, fixedEndAddrInMemory); data[n] = LO_BYTE(fixedEndAddrInMemory); data[n+1] = HI_BYTE(fixedEndAddrInMemory); } } return 1; // Archive repaired successfully }