123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209 |
- #include "NXFileObject.h"
- #include <new>
- #include "minizip/unzip.h"
- #include <nx/nxfile.h>
- #include <assert.h>
- class NXZipFile : NXFileObject
- {
- public:
- NXZipFile(unzFile zip_file);
- ~NXZipFile();
- /* NXFileObject implementation */
- ns_error_t Read(void *buffer, size_t bytes_requested, size_t *bytes_read);
- ns_error_t Write(const void *buffer, size_t bytes);
- ns_error_t Seek(uint64_t position);
- ns_error_t Tell(uint64_t *position);
- ns_error_t PeekByte(uint8_t *byte);
- ns_error_t Sync();
- ns_error_t Truncate();
- // TODO(benski) implementation EOF
- // TODO(benski) implement region locking
- private:
- unzFile zip_file;
- };
- NXZipFile::NXZipFile(unzFile zip_file) : zip_file(zip_file)
- {
- }
- NXZipFile::~NXZipFile()
- {
- if (zip_file) {
- unzCloseCurrentFile(zip_file);
- unzClose(zip_file);
- zip_file=0;
- }
- }
- /* NXFileObject implementation */
- ns_error_t NXZipFile::Read(void *buffer, size_t bytes_requested, size_t *bytes_read)
- {
- int zret = unzReadCurrentFile(zip_file, buffer, (unsigned int)bytes_requested);
- if (zret == 0) {
- if (bytes_read) {
- *bytes_read = 0;
- }
- return NErr_EndOfFile;
- } else if (zret > 0) {
- if (bytes_read) {
- *bytes_read = (size_t)zret;
- }
- return NErr_Success;
- } else {
- if (bytes_read) {
- *bytes_read = 0;
- }
- return NErr_Error;
- }
- }
- ns_error_t NXZipFile::Write(const void *buffer, size_t bytes)
- {
- return NErr_NotImplemented;
- }
- ns_error_t NXZipFile::Seek(uint64_t position)
- {
- // TODO(benski) error check)
- unzSetOffset64(zip_file, position);
- return NErr_Success;
- }
- ns_error_t NXZipFile::Tell(uint64_t *position)
- {
- *position = unzGetOffset64(zip_file);
- return NErr_Success;
- }
- ns_error_t NXZipFile::PeekByte(uint8_t *byte)
- {
- return NErr_NotImplemented;
- }
- ns_error_t NXZipFile::Sync()
- {
- return NErr_NotImplemented;
- }
- ns_error_t NXZipFile::Truncate()
- {
- return NErr_NotImplemented;
- }
- static voidpf ZCALLBACK unzip_nxfile_open OF((voidpf opaque, const void* filename, int mode))
- {
- nx_file_t f;
- if (NXFileOpenFile(&f, (nx_uri_t)filename, nx_file_FILE_read_binary) != NErr_Success) {
- return 0;
- }
- return f;
- }
- static uLong ZCALLBACK unzip_nxfile_read OF((voidpf opaque, voidpf stream, void* buf, uLong size))
- {
- nx_file_t f = (nx_file_t)stream;
- size_t bytes_read;
- if (NXFileRead(f, buf, size, &bytes_read) != NErr_Success) {
- return 0;
- }
- return (uLong)bytes_read;
- }
- static int ZCALLBACK unzip_nxfile_close OF((voidpf opaque, voidpf stream))
- {
- NXFileRelease((nx_file_t)stream);
- return 0;
- }
- static ZPOS64_T ZCALLBACK unzip_nxfile_tell OF((voidpf opaque, voidpf stream))
- {
- nx_file_t f = (nx_file_t)stream;
- uint64_t position;
- if (NXFileTell(f, &position) == NErr_Success) {
- return (int64_t)position;
- } else {
- return -1;
- }
- }
- static long ZCALLBACK unzip_nxfile_seek OF((voidpf opaque, voidpf stream, ZPOS64_T offset, int whence))
- {
- nx_file_t f = (nx_file_t)stream;
- uint64_t position;
- if (whence == SEEK_SET) {
- position = offset;
- } else if (whence == SEEK_CUR) {
- ns_error_t err = NXFileTell(f, &position);
- if (err != NErr_Success) {
- return -1;
- }
- position += offset;
- } else if (whence == SEEK_END) {
- uint64_t length;
- NXFileLength(f, &length);
- position = length + offset;
- } else {
- return -1;
- }
- ns_error_t err = NXFileSeek(f, position);
- if (err == NErr_Success) {
- return 0;
- } else {
- return -1;
- }
- }
- #if 0
- open64_file_func zopen64_file;
- read_file_func zread_file;
- write_file_func zwrite_file;
- tell64_file_func ztell64_file;
- seek64_file_func zseek64_file;
- close_file_func zclose_file;
- testerror_file_func zerror_file;
- #endif
- ns_error_t NXFileOpenZip(nx_file_t *out_file, nx_uri_t filename, nx_string_t extension_hint)
- {
- #if 0
- typedef struct zlib_filefunc_def_s
- {
- open_file_func zopen_file;
- read_file_func zread_file;
- write_file_func zwrite_file;
- tell_file_func ztell_file;
- seek_file_func zseek_file;
- close_file_func zclose_file;
- testerror_file_func zerror_file;
- voidpf opaque;
- } zlib_filefunc_def;
- #endif
- zlib_filefunc64_def file_func = {0, };
- file_func.zopen64_file = unzip_nxfile_open;
- file_func.zread_file = unzip_nxfile_read;
- file_func.ztell64_file = unzip_nxfile_tell;
- file_func.zseek64_file = unzip_nxfile_seek;
- file_func.zclose_file = unzip_nxfile_close;
- unzFile zip_file = unzOpen2_64(filename, &file_func);
- if (zip_file == NULL) {
- return NErr_Error;
- }
- unzGoToFirstFile(zip_file);
- // TODO(benski): look for filename with extension_hint as extension
- // TODO(benski): search for anything with extension
- unzOpenCurrentFile(zip_file);
- NXZipFile *nx_zip_file = new (std::nothrow) NXZipFile(zip_file);
- if (!nx_zip_file) {
- unzCloseCurrentFile(zip_file);
- unzClose(zip_file);
- return NErr_OutOfMemory;
- }
- *out_file = (nx_file_t)nx_zip_file;
- return NErr_Success;
- }
|