Rev 127 | Rev 178 | Go to most recent revision | Blame | Compare with Previous | Last modification | View Log | RSS feed
#include <spk.h>CyString g_dir;#ifdef _WIN32#include <windows.h>#include <direct.h>//#include <shlobj.h>#else#include <dirent.h>#include <sys/types.h>#include <sys/param.h>#include <sys/stat.h>#include <unistd.h>#endifvoid PrintError ( int err ){switch ( err ){case CATERR_NODATFILE:printf ( "No dat file found\n" );break;case CATERR_NOCATFILE:printf ( "Unable to open cat file\n" );break;case CATERR_FILEEMPTY:printf ( "Cat file is empty\n" );break;case CATERR_READCAT:printf ( "Unable to read cat file\n" );break;case CATERR_DECRYPT:printf ( "Unable to decrypt cat file\n" );break;case CATERR_MISMATCH:printf ( "Dat file size mismatch\n" );break;}}void ListFiles ( CyString filename, CyString searchmask ){printf ( "Listing files in %s...", filename.c_str() );if ( !searchmask.Empty() )printf ( "(%s)", searchmask.c_str() );printf ( "\n");CCatFile catfile;int err = catfile.open(filename.ToString(), "", CATREAD_CATDECRYPT);if ( err == CATERR_NONE ){printf ( "Opened file\n" );for (unsigned int i = 0; i < catfile.GetNumFiles(); i++){SInCatFile *file = catfile.GetFile ( i );if ( !searchmask.Empty() ){if ( !searchmask.WildMatch(file->sFile) )continue;}printf ( "[%9s] %s\n", SPK::GetSizeString(file->lSize).c_str(), file->sFile.c_str() );}}elsePrintError ( err );}CyStringList *FindFiles(CyString filepattern){CFileIO File((filepattern.IsIn(":")) ? filepattern : g_dir + "/" + filepattern);CyStringList *files = File.GetDirIO().DirList(NullString, File.GetFilename());return files;}bool findFiles(Utils::CStringList &files, const Utils::String &filepattern){CFileIO File((filepattern.contains(":")) ? filepattern : g_dir.ToString() + "/" + filepattern);return File.GetDirIO().dirList(files, Utils::String::Null(), File.GetFilename().ToString());}void ExtractFile ( CyString filename, CyString to, bool preserve ){if ( !filename.IsIn ( "::" ) ) return;Utils::String catfile = filename.GetToken ( "::", 1, 1 ).ToString();Utils::String filemask = filename.GetToken ( "::", 2, 2 ).ToString();CCatFile cat;int err = cat.open(catfile, "", CATREAD_DAT);if ( err ){PrintError ( err );return;}// all filesif ( filemask == "*" ){for (unsigned int i = 0; i < cat.GetNumFiles(); i++){SInCatFile *f = cat.GetFile(i);if ( !cat.ExtractFile ( f, to ) )printf ( "Error: %s\n", cat.getErrorString().c_str() );elseprintf ( "File has been written (%s)\n", cat.errorString().c_str() );}return;}//TODO: add proper file mask for extracting//CyStringList *fileList = FindFiles(filemask);CyStringList *fileList = new CyStringList;fileList->PushBack(CyString(filemask));if ( !fileList || fileList->Empty() ){if ( fileList ) delete fileList;printf ( "Error: unable to find any files matching: %s\n", filemask.c_str() );return;}for ( SStringList *fl = fileList->Head(); fl; fl = fl->next ){CyString file = fl->str;if ( !cat.ExtractFile ( file, to, preserve ) )printf ( "Error: %s\n", cat.getErrorString().c_str() );elseprintf ( "File has been written (%s)\n", cat.errorString().c_str() );}delete fileList;}void AppendFile ( CyString C_File, CyString filepattern ){Utils::String catfile;Utils::String file;C_File = C_File.FindReplace("\\", "/");bool doFile = false;if ( !C_File.IsIn ( "::" ) ){catfile = C_File.ToString();doFile = true;}else{catfile = C_File.GetToken ( "::", 1, 1 ).ToString();file = C_File.GetToken ( "::", 2, 2 ).ToString();}CyStringList *list = FindFiles(filepattern);if ( !list || !list->Count() ){printf("Error: no files found to add: %s\n", filepattern.c_str());return;}CCatFile cat;int err = cat.open(catfile, "", CATREAD_CATDECRYPT);if ( err ){delete list;PrintError ( err );return;}for ( SStringList *fname = list->Head(); fname; fname = fname->next ){Utils::String filename = fname->str.ToString();if ( doFile )file = filename;if (!file.isin('.')){if ( file[file.length() - 1] != '/' )file += '/';file += CFileIO(filename).filename();}if ( cat.AppendFile(filename, file))printf ( "File %s has beed added to: %s::%s\n", filename.c_str(), catfile.c_str(), file.c_str() );elseprintf ( "Error: Unable to add file: %s\n", filename.c_str());}delete list;}void RemoveFile ( CyString C_File, CyString remfile ){// first open the cat fileCCatFile cat;int err = cat.open(C_File.ToString(), "", CATREAD_CATDECRYPT);if ( err ){PrintError ( err );return;}SInCatFile *f = cat.FindData ( remfile );if ( !f ){printf ( "Unable to find %s in cat file\n", remfile.c_str() );return;}if (cat.removeFile(f))printf ( "File has been removed from archive\n" );}void UnpackFile ( CyString file, CyString tofile ){Utils::CStringList list;if(!findFiles(list, file.ToString()) || !list.size()){printf("Error: no files found to unpack: %s\n", file.c_str());return;}for(auto itr = list.first(); itr; list.next()){Utils::String filename = CFileIO(file).dir() + "/" + itr->str;C_File f(filename);if ( !f.CheckValidFilePointer() )printf("Error: %s doesn't exists\n", filename.c_str() );else if ( !f.ReadFromFile() )printf("Error: unable to open file: %s\n", filename.c_str() );else{f.UnPCKFile();if ( tofile.Empty() )f.ChangeFileExt("xml");else if ( tofile.Left(2) == "*." )f.ChangeFileExt(tofile.Right(3));elsef.SetFilename(tofile);if ( !f.writeFilePointer() )printf("Error: unable to write file: %s\n", tofile.c_str() );elseprintf("%s has been unpacked to %s\n", file.c_str(), f.GetFilename().c_str() );}}}void PackFile ( CyString file, CyString tofile ){Utils::CStringList list;if(!findFiles(list, file.ToString()) || !list.size()){printf("Error: no files found to pack: %s\n", file.c_str());return;}for(auto itr = list.first(); itr; itr = list.next()){Utils::String filename = CFileIO(file).dir() + "/" + itr->str;C_File f(filename);if ( !f.CheckValidFilePointer() )printf("Error: %s doesn't exists\n", filename.c_str() );else if ( !f.ReadFromFile() )printf("Error: unable to open file: %s\n", filename.c_str() );else if ( !f.PCKFile() )printf("Error: unable to pack file: %s\n", filename.c_str() );else{if ( tofile.Empty() ){if ( f.CheckFileExt("bob") )f.ChangeFileExt("pbb");else if ( f.CheckFileExt("bod") )f.ChangeFileExt("pbd");elsef.ChangeFileExt("pck");}else if ( tofile.Left(2) == "*." )f.ChangeFileExt(tofile.Right(3));elsef.SetFilename(tofile);if ( !f.writeFilePointer() )printf("Error: unable to write file: %s\n", tofile.c_str() );elseprintf("%s has been packed to %s\n", file.c_str(), f.GetFilename().c_str() );}}}void PrintSyntax(CyString cmd){printf ( "Syntax: %s <flags> [arguments]\n", cmd.c_str() );printf ( "Flags:\n");printf ( "\t-l <filename> [filemask]\n");printf ( "\t\tLists the contents of a cat file, with optional search mask\n");printf ( "\t-x <catfile::filename> [dir]\n");printf ( "\t\textracts a file from a cat file to the optional directory\n");printf ( "\t-xp <catfile::filename> [dir]\n");printf ( "\t\textracts a file from a cat file to the optional directory, preserves directory structure\n");printf ( "\t-xa <catfile> [dir]\n");printf ( "\t\textracts all files to optional directory\n");printf ( "\t-a <filename> <catfile::tofile>\n");printf ( "\t\tAdds the file into a cat archive, saves it as <tofile>\n");printf ( "\t-r <catfile> <file>\n");printf ( "\t\tRemoves a file from an archive\n");printf ( "\t-u <filename> <tofile>\n");printf ( "\t\tUnpacks a file, ie from pck to xml/txt\n");printf ( "\t-p <filename> <tofile>\n");printf ( "\t\tPacks a file, ie from xml/txt to pck\n");}int main ( int argc, char **argv ){printf ( "\nCATPCK Tool V1.21 27/03/2011 (SPK: %.2f) Created by Cycrow\n\n", GetLibraryVersion() );// parse the cmd nameCyString cmd (argv[0]);cmd = cmd.FindReplace ( "\\", "/" );g_dir = cmd.GetToken ( 0, cmd.NumToken('/') - 1, '/' );cmd = cmd.GetToken ( cmd.NumToken('/'), '/' );if ( g_dir.Empty() ){#ifdef _WIN32g_dir = CyString(_getcwd(NULL, 0));#elseg_dir = CyString(getcwd(NULL, 0));#endifif ( g_dir.Empty() )g_dir = "./";}if ( argc < 2 )PrintSyntax(cmd);else{CyString command ( argv[1] );command.ToLower();if ( (command == "-l") || (command == "-list") ){if ( argc < 3 )printf ( "Syntax: %s -l <filename> [filemask]\n\tLists the contents of the cat file\n", cmd.c_str() );else if ( argc < 4 )ListFiles ( CyString(argv[2]), "" );elseListFiles ( CyString(argv[2]), CyString(argv[3]) );}else if ( (command == "-x") || (command == "-extract") || (command == "-xp") || (command == "-extractpreserve") ){if ( argc < 3 )printf ( "Syntax: %s %s <catfile::filename> [dir]\n\tExtracts a file from the cat archive\n", cmd.c_str(), command.c_str() );else if ( argc < 4 )ExtractFile ( CyString(argv[2]), CyString(""), (command == "-xp" || command == "-extractpreserve") ? true : false );elseExtractFile ( CyString(argv[2]), CyString(argv[3]), (command == "-xp" || command == "-extractpreserve") ? true : false );}else if ( (command == "-xa") || (command == "-extractall") ){if ( argc < 3 )printf ( "Syntax: %s %s <catfile> [dir]\n\tExtracts all files from the cat archive\n", cmd.c_str(), command.c_str() );else if ( argc < 4 )ExtractFile ( CyString(argv[2]) + "::*", CyString(""), true );elseExtractFile ( CyString(argv[2]) + "::*", CyString(argv[3]), true );}else if ( (command == "-a") || (command == "-append") ){if ( argc < 4 )printf ( "Syntax: %s -a <filename> <catfile::tofile>\n\tAppends a file into the archive\n", cmd.c_str() );elseAppendFile ( CyString(argv[3]), CyString(argv[2]) );}else if ( (command == "-r") || (command == "-remove") ){if ( argc < 4 )printf ( "Syntax: %s -r <catfile> <filename>\n\tRemoves a file from the archive\n", cmd.c_str() );elseRemoveFile ( CyString(argv[2]), CyString(argv[3]) );}else if ( (command == "-u") || (command == "-unpack") ){if ( argc < 3 )printf ( "Syntax: %s -u <filename> [to]\n\tUnpacks a file", cmd.c_str() );else if ( argc < 4 )UnpackFile ( CyString(argv[2]), CyString("") );elseUnpackFile ( CyString(argv[2]), CyString(argv[3]) );}else if ( (command == "-p") || (command == "-pack") ){if ( argc < 3 )printf ( "Syntax: %s -p <filename> [to]\n\tPacks a file to .pck", cmd.c_str() );else if ( argc < 4 )PackFile ( CyString(argv[2]), CyString("") );elsePackFile ( CyString(argv[2]), CyString(argv[3]) );}else{printf("Invalaid flag: %s\n\n", command.c_str());PrintSyntax(cmd);}}#ifdef _DEBUGchar pause;printf ( "\n\nPress a key to end\n" );scanf ( "%c", &pause );#endifreturn 0;}