Removed unneeded whitespace.
This commit is contained in:
@@ -28,80 +28,80 @@ using namespace std;
|
||||
namespace JMA
|
||||
{
|
||||
const char jma_magic[] = { 'J', 'M', 'A', 0, 'N' };
|
||||
const unsigned int jma_header_length = 5;
|
||||
const unsigned int jma_header_length = 5;
|
||||
const unsigned char jma_version = 1;
|
||||
const unsigned int jma_version_length = 1;
|
||||
const unsigned int jma_total_header_length = jma_header_length + jma_version_length + UINT_SIZE;
|
||||
|
||||
|
||||
//Convert DOS/zip/JMA integer time to to time_t
|
||||
time_t uint_to_time(unsigned short date, unsigned short time)
|
||||
{
|
||||
tm formatted_time;
|
||||
|
||||
|
||||
formatted_time.tm_mday = date & 0x1F;
|
||||
formatted_time.tm_mon = ((date >> 5) & 0xF) - 1;
|
||||
formatted_time.tm_year = ((date >> 9) & 0x7f) + 80;
|
||||
formatted_time.tm_sec = (time & 0x1F) * 2;
|
||||
formatted_time.tm_min = (time >> 5) & 0x3F;
|
||||
formatted_time.tm_hour = (time >> 11) & 0x1F;
|
||||
|
||||
|
||||
return(mktime(&formatted_time));
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
//Retreive the file block, what else?
|
||||
void jma_open::retrieve_file_block() throw(jma_errors)
|
||||
{
|
||||
unsigned char uint_buffer[UINT_SIZE];
|
||||
unsigned char ushort_buffer[USHORT_SIZE];
|
||||
|
||||
|
||||
//File block size is the last UINT in the file
|
||||
stream.seekg(-UINT_SIZE,ios::end);
|
||||
stream.read((char *)uint_buffer, UINT_SIZE);
|
||||
size_t file_block_size = charp_to_uint(uint_buffer);
|
||||
|
||||
|
||||
//Currently at the end of the file, so that's the file size
|
||||
size_t jma_file_size = stream.tellg();
|
||||
|
||||
|
||||
//The file block can't be larger than the JMA file without it's header.
|
||||
//This if can probably be improved
|
||||
if (file_block_size >= jma_file_size-jma_total_header_length)
|
||||
{
|
||||
throw(JMA_BAD_FILE);
|
||||
}
|
||||
|
||||
|
||||
//Seek to before file block so we can read the file block
|
||||
stream.seekg(-((int)file_block_size+UINT_SIZE),ios::end);
|
||||
|
||||
|
||||
//This is needed if the file block is compressed
|
||||
stringstream decompressed_file_block;
|
||||
//Pointer to where to read file block from (file or decompressed buffer)
|
||||
istream *file_block_stream;
|
||||
|
||||
|
||||
//Setup file info buffer and byte to read with
|
||||
jma_file_info file_info;
|
||||
char byte;
|
||||
|
||||
char byte;
|
||||
|
||||
stream.get(byte);
|
||||
if (!byte) //If file block is compressed
|
||||
{
|
||||
//Compressed size isn't counting the byte we just read or the UINT for compressed size
|
||||
size_t compressed_size = file_block_size - (1+UINT_SIZE);
|
||||
|
||||
|
||||
//Read decompressed size / true file block size
|
||||
stream.read((char *)uint_buffer, UINT_SIZE);
|
||||
file_block_size = charp_to_uint(uint_buffer);
|
||||
|
||||
|
||||
//Setup access methods for decompression
|
||||
ISequentialInStream_Istream compressed_data(stream);
|
||||
ISequentialOutStream_Ostream decompressed_data(decompressed_file_block);
|
||||
|
||||
|
||||
//Decompress the data
|
||||
if (!decompress_lzma_7z(compressed_data, compressed_size, decompressed_data, file_block_size))
|
||||
{
|
||||
throw(JMA_DECOMPRESS_FAILED);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
//Go to beginning, setup pointer to buffer
|
||||
decompressed_file_block.seekg(0, ios::beg);
|
||||
file_block_stream = &decompressed_file_block;
|
||||
@@ -111,8 +111,8 @@ namespace JMA
|
||||
stream.putback(byte); //Putback byte, byte is part of filename, not compressed indicator
|
||||
file_block_stream = &stream;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
//Minimum file name length is 2 bytes, a char and a null
|
||||
//Minimum comment length is 1 byte, a null
|
||||
//There are currently 2 UINTs and 2 USHORTs per file
|
||||
@@ -120,7 +120,7 @@ namespace JMA
|
||||
{
|
||||
//First stored in the file block is the file name null terminated
|
||||
file_info.name = "";
|
||||
|
||||
|
||||
file_block_stream->get(byte);
|
||||
while (byte)
|
||||
{
|
||||
@@ -132,8 +132,8 @@ namespace JMA
|
||||
if (!file_info.name.length())
|
||||
{
|
||||
throw(JMA_BAD_FILE);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
//Same trick as above for the comment
|
||||
file_info.comment = "";
|
||||
|
||||
@@ -143,38 +143,38 @@ namespace JMA
|
||||
file_info.comment += byte;
|
||||
file_block_stream->get(byte);
|
||||
}
|
||||
|
||||
|
||||
//Next is a UINT representing the file's size
|
||||
file_block_stream->read((char *)uint_buffer, UINT_SIZE);
|
||||
file_info.size = charp_to_uint(uint_buffer);
|
||||
|
||||
|
||||
//Followed by CRC32
|
||||
file_block_stream->read((char *)uint_buffer, UINT_SIZE);
|
||||
file_info.crc32 = charp_to_uint(uint_buffer);
|
||||
|
||||
|
||||
//Special USHORT representation of file's date
|
||||
file_block_stream->read((char *)ushort_buffer, USHORT_SIZE);
|
||||
file_info.date = charp_to_ushort(ushort_buffer);
|
||||
|
||||
|
||||
//Special USHORT representation of file's time
|
||||
file_block_stream->read((char *)ushort_buffer, USHORT_SIZE);
|
||||
file_info.time = charp_to_ushort(ushort_buffer);
|
||||
|
||||
|
||||
file_info.buffer = 0; //Pointing to null till we decompress files
|
||||
|
||||
|
||||
files.push_back(file_info); //Put file info into our structure
|
||||
|
||||
|
||||
//Subtract size of the file info we just read
|
||||
file_block_size -= file_info.name.length()+file_info.comment.length()+2+UINT_SIZE*2+USHORT_SIZE*2;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//Constructor for opening JMA files for reading
|
||||
jma_open::jma_open(const char *compressed_file_name) throw (jma_errors)
|
||||
jma_open::jma_open(const char *compressed_file_name) throw (jma_errors)
|
||||
{
|
||||
decompressed_buffer = 0;
|
||||
compressed_buffer = 0;
|
||||
|
||||
|
||||
stream.open(compressed_file_name, ios::in | ios::binary);
|
||||
if (!stream.is_open())
|
||||
{
|
||||
@@ -188,7 +188,7 @@ namespace JMA
|
||||
{
|
||||
throw(JMA_BAD_FILE);
|
||||
}
|
||||
|
||||
|
||||
//Not the cleanest code but logical
|
||||
stream.read((char *)header, 5);
|
||||
if (*header <= jma_version)
|
||||
@@ -216,7 +216,7 @@ namespace JMA
|
||||
{
|
||||
vector<jma_public_file_info> file_info_vector;
|
||||
jma_public_file_info file_info;
|
||||
|
||||
|
||||
for (vector<jma_file_info>::iterator i = files.begin(); i != files.end(); i++)
|
||||
{
|
||||
file_info.name = i->name;
|
||||
@@ -226,10 +226,10 @@ namespace JMA
|
||||
file_info.crc32 = i->crc32;
|
||||
file_info_vector.push_back(file_info);
|
||||
}
|
||||
|
||||
|
||||
return(file_info_vector);
|
||||
}
|
||||
|
||||
|
||||
//Skip forward a given number of chunks
|
||||
void jma_open::chunk_seek(unsigned int chunk_num) throw(jma_errors)
|
||||
{
|
||||
@@ -238,25 +238,25 @@ namespace JMA
|
||||
{
|
||||
throw(JMA_NO_OPEN);
|
||||
}
|
||||
|
||||
|
||||
//Clear possible errors so the seek will work
|
||||
stream.clear();
|
||||
|
||||
|
||||
//Move forward over header
|
||||
stream.seekg(jma_total_header_length, ios::beg);
|
||||
|
||||
unsigned char int4_buffer[UINT_SIZE];
|
||||
|
||||
unsigned char int4_buffer[UINT_SIZE];
|
||||
|
||||
while (chunk_num--)
|
||||
{
|
||||
//Read in size of chunk
|
||||
stream.read((char *)int4_buffer, UINT_SIZE);
|
||||
|
||||
|
||||
//Skip chunk plus it's CRC32
|
||||
stream.seekg(charp_to_uint(int4_buffer)+UINT_SIZE, ios::cur);
|
||||
stream.seekg(charp_to_uint(int4_buffer)+UINT_SIZE, ios::cur);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
//Return a vector of pointers to each file in the JMA, the buffer to hold all the files
|
||||
//must be initilized outside.
|
||||
vector<unsigned char *> jma_open::get_all_files(unsigned char *buffer) throw(jma_errors)
|
||||
@@ -266,19 +266,19 @@ namespace JMA
|
||||
{
|
||||
throw(JMA_NO_OPEN);
|
||||
}
|
||||
|
||||
|
||||
//Seek to the first chunk
|
||||
chunk_seek(0);
|
||||
|
||||
|
||||
//Set the buffer that decompressed data goes to
|
||||
decompressed_buffer = buffer;
|
||||
|
||||
|
||||
//If the JMA is not solid
|
||||
if (chunk_size)
|
||||
{
|
||||
unsigned char int4_buffer[UINT_SIZE];
|
||||
unsigned char int4_buffer[UINT_SIZE];
|
||||
size_t size = get_total_size(files);
|
||||
|
||||
|
||||
//For each chunk in the file...
|
||||
for (size_t remaining_size = size; remaining_size; remaining_size -= chunk_size)
|
||||
{
|
||||
@@ -299,7 +299,7 @@ namespace JMA
|
||||
|
||||
//Read all the compressed data in
|
||||
stream.read((char *)compressed_buffer, compressed_size);
|
||||
|
||||
|
||||
//Read the expected CRC of compressed data from the file
|
||||
stream.read((char *)int4_buffer, UINT_SIZE);
|
||||
|
||||
@@ -309,17 +309,17 @@ namespace JMA
|
||||
delete[] compressed_buffer;
|
||||
throw(JMA_BAD_FILE);
|
||||
}
|
||||
|
||||
|
||||
//Decompress the data, cleanup memory on failure
|
||||
if (!decompress_lzma_7z(compressed_buffer, compressed_size,
|
||||
decompressed_buffer+size-remaining_size,
|
||||
if (!decompress_lzma_7z(compressed_buffer, compressed_size,
|
||||
decompressed_buffer+size-remaining_size,
|
||||
(remaining_size > chunk_size) ? chunk_size : remaining_size))
|
||||
{
|
||||
delete[] compressed_buffer;
|
||||
throw(JMA_DECOMPRESS_FAILED);
|
||||
}
|
||||
delete[] compressed_buffer;
|
||||
|
||||
|
||||
if (remaining_size <= chunk_size) //If we just decompressed the remainder
|
||||
{
|
||||
break;
|
||||
@@ -328,25 +328,25 @@ namespace JMA
|
||||
}
|
||||
else //Solidly compressed JMA
|
||||
{
|
||||
unsigned char int4_buffer[UINT_SIZE];
|
||||
|
||||
unsigned char int4_buffer[UINT_SIZE];
|
||||
|
||||
//Read the size of the compressed data
|
||||
stream.read((char *)int4_buffer, UINT_SIZE);
|
||||
size_t compressed_size = charp_to_uint(int4_buffer);
|
||||
|
||||
//Get decompressed size
|
||||
size_t size = get_total_size(files);
|
||||
|
||||
|
||||
//Setup access methods for decompression
|
||||
ISequentialInStream_Istream compressed_data(stream);
|
||||
ISequentialOutStream_Array decompressed_data(reinterpret_cast<char*>(decompressed_buffer), size);
|
||||
|
||||
|
||||
//Decompress the data
|
||||
if (!decompress_lzma_7z(compressed_data, compressed_size, decompressed_data, size))
|
||||
{
|
||||
throw(JMA_DECOMPRESS_FAILED);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/*
|
||||
//Allocate memory of the right size to hold the compressed data in the JMA
|
||||
try
|
||||
@@ -357,14 +357,14 @@ namespace JMA
|
||||
{
|
||||
throw(JMA_NO_MEM_ALLOC);
|
||||
}
|
||||
|
||||
|
||||
//Copy the compressed data into memory
|
||||
stream.read((char *)compressed_buffer, compressed_size);
|
||||
size_t size = get_total_size(files);
|
||||
|
||||
|
||||
//Read the CRC of the compressed data
|
||||
stream.read((char *)int4_buffer, UINT_SIZE);
|
||||
|
||||
|
||||
//If it doesn't match, complain
|
||||
if (CRC32lib::CRC32(compressed_buffer, compressed_size) != charp_to_uint(int4_buffer))
|
||||
{
|
||||
@@ -381,10 +381,10 @@ namespace JMA
|
||||
delete[] compressed_buffer;
|
||||
*/
|
||||
}
|
||||
|
||||
|
||||
vector<unsigned char *> file_pointers;
|
||||
size_t size = 0;
|
||||
|
||||
|
||||
//For each file, add it's pointer to the vector, size is pointer offset in the buffer
|
||||
for (vector<jma_file_info>::iterator i = files.begin(); i != files.end(); i++)
|
||||
{
|
||||
@@ -394,7 +394,7 @@ namespace JMA
|
||||
}
|
||||
|
||||
//Return the vector of pointers
|
||||
return(file_pointers);
|
||||
return(file_pointers);
|
||||
}
|
||||
|
||||
//Extracts the file with a given name found in the archive to the given buffer
|
||||
@@ -404,10 +404,10 @@ namespace JMA
|
||||
{
|
||||
throw(JMA_NO_OPEN);
|
||||
}
|
||||
|
||||
|
||||
size_t size_to_skip = 0;
|
||||
size_t our_file_size = 0;
|
||||
|
||||
|
||||
//Search through the vector of file information
|
||||
for (vector<jma_file_info>::iterator i = files.begin(); i != files.end(); i++)
|
||||
{
|
||||
@@ -417,11 +417,11 @@ namespace JMA
|
||||
our_file_size = i->size;
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
//Keep a running total of size
|
||||
size_to_skip += i->size;
|
||||
}
|
||||
|
||||
|
||||
if (!our_file_size) //File with the specified name was not found in the archive
|
||||
{
|
||||
throw(JMA_FILE_NOT_FOUND);
|
||||
@@ -433,14 +433,14 @@ namespace JMA
|
||||
get_all_files(buffer);
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
if (chunk_size) //we are using non-solid archive..
|
||||
{
|
||||
unsigned int chunks_to_skip = size_to_skip / chunk_size;
|
||||
|
||||
|
||||
//skip over requisite number of chunks
|
||||
chunk_seek(chunks_to_skip);
|
||||
|
||||
|
||||
//Allocate memory for compressed and decompressed data
|
||||
unsigned char *comp_buffer = 0, *decomp_buffer = 0;
|
||||
try
|
||||
@@ -454,7 +454,7 @@ namespace JMA
|
||||
{
|
||||
throw(JMA_NO_MEM_ALLOC);
|
||||
}
|
||||
|
||||
|
||||
size_t first_chunk_offset = size_to_skip % chunk_size;
|
||||
unsigned char int4_buffer[UINT_SIZE];
|
||||
for (size_t i = 0; i < our_file_size;)
|
||||
@@ -462,29 +462,29 @@ namespace JMA
|
||||
//Get size
|
||||
stream.read((char *)int4_buffer, UINT_SIZE);
|
||||
size_t compressed_size = charp_to_uint(int4_buffer);
|
||||
|
||||
|
||||
//Read all the compressed data in
|
||||
stream.read((char *)comp_buffer, compressed_size);
|
||||
|
||||
//Read the CRC of the compressed data
|
||||
stream.read((char *)int4_buffer, UINT_SIZE);
|
||||
|
||||
|
||||
//If it doesn't match, complain
|
||||
if (CRC32lib::CRC32(comp_buffer, compressed_size) != charp_to_uint(int4_buffer))
|
||||
{
|
||||
delete[] comp_buffer;
|
||||
throw(JMA_BAD_FILE);
|
||||
}
|
||||
|
||||
|
||||
//Decompress chunk
|
||||
if (!decompress_lzma_7z(comp_buffer, compressed_size, decomp_buffer, chunk_size))
|
||||
{
|
||||
delete[] comp_buffer;
|
||||
throw(JMA_DECOMPRESS_FAILED);
|
||||
}
|
||||
|
||||
|
||||
size_t copy_amount = our_file_size-i > chunk_size-first_chunk_offset ? chunk_size-first_chunk_offset : our_file_size-i;
|
||||
|
||||
|
||||
memcpy(buffer+i, decomp_buffer+first_chunk_offset, copy_amount);
|
||||
first_chunk_offset = 0; //Set to zero since this is only for the first iteration
|
||||
i += copy_amount;
|
||||
@@ -502,11 +502,11 @@ namespace JMA
|
||||
{
|
||||
throw(JMA_NO_MEM_ALLOC);
|
||||
}
|
||||
|
||||
|
||||
get_all_files(decomp_buffer);
|
||||
|
||||
|
||||
memcpy(buffer, decomp_buffer+size_to_skip, our_file_size);
|
||||
|
||||
|
||||
delete[] decomp_buffer;
|
||||
}
|
||||
}
|
||||
@@ -515,32 +515,32 @@ namespace JMA
|
||||
{
|
||||
return(chunk_size ? false : true);
|
||||
}
|
||||
|
||||
|
||||
const char *jma_error_text(jma_errors error)
|
||||
{
|
||||
switch (error)
|
||||
{
|
||||
case JMA_NO_CREATE:
|
||||
return("JMA could not be created");
|
||||
|
||||
|
||||
case JMA_NO_MEM_ALLOC:
|
||||
return("Memory for JMA could be allocated");
|
||||
|
||||
|
||||
case JMA_NO_OPEN:
|
||||
return("JMA could not be opened");
|
||||
|
||||
|
||||
case JMA_BAD_FILE:
|
||||
return("Invalid/Corrupt JMA");
|
||||
|
||||
|
||||
case JMA_UNSUPPORTED_VERSION:
|
||||
return("JMA version not supported");
|
||||
|
||||
|
||||
case JMA_COMPRESS_FAILED:
|
||||
return("JMA compression failed");
|
||||
|
||||
|
||||
case JMA_DECOMPRESS_FAILED:
|
||||
return("JMA decompression failed");
|
||||
|
||||
|
||||
case JMA_FILE_NOT_FOUND:
|
||||
return("File not found in JMA");
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user