From 716747787439264d92e9ba1c48bb43146a0043b0 Mon Sep 17 00:00:00 2001 From: jakcron Date: Sun, 25 Mar 2018 19:52:56 +0800 Subject: [PATCH] [fnd] overloaded fnd::io::readFile to allow specifying an offset and size. --- lib/libfnd/include/fnd/io.h | 1 + lib/libfnd/source/io.cpp | 42 ++++++++++++++++++++++++++++++++ programs/xcitool/source/main.cpp | 20 +++++---------- 3 files changed, 49 insertions(+), 14 deletions(-) diff --git a/lib/libfnd/include/fnd/io.h b/lib/libfnd/include/fnd/io.h index e80d5c3..7318126 100644 --- a/lib/libfnd/include/fnd/io.h +++ b/lib/libfnd/include/fnd/io.h @@ -7,6 +7,7 @@ namespace fnd namespace io { void readFile(const std::string& path, MemoryBlob& blob); + void readFile(const std::string& path, size_t offset, size_t len, MemoryBlob& blob); void writeFile(const std::string& path, const MemoryBlob& blob); void writeFile(const std::string& path, const byte_t* data, size_t len); } diff --git a/lib/libfnd/source/io.cpp b/lib/libfnd/source/io.cpp index 2f4ce8e..0c2ef08 100644 --- a/lib/libfnd/source/io.cpp +++ b/lib/libfnd/source/io.cpp @@ -41,6 +41,48 @@ void io::readFile(const std::string& path, MemoryBlob & blob) fclose(fp); } +void fnd::io::readFile(const std::string& path, size_t offset, size_t len, MemoryBlob& blob) +{ + FILE* fp; + size_t filesz, filepos; + + if ((fp = fopen(path.c_str(), "rb")) == NULL) + { + throw Exception(kModuleName, "Failed to open \"" + path + "\": does not exist"); + } + + fseek(fp, 0, SEEK_END); + filesz = ftell(fp); + rewind(fp); + fseek(fp, offset, SEEK_SET); + + if (filesz < len || filesz < offset || filesz < (offset + len)) + { + throw Exception(kModuleName, "Failed to open \"" + path + "\": file to small"); + } + + try + { + blob.alloc(len); + } catch (const fnd::Exception& e) + { + fclose(fp); + throw fnd::Exception(kModuleName, "Failed to allocate memory for file: " + std::string(e.what())); + } + + for (filepos = 0; len > kBlockSize; len -= kBlockSize, filepos += kBlockSize) + { + fread(blob.getBytes() + filepos, 1, kBlockSize, fp); + } + + if (len) + { + fread(blob.getBytes() + filepos, 1, len, fp); + } + + fclose(fp); +} + void io::writeFile(const std::string& path, const MemoryBlob & blob) { writeFile(path, blob.getBytes(), blob.getSize()); diff --git a/programs/xcitool/source/main.cpp b/programs/xcitool/source/main.cpp index 7d66829..6159db3 100644 --- a/programs/xcitool/source/main.cpp +++ b/programs/xcitool/source/main.cpp @@ -250,7 +250,7 @@ void decryptXciHeader(const byte_t* src, byte_t* dst) const byte_t* src_iv = ((const sXciHeader*)src)->encryption_iv; byte_t iv[crypto::aes::kAesBlockSize]; - for (int i = 0; i < crypto::aes::kAesBlockSize; i++) + for (size_t i = 0; i < crypto::aes::kAesBlockSize; i++) { iv[i] = src_iv[15 - i]; } @@ -270,21 +270,13 @@ int main(int argc, char** argv) return 1; } - FILE* fp = fopen(argv[1], "rb"); - if (fp == nullptr) - { - printf("Failed to open file.\n"); - return 1; - } - + fnd::MemoryBlob xciFile; - xciFile.alloc(0x200); - fread(xciFile.getBytes(), 0x200, 1, fp); - fclose(fp); + fnd::io::readFile(argv[1], 0x100, 0x100, xciFile); - sXciHeader hdr; - decryptXciHeader(xciFile.getBytes() + 0x100, (byte_t*)&hdr); - printXciHeader(hdr, true); + sXciHeader* hdr = (sXciHeader*)xciFile.getBytes(); + decryptXciHeader(xciFile.getBytes(), xciFile.getBytes()); + printXciHeader(*hdr, true); return 0; } \ No newline at end of file