-hash function to crc32 function (tpf support)

Improvements:
-whole textures can be send to game (needed for zip and tpf)
-zip support (normal and as tpf format)
-tpf support
This commit is contained in:
code@koerner-de.net
2011-09-16 11:53:36 +00:00
parent b24123ddca
commit 6c04a6550d
25 changed files with 8103 additions and 124 deletions
+4 -1
View File
@@ -33,7 +33,6 @@ OTM_GUI/OTM_Event.cpp -text
OTM_GUI/OTM_Event.h -text
OTM_GUI/OTM_GUI.cpp -text
OTM_GUI/OTM_GUI.h -text
OTM_GUI/OTM_GUI.ico -text
OTM_GUI/OTM_GameInfo.cpp -text
OTM_GUI/OTM_GameInfo.h -text
OTM_GUI/OTM_GamePage.cpp -text
@@ -47,4 +46,8 @@ OTM_GUI/OTM_Server.cpp -text
OTM_GUI/OTM_Server.h -text
OTM_GUI/config.gcc -text
OTM_GUI/makefile -text
OTM_GUI/unzip.cpp -text
OTM_GUI/unzip.h -text
OTM_GUI/zip.cpp -text
OTM_GUI/zip.h -text
/OTM_GlobalDefines.h -text
+6
View File
@@ -16,6 +16,12 @@ You should have received a copy of the GNU General Public License
along with FooOpenTexMod. If not, see <http://www.gnu.org/licenses/>.
*/
/*
*
* BIG THANKS TO Michael Koch
* (proxydll_9.zip)
*
*/
#ifndef OTM_IDirect3D9_H_
+7
View File
@@ -17,6 +17,13 @@ along with FooOpenTexMod. If not, see <http://www.gnu.org/licenses/>.
*/
/*
*
* BIG THANKS TO Michael Koch
* (proxydll_9.zip)
*
*/
#ifndef OTM_IDirect3DDevice9_H_
#define OTM_IDirect3DDevice9_H_
+7 -3
View File
@@ -17,6 +17,13 @@ along with FooOpenTexMod. If not, see <http://www.gnu.org/licenses/>.
*/
/*
*
* BIG THANKS TO Matthew L (Azorbix)
* (Direct3D StarterKit v3.0)
*
*/
#ifndef OTM_IDirect3DTexture9_H
#define OTM_IDirect3DTexture9_H
@@ -28,9 +35,6 @@ along with FooOpenTexMod. If not, see <http://www.gnu.org/licenses/>.
//DWORD QuickChecksum(DWORD *pData, int size);
interface OTM_IDirect3DTexture9 : public IDirect3DTexture9
{
OTM_IDirect3DTexture9(IDirect3DTexture9 **ppTex, IDirect3DDevice9 *pIDirect3DDevice9, UINT Width, UINT Height, D3DFORMAT Format)
+103 -1
View File
@@ -66,6 +66,7 @@ OTM_TextureClient::~OTM_TextureClient(void)
//Message("end ~OTM_TextureClient(void): %lu\n", this);
}
int OTM_TextureClient::AddTexture( OTM_IDirect3DTexture9* pTexture)
{
if (pTexture->FAKE) return (RETURN_OK); // this is a fake texture
@@ -162,12 +163,80 @@ int OTM_TextureClient::AddTexture( OTM_IDirect3DTexture9* pTexture)
break;
}
}
MyTypeHash hash = GetHash( (unsigned char*) d3dlr.pBits, size);
//MyTypeHash hash = GetHash( (unsigned char*) d3dlr.pBits, size);
MyTypeHash hash = GetCRC32( (char*) d3dlr.pBits, size);
/*
if (hash==0X1FD33669ul)
{
for (int i=0; i<size; i++)
{
DWORD hash2 = QuickChecksum( (DWORD*) d3dlr.pBits, i);
Message("Hash: %#lX %#lX\n", hash, hash2);
}
}
*/
/*
DWORD hash2 = QuickChecksum( (char*) d3dlr.pBits, size);
switch(desc.Format)
{
case D3DFMT_A8R8G8B8:
{
size = 4*desc.Width*desc.Height;
break;
}
case D3DFMT_FORCE_DWORD:
{
size = 1*desc.Width*desc.Height;
break;
}
default:
{
size = (desc.Width*desc.Height)/2;
break;
}
}
DWORD hash3 = QuickChecksum( (char*) d3dlr.pBits, size);
DWORD hash4 = QuickChecksum( (char*) d3dlr.pBits, (desc.Width*desc.Height)/2);
DWORD hash5 = QuickChecksum( (char*) d3dlr.pBits, (desc.Width*desc.Height)/4);
DWORD hash6 = 0u;
if (pTexture->UnlockRect(0)!=D3D_OK)
{
return (RETURN_UnlockRect_FAILED);
}
LPD3DXBUFFER buffer;
if (D3D_OK==D3DXSaveTextureToFileInMemory( &buffer, D3DXIFF_DDS, pTexture->m_D3Dtex, NULL))
{
DWORD* data = (DWORD*) buffer->GetBufferPointer();
unsigned long int size = buffer->GetBufferSize();
hash6 = QuickChecksum( (char*) data, size);
buffer->Release();
}
Message("Hash: %#lX %#lX %#lX %#lX %#lX %#lX\n", hash, hash2, hash3, hash4, hash5, hash6);
DWORD XOR=0u;
switch (hash)
{
case 0X1FD33669ul: XOR = 0xDC00FEB1ul; break;
case 0X3B560BBFul: XOR = 0x2D1E4DBDul; break;
case 0X5D76CA77ul: XOR = 0xC1E8589Dul; break;
case 0X72E92068ul: XOR = 0x1A92B5F2ul; break;
case 0X9066971Eul: XOR = 0x3549742Dul; break;
case 0XB10C55B0ul: XOR = 0xF037EB98ul; break;
}
if (XOR)
{
Message("XOR: %#lX %#lX %#lX %#lX %#lX %#lX\n", hash, hash2^XOR, hash3^XOR, hash4^XOR, hash5^XOR, hash6^XOR);
}
*/
pTexture->Hash = hash; // note: this will only be done for original textures
if (BoolSaveAllTextures) SaveTexture(pTexture);
@@ -433,3 +502,36 @@ MyTypeHash OTM_TextureClient::GetHash(unsigned char *str, int len) // estimate t
return (hash);
}
/*
*
* BIG THANKS TO RS !!
*
* who gave me his hashing algorithm (well or crc32 algorithm^^)
*
The hash function is CRC32 using polynomial 0xEDB88320.
However, the hashed data is calculated incorrectly in TexMod: it's simply BytesPerPixel * Width * Height, from the beginning of the data (that is mapped using LockRect).
The problem is that it doesn't take the pitch into account and BytesPerPixel may be wrong for some rare formats (not sure about that).
*/
#define CRC32POLY 0xEDB88320u /* CRC-32 Polynom */
#define ulCrc_in 0xffffffff
unsigned int OTM_TextureClient::GetCRC32( char *pcDatabuf, unsigned int ulDatalen)
{
unsigned int crc = ulCrc_in;
for (unsigned int idx = 0u; idx<ulDatalen; idx++)
{
unsigned int data = *pcDatabuf++;
for (unsigned int bit = 0u; bit<8u; bit++, data >>=1)
{
crc = (crc >> 1) ^ (((crc ^ data) & 1) ? CRC32POLY : 0);
}
}
return (crc);
}
+1 -1
View File
@@ -80,7 +80,7 @@ private:
int LookUpToMod( OTM_IDirect3DTexture9* pTexture);
int LoadTexture( TextureFileStruct* file_in_memory, OTM_IDirect3DTexture9 **ppTexture);
MyTypeHash GetHash(unsigned char *str, int len);
unsigned int GetCRC32(char *pcDatabuf, unsigned int ulDatalen);
};
+99 -40
View File
@@ -125,9 +125,75 @@ int OTM_TextureServer::RemoveClient(OTM_TextureClient *client) // called from a
return (UnlockMutex());
}
int OTM_TextureServer::AddFile( char* buffer, unsigned int size, MyTypeHash hash, bool force) // called from the server
{
Message("OTM_TextureServer::AddFile( %lu %lu, %#lX, %d): %lu\n", buffer, size, hash, force, this);
TextureFileStruct* temp = NULL;
int num = CurrentMod.GetNumber();
for (int i = 0; i < num; i++) if (CurrentMod[i]->Hash == hash)
{
if (force) {temp = CurrentMod[i]; break;}
else return (RETURN_OK);
}
if (temp==NULL)
{
num = OldMod.GetNumber();
for (int i = 0; i < num; i++) if (OldMod[i]->Hash == hash)
{
temp = OldMod[i];
OldMod.Remove(temp);
CurrentMod.Add(temp);
if (force) break;
else return (RETURN_OK);
}
}
bool new_file = true;
if (temp!=NULL)
{
new_file = false;
if (temp->pData!=NULL) delete [] temp->pData;
temp->pData = NULL;
}
else
{
new_file = true;
temp = new TextureFileStruct;
temp->Reference = -1;
}
try
{
temp->pData = new char[size];
}
catch (...)
{
if (!new_file) CurrentMod.Remove( temp);
delete temp;
gl_ErrorState |= OTM_ERROR_MEMORY | OTM_ERROR_SERVER;
return (RETURN_NO_MEMORY);
}
for (unsigned int i=0; i<size; i++) temp->pData[i] = buffer[i];
temp->Checked = false;
temp->Size = size;
temp->pTexture = NULL;
temp->Hash = hash;
if (new_file) temp->ForceReload = false;
else temp->ForceReload = force;
Message("End AddFile( %lu)\n", hash);
if (new_file) return (CurrentMod.Add(temp));
else return (RETURN_OK);
}
int OTM_TextureServer::AddFile(wchar_t* file_name, MyTypeHash hash, bool force) // called from the server
{
Message("AddFile( %ls, %#lX, %d): %lu\n", file_name, hash, force, this);
Message("OTM_TextureServer::AddFile( %ls, %#lX, %d): %lu\n", file_name, hash, force, this);
TextureFileStruct* temp = NULL;
@@ -409,8 +475,11 @@ int OTM_TextureServer::MainLoop(void) // run as a separated thread !!
{
Message("MainLoop: begin\n");
if (Pipe.In == INVALID_HANDLE_VALUE) return (RETURN_PIPE_NOT_OPENED);
char buffer[BUFSIZE];
unsigned long size;
char *buffer;
try {buffer = new char[BIG_BUFSIZE];}
catch (...) {return (RETURN_NO_MEMORY);}
unsigned long num;
Message("MainLoop: started\n");
while (1)
@@ -418,22 +487,22 @@ int OTM_TextureServer::MainLoop(void) // run as a separated thread !!
Message("MainLoop: run\n");
bool ret = ReadFile(Pipe.In, // pipe handle
buffer, // buffer to receive reply
BUFSIZE, // size of buffer
&size, // number of bytes read
BIG_BUFSIZE, // size of buffer
&num, // number of bytes read
NULL); // not overlapped
Message("MainLoop: read something (%lu)\n", size);
Message("MainLoop: read something (%lu)\n", num);
//for (int i=0; i<size; i++) {Message("%d\n",buffer[i]);}
if (ret || GetLastError() == ERROR_MORE_DATA)
{
unsigned int pos = 0;
MsgStruct *commands;
wchar_t *file;
//wchar_t *file;
bool update_textures = false;
while (pos <= size - sizeof(MsgStruct))
while (pos <= num - sizeof(MsgStruct))
{
commands = (MsgStruct*) &buffer[pos];
unsigned int add_length = 0u;
unsigned int size = 0u;
bool force = false;
switch (commands->Control)
@@ -441,26 +510,24 @@ int OTM_TextureServer::MainLoop(void) // run as a separated thread !!
case CONTROL_FORCE_RELOAD_TEXTURE: force=true;
case CONTROL_ADD_TEXTURE:
{
int temp_pos = pos + sizeof(MsgStruct);
file = (wchar_t*) &buffer[temp_pos];
while (temp_pos < BUFSIZE && file[add_length])
{
add_length++;
temp_pos += sizeof(wchar_t);
}
add_length++;
temp_pos += sizeof(wchar_t); //to add the zero
Message("MainLoop: CONTROL_ADD_TEXTURE (%#lX %u, %u %u): %lu\n", commands->Hash, add_length, sizeof(MsgStruct), sizeof(char), this);
if (temp_pos < BUFSIZE)
{
AddFile(file, commands->Hash, force);
update_textures = true;
}
else add_length = 0;
size = commands->Value;
Message("MainLoop: CONTROL_ADD_TEXTURE (%#lX %u, %u %u): %lu\n", commands->Hash, size, sizeof(MsgStruct), sizeof(char), this);
if (pos + sizeof(MsgStruct) + size <= num) AddFile( (wchar_t*) &buffer[pos + sizeof(MsgStruct)], commands->Hash, force);
update_textures = true;
force = false;
break;
}
case CONTROL_FORCE_RELOAD_TEXTURE_DATA: force=true;
case CONTROL_ADD_TEXTURE_DATA:
{
size = commands->Value;
Message("MainLoop: CONTROL_ADD_TEXTURE (%#lX %u, %u %u): %lu\n", commands->Hash, size, sizeof(MsgStruct), sizeof(char), this);
if (pos + sizeof(MsgStruct) + size <= num) AddFile( &buffer[pos + sizeof(MsgStruct)], size, commands->Hash, force);
update_textures = true;
force = false;
break;
}
case CONTROL_REMOVE_TEXTURE:
{
Message("MainLoop: CONTROL_REMOVE_TEXTURE (%#lX): %lu\n", commands->Hash, this);
@@ -485,19 +552,8 @@ int OTM_TextureServer::MainLoop(void) // run as a separated thread !!
}
case CONTROL_SET_DIR:
{
int temp_pos = pos + sizeof(MsgStruct);
file = (wchar_t*) &buffer[temp_pos];
while (temp_pos < BUFSIZE && file[add_length])
{
add_length++;
temp_pos += sizeof(wchar_t);
}
add_length++;
temp_pos += sizeof(wchar_t); //to add the zero
Message("MainLoop: CONTROL_SET_DIR (%u): %lu\n", add_length, this);
if (temp_pos < BUFSIZE) SetSaveDirectory(file);
else add_length = 0;
size = commands->Value;
if (pos + sizeof(MsgStruct) +size <= num) SetSaveDirectory( (wchar_t*) &buffer[pos + sizeof(MsgStruct)]);
break;
}
@@ -525,17 +581,20 @@ int OTM_TextureServer::MainLoop(void) // run as a separated thread !!
break;
}
}
pos += sizeof(MsgStruct) + add_length * sizeof(wchar_t);
pos += sizeof(MsgStruct) + size;
}
if (update_textures) PropagateUpdate();
}
else
{
Message("MainLoop: error in ReadFile()\n");
delete [] buffer;
ClosePipe();
return (RETURN_OK);
}
}
delete [] buffer;
return (RETURN_OK);
}
+1
View File
@@ -44,6 +44,7 @@ public:
//following functions are public for testing purpose !!
int AddFile( char* buffer, unsigned int size, MyTypeHash hash, bool force);
int AddFile( wchar_t* file_name, MyTypeHash hash, bool force);
int RemoveFile( MyTypeHash hash);
+2 -2
View File
@@ -45,14 +45,14 @@ OTM_Client::~OTM_Client(void)
void* OTM_Client::Entry(void)
{
char buffer[BUFSIZE];
char buffer[SMALL_BUFSIZE];
while (1)
{
unsigned long size;
bool ret = ReadFile(
Pipe.In, // handle to pipe
buffer, // buffer to receive data
BUFSIZE, // size of buffer
SMALL_BUFSIZE, // size of buffer
&size, // number of bytes read
NULL); // not overlapped I/O
+5 -5
View File
@@ -91,16 +91,16 @@ OTM_Frame::OTM_Frame(const wxString& title, const wxPoint& pos, const wxSize& si
MainSizer = new wxBoxSizer(wxVERTICAL);
Notebook = new wxNotebook( this, wxID_ANY);
MainSizer->Add( Notebook, 1, wxEXPAND , 0 );
MainSizer->Add( (wxWindow*) Notebook, 1, wxEXPAND , 0 );
ButtonSizer = new wxBoxSizer(wxHORIZONTAL);
OpenButton = new wxButton( this, ID_Button_Open, Language.ButtonOpen, wxDefaultPosition, wxSize(100,24));
DirectoryButton = new wxButton( this, ID_Button_Path, Language.ButtonDirectory, wxDefaultPosition, wxSize(100,24));
UpdateButton = new wxButton( this, ID_Button_Update, Language.ButtonUpdate, wxDefaultPosition, wxSize(100,24));
ButtonSizer->Add( OpenButton, 1, wxEXPAND, 0);
ButtonSizer->Add( DirectoryButton, 1, wxEXPAND, 0);
ButtonSizer->Add( UpdateButton, 1, wxEXPAND, 0);
ButtonSizer->Add( (wxWindow*) OpenButton, 1, wxEXPAND, 0);
ButtonSizer->Add( (wxWindow*) DirectoryButton, 1, wxEXPAND, 0);
ButtonSizer->Add( (wxWindow*) UpdateButton, 1, wxEXPAND, 0);
MainSizer->Add( ButtonSizer, 0, wxEXPAND , 0 );
@@ -223,7 +223,7 @@ void OTM_Frame::OnButtonOpen(wxCommandEvent& WXUNUSED(event))
OTM_GamePage *page = (OTM_GamePage*) Notebook->GetCurrentPage();
if (page==NULL) return;
wxString file_name = wxFileSelector( Language.ChooseFile, TexturePath, "", "dds", "textures (*.dds)|*.dds", wxFD_OPEN | wxFD_FILE_MUST_EXIST, this);
wxString file_name = wxFileSelector( Language.ChooseFile, TexturePath, "", "*.*", "textures (*.dds)|*.dds|zip (*.zip)|*.zip|tpf (*.tpf)|*.tpf", wxFD_OPEN | wxFD_FILE_MUST_EXIST, this);
if ( !file_name.empty() )
{
TexturePath = file_name.BeforeLast( '/');
Binary file not shown.

Before

Width:  |  Height:  |  Size: 23 KiB

+333 -25
View File
@@ -20,7 +20,6 @@ along with FooOpenTexMod. If not, see <http://www.gnu.org/licenses/>.
#include "OTM_Main.h"
OTM_GamePage::OTM_GamePage( wxNotebook *parent, OTM_GameInfo *game, PipeStruct &pipe, OTM_Language &lang) : wxPanel(parent), Language(lang), Sender(pipe)
{
MainSizer = new wxBoxSizer(wxVERTICAL);
@@ -31,17 +30,17 @@ OTM_GamePage::OTM_GamePage( wxNotebook *parent, OTM_GameInfo *game, PipeStruct &
array = Language.Keys;
array[0] = Language.KeyBack;
ChoiceKeyBack = new wxChoice( this, wxID_ANY, wxDefaultPosition, wxDefaultSize, array);
MainSizer->Add( ChoiceKeyBack, 1, wxEXPAND, 0);
MainSizer->Add( (wxWindow*) ChoiceKeyBack, 1, wxEXPAND, 0);
array = Language.Keys;
array[0] = Language.KeySave;
ChoiceKeySave = new wxChoice( this, wxID_ANY, wxDefaultPosition, wxDefaultSize, array);
MainSizer->Add( ChoiceKeySave, 1, wxEXPAND, 0);
MainSizer->Add( (wxWindow*) ChoiceKeySave, 1, wxEXPAND, 0);
array = Language.Keys;
array[0] = Language.KeyNext;
ChoiceKeyNext = new wxChoice( this, wxID_ANY, wxDefaultPosition, wxDefaultSize, array);
MainSizer->Add( ChoiceKeyNext, 1, wxEXPAND, 0);
MainSizer->Add( (wxWindow*) ChoiceKeyNext, 1, wxEXPAND, 0);
Game->GetTextures( array);
@@ -53,11 +52,11 @@ OTM_GamePage::OTM_GamePage( wxNotebook *parent, OTM_GameInfo *game, PipeStruct &
CheckBoxes[0] = new wxCheckBox( this, -1, Language.CheckBoxSaveSingleTexture);
CheckBoxes[0]->SetValue( Game->GetSaveSingleTexture());
MainSizer->Add( CheckBoxes[0], 1, wxEXPAND, 0);
MainSizer->Add( (wxWindow*) CheckBoxes[0], 1, wxEXPAND, 0);
CheckBoxes[1] = new wxCheckBox( this, -1, Language.CheckBoxSaveAllTextures);
CheckBoxes[1]->SetValue( Game->GetSaveAllTextures());
MainSizer->Add( CheckBoxes[1], 1, wxEXPAND, 0);
MainSizer->Add( (wxWindow*) CheckBoxes[1], 1, wxEXPAND, 0);
@@ -68,7 +67,7 @@ OTM_GamePage::OTM_GamePage( wxNotebook *parent, OTM_GameInfo *game, PipeStruct &
name = name.AfterLast( '/');
CheckBoxes[i] = new wxCheckBox( this, -1, name);
CheckBoxes[i]->SetValue( true);
MainSizer->Add( CheckBoxes[i], 1, wxEXPAND, 0);
MainSizer->Add( (wxWindow*) CheckBoxes[i], 1, wxEXPAND, 0);
}
SetSizer(MainSizer);
}
@@ -94,7 +93,7 @@ void OTM_GamePage::AddTexture( const wxString &file_name)
wxString file = file_name.AfterLast( '/');
CheckBoxes[NumberOfEntry] = new wxCheckBox( this, -1, file);
CheckBoxes[NumberOfEntry]->SetValue( true);
MainSizer->Add( CheckBoxes[NumberOfEntry], 1, wxEXPAND, 0);
MainSizer->Add( (wxWindow*) CheckBoxes[NumberOfEntry], 1, wxEXPAND, 0);
NumberOfEntry++;
MainSizer->Layout();
@@ -142,37 +141,346 @@ int OTM_GamePage::UpdateGame(void)
if (NumberOfEntry<=2) return 0;
wxArrayString textures;
wxArrayString send_tex;
Game->GetTextures( textures);
int num = textures.GetCount();
unsigned long hash [num];
bool add[num];
bool force[num];
if (num!=NumberOfEntry-2) return -1;
wxString name;
AddTextureClass *tex = new AddTextureClass[num];
wxString file_type;
unsigned long temp_hash;
int count = 0;
for (int i=0; i<num; i++)
{
file_type = textures[i];
file_type = file_type.AfterLast( '.');
name = textures[i];
name = name.AfterLast( '\\');
name = name.BeforeLast( '.');
if (name.ToULong( &temp_hash, 16))
if (file_type == L"zip")
{
send_tex.Add( textures[i]);
add[count] = CheckBoxes[i+2]->GetValue();
force[count] = true;
hash[count++] = temp_hash;
AddZip( &tex[i], textures[i], CheckBoxes[i+2]->GetValue(), true, false);
}
else if (file_type == L"tpf")
{
AddZip( &tex[i], textures[i], CheckBoxes[i+2]->GetValue(), true, true);
}
else if (file_type == L"dds")
{
AddFile( &tex[i], textures[i], CheckBoxes[i+2]->GetValue(), true);
}
else
{
wxString msg = Language.FileNotSupported;
msg << textures[i];
wxMessageBox(msg, "ERROR", wxOK);
}
else wxMessageBox("UpdateGame(): no Ulong", "Info", wxOK);
}
if (count) return Sender.SendTextures( send_tex, hash, add, force);
Sender.SendTextures( num, tex);
return 0;
}
int OTM_GamePage::AddFile( AddTextureClass *tex, wxString file, bool add, bool force)
{
tex->SetSize(1);
unsigned long temp_hash;
wxString name = file.AfterLast( '_');
name = name.BeforeLast( '.');
if (!name.ToULong( &temp_hash, 16)) return -1; // return if hash could not be extracted
tex->Add[0] = add;
if (add)
{
wxFile dat(file, wxFile::read);
if (!dat.IsOpened()) {return -1;}
unsigned len = file.Length();
try {tex->Textures[0] = new char [len];}
catch (...) {tex->Textures[0] = NULL; return -1;}
unsigned int result = dat.Read( (void*) tex->Textures[0], len);
dat.Close();
if (result != len) return -1;
tex->Size[0] = len;
}
else {tex->Size[0] = 0; tex->Textures[0] = NULL;}
tex->Num = 1;
tex->Force[0] = true;
tex->Hash[0] = temp_hash;
return 0;
}
int OTM_GamePage::AddZip( AddTextureClass *tex, wxString file, bool add, bool force, bool tpf)
{
wxFile dat(file, wxFile::read);
if (!dat.IsOpened()) {return -1;}
unsigned len = dat.Length();
unsigned char* buffer;
try {buffer = new unsigned char [len];}
catch (...) {return -1;}
unsigned int result = dat.Read( buffer, len);
dat.Close();
if (result != len) return -1;
if (tpf)
{
/*
*
* BIG THANKS TO Tonttu
* (TPFcreate 1.5)
*
*/
unsigned int TPF_XOR = 0x3FA43FA4u;
const char pw[] = {0x73, 0x2A, 0x63, 0x7D, 0x5F, 0x0A, 0xA6, 0xBD,
0x7D, 0x65, 0x7E, 0x67, 0x61, 0x2A, 0x7F, 0x7F,
0x74, 0x61, 0x67, 0x5B, 0x60, 0x70, 0x45, 0x74,
0x5C, 0x22, 0x74, 0x5D, 0x6E, 0x6A, 0x73, 0x41,
0x77, 0x6E, 0x46, 0x47, 0x77, 0x49, 0x0C, 0x4B,
0x46, 0x6F, '\0'};
unsigned int j=0;
while ( j <= result - 4 )
{
*( unsigned int* )( &buffer[j] ) ^= TPF_XOR;
j += 4;
}
while ( j < result )
{
buffer[j] ^= (unsigned char )( TPF_XOR >> 24 );
TPF_XOR <<= 4;
j++;
}
if (add) AddContent( (char*) buffer, len, pw, tex, add, force);
else RemoveContent( (char*) buffer, len, pw, tex, add, force);
}
else
{
if (add) AddContent( (char*) buffer, len, NULL, tex, add, force);
else RemoveContent( (char*) buffer, len, NULL, tex, add, force);
}
delete [] buffer;
return 0;
}
int OTM_GamePage::AddContent( char* buffer, unsigned int len, const char* pw, AddTextureClass *tex, bool add, bool force)
{
HZIP hz = OpenZip( (void*) buffer, len, pw);
ZIPENTRY ze;
int index;
FindZipItem( hz, L"texmod.def", false, &index, &ze);
if (index>=0) //if texmod.def is present in the zip file
{
char* def;
int len = ze.unc_size;
try {def=new char[len+1];}
catch(...) {CloseZip(hz); return -1;}
ZRESULT zr = UnzipItem( hz,index, def, len);
if (zr!=ZR_OK && zr!=ZR_MORE) {delete [] def; CloseZip(hz); return -1;}
def[len]=0;
int count = 0;
for (int i=0; i<len; i++) if (def[i]=='\n') count++;
if (def[len-1]!='\n') count++;
tex->SetSize(count+1);
unsigned long temp_hash;
int pos = 0;
count = 0;
wxString def_file;
def_file = def;
wxString conv;
while (1)
{
if (def_file.Len()<11) break;
conv = def_file.BeforeFirst( '|');
if (!conv.ToULong( &temp_hash, 16))
{
def_file = def_file.AfterFirst( '\n');
continue;
}
def_file = def_file.AfterFirst( '|');
conv = def_file.BeforeFirst( '\n');
conv.Replace( "\r", "");
FindZipItem( hz, conv.wc_str(), false, &index, &ze); // look for texture
if (index>=0)
{
try {tex->Textures[count] = new char[ze.unc_size];}
catch(...)
{
tex->Textures[count] = NULL;
def_file = def_file.AfterFirst( '\n');
continue;
}
if (ZR_OK!=UnzipItem( hz, index, tex->Textures[count], ze.unc_size))
{
delete [] tex->Textures[count];
tex->Textures[count] = NULL;
}
else
{
tex->Hash[count] = temp_hash;
tex->Add[count] = true;
tex->Size[count] = ze.unc_size;
tex->Force[count] = force;
count++;
}
}
def_file = def_file.AfterFirst( '\n');
}
tex->Num = count;
}
else // texmod.def is not present in the zip file
{
wxString name;
wxString file;
GetZipItem( hz, -1, &ze); //ask for number of entries
index = ze.index;
tex->SetSize(index);
int count = 0;
unsigned long temp_hash;
for (int i=0; i<index; i++)
{
if (GetZipItem( hz, i, &ze)!=ZR_OK) continue; //ask for name and size
file = ze.name;
name = file.AfterLast( '.');
if (name!="dds") continue; //if this is not texture file, continue
name = file.AfterLast( '_');
name = name.BeforeLast( '.');
if (!name.ToULong( &temp_hash, 16)) continue; //if hash couldt not be extracted
try {tex->Textures[count] = new char[ze.unc_size];}
catch(...)
{
tex->Textures[count] = NULL;
continue;
}
ZRESULT rz = UnzipItem( hz, i, tex->Textures[count], ze.unc_size);
if (ZR_OK!=rz)
{
delete [] tex->Textures[count];
tex->Textures[count] = NULL;
}
else
{
tex->Hash[count] = temp_hash;
tex->Add[count] = true;
tex->Size[count] = ze.unc_size;
tex->Force[count] = force;
count++;
}
}
tex->Num = count;
}
CloseZip(hz);
return 0;
}
int OTM_GamePage::RemoveContent( char* buffer, unsigned int len, const char* pw, AddTextureClass *tex, bool add, bool force)
{
HZIP hz = OpenZip( (void*) buffer, len, pw);
ZIPENTRY ze;
int index;
FindZipItem( hz, L"texmod.def", true, &index, &ze);
if (index>=0)
{
char* def;
int len = ze.unc_size;
try {def=new char[len+1];}
catch(...) {return -1;}
if (ZR_OK!=UnzipItem( hz,index, def, len)) {delete [] def; return -1;}
def[len]=0;
int count = 0;
for (int i=0; i<len; i++) if (def[i]=='\n') count++;
if (def[len-1]!='\n') count++;
tex->SetSize(count);
unsigned long temp_hash;
int pos = 0;
count = 0;
wxString def_file;
def_file = def;
wxString conv;
while (1)
{
if (def_file.Len()<11) break;
conv = def_file.BeforeFirst( '|');
if (!conv.ToULong( &temp_hash, 16))
{
def_file = def_file.AfterFirst( '\n');
continue;
}
tex->Hash[count] = temp_hash;
tex->Add[count] = false;
tex->Size[count] = 0;
tex->Force[count] = force;
count++;
def_file = def_file.AfterFirst( '\n');
}
tex->Num = count;
}
else
{
wxString name;
wxString file;
GetZipItem( hz, -1, &ze);
index = ze.index;
tex->SetSize(index);
int count = 0;
unsigned long temp_hash;
for (int i=0; i<index; i++)
{
if (GetZipItem( hz, i, &ze)!=ZR_OK) continue;
file = ze.name;
name = file.AfterLast( '.');
if (name!="dds") continue;
name = file.AfterLast( '_');
name = name.BeforeLast( '.');
if (!name.ToULong( &temp_hash, 16)) continue;
tex->Hash[count] = temp_hash;
tex->Add[count] = false;
tex->Size[count] = 0;
tex->Force[count] = force;
count++;
}
tex->Num = count;
}
CloseZip(hz);
return 0;
}
+11
View File
@@ -22,6 +22,7 @@ along with FooOpenTexMod. If not, see <http://www.gnu.org/licenses/>.
#define OTM_GAMEPAGE_H_
#include "OTM_Main.h"
#include "unzip.h"
// this page is opened if a game is started.
class OTM_GamePage : public wxPanel
@@ -31,10 +32,20 @@ public:
virtual ~OTM_GamePage(void);
void AddTexture( const wxString &file_name);
void SetPath( const wxString &file_name);
int UpdateGame(void);
private:
int AddFile( AddTextureClass *tex, wxString file, bool add, bool force);
int AddZip( AddTextureClass *tex, wxString file, bool add, bool force, bool tpf);
int AddContent( char* buffer, unsigned int len, const char* pw, AddTextureClass *tex, bool add, bool force);
int RemoveContent( char* buffer, unsigned int len, const char* pw, AddTextureClass *tex, bool add, bool force);
wxChoice *ChoiceKeyBack;
wxChoice *ChoiceKeySave;
wxChoice *ChoiceKeyNext;
+2
View File
@@ -47,6 +47,8 @@ int OTM_Language::LoadLanguage(int lang)
CheckBoxSaveSingleTexture = L"Save single texture";
CheckBoxSaveAllTextures = L"Save all textures";
FileNotSupported = L"This file type is not supported:\n";
}
LoadKeys(lang);
+3
View File
@@ -53,6 +53,9 @@ public:
wxString KeyNext;
wxArrayString Keys;
wxString FileNotSupported;
private:
int LoadKeys(int lang);
};
+2
View File
@@ -37,11 +37,13 @@ along with FooOpenTexMod. If not, see <http://www.gnu.org/licenses/>.
#define wxUSE_FILEDLG 1
#define wxUSE_DIRDLG 1
#define wxUSE_CHOICE 1
#define wxUSE_FILE 1
#endif
#include "wx\wx.h"
#include "wx\notebook.h"
#include <wx/file.h>
//#include <wx/thread.h>
//#include "wx/checkbox.h"
//#include <wx/msgdlg.h>
+72 -34
View File
@@ -20,12 +20,54 @@ along with FooOpenTexMod. If not, see <http://www.gnu.org/licenses/>.
#include "OTM_Main.h"
AddTextureClass::AddTextureClass(void)
{
Num = 0;
Textures = NULL;
Size = NULL;
Hash = NULL;
Force = NULL;
Add = NULL;
Len=0;
}
void AddTextureClass::SetSize(int num)
{
Num = 0;
Force = new bool[num];
Add = new bool[num];
Size = new unsigned int[num];
for (int i=0; i<num; i++) Size[i] = 0;
Hash = new unsigned long[num];
Textures = new char*[num];
for (int i=0; i<num; i++) Textures[i] = NULL;
Len = num;
}
AddTextureClass::~AddTextureClass(void)
{
if (Force!=NULL) delete [] Force;
if (Add!=NULL) delete [] Add;
if (Size!=NULL) delete [] Size;
if (Hash!=NULL) delete [] Hash;
if (Textures!=NULL)
{
for (unsigned int j=0; j<Len; j++) if (Textures[j]!=NULL) delete [] Textures[j];
delete [] Textures;
}
}
OTM_Sender::OTM_Sender(PipeStruct &pipe) : Pipe(pipe)
{
try {Buffer = new char[BIG_BUFSIZE];}
catch (...) {Buffer=NULL;}
}
OTM_Sender::~OTM_Sender(void)
{
if (Buffer!=NULL) delete [] Buffer;
}
int OTM_Sender::SendSaveAllTextures(bool val)
@@ -51,44 +93,39 @@ int OTM_Sender::SendSaveSingleTexture(bool val)
}
int OTM_Sender::SendTextures(const wxArrayString &textures, unsigned long *hash, bool *add, bool *force)
int OTM_Sender::SendTextures(unsigned int num, AddTextureClass *tex)
{
char buffer[BUFSIZE];
int num = textures.GetCount();
if (Buffer==NULL) return (RETURN_NO_MEMORY);
//wxMessageBox("OTM_Sender::SendTextures", "start", wxOK);
MsgStruct *msg;
int pos = 0;
int old_pos = 0;
for (int i=0; i<num; i++)
for (unsigned int i=0u; i<num; i++) for (unsigned int j=0u; j<tex[i].Num; j++)
{
msg = (MsgStruct*) &buffer[pos];
msg->Hash = hash[i];
if (add[i])
if (tex[i].Size[j]+sizeof(MsgStruct)+pos>BIG_BUFSIZE)
{
if (force[i]) msg->Control = CONTROL_FORCE_RELOAD_TEXTURE;
else msg->Control = CONTROL_ADD_TEXTURE;
if (int ret = SendToGame( Buffer, pos)) return ret;
pos = 0;
}
else msg->Control = CONTROL_REMOVE_TEXTURE;
msg->Value = 0;
msg = (MsgStruct*) &Buffer[pos];
msg->Hash = tex[i].Hash[j];
msg->Value = tex[i].Size[j];
pos += sizeof(MsgStruct);
if (add[i] && pos<BUFSIZE)
if (tex[i].Add[j])
{
const wchar_t *file = textures[i].wc_str();
wchar_t *buff_file = (wchar_t*) &buffer[pos];
int len = 0;
while (file[len] && (pos+len*sizeof(wchar_t))<BUFSIZE) {buff_file[len] = file[len]; len++;};
if ((pos+len*sizeof(wchar_t))<BUFSIZE) buff_file[len] = 0;
len++;
pos+=len*sizeof(wchar_t);
if (tex[i].Force[j]) msg->Control = CONTROL_FORCE_RELOAD_TEXTURE_DATA;
else msg->Control = CONTROL_ADD_TEXTURE_DATA;
char* temp = tex[i].Textures[j];
for (unsigned int l=0; l<tex[i].Size[j]; l++) Buffer[pos+l] = temp[l];
pos+=tex[i].Size[j];
}
if (pos>=BUFSIZE)
{
if (int ret = SendToGame( buffer, old_pos)) return ret;
pos = 0; old_pos = 0; i--;
}
else old_pos = pos;
else msg->Control = CONTROL_REMOVE_TEXTURE;
}
if (old_pos) if (int ret = SendToGame( buffer, old_pos)) return ret;
if (pos) if (int ret = SendToGame( Buffer, pos)) return ret;
return 0;
}
@@ -127,29 +164,30 @@ int OTM_Sender::SendKeyNext(int key)
int OTM_Sender::SendPath( const wxString &path)
{
char buffer[BUFSIZE];
MsgStruct *msg = (MsgStruct*) buffer;
MsgStruct *msg = (MsgStruct*) Buffer;
msg->Hash = 0u;
msg->Control = CONTROL_SET_DIR;
msg->Value = 0;
const wchar_t *file = path.wc_str();
wchar_t *buff_file = (wchar_t*) &buffer[sizeof(MsgStruct)];
wchar_t *buff_file = (wchar_t*) &Buffer[sizeof(MsgStruct)];
int len = 0;
while (file[len] && (sizeof(MsgStruct)+len*sizeof(wchar_t))<BUFSIZE) {buff_file[len] = file[len]; len++;};
if ((sizeof(MsgStruct)+len*sizeof(wchar_t))<BUFSIZE) buff_file[len] = 0;
while (file[len] && (sizeof(MsgStruct)+len*sizeof(wchar_t))<BIG_BUFSIZE) {buff_file[len] = file[len]; len++;};
if ((sizeof(MsgStruct)+len*sizeof(wchar_t))<BIG_BUFSIZE) buff_file[len] = 0;
len++;
return SendToGame( buffer, sizeof(MsgStruct)+len*sizeof(wchar_t));
msg->Value = len*sizeof(wchar_t);
return SendToGame( Buffer, sizeof(MsgStruct)+len*sizeof(wchar_t));
}
int OTM_Sender::SendToGame( void *msg, unsigned long len)
{
if (len==0) return (RETURN_BAD_ARGUMENT);
unsigned long num;
if (Pipe.Out==INVALID_HANDLE_VALUE) return -1;
bool ret = WriteFile( Pipe.Out, (const void*) msg, len, &num, NULL);
if (!ret || len!=num) return -1;
if (!FlushFileBuffers(Pipe.Out)) return -1;
return 0;
}
+20 -1
View File
@@ -22,6 +22,24 @@ along with FooOpenTexMod. If not, see <http://www.gnu.org/licenses/>.
#define OTM_SENDER_H_
#include "OTM_Main.h"
class AddTextureClass
{
public:
AddTextureClass(void);
void SetSize(int num);
~AddTextureClass(void);
unsigned int Num;
char **Textures;
unsigned int *Size;
unsigned long *Hash;
bool *Add;
bool *Force;
unsigned int Len;
};
// an object of this class is owned by each OTM_GamePage object. It act as sender ^^
class OTM_Sender
{
@@ -32,7 +50,7 @@ public:
int SendSaveAllTextures(bool val);
int SendSaveSingleTexture(bool val);
int SendTextures(const wxArrayString &textures, unsigned long *hash, bool *add, bool *force);
int SendTextures(unsigned int num, AddTextureClass *tex);
int SendKeyBack(int key);
int SendKeySave(int key);
@@ -42,6 +60,7 @@ public:
private:
char *Buffer;
int SendToGame( void* msg, unsigned long len);
PipeStruct &Pipe;
};
+6 -6
View File
@@ -38,7 +38,7 @@ void* OTM_Server::Entry(void)
bool fConnected = false;
HANDLE pipe_in;
HANDLE pipe_out;
char buffer[BUFSIZE];
char buffer[SMALL_BUFSIZE];
wxString abort = ABORT_SERVER;
while(1)
@@ -53,8 +53,8 @@ void* OTM_Server::Entry(void)
PIPE_TYPE_BYTE | // byte type pipe
PIPE_WAIT, // blocking mode
PIPE_UNLIMITED_INSTANCES, // max. instances
BUFSIZE, // output buffer size
BUFSIZE, // input buffer size
SMALL_BUFSIZE, // output buffer size
SMALL_BUFSIZE, // input buffer size
0, // client time-out
NULL); // default security attribute
if (pipe_in == INVALID_HANDLE_VALUE) return NULL;
@@ -65,8 +65,8 @@ void* OTM_Server::Entry(void)
PIPE_TYPE_BYTE | // byte type pipe
PIPE_WAIT, // blocking mode
PIPE_UNLIMITED_INSTANCES, // max. instances
BUFSIZE, // output buffer size
BUFSIZE, // input buffer size
BIG_BUFSIZE, // output buffer size
BIG_BUFSIZE, // input buffer size
0, // client time-out
NULL); // default security attribute
if (pipe_out == INVALID_HANDLE_VALUE) return NULL;
@@ -87,7 +87,7 @@ void* OTM_Server::Entry(void)
bool fSuccess = ReadFile(
pipe_in, // handle to pipe
buffer, // buffer to receive data
BUFSIZE, // size of buffer
SMALL_BUFSIZE, // size of buffer
&num, // number of bytes read
NULL); // not overlapped I/O
+4 -3
View File
@@ -31,6 +31,7 @@ MINIMAL_CXXFLAGS = $(__DEBUGINFO) $(__OPTIMIZEFLAG_2) $(__THREADSFLAG) \
$(__EXCEPTIONSFLAG_6) -Wno-ctor-dtor-privacy $(CPPFLAGS) $(CXXFLAGS)
MINIMAL_OBJECTS = \
$(OBJS)\OTM_rc.o \
$(OBJS)\unzip.o \
$(OBJS)\OTM_GUI.o \
$(OBJS)\OTM_GameInfo.o \
$(OBJS)\OTM_GamePage.o \
@@ -232,12 +233,12 @@ clean:
$(OBJS_exe)\OTM_GUI.exe: $(MINIMAL_OBJECTS) $(OBJS)\OTM_rc.o
$(CXX) -o $@ $(MINIMAL_OBJECTS) $(LDFLAGS) $(__DEBUGINFO) $(__THREADSFLAG) -L$(LIBDIRNAME) -Wl,--subsystem,windows -mwindows $(__WXLIB_CORE_p) $(__WXLIB_BASE_p) $(__WXLIB_MONO_p) $(__LIB_TIFF_p) $(__LIB_JPEG_p) $(__LIB_PNG_p) -lwxzlib$(WXDEBUGFLAG) -lwxregex$(WXUNICODEFLAG)$(WXDEBUGFLAG) -lwxexpat$(WXDEBUGFLAG) $(EXTRALIBS_FOR_BASE) $(__UNICOWS_LIB_p) $(__GDIPLUS_LIB_p) -lkernel32 -luser32 -lgdi32 -lcomdlg32 -lwinspool -lwinmm -lshell32 -lcomctl32 -lole32 -loleaut32 -luuid -lrpcrt4 -ladvapi32 -lwsock32 -lodbc32
#$(OBJS)\SR_rc.o: SR.rc
# windres --use-temp-file -i$< -o$@ --define __WXMSW__ $(__WXUNIV_DEFINE_p_1) $(__DEBUG_DEFINE_p_1) $(__EXCEPTIONS_DEFINE_p_1) $(__RTTI_DEFINE_p_1) $(__THREAD_DEFINE_p_1) $(__UNICODE_DEFINE_p_1) $(__MSLU_DEFINE_p_1) $(__GFXCTX_DEFINE_p_1) --include-dir $(SETUPHDIR) --include-dir $(WX_DIR)/include --include-dir . $(__DLLFLAG_p_1)
$(OBJS)\OTM_rc.o: OTM.rc OTM.ico
windres --use-temp-file -i $< -o $@
$(OBJS)\unzip.o: ./unzip.cpp
$(CXX) -c -o $@ $(MINIMAL_CXXFLAGS) $(CPPDEPS) $<
$(OBJS)\OTM_GUI.o: ./OTM_GUI.cpp
$(CXX) -c -o $@ $(MINIMAL_CXXFLAGS) $(CPPDEPS) $<
+4164
View File
File diff suppressed because it is too large Load Diff
+214
View File
@@ -0,0 +1,214 @@
#ifndef _unzip_H
#define _unzip_H
// UNZIPPING functions -- for unzipping.
// This file is a repackaged form of extracts from the zlib code available
// at www.gzip.org/zlib, by Jean-Loup Gailly and Mark Adler. The original
// copyright notice may be found in unzip.cpp. The repackaging was done
// by Lucian Wischik to simplify and extend its use in Windows/C++. Also
// encryption and unicode filenames have been added.
#ifndef _zip_H
DECLARE_HANDLE(HZIP);
#endif
// An HZIP identifies a zip file that has been opened
typedef DWORD ZRESULT;
// return codes from any of the zip functions. Listed later.
typedef struct
{ int index; // index of this file within the zip
TCHAR name[MAX_PATH]; // filename within the zip
DWORD attr; // attributes, as in GetFileAttributes.
FILETIME atime,ctime,mtime;// access, create, modify filetimes
long comp_size; // sizes of item, compressed and uncompressed. These
long unc_size; // may be -1 if not yet known (e.g. being streamed in)
} ZIPENTRY;
HZIP OpenZip(const TCHAR *fn, const char *password);
HZIP OpenZip(void *z,unsigned int len, const char *password);
HZIP OpenZipHandle(HANDLE h, const char *password);
// OpenZip - opens a zip file and returns a handle with which you can
// subsequently examine its contents. You can open a zip file from:
// from a pipe: OpenZipHandle(hpipe_read,0);
// from a file (by handle): OpenZipHandle(hfile,0);
// from a file (by name): OpenZip("c:\\test.zip","password");
// from a memory block: OpenZip(bufstart, buflen,0);
// If the file is opened through a pipe, then items may only be
// accessed in increasing order, and an item may only be unzipped once,
// although GetZipItem can be called immediately before and after unzipping
// it. If it's opened in any other way, then full random access is possible.
// Note: pipe input is not yet implemented.
// Note: zip passwords are ascii, not unicode.
// Note: for windows-ce, you cannot close the handle until after CloseZip.
// but for real windows, the zip makes its own copy of your handle, so you
// can close yours anytime.
ZRESULT GetZipItem(HZIP hz, int index, ZIPENTRY *ze);
// GetZipItem - call this to get information about an item in the zip.
// If index is -1 and the file wasn't opened through a pipe,
// then it returns information about the whole zipfile
// (and in particular ze.index returns the number of index items).
// Note: the item might be a directory (ze.attr & FILE_ATTRIBUTE_DIRECTORY)
// See below for notes on what happens when you unzip such an item.
// Note: if you are opening the zip through a pipe, then random access
// is not possible and GetZipItem(-1) fails and you can't discover the number
// of items except by calling GetZipItem on each one of them in turn,
// starting at 0, until eventually the call fails. Also, in the event that
// you are opening through a pipe and the zip was itself created into a pipe,
// then then comp_size and sometimes unc_size as well may not be known until
// after the item has been unzipped.
ZRESULT FindZipItem(HZIP hz, const TCHAR *name, bool ic, int *index, ZIPENTRY *ze);
// FindZipItem - finds an item by name. ic means 'insensitive to case'.
// It returns the index of the item, and returns information about it.
// If nothing was found, then index is set to -1 and the function returns
// an error code.
ZRESULT UnzipItem(HZIP hz, int index, const TCHAR *fn);
ZRESULT UnzipItem(HZIP hz, int index, void *z,unsigned int len);
ZRESULT UnzipItemHandle(HZIP hz, int index, HANDLE h);
// UnzipItem - given an index to an item, unzips it. You can unzip to:
// to a pipe: UnzipItemHandle(hz,i, hpipe_write);
// to a file (by handle): UnzipItemHandle(hz,i, hfile);
// to a file (by name): UnzipItem(hz,i, ze.name);
// to a memory block: UnzipItem(hz,i, buf,buflen);
// In the final case, if the buffer isn't large enough to hold it all,
// then the return code indicates that more is yet to come. If it was
// large enough, and you want to know precisely how big, GetZipItem.
// Note: zip files are normally stored with relative pathnames. If you
// unzip with ZIP_FILENAME a relative pathname then the item gets created
// relative to the current directory - it first ensures that all necessary
// subdirectories have been created. Also, the item may itself be a directory.
// If you unzip a directory with ZIP_FILENAME, then the directory gets created.
// If you unzip it to a handle or a memory block, then nothing gets created
// and it emits 0 bytes.
ZRESULT SetUnzipBaseDir(HZIP hz, const TCHAR *dir);
// if unzipping to a filename, and it's a relative filename, then it will be relative to here.
// (defaults to current-directory).
ZRESULT CloseZip(HZIP hz);
// CloseZip - the zip handle must be closed with this function.
unsigned int FormatZipMessage(ZRESULT code, TCHAR *buf,unsigned int len);
// FormatZipMessage - given an error code, formats it as a string.
// It returns the length of the error message. If buf/len points
// to a real buffer, then it also writes as much as possible into there.
// These are the result codes:
#define ZR_OK 0x00000000 // nb. the pseudo-code zr-recent is never returned,
#define ZR_RECENT 0x00000001 // but can be passed to FormatZipMessage.
// The following come from general system stuff (e.g. files not openable)
#define ZR_GENMASK 0x0000FF00
#define ZR_NODUPH 0x00000100 // couldn't duplicate the handle
#define ZR_NOFILE 0x00000200 // couldn't create/open the file
#define ZR_NOALLOC 0x00000300 // failed to allocate some resource
#define ZR_WRITE 0x00000400 // a general error writing to the file
#define ZR_NOTFOUND 0x00000500 // couldn't find that file in the zip
#define ZR_MORE 0x00000600 // there's still more data to be unzipped
#define ZR_CORRUPT 0x00000700 // the zipfile is corrupt or not a zipfile
#define ZR_READ 0x00000800 // a general error reading the file
#define ZR_PASSWORD 0x00001000 // we didn't get the right password to unzip the file
// The following come from mistakes on the part of the caller
#define ZR_CALLERMASK 0x00FF0000
#define ZR_ARGS 0x00010000 // general mistake with the arguments
#define ZR_NOTMMAP 0x00020000 // tried to ZipGetMemory, but that only works on mmap zipfiles, which yours wasn't
#define ZR_MEMSIZE 0x00030000 // the memory size is too small
#define ZR_FAILED 0x00040000 // the thing was already failed when you called this function
#define ZR_ENDED 0x00050000 // the zip creation has already been closed
#define ZR_MISSIZE 0x00060000 // the indicated input file size turned out mistaken
#define ZR_PARTIALUNZ 0x00070000 // the file had already been partially unzipped
#define ZR_ZMODE 0x00080000 // tried to mix creating/opening a zip
// The following come from bugs within the zip library itself
#define ZR_BUGMASK 0xFF000000
#define ZR_NOTINITED 0x01000000 // initialisation didn't work
#define ZR_SEEK 0x02000000 // trying to seek in an unseekable file
#define ZR_NOCHANGE 0x04000000 // changed its mind on storage, but not allowed
#define ZR_FLATE 0x05000000 // an internal error in the de/inflation code
// e.g.
//
// SetCurrentDirectory("c:\\docs\\stuff");
// HZIP hz = OpenZip("c:\\stuff.zip",0);
// ZIPENTRY ze; GetZipItem(hz,-1,&ze); int numitems=ze.index;
// for (int i=0; i<numitems; i++)
// { GetZipItem(hz,i,&ze);
// UnzipItem(hz,i,ze.name);
// }
// CloseZip(hz);
//
//
// HRSRC hrsrc = FindResource(hInstance,MAKEINTRESOURCE(1),RT_RCDATA);
// HANDLE hglob = LoadResource(hInstance,hrsrc);
// void *zipbuf=LockResource(hglob);
// unsigned int ziplen=SizeofResource(hInstance,hrsrc);
// HZIP hz = OpenZip(zipbuf, ziplen, 0);
// - unzip to a membuffer -
// ZIPENTRY ze; int i; FindZipItem(hz,"file.dat",true,&i,&ze);
// char *ibuf = new char[ze.unc_size];
// UnzipItem(hz,i, ibuf, ze.unc_size);
// delete[] ibuf;
// - unzip to a fixed membuff -
// ZIPENTRY ze; int i; FindZipItem(hz,"file.dat",true,&i,&ze);
// char ibuf[1024]; ZRESULT zr=ZR_MORE; unsigned long totsize=0;
// while (zr==ZR_MORE)
// { zr = UnzipItem(hz,i, ibuf,1024);
// unsigned long bufsize=1024; if (zr==ZR_OK) bufsize=ze.unc_size-totsize;
// totsize+=bufsize;
// }
// - unzip to a pipe -
// HANDLE hwrite; HANDLE hthread=CreateWavReaderThread(&hwrite);
// int i; ZIPENTRY ze; FindZipItem(hz,"sound.wav",true,&i,&ze);
// UnzipItemHandle(hz,i, hwrite);
// CloseHandle(hwrite);
// WaitForSingleObject(hthread,INFINITE);
// CloseHandle(hwrite); CloseHandle(hthread);
// - finished -
// CloseZip(hz);
// // note: no need to free resources obtained through Find/Load/LockResource
//
//
// SetCurrentDirectory("c:\\docs\\pipedzipstuff");
// HANDLE hread,hwrite; CreatePipe(&hread,&hwrite,0,0);
// CreateZipWriterThread(hwrite);
// HZIP hz = OpenZipHandle(hread,0);
// for (int i=0; ; i++)
// { ZIPENTRY ze;
// ZRESULT zr=GetZipItem(hz,i,&ze); if (zr!=ZR_OK) break; // no more
// UnzipItem(hz,i, ze.name);
// }
// CloseZip(hz);
//
//
// Now we indulge in a little skullduggery so that the code works whether
// the user has included just zip or both zip and unzip.
// Idea: if header files for both zip and unzip are present, then presumably
// the cpp files for zip and unzip are both present, so we will call
// one or the other of them based on a dynamic choice. If the header file
// for only one is present, then we will bind to that particular one.
ZRESULT CloseZipU(HZIP hz);
unsigned int FormatZipMessageU(ZRESULT code, TCHAR *buf,unsigned int len);
bool IsZipHandleU(HZIP hz);
#ifdef _zip_H
#undef CloseZip
#define CloseZip(hz) (IsZipHandleU(hz)?CloseZipU(hz):CloseZipZ(hz))
#else
#define CloseZip CloseZipU
#define FormatZipMessage FormatZipMessageU
#endif
#endif // _unzip_H
+2830
View File
File diff suppressed because it is too large Load Diff
+203
View File
@@ -0,0 +1,203 @@
#ifndef _zip_H
#define _zip_H
// ZIP functions -- for creating zip files
// This file is a repackaged form of the Info-Zip source code available
// at www.info-zip.org. The original copyright notice may be found in
// zip.cpp. The repackaging was done by Lucian Wischik to simplify and
// extend its use in Windows/C++. Also to add encryption and unicode.
#ifndef _unzip_H
DECLARE_HANDLE(HZIP);
#endif
// An HZIP identifies a zip file that is being created
typedef DWORD ZRESULT;
// return codes from any of the zip functions. Listed later.
HZIP CreateZip(const TCHAR *fn, const char *password);
HZIP CreateZip(void *buf,unsigned int len, const char *password);
HZIP CreateZipHandle(HANDLE h, const char *password);
// CreateZip - call this to start the creation of a zip file.
// As the zip is being created, it will be stored somewhere:
// to a pipe: CreateZipHandle(hpipe_write);
// in a file (by handle): CreateZipHandle(hfile);
// in a file (by name): CreateZip("c:\\test.zip");
// in memory: CreateZip(buf, len);
// or in pagefile memory: CreateZip(0, len);
// The final case stores it in memory backed by the system paging file,
// where the zip may not exceed len bytes. This is a bit friendlier than
// allocating memory with new[]: it won't lead to fragmentation, and the
// memory won't be touched unless needed. That means you can give very
// large estimates of the maximum-size without too much worry.
// As for the password, it lets you encrypt every file in the archive.
// (This api doesn't support per-file encryption.)
// Note: because pipes don't allow random access, the structure of a zipfile
// created into a pipe is slightly different from that created into a file
// or memory. In particular, the compressed-size of the item cannot be
// stored in the zipfile until after the item itself. (Also, for an item added
// itself via a pipe, the uncompressed-size might not either be known until
// after.) This is not normally a problem. But if you try to unzip via a pipe
// as well, then the unzipper will not know these things about the item until
// after it has been unzipped. Therefore: for unzippers which don't just write
// each item to disk or to a pipe, but instead pre-allocate memory space into
// which to unzip them, then either you have to create the zip not to a pipe,
// or you have to add items not from a pipe, or at least when adding items
// from a pipe you have to specify the length.
// Note: for windows-ce, you cannot close the handle until after CloseZip.
// but for real windows, the zip makes its own copy of your handle, so you
// can close yours anytime.
ZRESULT ZipAdd(HZIP hz,const TCHAR *dstzn, const TCHAR *fn);
ZRESULT ZipAdd(HZIP hz,const TCHAR *dstzn, void *src,unsigned int len);
ZRESULT ZipAddHandle(HZIP hz,const TCHAR *dstzn, HANDLE h);
ZRESULT ZipAddHandle(HZIP hz,const TCHAR *dstzn, HANDLE h, unsigned int len);
ZRESULT ZipAddFolder(HZIP hz,const TCHAR *dstzn);
// ZipAdd - call this for each file to be added to the zip.
// dstzn is the name that the file will be stored as in the zip file.
// The file to be added to the zip can come
// from a pipe: ZipAddHandle(hz,"file.dat", hpipe_read);
// from a file: ZipAddHandle(hz,"file.dat", hfile);
// from a filen: ZipAdd(hz,"file.dat", "c:\\docs\\origfile.dat");
// from memory: ZipAdd(hz,"subdir\\file.dat", buf,len);
// (folder): ZipAddFolder(hz,"subdir");
// Note: if adding an item from a pipe, and if also creating the zip file itself
// to a pipe, then you might wish to pass a non-zero length to the ZipAddHandle
// function. This will let the zipfile store the item's size ahead of the
// compressed item itself, which in turn makes it easier when unzipping the
// zipfile from a pipe.
ZRESULT ZipGetMemory(HZIP hz, void **buf, unsigned long *len);
// ZipGetMemory - If the zip was created in memory, via ZipCreate(0,len),
// then this function will return information about that memory block.
// buf will receive a pointer to its start, and len its length.
// Note: you can't add any more after calling this.
ZRESULT CloseZip(HZIP hz);
// CloseZip - the zip handle must be closed with this function.
unsigned int FormatZipMessage(ZRESULT code, TCHAR *buf,unsigned int len);
// FormatZipMessage - given an error code, formats it as a string.
// It returns the length of the error message. If buf/len points
// to a real buffer, then it also writes as much as possible into there.
// These are the result codes:
#define ZR_OK 0x00000000 // nb. the pseudo-code zr-recent is never returned,
#define ZR_RECENT 0x00000001 // but can be passed to FormatZipMessage.
// The following come from general system stuff (e.g. files not openable)
#define ZR_GENMASK 0x0000FF00
#define ZR_NODUPH 0x00000100 // couldn't duplicate the handle
#define ZR_NOFILE 0x00000200 // couldn't create/open the file
#define ZR_NOALLOC 0x00000300 // failed to allocate some resource
#define ZR_WRITE 0x00000400 // a general error writing to the file
#define ZR_NOTFOUND 0x00000500 // couldn't find that file in the zip
#define ZR_MORE 0x00000600 // there's still more data to be unzipped
#define ZR_CORRUPT 0x00000700 // the zipfile is corrupt or not a zipfile
#define ZR_READ 0x00000800 // a general error reading the file
// The following come from mistakes on the part of the caller
#define ZR_CALLERMASK 0x00FF0000
#define ZR_ARGS 0x00010000 // general mistake with the arguments
#define ZR_NOTMMAP 0x00020000 // tried to ZipGetMemory, but that only works on mmap zipfiles, which yours wasn't
#define ZR_MEMSIZE 0x00030000 // the memory size is too small
#define ZR_FAILED 0x00040000 // the thing was already failed when you called this function
#define ZR_ENDED 0x00050000 // the zip creation has already been closed
#define ZR_MISSIZE 0x00060000 // the indicated input file size turned out mistaken
#define ZR_PARTIALUNZ 0x00070000 // the file had already been partially unzipped
#define ZR_ZMODE 0x00080000 // tried to mix creating/opening a zip
// The following come from bugs within the zip library itself
#define ZR_BUGMASK 0xFF000000
#define ZR_NOTINITED 0x01000000 // initialisation didn't work
#define ZR_SEEK 0x02000000 // trying to seek in an unseekable file
#define ZR_NOCHANGE 0x04000000 // changed its mind on storage, but not allowed
#define ZR_FLATE 0x05000000 // an internal error in the de/inflation code
// e.g.
//
// (1) Traditional use, creating a zipfile from existing files
// HZIP hz = CreateZip("c:\\simple1.zip",0);
// ZipAdd(hz,"znsimple.bmp", "c:\\simple.bmp");
// ZipAdd(hz,"znsimple.txt", "c:\\simple.txt");
// CloseZip(hz);
//
// (2) Memory use, creating an auto-allocated mem-based zip file from various sources
// HZIP hz = CreateZip(0,100000, 0);
// // adding a conventional file...
// ZipAdd(hz,"src1.txt", "c:\\src1.txt");
// // adding something from memory...
// char buf[1000]; for (int i=0; i<1000; i++) buf[i]=(char)(i&0x7F);
// ZipAdd(hz,"file.dat", buf,1000);
// // adding something from a pipe...
// HANDLE hread,hwrite; CreatePipe(&hread,&hwrite,NULL,0);
// HANDLE hthread = CreateThread(0,0,ThreadFunc,(void*)hwrite,0,0);
// ZipAdd(hz,"unz3.dat", hread,1000); // the '1000' is optional.
// WaitForSingleObject(hthread,INFINITE);
// CloseHandle(hthread); CloseHandle(hread);
// ... meanwhile DWORD WINAPI ThreadFunc(void *dat)
// { HANDLE hwrite = (HANDLE)dat;
// char buf[1000]={17};
// DWORD writ; WriteFile(hwrite,buf,1000,&writ,NULL);
// CloseHandle(hwrite);
// return 0;
// }
// // and now that the zip is created, let's do something with it:
// void *zbuf; unsigned long zlen; ZipGetMemory(hz,&zbuf,&zlen);
// HANDLE hfz = CreateFile("test2.zip",GENERIC_WRITE,0,0,CREATE_ALWAYS,FILE_ATTRIBUTE_NORMAL,0);
// DWORD writ; WriteFile(hfz,zbuf,zlen,&writ,NULL);
// CloseHandle(hfz);
// CloseZip(hz);
//
// (3) Handle use, for file handles and pipes
// HANDLE hzread,hzwrite; CreatePipe(&hzread,&hzwrite,0,0);
// HANDLE hthread = CreateThread(0,0,ZipReceiverThread,(void*)hzread,0,0);
// HZIP hz = CreateZipHandle(hzwrite,0);
// // ... add to it
// CloseZip(hz);
// CloseHandle(hzwrite);
// WaitForSingleObject(hthread,INFINITE);
// CloseHandle(hthread);
// ... meanwhile DWORD WINAPI ZipReceiverThread(void *dat)
// { HANDLE hread = (HANDLE)dat;
// char buf[1000];
// while (true)
// { DWORD red; ReadFile(hread,buf,1000,&red,NULL);
// // ... and do something with this zip data we're receiving
// if (red==0) break;
// }
// CloseHandle(hread);
// return 0;
// }
// Now we indulge in a little skullduggery so that the code works whether
// the user has included just zip or both zip and unzip.
// Idea: if header files for both zip and unzip are present, then presumably
// the cpp files for zip and unzip are both present, so we will call
// one or the other of them based on a dynamic choice. If the header file
// for only one is present, then we will bind to that particular one.
ZRESULT CloseZipZ(HZIP hz);
unsigned int FormatZipMessageZ(ZRESULT code, char *buf,unsigned int len);
bool IsZipHandleZ(HZIP hz);
#ifdef _unzip_H
#undef CloseZip
#define CloseZip(hz) (IsZipHandleZ(hz)?CloseZipZ(hz):CloseZipU(hz))
#else
#define CloseZip CloseZipZ
#define FormatZipMessage FormatZipMessageZ
#endif
#endif
+4 -2
View File
@@ -4,8 +4,8 @@
//#define MyTypeHash DWORD64
#define MyTypeHash DWORD32
//define the buffer to 131072 byte, note that the array is in the stack, don't over do this
#define BUFSIZE 1<<17
#define BIG_BUFSIZE 1<<24
#define SMALL_BUFSIZE 1<<10
typedef struct
{
@@ -26,6 +26,8 @@ typedef struct
#define CONTROL_ADD_TEXTURE 1
#define CONTROL_FORCE_RELOAD_TEXTURE 2
#define CONTROL_REMOVE_TEXTURE 3
#define CONTROL_FORCE_RELOAD_TEXTURE_DATA 4
#define CONTROL_ADD_TEXTURE_DATA 5
#define CONTROL_SAVE_ALL 10