| 535 | |
| 536 | template<typename Platform> |
| 537 | bool NFS2<Platform>::LoadTRK(std::string trk_path, const shared_ptr<typename Platform::TRACK> &track) { |
| 538 | LOG(INFO) << "Loading TRK File located at " << trk_path; |
| 539 | ifstream trk(trk_path, ios::in | ios::binary); |
| 540 | // TRK file header data |
| 541 | unsigned char header[4]; |
| 542 | long unknownHeader[5]; |
| 543 | |
| 544 | // Check we're in a valid TRK file |
| 545 | if (trk.read(((char *) header), sizeof(unsigned char) * 4).gcount() != sizeof(unsigned char) * 4) { |
| 546 | LOG(WARNING) << "Couldn't open file/truncated."; |
| 547 | return false; |
| 548 | } |
| 549 | // Header should contain TRAC |
| 550 | if (memcmp(header, "TRAC", sizeof(header)) != 0) { |
| 551 | LOG(WARNING) << "Invalid TRK Header."; |
| 552 | return false; |
| 553 | } |
| 554 | |
| 555 | // Unknown header data |
| 556 | if (trk.read(((char *) unknownHeader), sizeof(uint32_t) * 5).gcount() != sizeof(uint32_t) * 5) return false; |
| 557 | |
| 558 | // Basic Track data |
| 559 | trk.read((char *) &track->nSuperBlocks, sizeof(uint32_t)); |
| 560 | trk.read((char *) &track->nBlocks, sizeof(uint32_t)); |
| 561 | track->superblocks = static_cast<typename Platform::SUPERBLOCK *>(calloc(track->nBlocks, sizeof(typename Platform::SUPERBLOCK))); |
| 562 | |
| 563 | // Offsets of Superblocks in TRK file |
| 564 | uint32_t *superblockOffsets = static_cast<uint32_t *>(calloc(track->nSuperBlocks, sizeof(uint32_t))); |
| 565 | if (trk.read(((char *) superblockOffsets), track->nSuperBlocks * sizeof(uint32_t)).gcount() != track->nSuperBlocks * sizeof(uint32_t)) { |
| 566 | free(superblockOffsets); |
| 567 | return false; |
| 568 | } |
| 569 | |
| 570 | // Reference coordinates for each block |
| 571 | track->blockReferenceCoords = static_cast<VERT_HIGHP *>(calloc(track->nBlocks, sizeof(VERT_HIGHP))); |
| 572 | if (trk.read((char *) track->blockReferenceCoords, track->nBlocks * sizeof(VERT_HIGHP)).gcount() != track->nBlocks * sizeof(VERT_HIGHP)) { |
| 573 | free(superblockOffsets); |
| 574 | return false; |
| 575 | } |
| 576 | |
| 577 | for (uint32_t superBlock_Idx = 0; superBlock_Idx < track->nSuperBlocks; ++superBlock_Idx) { |
| 578 | LOG(DEBUG) << "SuperBlock " << superBlock_Idx + 1 << " of " << track->nSuperBlocks; |
| 579 | // Get the superblock header |
| 580 | auto *superblock = &track->superblocks[superBlock_Idx]; |
| 581 | trk.seekg(superblockOffsets[superBlock_Idx], ios_base::beg); |
| 582 | trk.read((char *) &superblock->superBlockSize, sizeof(uint32_t)); |
| 583 | trk.read((char *) &superblock->nBlocks, sizeof(uint32_t)); |
| 584 | trk.read((char *) &superblock->padding, sizeof(uint32_t)); |
| 585 | |
| 586 | if (superblock->nBlocks != 0) { |
| 587 | // Get the offsets of the child blocks within superblock |
| 588 | uint32_t *blockOffsets = (uint32_t *) calloc(static_cast<size_t>(superblock->nBlocks), sizeof(uint32_t)); |
| 589 | trk.read((char *) blockOffsets, superblock->nBlocks * sizeof(uint32_t)); |
| 590 | superblock->trackBlocks = static_cast<typename Platform::TRKBLOCK *>(calloc(static_cast<size_t>(superblock->nBlocks), sizeof(typename Platform::TRKBLOCK))); |
| 591 | |
| 592 | for (uint32_t block_Idx = 0; block_Idx < superblock->nBlocks; ++block_Idx) { |
| 593 | auto *trackblock = &superblock->trackBlocks[block_Idx]; |
| 594 | // Read Header |
nothing calls this directly
no outgoing calls
no test coverage detected