| 1 | cycrow | 1 | #include "spk.h"
 | 
        
           |  |  | 2 | #include "emp.h"
 | 
        
           |  |  | 3 |   | 
        
           |  |  | 4 | #include <time.h>
 | 
        
           |  |  | 5 | #include <vector>
 | 
        
           |  |  | 6 |   | 
        
           |  |  | 7 | #ifdef _RAR
 | 
        
           |  |  | 8 | #include <unrar.h>
 | 
        
           |  |  | 9 | #endif
 | 
        
           |  |  | 10 |   | 
        
           |  |  | 11 | enum {READ_START, READ_GLOBAL, READ_SCRIPT, READ_SCRIPTFILE, READ_WARES};
 | 
        
           |  |  | 12 | enum { EXTRACT, TEST, PRINT, LIST };
 | 
        
           |  |  | 13 |   | 
        
           |  |  | 14 | typedef struct SDummyEntry {
 | 
        
           |  |  | 15 | 	CyString		sSection;
 | 
        
           |  |  | 16 | 	CyStringList	lEntries;
 | 
        
           |  |  | 17 | } SDummyEntry;
 | 
        
           |  |  | 18 |   | 
        
           |  |  | 19 | typedef struct SComponantEntry2 {
 | 
        
           |  |  | 20 | 	CyString		sSection;
 | 
        
           |  |  | 21 | 	CyStringList	lEntries;
 | 
        
           |  |  | 22 | } SComponantEntry2;
 | 
        
           |  |  | 23 |   | 
        
           |  |  | 24 | typedef struct SComponantEntry {
 | 
        
           |  |  | 25 | 	CyString		sSection;
 | 
        
           |  |  | 26 | 	CLinkList<SComponantEntry2>	lEntries;
 | 
        
           |  |  | 27 | } SComponantEntry;
 | 
        
           |  |  | 28 |   | 
        
           |  |  | 29 | CPackages::CPackages()
 | 
        
           |  |  | 30 | {
 | 
        
           |  |  | 31 | 	m_bRenameText = false;
 | 
        
           |  |  | 32 | 	m_iLanguage = 0;
 | 
        
           |  |  | 33 | 	m_iGame = -1;
 | 
        
           |  |  | 34 | 	m_iGameVersion = -1;
 | 
        
           |  |  | 35 | 	m_iGameFlags = 0;
 | 
        
           |  |  | 36 | 	m_bSurpressProtectedWarning = false;
 | 
        
           |  |  | 37 | 	m_iMaxPatch = 1;
 | 
        
           |  |  | 38 | 	m_iLastUpdated = 0;
 | 
        
           |  |  | 39 | 	m_iFakePatch = -1;
 | 
        
           |  |  | 40 | 	m_bVanilla = true;
 | 
        
           |  |  | 41 | 	m_pEnabledMod = NULL;
 | 
        
           |  |  | 42 | 	m_bForceModInstall = false;
 | 
        
           |  |  | 43 | 	m_bLoaded = false;
 | 
        
           |  |  | 44 | 	m_bRedo = false;
 | 
        
           |  |  | 45 | 	m_bOldPlugin = false;
 | 
        
           |  |  | 46 | 	m_bUsedWare = false;
 | 
        
           |  |  | 47 | 	m_pPackageNode = NULL;
 | 
        
           |  |  | 48 | 	m_bRemoveDir = false;
 | 
        
           |  |  | 49 | 	m_bDisableVanilla = false;
 | 
        
           |  |  | 50 | 	m_bLoadVFS = true;
 | 
        
           |  |  | 51 | 	m_iSaveGame = -1;
 | 
        
           |  |  | 52 | 	m_iSaveGameManager = -1;
 | 
        
           |  |  | 53 | 	m_bForceEMP = false;
 | 
        
           |  |  | 54 |   | 
        
           |  |  | 55 | 	for ( int i = 0; i < WAREBUFFERS; i++ )
 | 
        
           |  |  | 56 | 		m_iWareBuffer[i] = 0;
 | 
        
           |  |  | 57 | 	m_iShipBuffer = 0;
 | 
        
           |  |  | 58 | }
 | 
        
           |  |  | 59 |   | 
        
           |  |  | 60 | CPackages::~CPackages ()
 | 
        
           |  |  | 61 | {
 | 
        
           |  |  | 62 | 	m_lDisableList.clear();
 | 
        
           |  |  | 63 | 	m_lEnableList.clear();
 | 
        
           |  |  | 64 | 	this->Reset();
 | 
        
           |  |  | 65 | }
 | 
        
           |  |  | 66 |   | 
        
           |  |  | 67 | void CPackages::SetVanilla(bool b)
 | 
        
           |  |  | 68 | {
 | 
        
           |  |  | 69 | 	if ( m_bVanilla != b && b ) {
 | 
        
           |  |  | 70 | 		for ( CListNode<CBaseFile> *pNode = m_lPackages.Front(); pNode; pNode = pNode->next() ) {
 | 
        
           |  |  | 71 | 			pNode->Data()->SetModifiedEnabled(pNode->Data()->IsEnabled());
 | 
        
           |  |  | 72 | 		}
 | 
        
           |  |  | 73 | 	}
 | 
        
           |  |  | 74 | 	m_bVanilla = b;
 | 
        
           |  |  | 75 | }
 | 
        
           |  |  | 76 |   | 
        
           |  |  | 77 | void CPackages::Reset()
 | 
        
           |  |  | 78 | {
 | 
        
           |  |  | 79 | 	m_lFiles.MemoryClear();
 | 
        
           |  |  | 80 | 	m_lUninstallFiles.MemoryClear();
 | 
        
           |  |  | 81 | 	for ( CListNode<CBaseFile> *pNode = m_lPackages.Front(); pNode; pNode = pNode->next() )
 | 
        
           |  |  | 82 | 		pNode->Data()->GetFileList()->clear();
 | 
        
           |  |  | 83 | 	m_lPackages.MemoryClear();
 | 
        
           |  |  | 84 | 	m_lOriginalFiles.MemoryClear();
 | 
        
           |  |  | 85 | 	m_iFakePatch = -1;
 | 
        
           |  |  | 86 | 	m_bVanilla = false;
 | 
        
           |  |  | 87 | 	m_pEnabledMod = NULL;
 | 
        
           |  |  | 88 | 	m_bLoaded = false;
 | 
        
           |  |  | 89 | 	m_iLanguage = 0;
 | 
        
           |  |  | 90 | 	m_bOldPlugin = false;
 | 
        
           |  |  | 91 | 	m_bRemoveDir = false;
 | 
        
           |  |  | 92 | 	m_bDisableVanilla = false;
 | 
        
           |  |  | 93 | 	m_bSurpressProtectedWarning = false;
 | 
        
           |  |  | 94 | 	m_iSaveGame = -1;
 | 
        
           |  |  | 95 | 	m_iSaveGameManager = -1;
 | 
        
           |  |  | 96 | 	m_sSetMod = "";
 | 
        
           |  |  | 97 |   | 
        
           |  |  | 98 | 	for ( int i = 0; i < WAREBUFFERS; i++ )
 | 
        
           |  |  | 99 | 	{
 | 
        
           |  |  | 100 | 		m_iWareBuffer[i] = 0;
 | 
        
           |  |  | 101 | 		m_lGameWares[i].MemoryClear();
 | 
        
           |  |  | 102 | 	}
 | 
        
           |  |  | 103 | 	m_iShipBuffer = 0;
 | 
        
           |  |  | 104 |   | 
        
           |  |  | 105 | 	m_lGameShips.MemoryClear();
 | 
        
           |  |  | 106 | 	m_lAvailablePackages.MemoryClear();
 | 
        
           |  |  | 107 | 	m_lInstallList.MemoryClear();
 | 
        
           |  |  | 108 | 	m_lEnableList.MemoryClear();
 | 
        
           |  |  | 109 | 	m_lDisableList.MemoryClear();
 | 
        
           |  |  | 110 |   | 
        
           |  |  | 111 | 	m_lCreatedFiles.Clear();
 | 
        
           |  |  | 112 | 	m_lNonRemovedFiles.Clear();
 | 
        
           |  |  | 113 | 	m_lGlobals.Clear();
 | 
        
           |  |  | 114 | 	m_lFakePatchOrder.Clear();
 | 
        
           |  |  | 115 | }
 | 
        
           |  |  | 116 |   | 
        
           |  |  | 117 | void CPackages::LoadVirtualFileSystem()
 | 
        
           |  |  | 118 | {
 | 
        
           |  |  | 119 | 	if ( !m_bLoadVFS )
 | 
        
           |  |  | 120 | 		return;
 | 
        
           |  |  | 121 |   | 
        
           |  |  | 122 | 	if ( m_pEnabledMod )
 | 
        
           |  |  | 123 | 	{
 | 
        
           |  |  | 124 | 		C_File *f;
 | 
        
           |  |  | 125 | 		for ( f = m_pEnabledMod->GetFirstFile(FILETYPE_MOD); f; f = m_pEnabledMod->GetNextFile(f) )
 | 
        
           |  |  | 126 | 		{
 | 
        
           |  |  | 127 | 			if ( f->IsFakePatch() ) continue;
 | 
        
           |  |  | 128 | 			if ( f->CheckFileExt("cat") ) break;
 | 
        
           |  |  | 129 | 		}
 | 
        
           |  |  | 130 |   | 
        
           |  |  | 131 | 		if ( f )
 | 
        
           |  |  | 132 | 			m_pGameVFS.LoadFilesystem(m_sCurrentDir, f->GetFilePointer(), 0);
 | 
        
           |  |  | 133 | 		else
 | 
        
           |  |  | 134 | 			m_pGameVFS.LoadFilesystem(m_sCurrentDir, NullString, 0);
 | 
        
           |  |  | 135 | 	}
 | 
        
           |  |  | 136 | 	else
 | 
        
           |  |  | 137 | 		m_pGameVFS.LoadFilesystem(m_sCurrentDir, NullString, 0);
 | 
        
           |  |  | 138 | }
 | 
        
           |  |  | 139 |   | 
        
           |  |  | 140 | bool CPackages::IsOldDir(CyString dir)
 | 
        
           |  |  | 141 | {
 | 
        
           |  |  | 142 | 	bool oldPlugin = false;
 | 
        
           |  |  | 143 |   | 
        
           |  |  | 144 | 	dir = dir.FindReplace("\\", "/");
 | 
        
           |  |  | 145 | 	CFileIO datFile(dir + "/PluginManager/pluginmanager.dat");
 | 
        
           |  |  | 146 | 	if ( datFile.Exists() )
 | 
        
           |  |  | 147 | 	{
 | 
        
           |  |  | 148 | 		std::vector<CyString> *readFile = datFile.ReadLines();
 | 
        
           |  |  | 149 | 		if ( readFile )
 | 
        
           |  |  | 150 | 		{
 | 
        
           |  |  | 151 | 			for ( int i = 0; i < (int)readFile->size(); i++ )
 | 
        
           |  |  | 152 | 			{
 | 
        
           |  |  | 153 | 				CyString line(readFile->at(i));
 | 
        
           |  |  | 154 | 				CyString cmd = line.GetToken(":", 1, 1).lower();
 | 
        
           |  |  | 155 | 				if ( cmd == "<script>" || cmd == "</scripts>" )
 | 
        
           |  |  | 156 | 					break;
 | 
        
           |  |  | 157 | 				else if ( cmd == "spkinstaller" || cmd == "globalfiles" )
 | 
        
           |  |  | 158 | 					break;
 | 
        
           |  |  | 159 | 				else if ( cmd == "pluginmanager" )
 | 
        
           |  |  | 160 | 				{
 | 
        
           |  |  | 161 | 					oldPlugin = true;
 | 
        
           |  |  | 162 | 					break;
 | 
        
           |  |  | 163 | 				}
 | 
        
           |  |  | 164 | 			}
 | 
        
           |  |  | 165 |   | 
        
           |  |  | 166 | 			delete readFile;
 | 
        
           |  |  | 167 | 		}
 | 
        
           |  |  | 168 | 	}
 | 
        
           |  |  | 169 |   | 
        
           |  |  | 170 | 	return oldPlugin;
 | 
        
           |  |  | 171 | }
 | 
        
           |  |  | 172 |   | 
        
           |  |  | 173 | bool CPackages::Read ( CyString dir, CProgressInfo *progress )
 | 
        
           |  |  | 174 | {
 | 
        
           |  |  | 175 | 	m_sCurrentDir = dir;
 | 
        
           |  |  | 176 | 	m_sCurrentDir = m_sCurrentDir.FindReplace("\\", "/");
 | 
        
           |  |  | 177 | 	m_bOldPlugin = false;
 | 
        
           |  |  | 178 | 	m_lCreatedFiles.Clear();
 | 
        
           |  |  | 179 | 	m_bRemoveDir = false;
 | 
        
           |  |  | 180 | 	m_bSurpressProtectedWarning = false;
 | 
        
           |  |  | 181 | 	m_iSaveGame = -1;
 | 
        
           |  |  | 182 | 	m_iSaveGameManager = -1;
 | 
        
           |  |  | 183 | 	m_lNonRemovedFiles.Clear();
 | 
        
           |  |  | 184 | 	m_lGlobals.Clear();
 | 
        
           |  |  | 185 | 	m_lFakePatchOrder.Clear();
 | 
        
           |  |  | 186 |   | 
        
           |  |  | 187 | 	m_bVanilla = true;
 | 
        
           |  |  | 188 |   | 
        
           |  |  | 189 | 	// check the pluginmanager data file exists
 | 
        
           |  |  | 190 | 	CFileIO datFile(m_sCurrentDir + "/PluginManager/pluginmanager.dat");
 | 
        
           |  |  | 191 | 	if ( datFile.Exists() )
 | 
        
           |  |  | 192 | 	{
 | 
        
           |  |  | 193 | 		std::vector<CyString> *readFile = datFile.ReadLines();
 | 
        
           |  |  | 194 | 		if ( readFile )
 | 
        
           |  |  | 195 | 		{
 | 
        
           |  |  | 196 | 			float fVersion = 0;
 | 
        
           |  |  | 197 | 			bool spkinstaller = false;
 | 
        
           |  |  | 198 | 			float fBeta = 0;
 | 
        
           |  |  | 199 |   | 
        
           |  |  | 200 | 			int iStatus = READ_START;
 | 
        
           |  |  | 201 | 			int iCount = 0;
 | 
        
           |  |  | 202 | 			int iWare = -1;
 | 
        
           |  |  | 203 | 			int iShip = -1;
 | 
        
           |  |  | 204 |   | 
        
           |  |  | 205 | 			CBaseFile *packageFile = 0;
 | 
        
           |  |  | 206 |   | 
        
           |  |  | 207 | 			for ( int i = 0; i < (int)readFile->size(); i++ )
 | 
        
           |  |  | 208 | 			{
 | 
        
           |  |  | 209 | 				CyString line(readFile->at(i));
 | 
        
           |  |  | 210 |   | 
        
           |  |  | 211 | 				CyString cmd = line.GetToken(":", 1, 1).lower();
 | 
        
           |  |  | 212 | 				CyString rest = line.GetToken(":", 2).RemoveFirstSpace();
 | 
        
           |  |  | 213 |   | 
        
           |  |  | 214 | 				if ( iStatus == READ_GLOBAL )
 | 
        
           |  |  | 215 | 				{
 | 
        
           |  |  | 216 | 					if ( cmd == "<script>" )
 | 
        
           |  |  | 217 | 					{
 | 
        
           |  |  | 218 | 						packageFile = new CSpkFile();
 | 
        
           |  |  | 219 | 						iStatus = READ_SCRIPT;
 | 
        
           |  |  | 220 | 					}
 | 
        
           |  |  | 221 | 					else if ( cmd == "<ship>" )
 | 
        
           |  |  | 222 | 					{
 | 
        
           |  |  | 223 | 						packageFile = new CXspFile();
 | 
        
           |  |  | 224 | 						iStatus = READ_SCRIPT;
 | 
        
           |  |  | 225 | 					}
 | 
        
           |  |  | 226 | 					else if ( cmd == "<base>" )
 | 
        
           |  |  | 227 | 					{
 | 
        
           |  |  | 228 | 						packageFile = new CBaseFile();
 | 
        
           |  |  | 229 | 						iStatus = READ_SCRIPT;
 | 
        
           |  |  | 230 | 					}
 | 
        
           |  |  | 231 | 					else if ( cmd == "<archive>" )
 | 
        
           |  |  | 232 | 					{
 | 
        
           |  |  | 233 | 						packageFile = new CArchiveFile();
 | 
        
           |  |  | 234 | 						iStatus = READ_SCRIPT;
 | 
        
           |  |  | 235 | 					}
 | 
        
           |  |  | 236 | 					else if ( cmd != "</scripts>" )
 | 
        
           |  |  | 237 | 					{
 | 
        
           |  |  | 238 | 						int game = 0;
 | 
        
           |  |  | 239 | 						bool disabled = false;
 | 
        
           |  |  | 240 | 						CyString fileName = line.GetToken(":", 5);
 | 
        
           |  |  | 241 | 						CyString origName;
 | 
        
           |  |  | 242 | 						if ( fileName.Left(2) == "D#" )
 | 
        
           |  |  | 243 | 						{
 | 
        
           |  |  | 244 | 							fileName.Erase(0, 2);
 | 
        
           |  |  | 245 | 							disabled = true;
 | 
        
           |  |  | 246 | 						}
 | 
        
           |  |  | 247 | 						if ( fileName.Left(2) == "G#" ) {
 | 
        
           |  |  | 248 | 							fileName.Erase(0, 2);
 | 
        
           |  |  | 249 | 							game = fileName.GetToken("#", 1, 1).ToInt();
 | 
        
           |  |  | 250 | 							fileName = fileName.GetToken("#", 2);
 | 
        
           |  |  | 251 | 						}
 | 
        
           |  |  | 252 | 						if ( fileName.IsIn("O#") )
 | 
        
           |  |  | 253 | 						{
 | 
        
           |  |  | 254 | 							origName = fileName.GetToken("O#", 2, 2);
 | 
        
           |  |  | 255 | 							fileName = fileName.GetToken("O#", 1, 1);
 | 
        
           |  |  | 256 | 						}
 | 
        
           |  |  | 257 |   | 
        
           |  |  | 258 | 						C_File *newFile = new C_File( m_sCurrentDir + fileName );
 | 
        
           |  |  | 259 | 						newFile->SetGame(game);
 | 
        
           |  |  | 260 | 						newFile->SetOriginalName(origName);
 | 
        
           |  |  | 261 | 						newFile->SetDisabled(disabled);
 | 
        
           |  |  | 262 | 						newFile->SetFileType(line.GetToken(":", 1, 1).ToInt());
 | 
        
           |  |  | 263 | 						newFile->SetCreationTime((time_t)line.GetToken(":", 2, 2).ToInt());
 | 
        
           |  |  | 264 | 						newFile->SetDir(line.GetToken(":", 3, 3));
 | 
        
           |  |  | 265 | 						if ( line.GetToken(":", 4, 4).ToInt() )
 | 
        
           |  |  | 266 | 							newFile->SetShared(true);
 | 
        
           |  |  | 267 | 						newFile->UpdateSigned();
 | 
        
           |  |  | 268 |   | 
        
           |  |  | 269 | 						m_lFiles.push_back(newFile);
 | 
        
           |  |  | 270 | 					}
 | 
        
           |  |  | 271 | 				}
 | 
        
           |  |  | 272 | 				else if ( iStatus == READ_SCRIPT )
 | 
        
           |  |  | 273 | 				{
 | 
        
           |  |  | 274 | 					if ( cmd == "installspk" )
 | 
        
           |  |  | 275 | 						packageFile->SetFilename(rest);
 | 
        
           |  |  | 276 | 					else if ( cmd == "files" )
 | 
        
           |  |  | 277 | 					{
 | 
        
           |  |  | 278 | 						iStatus = READ_SCRIPTFILE;
 | 
        
           |  |  | 279 | 						if ( spkinstaller )
 | 
        
           |  |  | 280 | 						{
 | 
        
           |  |  | 281 | 							int max;
 | 
        
           |  |  | 282 | 							CyString *files = rest.SplitToken(' ', &max);
 | 
        
           |  |  | 283 |   | 
        
           |  |  | 284 | 							for ( int i = 0; i < max; i++ )
 | 
        
           |  |  | 285 | 							{
 | 
        
           |  |  | 286 | 								int fileNum = files[i].ToInt();
 | 
        
           |  |  | 287 | 								if ( fileNum >= 0 && fileNum < m_lFiles.size() )
 | 
        
           |  |  | 288 | 									packageFile->AddFile(m_lFiles[fileNum]);
 | 
        
           |  |  | 289 | 							}
 | 
        
           |  |  | 290 |   | 
        
           |  |  | 291 | 							CLEANSPLIT(files, max);
 | 
        
           |  |  | 292 | 						}
 | 
        
           |  |  | 293 | 					}
 | 
        
           |  |  | 294 | 					else if ( cmd == "disabled" )
 | 
        
           |  |  | 295 | 						packageFile->SetEnabled(false);
 | 
        
           |  |  | 296 | 					else if ( cmd == "modifieddisabled" )
 | 
        
           |  |  | 297 | 						packageFile->SetModifiedEnabled(false);
 | 
        
           |  |  | 298 | 					else if ( cmd == "icon" )
 | 
        
           |  |  | 299 | 					{
 | 
        
           |  |  | 300 | 						C_File *icon = new C_File(rest.GetToken(" ", 2));
 | 
        
           |  |  | 301 | 						packageFile->SetIcon(icon, rest.GetToken(" ", 1, 1));
 | 
        
           |  |  | 302 | 					}
 | 
        
           |  |  | 303 | 					else
 | 
        
           | 14 | cycrow | 304 | 						packageFile->ParseValueLine(line.ToString());
 | 
        
           | 1 | cycrow | 305 | 				}
 | 
        
           |  |  | 306 | 				else if ( iStatus == READ_SCRIPTFILE )
 | 
        
           |  |  | 307 | 				{
 | 
        
           |  |  | 308 | 					if ( cmd == "<script>" )
 | 
        
           |  |  | 309 | 					{
 | 
        
           |  |  | 310 | 						if ( packageFile->IsMod() && packageFile->IsEnabled() )
 | 
        
           |  |  | 311 | 							m_pEnabledMod = packageFile;
 | 
        
           |  |  | 312 |   | 
        
           |  |  | 313 | 						m_lPackages.push_back(packageFile);
 | 
        
           |  |  | 314 | 						this->ConvertOldPackage(packageFile);
 | 
        
           |  |  | 315 | 						packageFile = new CSpkFile();
 | 
        
           |  |  | 316 | 						iStatus = READ_SCRIPT;
 | 
        
           |  |  | 317 |   | 
        
           |  |  | 318 | 					}
 | 
        
           |  |  | 319 | 					else if ( cmd == "<ship>" )
 | 
        
           |  |  | 320 | 					{
 | 
        
           |  |  | 321 | 						m_lPackages.push_back(packageFile);
 | 
        
           |  |  | 322 | 						this->ConvertOldPackage(packageFile);
 | 
        
           |  |  | 323 | 						packageFile = new CXspFile();
 | 
        
           |  |  | 324 | 						iStatus = READ_SCRIPT;
 | 
        
           |  |  | 325 | 					}
 | 
        
           |  |  | 326 | 					else if ( cmd == "<base>" )
 | 
        
           |  |  | 327 | 					{
 | 
        
           |  |  | 328 | 						m_lPackages.push_back(packageFile);
 | 
        
           |  |  | 329 | 						this->ConvertOldPackage(packageFile);
 | 
        
           |  |  | 330 | 						packageFile = new CBaseFile();
 | 
        
           |  |  | 331 | 						iStatus = READ_SCRIPT;
 | 
        
           |  |  | 332 | 					}
 | 
        
           |  |  | 333 | 					else if ( cmd == "<archive>" )
 | 
        
           |  |  | 334 | 					{
 | 
        
           |  |  | 335 | 						m_lPackages.push_back(packageFile);
 | 
        
           |  |  | 336 | 						this->ConvertOldPackage(packageFile);
 | 
        
           |  |  | 337 | 						packageFile = new CArchiveFile();
 | 
        
           |  |  | 338 | 						iStatus = READ_SCRIPT;
 | 
        
           |  |  | 339 | 					}
 | 
        
           |  |  | 340 | 					else if ( cmd == "</scripts>" )
 | 
        
           |  |  | 341 | 					{
 | 
        
           |  |  | 342 | 						if ( packageFile->IsMod() && packageFile->IsEnabled() )
 | 
        
           |  |  | 343 | 							m_pEnabledMod = packageFile;
 | 
        
           |  |  | 344 |   | 
        
           |  |  | 345 | 						m_lPackages.push_back(packageFile);
 | 
        
           |  |  | 346 | 						this->ConvertOldPackage(packageFile);
 | 
        
           |  |  | 347 | 					}
 | 
        
           |  |  | 348 | 					else
 | 
        
           |  |  | 349 | 					{
 | 
        
           |  |  | 350 | 						int fileNum = line.GetToken("::", 1, 1).ToInt();
 | 
        
           |  |  | 351 | 						if ( fileNum >= 0 && fileNum < m_lFiles.size() )
 | 
        
           |  |  | 352 | 							packageFile->AddFile(m_lFiles[fileNum]);
 | 
        
           |  |  | 353 | 					}
 | 
        
           |  |  | 354 | 				}
 | 
        
           |  |  | 355 | 				else if ( iWare != -1 )
 | 
        
           |  |  | 356 | 				{
 | 
        
           |  |  | 357 | 					--iCount;
 | 
        
           |  |  | 358 |   | 
        
           |  |  | 359 | 					SGameWare *gm = new SGameWare;
 | 
        
           |  |  | 360 | 					gm->iPos = line.GetToken(" ", 1, 1).ToInt();
 | 
        
           |  |  | 361 | 					gm->iType = line.GetToken(" ", 2, 2).ToInt();
 | 
        
           |  |  | 362 | 					gm->cType = line.GetToken(" ", 3, 3)[0];
 | 
        
           |  |  | 363 | 					gm->pWare = NULL;
 | 
        
           |  |  | 364 | 					gm->sWareName = line.GetToken(" ", 4);
 | 
        
           |  |  | 365 | 					m_lGameWares[iWare].push_back(gm);
 | 
        
           |  |  | 366 | 					if ( iCount <= 0 )
 | 
        
           |  |  | 367 | 						iWare = -1;
 | 
        
           |  |  | 368 | 				}
 | 
        
           |  |  | 369 | 				else if ( iShip != -1 )
 | 
        
           |  |  | 370 | 				{
 | 
        
           |  |  | 371 | 					--iCount;
 | 
        
           |  |  | 372 |   | 
        
           |  |  | 373 | 					SGameShip *gm = new SGameShip;
 | 
        
           |  |  | 374 | 					gm->iType = line.GetToken(" ", 1, 1).ToInt();
 | 
        
           |  |  | 375 | 					if ( line.GetToken(" ", 2, 2).Left(4) == "$#C:" )
 | 
        
           |  |  | 376 | 					{
 | 
        
           |  |  | 377 | 						gm->sShipClass = line.GetToken(" ", 2, 2).Right(-4);
 | 
        
           |  |  | 378 | 						gm->sShipID = line.GetToken(" ", 3);
 | 
        
           |  |  | 379 | 					}
 | 
        
           |  |  | 380 | 					else
 | 
        
           |  |  | 381 | 					{
 | 
        
           |  |  | 382 | 						gm->sShipID = line.GetToken(" ", 2);
 | 
        
           |  |  | 383 | 						gm->sShipClass = "OBJ_SHIP_M5";
 | 
        
           |  |  | 384 | 					}
 | 
        
           |  |  | 385 | 					gm->pPackage = NULL;
 | 
        
           |  |  | 386 | 					m_lGameShips.push_back(gm);
 | 
        
           |  |  | 387 | 					if ( iCount <= 0 )
 | 
        
           |  |  | 388 | 						iShip = -1;
 | 
        
           |  |  | 389 | 				}
 | 
        
           |  |  | 390 | 				else if ( cmd.Compare("savegamemanager") )
 | 
        
           |  |  | 391 | 					m_iSaveGameManager = rest.ToInt();
 | 
        
           |  |  | 392 | 				else if ( cmd.Compare("savegame") )
 | 
        
           |  |  | 393 | 					m_iSaveGame = rest.ToInt();
 | 
        
           |  |  | 394 | 				else if ( cmd == "fakepatch" )
 | 
        
           |  |  | 395 | 					m_iFakePatch = rest.ToInt();
 | 
        
           |  |  | 396 | 				else if ( cmd == "updatetime" )
 | 
        
           |  |  | 397 | 					m_iLastUpdated = rest.ToInt();
 | 
        
           |  |  | 398 | 				else if ( cmd == "surpressprotectedwarning" )
 | 
        
           |  |  | 399 | 					m_bSurpressProtectedWarning = true;
 | 
        
           |  |  | 400 | 				else if ( cmd == "pluginmanager" )
 | 
        
           |  |  | 401 | 				{
 | 
        
           |  |  | 402 | 					fVersion = rest.ToFloat();
 | 
        
           |  |  | 403 | 					m_bOldPlugin = true;
 | 
        
           |  |  | 404 | 				}
 | 
        
           |  |  | 405 | 				else if ( cmd == "setmod" )
 | 
        
           |  |  | 406 | 					m_sSetMod = rest;
 | 
        
           |  |  | 407 | 				else if ( cmd == "shipbuffer" )
 | 
        
           |  |  | 408 | 					m_iShipBuffer = rest.ToInt();
 | 
        
           |  |  | 409 | 				else if ( cmd == "warebuffers" )
 | 
        
           |  |  | 410 | 				{
 | 
        
           |  |  | 411 | 					int max = rest.NumToken(" ");
 | 
        
           |  |  | 412 | 					for ( int i = 0; i < WAREBUFFERS; i++ )
 | 
        
           |  |  | 413 | 					{
 | 
        
           |  |  | 414 | 						if ( i > max )
 | 
        
           |  |  | 415 | 							m_iWareBuffer[i] = 0;
 | 
        
           |  |  | 416 | 						else
 | 
        
           |  |  | 417 | 							m_iWareBuffer[i] = rest.GetToken(" ", i + 1, i + 1).ToInt();
 | 
        
           |  |  | 418 | 					}
 | 
        
           |  |  | 419 | 				}
 | 
        
           |  |  | 420 | 				else if ( cmd == "createdfile" )
 | 
        
           |  |  | 421 | 					m_lCreatedFiles.PushBack(rest);
 | 
        
           |  |  | 422 | 				else if ( cmd == "wares" )
 | 
        
           |  |  | 423 | 				{
 | 
        
           |  |  | 424 | 					iWare = rest.GetToken(" ", 1, 1).ToInt();
 | 
        
           |  |  | 425 | 					iCount = rest.GetToken(" ", 2, 2).ToInt();
 | 
        
           |  |  | 426 | 				}
 | 
        
           |  |  | 427 | 				else if ( cmd == "ships" )
 | 
        
           |  |  | 428 | 				{
 | 
        
           |  |  | 429 | 					iShip = 1;
 | 
        
           |  |  | 430 | 					iCount = rest.GetToken(" ", 1, 1).ToInt();
 | 
        
           |  |  | 431 | 				}
 | 
        
           |  |  | 432 | 				else if ( cmd == "modified" )
 | 
        
           |  |  | 433 | 					m_bVanilla = false;
 | 
        
           |  |  | 434 | 				else if ( cmd == "spkinstaller" )
 | 
        
           |  |  | 435 | 				{
 | 
        
           |  |  | 436 | 					fVersion = rest.ToFloat();
 | 
        
           |  |  | 437 | 					spkinstaller = true;
 | 
        
           |  |  | 438 | 				}
 | 
        
           |  |  | 439 | 				else if ( cmd == "BetaVersion" )
 | 
        
           |  |  | 440 | 					fBeta = rest.ToFloat();
 | 
        
           |  |  | 441 | 				else if ( cmd == "Uninstall" )
 | 
        
           |  |  | 442 | 				{
 | 
        
           |  |  | 443 | 					C_File *uf = new C_File();
 | 
        
           |  |  | 444 | 					uf->SetFileType(FILETYPE_SCRIPT);
 | 
        
           |  |  | 445 | 					uf->SetCreationTime(rest.GetToken(" ", 1, 1).ToInt());
 | 
        
           |  |  | 446 | 					uf->SetFilename(m_sCurrentDir + "/Scripts/" + rest.GetToken(" ", 2));
 | 
        
           |  |  | 447 | 					m_lUninstallFiles.push_back(uf);
 | 
        
           |  |  | 448 | 				}
 | 
        
           |  |  | 449 | 				else if ( cmd == "NonRemovedFile" )
 | 
        
           |  |  | 450 | 				{
 | 
        
           |  |  | 451 | 					if ( !CFileIO(rest).Remove() )
 | 
        
           |  |  | 452 | 						m_lNonRemovedFiles.PushBack(rest);
 | 
        
           |  |  | 453 | 				}
 | 
        
           |  |  | 454 | 				else if ( cmd == "Original" )
 | 
        
           |  |  | 455 | 				{
 | 
        
           |  |  | 456 | 					C_File *uf = new C_File();
 | 
        
           |  |  | 457 | 					uf->SetFileType(rest.GetToken(" ", 1, 1).ToInt());
 | 
        
           |  |  | 458 | 					if ( uf->GetFileType() == FILETYPE_EXTRA )
 | 
        
           |  |  | 459 | 					{
 | 
        
           |  |  | 460 | 						uf->SetDir(rest.GetToken(" ", 2).GetToken(":", 2));
 | 
        
           |  |  | 461 | 						uf->SetFilename(rest.GetToken(" ", 2).GetToken(":", 1, 1));
 | 
        
           |  |  | 462 | 					}
 | 
        
           |  |  | 463 | 					else
 | 
        
           |  |  | 464 | 						uf->SetFilename(rest.GetToken(" ", 2));
 | 
        
           |  |  | 465 | 					uf->SetFilename(m_sCurrentDir + "/" + uf->GetNameDirectory(NULL));
 | 
        
           |  |  | 466 | 					m_lOriginalFiles.push_back(uf);
 | 
        
           |  |  | 467 | 				}
 | 
        
           |  |  | 468 | 				else if ( cmd.Compare("GlobalSetting") )
 | 
        
           |  |  | 469 | 					m_lGlobals.PushBack(rest.GetToken(":", 1, 1), rest.GetToken(":", 2));
 | 
        
           |  |  | 470 | 				else if ( cmd.Compare("FakePatchOrder") )
 | 
        
           |  |  | 471 | 					m_lFakePatchOrder.PushBack(rest.GetToken(":", 1, 1), rest.GetToken(":", 2));
 | 
        
           |  |  | 472 | 				else if ( cmd == "globalfiles" )
 | 
        
           |  |  | 473 | 					iStatus = READ_GLOBAL;
 | 
        
           |  |  | 474 |   | 
        
           |  |  | 475 | 				if ( progress )
 | 
        
           |  |  | 476 | 				{
 | 
        
           |  |  | 477 | 					progress->UpdateProgress((long)i, (long)readFile->size());
 | 
        
           |  |  | 478 | 				}
 | 
        
           |  |  | 479 | 			}
 | 
        
           |  |  | 480 | 			readFile->clear();
 | 
        
           |  |  | 481 |   | 
        
           |  |  | 482 | 			if ( !spkinstaller )
 | 
        
           |  |  | 483 | 				m_bRedo = true;
 | 
        
           |  |  | 484 |   | 
        
           |  |  | 485 | 			delete readFile;
 | 
        
           |  |  | 486 | 		}
 | 
        
           |  |  | 487 | 	}
 | 
        
           |  |  | 488 |   | 
        
           |  |  | 489 | 	if ( m_pEnabledMod && !m_pEnabledMod->IsEnabled() )
 | 
        
           |  |  | 490 | 		m_pEnabledMod = NULL;
 | 
        
           |  |  | 491 |   | 
        
           |  |  | 492 | 	m_iGame = m_gameExe.GetGameType(m_sCurrentDir) + 1;
 | 
        
           |  |  | 493 | 	m_iGameVersion = m_gameExe.GetGameVersion(m_sCurrentDir, &m_sGameVersion) + 1;
 | 
        
           |  |  | 494 | 	m_iGameFlags = m_gameExe.GetGameFlags(m_iGame - 1);
 | 
        
           |  |  | 495 | 	m_iMaxPatch = m_gameExe.GetMaxPatch(m_iGame - 1);
 | 
        
           |  |  | 496 |   | 
        
           |  |  | 497 | 	// find the fake patch
 | 
        
           |  |  | 498 | 	if ( !ReadyFakePatch() )
 | 
        
           |  |  | 499 | 		return false;
 | 
        
           |  |  | 500 |   | 
        
           |  |  | 501 | 	this->RemoveCreatedFiles();
 | 
        
           |  |  | 502 |   | 
        
           |  |  | 503 | 	// match up wares
 | 
        
           |  |  | 504 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 505 | 	{
 | 
        
           |  |  | 506 | 		if ( node->Data()->GetType() == TYPE_SPK )
 | 
        
           |  |  | 507 | 		{
 | 
        
           |  |  | 508 | 			CSpkFile *p = (CSpkFile *)node->Data();
 | 
        
           |  |  | 509 | 			for ( CListNode<SWares> *wNode = p->GetWaresList()->Front(); wNode; wNode = wNode->next() )
 | 
        
           |  |  | 510 | 			{
 | 
        
           |  |  | 511 | 				SWares *w = wNode->Data();
 | 
        
           |  |  | 512 | 				for ( CListNode<SGameWare> *gNode = m_lGameWares[CPackages::ConvertWareType(w->cType)].Front(); gNode; gNode = gNode->next() )
 | 
        
           |  |  | 513 | 				{
 | 
        
           | 10 | cycrow | 514 | 					if ( w->sID == gNode->Data()->sWareName.ToString() )
 | 
        
           | 1 | cycrow | 515 | 					{
 | 
        
           |  |  | 516 | 						gNode->Data()->pWare = w;
 | 
        
           |  |  | 517 | 						break;
 | 
        
           |  |  | 518 | 					}
 | 
        
           |  |  | 519 | 				}
 | 
        
           |  |  | 520 | 			}
 | 
        
           |  |  | 521 | 		}
 | 
        
           |  |  | 522 | 		else if ( node->Data()->GetType() == TYPE_XSP )
 | 
        
           |  |  | 523 | 		{
 | 
        
           |  |  | 524 | 			CXspFile *p = (CXspFile *)node->Data();
 | 
        
           |  |  | 525 | 			for ( CListNode<SGameShip> *gNode = m_lGameShips.Front(); gNode; gNode = gNode->next() )
 | 
        
           |  |  | 526 | 			{
 | 
        
           | 14 | cycrow | 527 | 				if ( p->GetShipID().Compare(gNode->Data()->sShipID.ToString()) )
 | 
        
           | 1 | cycrow | 528 | 				{
 | 
        
           |  |  | 529 | 					gNode->Data()->pPackage = p;
 | 
        
           |  |  | 530 | 					break;
 | 
        
           |  |  | 531 | 				}
 | 
        
           |  |  | 532 | 			}
 | 
        
           |  |  | 533 | 		}
 | 
        
           |  |  | 534 | 	}
 | 
        
           |  |  | 535 |   | 
        
           |  |  | 536 | 	// check the purged time
 | 
        
           |  |  | 537 | 	this->PurgeGameObjects();
 | 
        
           |  |  | 538 |   | 
        
           |  |  | 539 | 	m_bLoaded = true;
 | 
        
           |  |  | 540 |   | 
        
           |  |  | 541 | 	return true;
 | 
        
           |  |  | 542 | }
 | 
        
           |  |  | 543 |   | 
        
           |  |  | 544 | void CPackages::RemoveCreatedFiles()
 | 
        
           |  |  | 545 | {
 | 
        
           |  |  | 546 | 	for ( SStringList *node = m_lCreatedFiles.Head(); node; node = node->next )
 | 
        
           |  |  | 547 | 	{
 | 
        
           |  |  | 548 | 		if ( CFileIO(node->str).Exists() )
 | 
        
           |  |  | 549 | 			CFileIO(node->str).Remove();
 | 
        
           |  |  | 550 | 		else if ( CFileIO(m_sCurrentDir + "/" + node->str).Exists() )
 | 
        
           |  |  | 551 | 			CFileIO(m_sCurrentDir + "/" + node->str).Remove();
 | 
        
           |  |  | 552 | 	}
 | 
        
           |  |  | 553 |   | 
        
           |  |  | 554 | 	m_lCreatedFiles.Clear();
 | 
        
           |  |  | 555 | }
 | 
        
           |  |  | 556 |   | 
        
           |  |  | 557 | void CPackages::PurgeGameObjects()
 | 
        
           |  |  | 558 | {
 | 
        
           |  |  | 559 | 	// check for the log file
 | 
        
           |  |  | 560 | 	CyString logDir = GetLogDirectory();
 | 
        
           |  |  | 561 | 	CFileIO LogFile(logDir + "/log0" + CyString::Number(PMTEXTFILE).PadNumber(4) + ".txt");
 | 
        
           |  |  | 562 | 	if ( LogFile.Exists() )
 | 
        
           |  |  | 563 | 	{
 | 
        
           |  |  | 564 | 		// read the log file to memory
 | 
        
           |  |  | 565 | 		std::vector<CyString> *lines = LogFile.ReadLines();
 | 
        
           |  |  | 566 | 		if ( lines )
 | 
        
           |  |  | 567 | 		{
 | 
        
           |  |  | 568 | 			for ( int i = 0; i < (int)lines->size(); i++ )
 | 
        
           |  |  | 569 | 			{
 | 
        
           |  |  | 570 | 				CyString line(lines->at(i));
 | 
        
           |  |  | 571 | 				CyString start = line.GetToken(":", 1, 1).ToLower();
 | 
        
           |  |  | 572 | 				CyString rest = line.GetToken(":", 2, 2).RemoveFirstSpace();
 | 
        
           |  |  | 573 | 				if ( start.Compare("purged") )
 | 
        
           |  |  | 574 | 				{
 | 
        
           |  |  | 575 | 					long time = rest.ToLong();
 | 
        
           |  |  | 576 | 					if ( time == m_iLastUpdated )
 | 
        
           |  |  | 577 | 					{
 | 
        
           |  |  | 578 | 						this->PurgeWares();
 | 
        
           |  |  | 579 | 						this->PurgeShips();
 | 
        
           |  |  | 580 | 						this->RemoveUninstallScripts();
 | 
        
           |  |  | 581 | 					}
 | 
        
           |  |  | 582 | 				}
 | 
        
           |  |  | 583 | 			}
 | 
        
           |  |  | 584 |   | 
        
           |  |  | 585 | 			delete lines;
 | 
        
           |  |  | 586 | 		}
 | 
        
           |  |  | 587 | 		// remove the log file
 | 
        
           |  |  | 588 | 		LogFile.Remove();
 | 
        
           |  |  | 589 | 	}
 | 
        
           |  |  | 590 | }
 | 
        
           |  |  | 591 |   | 
        
           |  |  | 592 | void CPackages::PurgeWares()
 | 
        
           |  |  | 593 | {
 | 
        
           |  |  | 594 | 	// mark all delete wares as available
 | 
        
           |  |  | 595 | 	for ( int i = 0; i < WAREBUFFERS; i++ )
 | 
        
           |  |  | 596 | 	{
 | 
        
           |  |  | 597 | 		for ( CListNode<SGameWare> *node = m_lGameWares[i].Front(); node; node = node->next() )
 | 
        
           |  |  | 598 | 		{
 | 
        
           |  |  | 599 | 			SGameWare *w = node->Data();
 | 
        
           |  |  | 600 | 			if ( !w ) continue;
 | 
        
           |  |  | 601 | 			if ( w->iType == WARETYPE_DELETED )
 | 
        
           |  |  | 602 | 				w->iType = WARETYPE_NONE;
 | 
        
           |  |  | 603 | 		}
 | 
        
           |  |  | 604 | 		m_lGameWares[i].RemoveEmpty();
 | 
        
           |  |  | 605 | 	}
 | 
        
           |  |  | 606 | }
 | 
        
           |  |  | 607 |   | 
        
           |  |  | 608 | void CPackages::PurgeShips()
 | 
        
           |  |  | 609 | {
 | 
        
           |  |  | 610 | 	for ( CListNode<SGameShip> *node = m_lGameShips.Front(); node; node = node->next() )
 | 
        
           |  |  | 611 | 	{
 | 
        
           |  |  | 612 | 		if ( !node->Data() )
 | 
        
           |  |  | 613 | 			continue;
 | 
        
           |  |  | 614 | 		if ( node->Data()->iType == WARETYPE_DELETED )
 | 
        
           |  |  | 615 | 			node->Data()->iType = WARETYPE_NONE;
 | 
        
           |  |  | 616 | 	}
 | 
        
           |  |  | 617 | 	m_lGameShips.RemoveEmpty();
 | 
        
           |  |  | 618 | }
 | 
        
           |  |  | 619 |   | 
        
           |  |  | 620 | CyString CPackages::GetLogDirectory()
 | 
        
           |  |  | 621 | {
 | 
        
           |  |  | 622 | 	CyString logDir = m_sCurrentDir;
 | 
        
           |  |  | 623 | 	if ( m_iGameFlags & EXEFLAG_MYDOCLOG )
 | 
        
           |  |  | 624 | 	{
 | 
        
           |  |  | 625 | 		SGameExe *exe = m_gameExe.GetGame(m_iGame - 1);
 | 
        
           |  |  | 626 | 		if ( exe )
 | 
        
           |  |  | 627 | 		{
 | 
        
           |  |  | 628 | 			if ( !exe->sMyDoc.Empty() )
 | 
        
           |  |  | 629 | 				logDir = m_sMyDoc + "/" + exe->sMyDoc;
 | 
        
           |  |  | 630 | 		}
 | 
        
           |  |  | 631 | 	}
 | 
        
           |  |  | 632 |   | 
        
           |  |  | 633 | 	return logDir;
 | 
        
           |  |  | 634 | }
 | 
        
           |  |  | 635 |   | 
        
           |  |  | 636 | CyString CPackages::GetLogDirectory(CyString gameExe)
 | 
        
           |  |  | 637 | {
 | 
        
           |  |  | 638 | 	CyString logDir = m_sCurrentDir;
 | 
        
           |  |  | 639 | 	if ( m_iGameFlags & EXEFLAG_MYDOCLOG )
 | 
        
           |  |  | 640 | 	{
 | 
        
           |  |  | 641 | 		SGameExe *exe = m_gameExe.GetGameExe(CFileIO(gameExe).GetFilename());
 | 
        
           |  |  | 642 | 		if ( exe )
 | 
        
           |  |  | 643 | 		{
 | 
        
           |  |  | 644 | 			if ( !exe->sMyDoc.Empty() )
 | 
        
           |  |  | 645 | 				logDir = m_sMyDoc + "/" + exe->sMyDoc;
 | 
        
           |  |  | 646 | 		}
 | 
        
           |  |  | 647 | 	}
 | 
        
           |  |  | 648 |   | 
        
           |  |  | 649 | 	return CFileIO(logDir).GetFullFilename();
 | 
        
           |  |  | 650 | }
 | 
        
           |  |  | 651 |   | 
        
           |  |  | 652 | CyString CPackages::GetSaveDirectory()
 | 
        
           |  |  | 653 | {
 | 
        
           |  |  | 654 | 	CyString logDir = this->GetLogDirectory();
 | 
        
           |  |  | 655 | 	if ( m_iGameFlags & EXEFLAG_NOSAVESUBDIR )
 | 
        
           |  |  | 656 | 		return logDir;
 | 
        
           |  |  | 657 |   | 
        
           |  |  | 658 | 	return logDir + "/save";
 | 
        
           |  |  | 659 | }
 | 
        
           |  |  | 660 |   | 
        
           |  |  | 661 | bool CPackages::ReadyFakePatch()
 | 
        
           |  |  | 662 | {
 | 
        
           |  |  | 663 | 	// already exists, lets skip it
 | 
        
           |  |  | 664 | 	if ( CFileIO(m_sCurrentDir + "/PluginManager/PlugMan_Fake.cat").Exists() && CFileIO(m_sCurrentDir + "/PluginManager/PlugMan_Fake.dat").Exists() )
 | 
        
           |  |  | 665 | 		return true;
 | 
        
           |  |  | 666 |   | 
        
           |  |  | 667 | 	// if only one of them exists, lets remove them
 | 
        
           |  |  | 668 | 	if ( CFileIO(m_sCurrentDir + "/PluginManager/PlugMan_Fake.cat").Exists() )
 | 
        
           |  |  | 669 | 		CFileIO(m_sCurrentDir + "/PluginManager/PlugMan_Fake.cat").Remove();
 | 
        
           |  |  | 670 | 	if ( CFileIO(m_sCurrentDir + "/PluginManager/PlugMan_Fake.dat").Exists() )
 | 
        
           |  |  | 671 | 		CFileIO(m_sCurrentDir + "/PluginManager/PlugMan_Fake.dat").Remove();
 | 
        
           |  |  | 672 |   | 
        
           |  |  | 673 | 	// now lets find the fake patch
 | 
        
           |  |  | 674 | 	CyString useFile;
 | 
        
           |  |  | 675 | 	if ( m_iFakePatch > 0 )
 | 
        
           |  |  | 676 | 	{
 | 
        
           |  |  | 677 | 		CyString file = CyString::Number(m_iFakePatch).PadNumber(2);
 | 
        
           |  |  | 678 | 		if ( CheckValidPluginManagerFile(file) )
 | 
        
           |  |  | 679 | 			useFile = file;
 | 
        
           |  |  | 680 | 		else if ( CheckIfPluginManagerFile(file) )
 | 
        
           |  |  | 681 | 			useFile = file;
 | 
        
           |  |  | 682 | 	}
 | 
        
           |  |  | 683 |   | 
        
           |  |  | 684 | 	if ( useFile.Empty() )
 | 
        
           |  |  | 685 | 	{
 | 
        
           |  |  | 686 | 		int nextfree = this->FindNextFakePatch();
 | 
        
           |  |  | 687 | 		--nextfree; // gets the end fake patch
 | 
        
           |  |  | 688 |   | 
        
           |  |  | 689 | 		// work backwards till we find a valid one
 | 
        
           |  |  | 690 | 		while ( nextfree > m_iMaxPatch )
 | 
        
           |  |  | 691 | 		{
 | 
        
           |  |  | 692 | 			CyString file = CyString::Number(nextfree).PadNumber(2);
 | 
        
           |  |  | 693 | 			if ( CheckValidPluginManagerFile(file) )
 | 
        
           |  |  | 694 | 			{
 | 
        
           |  |  | 695 | 				useFile = file;
 | 
        
           |  |  | 696 | 				break;
 | 
        
           |  |  | 697 | 			}
 | 
        
           |  |  | 698 | 			--nextfree;
 | 
        
           |  |  | 699 | 		}
 | 
        
           |  |  | 700 | 	}
 | 
        
           |  |  | 701 |   | 
        
           |  |  | 702 | 	CyString addonDir = this->GetAddonDir();
 | 
        
           |  |  | 703 |   | 
        
           |  |  | 704 | 	// couldn't find the correct file, lets search for it
 | 
        
           |  |  | 705 | 	if ( useFile.Empty() ) {
 | 
        
           |  |  | 706 | 		int nextfree = this->FindNextFakePatch();
 | 
        
           |  |  | 707 | 		--nextfree; // gets the end fake patch
 | 
        
           |  |  | 708 |   | 
        
           |  |  | 709 | 		// work backwards till we find a valid one
 | 
        
           |  |  | 710 | 		while ( nextfree > m_iMaxPatch )
 | 
        
           |  |  | 711 | 		{
 | 
        
           |  |  | 712 | 			CyString file = CyString::Number(nextfree).PadNumber(2);
 | 
        
           |  |  | 713 | 			if ( CheckIfPluginManagerFile(file) )
 | 
        
           |  |  | 714 | 			{
 | 
        
           |  |  | 715 | 				useFile = file;
 | 
        
           |  |  | 716 | 				break;
 | 
        
           |  |  | 717 | 			}
 | 
        
           |  |  | 718 | 			--nextfree;
 | 
        
           |  |  | 719 | 		}		
 | 
        
           |  |  | 720 | 	}
 | 
        
           |  |  | 721 |   | 
        
           |  |  | 722 | 	if ( !useFile.Empty() )
 | 
        
           |  |  | 723 | 	{
 | 
        
           |  |  | 724 | 		// lets check whats in the file first
 | 
        
           |  |  | 725 | 		CCatFile openCat;
 | 
        
           |  |  | 726 | 		if ( openCat.Open(m_sCurrentDir + "/" + useFile + ".cat", addonDir, CATREAD_CATDECRYPT, false) == CATERR_NONE )
 | 
        
           |  |  | 727 | 		{
 | 
        
           |  |  | 728 | 			CLinkList<SInCatFile> *files = openCat.GetFiles();
 | 
        
           |  |  | 729 | 			bool found = false;
 | 
        
           |  |  | 730 | 			if ( files )
 | 
        
           |  |  | 731 | 			{
 | 
        
           |  |  | 732 | 				CyString useAddonDir = addonDir;
 | 
        
           |  |  | 733 | 				if ( !useAddonDir.Empty() ) useAddonDir += "\\";
 | 
        
           |  |  | 734 | 				for ( SInCatFile *inCat = files->First(); inCat; inCat = files->Next() )
 | 
        
           |  |  | 735 | 				{
 | 
        
           |  |  | 736 | 					if ( inCat->sFile.Compare("PlugMan\\TFake.pck") )
 | 
        
           |  |  | 737 | 						continue;
 | 
        
           |  |  | 738 | 					if ( inCat->sFile.Compare(useAddonDir + "t\\44" + CyString::Number(PMTEXTFILE).PadNumber(4) + ".pck") )
 | 
        
           |  |  | 739 | 						continue;
 | 
        
           |  |  | 740 | 					if ( inCat->sFile.Compare(useAddonDir + "t\\" + CyString::Number(PMTEXTFILE).PadNumber(4) + "-L044.pck") )
 | 
        
           |  |  | 741 | 						continue;
 | 
        
           |  |  | 742 |   | 
        
           |  |  | 743 | 					found = true;
 | 
        
           |  |  | 744 | 					break;
 | 
        
           |  |  | 745 | 				}
 | 
        
           |  |  | 746 | 			}
 | 
        
           |  |  | 747 |   | 
        
           |  |  | 748 | 			// no files, jsut delete them
 | 
        
           |  |  | 749 | 			CFileIO catFile(m_sCurrentDir + "/" + useFile + ".cat");
 | 
        
           |  |  | 750 | 			if ( !files || !found )
 | 
        
           |  |  | 751 | 			{
 | 
        
           |  |  | 752 | 				if ( catFile.Remove() )
 | 
        
           |  |  | 753 | 				{
 | 
        
           |  |  | 754 | 					CFileIO datFile(m_sCurrentDir + "/" + useFile + ".dat");
 | 
        
           |  |  | 755 | 					if ( datFile.Remove() )
 | 
        
           |  |  | 756 | 						return true;
 | 
        
           |  |  | 757 | 				}
 | 
        
           |  |  | 758 | 			}
 | 
        
           |  |  | 759 | 			else
 | 
        
           |  |  | 760 | 			{
 | 
        
           |  |  | 761 | 				if ( catFile.Rename(m_sCurrentDir + "/PluginManager/PlugMan_Fake.cat") )
 | 
        
           |  |  | 762 | 				{
 | 
        
           |  |  | 763 | 					CFileIO datFile(m_sCurrentDir + "/" + useFile + ".dat");
 | 
        
           |  |  | 764 |   | 
        
           |  |  | 765 | 					if ( datFile.Rename(m_sCurrentDir + "/PluginManager/PlugMan_Fake.dat") )
 | 
        
           |  |  | 766 | 						return true;
 | 
        
           |  |  | 767 |   | 
        
           |  |  | 768 | 					// TODO: it failed, restore cat file and do error
 | 
        
           |  |  | 769 | 				}
 | 
        
           |  |  | 770 | 			}
 | 
        
           |  |  | 771 | 		}
 | 
        
           |  |  | 772 |   | 
        
           |  |  | 773 | 		// if we're here, we tryed, and failed
 | 
        
           |  |  | 774 | 		return false;
 | 
        
           |  |  | 775 | 	}
 | 
        
           |  |  | 776 |   | 
        
           |  |  | 777 | 	// otherwise we didn't need to (hopefully)
 | 
        
           |  |  | 778 | 	return true;
 | 
        
           |  |  | 779 | }
 | 
        
           |  |  | 780 |   | 
        
           |  |  | 781 |   | 
        
           |  |  | 782 | bool CPackages::CheckIfPluginManagerFile(CyString filename)
 | 
        
           |  |  | 783 | {
 | 
        
           |  |  | 784 | 	bool found = false;
 | 
        
           |  |  | 785 |   | 
        
           |  |  | 786 | 	CFileIO catFile(m_sCurrentDir + "/" + filename + ".cat");
 | 
        
           |  |  | 787 | 	if ( catFile.Exists() && CFileIO(m_sCurrentDir + "/" + filename + ".dat").Exists() )
 | 
        
           |  |  | 788 | 	{
 | 
        
           |  |  | 789 | 		CCatFile openFile;
 | 
        
           |  |  | 790 | 		if ( openFile.Open(catFile.GetFullFilename(), this->GetAddonDir(), CATREAD_CATDECRYPT, false) == CATERR_NONE )
 | 
        
           |  |  | 791 | 		{
 | 
        
           |  |  | 792 | 			int count = 0;
 | 
        
           |  |  | 793 | 			int noncount = 0;
 | 
        
           |  |  | 794 |   | 
        
           |  |  | 795 | 			// check for some of the files
 | 
        
           |  |  | 796 | 			for ( CListNode<C_File> *node = m_lFiles.Front(); node; node = node->next() ) {
 | 
        
           |  |  | 797 | 				if ( node->Data()->GetFullDir().IsIn("::") ) {
 | 
        
           |  |  | 798 | 					if (CFileIO(node->Data()->GetFullDir().GetToken("::", 1, 1)).GetFilename().Compare("PlugMan_Fake.cat") ) {
 | 
        
           |  |  | 799 | 						CyString filename = node->Data()->GetFilePointer().GetToken("::", 2, 2);
 | 
        
           |  |  | 800 | 						filename = filename.findreplace("/", "\\");
 | 
        
           |  |  | 801 | 						if ( openFile.FindData(filename) )
 | 
        
           |  |  | 802 | 							++count;
 | 
        
           |  |  | 803 | 						else
 | 
        
           |  |  | 804 | 							++noncount;
 | 
        
           |  |  | 805 | 					}
 | 
        
           |  |  | 806 | 				}
 | 
        
           |  |  | 807 | 			}
 | 
        
           |  |  | 808 |   | 
        
           |  |  | 809 | 			if ( (count && !noncount) || (count > noncount) )
 | 
        
           |  |  | 810 | 				found = true;
 | 
        
           |  |  | 811 | 		}
 | 
        
           |  |  | 812 | 	}
 | 
        
           |  |  | 813 |   | 
        
           |  |  | 814 | 	return found;
 | 
        
           |  |  | 815 | }
 | 
        
           |  |  | 816 |   | 
        
           |  |  | 817 | bool CPackages::CheckValidPluginManagerFile(CyString filename)
 | 
        
           |  |  | 818 | {
 | 
        
           |  |  | 819 | 	bool found = false;
 | 
        
           |  |  | 820 |   | 
        
           |  |  | 821 | 	// both the cat file and dat file exists, lets open it
 | 
        
           |  |  | 822 | 	CFileIO catFile(m_sCurrentDir + "/" + filename + ".cat");
 | 
        
           |  |  | 823 | 	if ( catFile.Exists() && CFileIO(m_sCurrentDir + "/" + filename + ".dat").Exists() )
 | 
        
           |  |  | 824 | 	{
 | 
        
           |  |  | 825 | 		CCatFile openFile;
 | 
        
           |  |  | 826 | 		if ( openFile.Open(catFile.GetFullFilename(), this->GetAddonDir(), CATREAD_CATDECRYPT, false) == CATERR_NONE )
 | 
        
           |  |  | 827 | 		{
 | 
        
           |  |  | 828 | 			if ( openFile.FindData("PlugMan\\TFake.pck") )
 | 
        
           |  |  | 829 | 				return true;
 | 
        
           |  |  | 830 | 			if ( openFile.FindData("pluginmanagerfake.pck") )
 | 
        
           |  |  | 831 | 				return true;
 | 
        
           |  |  | 832 | 		}
 | 
        
           |  |  | 833 | 	}
 | 
        
           |  |  | 834 |   | 
        
           |  |  | 835 | 	return found;
 | 
        
           |  |  | 836 | }
 | 
        
           |  |  | 837 |   | 
        
           |  |  | 838 | /**
 | 
        
           |  |  | 839 |  * Converts a package in old format
 | 
        
           |  |  | 840 |  *
 | 
        
           |  |  | 841 |  * Some entries in older packages need to be changed for the new installer
 | 
        
           |  |  | 842 |  * These Include:
 | 
        
           |  |  | 843 |  *		- Game Version, old format is an id of position in the Data/exe file, new is 2 values, one for game, one for the version
 | 
        
           |  |  | 844 |  */
 | 
        
           |  |  | 845 | void CPackages::ConvertOldPackage(CBaseFile *package)
 | 
        
           |  |  | 846 | {
 | 
        
           |  |  | 847 | 	for ( CListNode<SGameCompat> *gNode = package->GetGameCompatabilityList()->Front(); gNode; gNode = gNode->next() ) {
 | 
        
           |  |  | 848 | 		if ( gNode->Data()->iGame == -1 ) {
 | 
        
           |  |  | 849 | 			// all versions
 | 
        
           |  |  | 850 | 			if ( gNode->Data()->iVersion == 0 )
 | 
        
           |  |  | 851 | 				gNode->Data()->iGame = 0;
 | 
        
           |  |  | 852 | 			else
 | 
        
           |  |  | 853 | 			{
 | 
        
           |  |  | 854 | 				int version = 0;
 | 
        
           |  |  | 855 | 				gNode->Data()->iGame = m_gameExe.ConvertGameType(gNode->Data()->iVersion, &version);
 | 
        
           |  |  | 856 | 				gNode->Data()->iVersion = version;
 | 
        
           |  |  | 857 | 			}
 | 
        
           |  |  | 858 | 		}
 | 
        
           |  |  | 859 | 	}
 | 
        
           |  |  | 860 |   | 
        
           |  |  | 861 | 	if ( package->GetForumLink().Empty() && package->GetWebSite().IsIn("forum.egosoft"))
 | 
        
           |  |  | 862 | 	{
 | 
        
           |  |  | 863 | 		package->SetForumLink(package->GetWebSite());
 | 
        
           |  |  | 864 | 		package->SetWebSite("");
 | 
        
           |  |  | 865 | 	}
 | 
        
           |  |  | 866 |   | 
        
           |  |  | 867 | 	// convert the version
 | 
        
           |  |  | 868 | 	if ( package->GetType() == TYPE_SPK )
 | 
        
           |  |  | 869 | 	{
 | 
        
           |  |  | 870 | 		CSpkFile *spk = (CSpkFile *)package;
 | 
        
           | 6 | cycrow | 871 | 		if ( spk->GetScriptType() == CSpkFile::SCRIPTTYPE_CUSTOM )
 | 
        
           | 1 | cycrow | 872 | 		{
 | 
        
           |  |  | 873 | 			CyString type = spk->GetScriptTypeString(44);
 | 
        
           |  |  | 874 | 			if ( type.Compare("Ship Upgrade") )
 | 
        
           | 6 | cycrow | 875 | 				spk->SetScriptType(CSpkFile::SCRIPTTYPE_SHIPUPGRADE);
 | 
        
           | 1 | cycrow | 876 | 			else if ( type.Compare("Trade Script") )
 | 
        
           | 6 | cycrow | 877 | 				spk->SetScriptType(CSpkFile::SCRIPTTYPE_TRADE);
 | 
        
           | 1 | cycrow | 878 | 			else if ( type.Compare("Fleet Management") )
 | 
        
           | 6 | cycrow | 879 | 				spk->SetScriptType(CSpkFile::SCRIPTTYPE_FLEET);
 | 
        
           | 1 | cycrow | 880 | 			else if ( type.Compare("Navigation Script") )
 | 
        
           | 6 | cycrow | 881 | 				spk->SetScriptType(CSpkFile::SCRIPTTYPE_NAVIGATION);
 | 
        
           | 1 | cycrow | 882 | 			else if ( type.Compare("Piracy") )
 | 
        
           | 6 | cycrow | 883 | 				spk->SetScriptType(CSpkFile::SCRIPTTYPE_PIRACY);
 | 
        
           | 1 | cycrow | 884 | 			else if ( type.Compare("Other") )
 | 
        
           | 6 | cycrow | 885 | 				spk->SetScriptType(CSpkFile::SCRIPTTYPE_OTHER);
 | 
        
           | 1 | cycrow | 886 | 			else if ( type.Compare("Ship Command") )
 | 
        
           | 6 | cycrow | 887 | 				spk->SetScriptType(CSpkFile::SCRIPTTYPE_SHIPCOMMAND);
 | 
        
           | 1 | cycrow | 888 | 			else if ( type.Compare("Station Command") )
 | 
        
           | 6 | cycrow | 889 | 				spk->SetScriptType(CSpkFile::SCRIPTTYPE_STATIONCOMMAND);
 | 
        
           | 1 | cycrow | 890 | 			else if ( type.Compare("al plugin") )
 | 
        
           | 6 | cycrow | 891 | 				spk->SetScriptType(CSpkFile::SCRIPTTYPE_ALPLUGIN);
 | 
        
           | 1 | cycrow | 892 | 			else if ( type.Compare("combat script") )
 | 
        
           | 6 | cycrow | 893 | 				spk->SetScriptType(CSpkFile::SCRIPTTYPE_COMBAT);
 | 
        
           | 1 | cycrow | 894 | 			else if ( type.Compare("bbs and missions") )
 | 
        
           | 6 | cycrow | 895 | 				spk->SetScriptType(CSpkFile::SCRIPTTYPE_MISSION);
 | 
        
           | 1 | cycrow | 896 | 			else if ( type.Compare("extension mod") )
 | 
        
           | 6 | cycrow | 897 | 				spk->SetScriptType(CSpkFile::SCRIPTTYPE_EXTENSION);
 | 
        
           | 1 | cycrow | 898 | 			else if ( type.Compare("rebalance mod") )
 | 
        
           | 6 | cycrow | 899 | 				spk->SetScriptType(CSpkFile::SCRIPTTYPE_REBALANCE);
 | 
        
           | 1 | cycrow | 900 | 			else if ( type.Compare("general mod") )
 | 
        
           | 6 | cycrow | 901 | 				spk->SetScriptType(CSpkFile::SCRIPTTYPE_GENERALMOD);
 | 
        
           | 1 | cycrow | 902 | 			else if ( type.Compare("total conversion") )
 | 
        
           | 6 | cycrow | 903 | 				spk->SetScriptType(CSpkFile::SCRIPTTYPE_TOTAL);
 | 
        
           | 1 | cycrow | 904 | 			else if ( type.Compare("cheat script") )
 | 
        
           | 6 | cycrow | 905 | 				spk->SetScriptType(CSpkFile::SCRIPTTYPE_CHEAT);
 | 
        
           | 1 | cycrow | 906 | 			else if ( type == "Library Script" )
 | 
        
           |  |  | 907 | 			{
 | 
        
           |  |  | 908 | 				spk->SetScriptType("");
 | 
        
           |  |  | 909 | 				spk->SetLibrary();
 | 
        
           |  |  | 910 | 			}
 | 
        
           |  |  | 911 |   | 
        
           | 6 | cycrow | 912 | 			if ( spk->GetScriptType() != CSpkFile::SCRIPTTYPE_CUSTOM )
 | 
        
           | 1 | cycrow | 913 | 				spk->SetScriptType("");
 | 
        
           |  |  | 914 | 		}
 | 
        
           |  |  | 915 | 	}
 | 
        
           |  |  | 916 | 	else if ( package->GetType() == TYPE_XSP )
 | 
        
           |  |  | 917 | 	{
 | 
        
           |  |  | 918 | 		CXspFile *xsp = (CXspFile *)package;
 | 
        
           | 14 | cycrow | 919 | 		Utils::String data = xsp->GetShipData();
 | 
        
           | 1 | cycrow | 920 |   | 
        
           |  |  | 921 | 		for ( int i = 17; i <= 18; i++ )
 | 
        
           |  |  | 922 | 		{
 | 
        
           | 14 | cycrow | 923 | 			Utils::String model = data.token(";", i);
 | 
        
           |  |  | 924 | 			Utils::String modelExt = model.right(4);
 | 
        
           | 1 | cycrow | 925 | 			// check file extension
 | 
        
           |  |  | 926 | 			if ( modelExt.Compare(".bod") || modelExt.Compare(".pbd") )
 | 
        
           | 14 | cycrow | 927 | 				data = data.replaceToken(";", i, model.left(-4));
 | 
        
           | 1 | cycrow | 928 | 		}
 | 
        
           |  |  | 929 |   | 
        
           |  |  | 930 | 		xsp->SetShipData(data);
 | 
        
           |  |  | 931 | 	}
 | 
        
           |  |  | 932 |   | 
        
           |  |  | 933 | 	// any extra files that are in director folder
 | 
        
           |  |  | 934 | 	if ( package->AnyFileType(FILETYPE_EXTRA) )
 | 
        
           |  |  | 935 | 	{
 | 
        
           |  |  | 936 | 		for ( C_File *f = package->GetFirstFile(FILETYPE_EXTRA); f; f = package->GetNextFile(f) )
 | 
        
           |  |  | 937 | 		{
 | 
        
           |  |  | 938 | 			if ( !f->GetDir().Compare("director") )
 | 
        
           |  |  | 939 | 				continue;
 | 
        
           |  |  | 940 | 			if ( f->CheckFileExt("xml") || f->CheckFileExt("pck") )
 | 
        
           |  |  | 941 | 			{
 | 
        
           |  |  | 942 | 				f->SetDir("");
 | 
        
           |  |  | 943 | 				f->SetFileType(FILETYPE_MISSION);
 | 
        
           |  |  | 944 | 			}
 | 
        
           |  |  | 945 | 		}
 | 
        
           |  |  | 946 | 	}
 | 
        
           |  |  | 947 | }
 | 
        
           |  |  | 948 |   | 
        
           |  |  | 949 | void CPackages::UpdatePackage(CBaseFile *p)
 | 
        
           |  |  | 950 | {
 | 
        
           |  |  | 951 | 	if ( p->GetType() != TYPE_SPK )
 | 
        
           |  |  | 952 | 		return;
 | 
        
           |  |  | 953 |   | 
        
           |  |  | 954 | 	CSpkFile *package = (CSpkFile *)p;
 | 
        
           |  |  | 955 |   | 
        
           |  |  | 956 | 	// update the signed status
 | 
        
           |  |  | 957 | 	package->UpdateSigned(true);
 | 
        
           |  |  | 958 |   | 
        
           |  |  | 959 | 	// check for another mod
 | 
        
           |  |  | 960 | 	if ( !package->IsAnotherMod() )
 | 
        
           |  |  | 961 | 		return;
 | 
        
           |  |  | 962 |   | 
        
           |  |  | 963 | 	package->SetParent((CSpkFile *)FindSpkPackage(package->GetOtherName(), package->GetOtherAuthor()));
 | 
        
           |  |  | 964 | }
 | 
        
           |  |  | 965 |   | 
        
           |  |  | 966 | /**
 | 
        
           |  |  | 967 |  * Updates the package list once data has been read
 | 
        
           |  |  | 968 |  *
 | 
        
           |  |  | 969 |  * Finds any original Files
 | 
        
           |  |  | 970 |  * Updates Signed status of all packages
 | 
        
           |  |  | 971 |  */
 | 
        
           |  |  | 972 | bool CPackages::UpdatePackages(int doStatus, bool individual)
 | 
        
           |  |  | 973 | {
 | 
        
           |  |  | 974 | 	// if theres no original files, then set the current structure as the base
 | 
        
           |  |  | 975 | 	if ( doStatus == 0 || doStatus == -1 )
 | 
        
           |  |  | 976 | 	{
 | 
        
           |  |  | 977 | 		if ( m_lOriginalFiles.empty() || m_bRedo )
 | 
        
           |  |  | 978 | 		{
 | 
        
           |  |  | 979 | 			StoreOriginalFiles(FILETYPE_SCRIPT, "scripts");
 | 
        
           |  |  | 980 | 			StoreOriginalFiles(FILETYPE_TEXT, "t");
 | 
        
           |  |  | 981 | 			StoreOriginalFiles(FILETYPE_SOUND, "soundtrack");
 | 
        
           |  |  | 982 | 			StoreOriginalFiles(FILETYPE_EXTRA, "mov");
 | 
        
           |  |  | 983 | 		}
 | 
        
           |  |  | 984 | 	}
 | 
        
           |  |  | 985 |   | 
        
           |  |  | 986 | 	// update each package
 | 
        
           |  |  | 987 | 	// parent/child, signed status
 | 
        
           |  |  | 988 | 	if ( doStatus == -1 || doStatus == 1 )
 | 
        
           |  |  | 989 | 	{
 | 
        
           |  |  | 990 | 		if ( individual )
 | 
        
           |  |  | 991 | 		{
 | 
        
           |  |  | 992 | 			// no package, most likly none installed
 | 
        
           |  |  | 993 | 			if ( !m_pPackageNode )
 | 
        
           |  |  | 994 | 				return false;
 | 
        
           |  |  | 995 |   | 
        
           |  |  | 996 | 			this->UpdatePackage(m_pPackageNode->Data());
 | 
        
           |  |  | 997 |   | 
        
           |  |  | 998 | 			// move to the next package
 | 
        
           |  |  | 999 | 			m_pPackageNode = m_pPackageNode->next();
 | 
        
           |  |  | 1000 | 			if ( !m_pPackageNode )
 | 
        
           |  |  | 1001 | 				return false;
 | 
        
           |  |  | 1002 | 		}
 | 
        
           |  |  | 1003 | 		else
 | 
        
           |  |  | 1004 | 		{
 | 
        
           |  |  | 1005 | 			for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 1006 | 				this->UpdatePackage(node->Data());
 | 
        
           |  |  | 1007 | 		}
 | 
        
           |  |  | 1008 | 	}
 | 
        
           |  |  | 1009 |   | 
        
           |  |  | 1010 | 	if ( doStatus == -1 || doStatus == 2 )
 | 
        
           |  |  | 1011 | 		this->LoadVirtualFileSystem();
 | 
        
           |  |  | 1012 |   | 
        
           |  |  | 1013 | 	// adjust save games
 | 
        
           |  |  | 1014 | 	if ( doStatus == -1 || doStatus == 3 )
 | 
        
           |  |  | 1015 | 	{
 | 
        
           |  |  | 1016 | 		/*
 | 
        
           |  |  | 1017 | 		// load our save games to the active mydocs
 | 
        
           |  |  | 1018 | 		if ( m_iSaveGame != -1 )
 | 
        
           |  |  | 1019 | 		{
 | 
        
           |  |  | 1020 | 			// check we have a valid save game directory
 | 
        
           |  |  | 1021 | 			CDirIO Dir(this->GetSaveDirectory());
 | 
        
           |  |  | 1022 | 			if ( Dir.Exists() )
 | 
        
           |  |  | 1023 | 			{
 | 
        
           |  |  | 1024 | 				// now check our directory already exists
 | 
        
           |  |  | 1025 | 				// if we are vanilla mode, then make sure we use the vanilla saves if exists
 | 
        
           |  |  | 1026 | 				CyString d = CyString("game_") + (long)m_iSaveGame + "/";
 | 
        
           |  |  | 1027 | 				if ( m_bVanilla )
 | 
        
           |  |  | 1028 | 					d += "Vanilla";
 | 
        
           |  |  | 1029 | 				else
 | 
        
           |  |  | 1030 | 					d += "Modified";
 | 
        
           |  |  | 1031 |   | 
        
           |  |  | 1032 | 				// copy the files back over
 | 
        
           |  |  | 1033 | 				if ( Dir.Exists(d) )
 | 
        
           |  |  | 1034 | 				{
 | 
        
           |  |  | 1035 | 					// if vanilla, remove files first
 | 
        
           |  |  | 1036 | 					if ( m_bVanilla )
 | 
        
           |  |  | 1037 | 					{
 | 
        
           |  |  | 1038 | 						CyStringList *lDirs = Dir.DirList();
 | 
        
           |  |  | 1039 | 						if ( lDirs )
 | 
        
           |  |  | 1040 | 						{
 | 
        
           |  |  | 1041 | 							for ( SStringList *node = lDirs->Head(); node; node = node->next )
 | 
        
           |  |  | 1042 | 							{
 | 
        
           |  |  | 1043 | 								if ( !Dir.IsFile(node->str) || !CFileIO(node->str).CheckFileExtension("sav") )
 | 
        
           |  |  | 1044 | 									continue;
 | 
        
           |  |  | 1045 | 								CFileIO(Dir.File(node->str)).Remove();
 | 
        
           |  |  | 1046 | 							}
 | 
        
           |  |  | 1047 |   | 
        
           |  |  | 1048 | 							delete lDirs;
 | 
        
           |  |  | 1049 | 						}
 | 
        
           |  |  | 1050 | 					}
 | 
        
           |  |  | 1051 |   | 
        
           |  |  | 1052 | 					// copy files to normal save game directory
 | 
        
           |  |  | 1053 | 					CDirIO FromDir(Dir.Dir(d));
 | 
        
           |  |  | 1054 | 					CyStringList *lDirs = FromDir.DirList();
 | 
        
           |  |  | 1055 | 					if ( lDirs )
 | 
        
           |  |  | 1056 | 					{
 | 
        
           |  |  | 1057 | 						for ( SStringList *node = lDirs->Head(); node; node = node->next )
 | 
        
           |  |  | 1058 | 						{
 | 
        
           |  |  | 1059 | 							if ( !FromDir.IsFile(node->str) || !CFileIO(node->str).CheckFileExtension("sav") )
 | 
        
           |  |  | 1060 | 								continue;
 | 
        
           |  |  | 1061 | 							CFileIO F(FromDir.File(node->str));
 | 
        
           |  |  | 1062 | 							F.Copy(Dir.File(F.GetFilename()));
 | 
        
           |  |  | 1063 | 						}
 | 
        
           |  |  | 1064 |   | 
        
           |  |  | 1065 | 						delete lDirs;
 | 
        
           |  |  | 1066 | 					}
 | 
        
           |  |  | 1067 | 				}
 | 
        
           |  |  | 1068 | 			}
 | 
        
           |  |  | 1069 | 		}*/
 | 
        
           |  |  | 1070 | 	}
 | 
        
           |  |  | 1071 |   | 
        
           |  |  | 1072 | 	m_bRedo = false;
 | 
        
           |  |  | 1073 | 	return true;
 | 
        
           |  |  | 1074 | }
 | 
        
           |  |  | 1075 |   | 
        
           |  |  | 1076 | int CPackages::CheckOpenPackage(CyString file, int *error)
 | 
        
           |  |  | 1077 | {
 | 
        
           |  |  | 1078 | 	// first check if it exists
 | 
        
           |  |  | 1079 | 	if ( !CFileIO(file).Exists() )
 | 
        
           |  |  | 1080 | 	{
 | 
        
           |  |  | 1081 | 		*error = INSTALLERR_NOEXIST;
 | 
        
           |  |  | 1082 | 		return -1;
 | 
        
           |  |  | 1083 | 	}
 | 
        
           |  |  | 1084 |   | 
        
           |  |  | 1085 | 	// open the spk file
 | 
        
           |  |  | 1086 | 	float fVersion = 0.0f;
 | 
        
           |  |  | 1087 | 	int check = CBaseFile::CheckFile(file, &fVersion);
 | 
        
           |  |  | 1088 |   | 
        
           |  |  | 1089 | 	// wrong version
 | 
        
           |  |  | 1090 | 	if ( fVersion > (float)FILEVERSION )
 | 
        
           |  |  | 1091 | 	{
 | 
        
           |  |  | 1092 | 		*error = INSTALLERR_VERSION;
 | 
        
           |  |  | 1093 | 		return -1;
 | 
        
           |  |  | 1094 | 	}
 | 
        
           |  |  | 1095 |   | 
        
           |  |  | 1096 | 	return check;
 | 
        
           |  |  | 1097 | }
 | 
        
           |  |  | 1098 |   | 
        
           |  |  | 1099 | CMultiSpkFile *CPackages::OpenMultiPackage(CyString file, int *error, CProgressInfo *progress)
 | 
        
           |  |  | 1100 | {
 | 
        
           |  |  | 1101 | 	int check = CheckOpenPackage(file, error);
 | 
        
           |  |  | 1102 | 	if ( *error == -1 )
 | 
        
           |  |  | 1103 | 		return false;
 | 
        
           |  |  | 1104 |   | 
        
           |  |  | 1105 | 	if ( check != SPKFILE_MULTI )
 | 
        
           |  |  | 1106 | 	{
 | 
        
           |  |  | 1107 | 		*error = INSTALLERR_NOMULTI;
 | 
        
           |  |  | 1108 | 		return false;
 | 
        
           |  |  | 1109 | 	}
 | 
        
           |  |  | 1110 |   | 
        
           |  |  | 1111 | 	*error = INSTALLERR_NONE;
 | 
        
           |  |  | 1112 |   | 
        
           |  |  | 1113 | 	CMultiSpkFile *package = new CMultiSpkFile;
 | 
        
           |  |  | 1114 |   | 
        
           |  |  | 1115 | 	bool ret = false;
 | 
        
           |  |  | 1116 | 	if ( package->ReadFile(file, true) )
 | 
        
           |  |  | 1117 | 	{
 | 
        
           |  |  | 1118 | 		if ( package->ReadAllPackages(SPKREAD_NODATA) )
 | 
        
           |  |  | 1119 | 		{
 | 
        
           |  |  | 1120 | 			for ( CListNode<SMultiSpkFile> *node = package->GetFileList()->Front(); node; node = node->next() )
 | 
        
           |  |  | 1121 | 				this->ConvertOldPackage(node->Data()->pFile);
 | 
        
           |  |  | 1122 |   | 
        
           |  |  | 1123 | 			ret = true;
 | 
        
           |  |  | 1124 | 		}
 | 
        
           |  |  | 1125 | 	}
 | 
        
           |  |  | 1126 |   | 
        
           |  |  | 1127 | 	if ( ret )
 | 
        
           |  |  | 1128 | 		return package;
 | 
        
           |  |  | 1129 |   | 
        
           |  |  | 1130 | 	delete package;
 | 
        
           |  |  | 1131 | 	return NULL;
 | 
        
           |  |  | 1132 | }
 | 
        
           |  |  | 1133 |   | 
        
           |  |  | 1134 | bool CPackages::OpenMultiPackage ( CyString file, CLinkList<CBaseFile> *packageList, int *error, CProgressInfo *progress )
 | 
        
           |  |  | 1135 | {
 | 
        
           |  |  | 1136 | 	int check = CheckOpenPackage(file, error);
 | 
        
           |  |  | 1137 | 	if ( *error == -1 )
 | 
        
           |  |  | 1138 | 		return false;
 | 
        
           |  |  | 1139 |   | 
        
           |  |  | 1140 | 	if ( check != SPKFILE_MULTI )
 | 
        
           |  |  | 1141 | 	{
 | 
        
           |  |  | 1142 | 		*error = INSTALLERR_NOMULTI;
 | 
        
           |  |  | 1143 | 		return false;
 | 
        
           |  |  | 1144 | 	}
 | 
        
           |  |  | 1145 |   | 
        
           |  |  | 1146 | 	*error = INSTALLERR_NONE;
 | 
        
           |  |  | 1147 |   | 
        
           |  |  | 1148 | 	CMultiSpkFile *package = new CMultiSpkFile;
 | 
        
           |  |  | 1149 |   | 
        
           |  |  | 1150 | 	bool ret = false;
 | 
        
           |  |  | 1151 | 	if ( package->ReadFile(file, true) )
 | 
        
           |  |  | 1152 | 	{
 | 
        
           |  |  | 1153 | 		if ( package->ReadAllPackages(SPKREAD_ALL, packageList) )
 | 
        
           |  |  | 1154 | 		{
 | 
        
           |  |  | 1155 | 			for ( CListNode<CBaseFile> *node = packageList->Front(); node; node = node->next() )
 | 
        
           |  |  | 1156 | 				this->ConvertOldPackage(node->Data());
 | 
        
           |  |  | 1157 |   | 
        
           |  |  | 1158 |   | 
        
           |  |  | 1159 | 			ret = true;
 | 
        
           |  |  | 1160 | 		}
 | 
        
           |  |  | 1161 | 	}
 | 
        
           |  |  | 1162 |   | 
        
           |  |  | 1163 | 	delete package;
 | 
        
           |  |  | 1164 |   | 
        
           |  |  | 1165 | 	return ret;
 | 
        
           |  |  | 1166 | }
 | 
        
           |  |  | 1167 |   | 
        
           |  |  | 1168 | int CPackages::PrepareMultiPackage ( CyString file, CLinkList<CBaseFile> *errorPackageList, int *error, CProgressInfo *progress )
 | 
        
           |  |  | 1169 | {
 | 
        
           |  |  | 1170 | 	int check = CheckOpenPackage(file, error);
 | 
        
           |  |  | 1171 | 	if ( *error == -1 )
 | 
        
           |  |  | 1172 | 		return 0;
 | 
        
           |  |  | 1173 |   | 
        
           |  |  | 1174 | 	if ( check != SPKFILE_MULTI )
 | 
        
           |  |  | 1175 | 	{
 | 
        
           |  |  | 1176 | 		*error = INSTALLERR_NOMULTI;
 | 
        
           |  |  | 1177 | 		return 0;
 | 
        
           |  |  | 1178 | 	}
 | 
        
           |  |  | 1179 |   | 
        
           |  |  | 1180 | 	*error = INSTALLERR_NONE;
 | 
        
           |  |  | 1181 |   | 
        
           |  |  | 1182 | 	CMultiSpkFile *package = new CMultiSpkFile;
 | 
        
           |  |  | 1183 |   | 
        
           |  |  | 1184 | 	int count = 0;
 | 
        
           |  |  | 1185 | 	if ( package->ReadFile(file, true) )
 | 
        
           |  |  | 1186 | 	{
 | 
        
           |  |  | 1187 | 		CLinkList<CBaseFile> packageList;
 | 
        
           |  |  | 1188 | 		if ( package->ReadAllPackages(SPKREAD_ALL, &packageList) )
 | 
        
           |  |  | 1189 | 		{
 | 
        
           |  |  | 1190 | 			for ( CListNode<CBaseFile> *node = packageList.Front(); node; node = node->next() )
 | 
        
           |  |  | 1191 | 			{
 | 
        
           |  |  | 1192 | 				CBaseFile *p = node->Data();
 | 
        
           |  |  | 1193 | 				this->ConvertOldPackage(p);
 | 
        
           |  |  | 1194 | 				int error = this->PrepareInstallPackage(p);
 | 
        
           |  |  | 1195 | 				if ( error )
 | 
        
           |  |  | 1196 | 				{
 | 
        
           |  |  | 1197 | 					node->Data()->SetLoadError(error);
 | 
        
           |  |  | 1198 | 					errorPackageList->push_back(p);
 | 
        
           |  |  | 1199 | 				}
 | 
        
           |  |  | 1200 | 				else
 | 
        
           |  |  | 1201 | 					++count;
 | 
        
           |  |  | 1202 | 			}
 | 
        
           |  |  | 1203 | 		}
 | 
        
           |  |  | 1204 | 		packageList.clear();
 | 
        
           |  |  | 1205 | 	}
 | 
        
           |  |  | 1206 |   | 
        
           |  |  | 1207 | 	for ( SMultiSpkFile *ms = package->GetFileList()->First(); ms; ms = package->GetFileList()->Next() )
 | 
        
           |  |  | 1208 | 		ms->pFile = NULL;
 | 
        
           |  |  | 1209 | 	delete package;
 | 
        
           |  |  | 1210 |   | 
        
           |  |  | 1211 | 	return count;
 | 
        
           |  |  | 1212 | }
 | 
        
           |  |  | 1213 |   | 
        
           |  |  | 1214 | CBaseFile *CPackages::OpenPackage(CyString file, int *error, CProgressInfo *progress, int readtype, int flags)
 | 
        
           |  |  | 1215 | {
 | 
        
           |  |  | 1216 | 	int check = CheckOpenPackage(file, error);
 | 
        
           |  |  | 1217 | 	if ( *error == -1 )
 | 
        
           |  |  | 1218 | 		return NULL;
 | 
        
           |  |  | 1219 |   | 
        
           |  |  | 1220 | 	CBaseFile *installFile = 0;
 | 
        
           |  |  | 1221 |   | 
        
           |  |  | 1222 | 	if ( progress )
 | 
        
           |  |  | 1223 | 		progress->DoHalf();
 | 
        
           |  |  | 1224 |   | 
        
           |  |  | 1225 | 	switch (check)
 | 
        
           |  |  | 1226 | 	{
 | 
        
           |  |  | 1227 | 		case SPKFILE_OLD:
 | 
        
           |  |  | 1228 | 			*error = INSTALLERR_OLD;
 | 
        
           |  |  | 1229 | 			return NULL;
 | 
        
           |  |  | 1230 | 		case SPKFILE_INVALID:
 | 
        
           |  |  | 1231 | 			// convert xsp
 | 
        
           |  |  | 1232 | 			if ( CFileIO(file).CheckFileExtension("xsp") )
 | 
        
           |  |  | 1233 | 			{
 | 
        
           |  |  | 1234 | 				installFile = new CXspFile();
 | 
        
           |  |  | 1235 | 				if ( !((CXspFile *)installFile)->ConvertOld(file) )
 | 
        
           |  |  | 1236 | 				{
 | 
        
           |  |  | 1237 | 					delete installFile;
 | 
        
           |  |  | 1238 | 					return NULL;
 | 
        
           |  |  | 1239 | 				}
 | 
        
           |  |  | 1240 | 				break;
 | 
        
           |  |  | 1241 | 			}
 | 
        
           |  |  | 1242 | 			*error = INSTALLERR_INVALID;
 | 
        
           |  |  | 1243 | 			return NULL;
 | 
        
           |  |  | 1244 | 		case SPKFILE_BASE:
 | 
        
           |  |  | 1245 | 			installFile = new CBaseFile();
 | 
        
           |  |  | 1246 | 			if ( !installFile->ReadFile(file, readtype, progress) )
 | 
        
           |  |  | 1247 | 			{
 | 
        
           |  |  | 1248 | 				delete installFile;
 | 
        
           |  |  | 1249 | 				return NULL;
 | 
        
           |  |  | 1250 | 			}
 | 
        
           |  |  | 1251 | 			break;
 | 
        
           |  |  | 1252 | 		case SPKFILE_SINGLE:
 | 
        
           |  |  | 1253 | 			installFile = new CSpkFile();
 | 
        
           |  |  | 1254 | 			if ( !((CSpkFile *)installFile)->ReadFile(file, readtype, progress) )
 | 
        
           |  |  | 1255 | 			{
 | 
        
           |  |  | 1256 | 				delete installFile;
 | 
        
           |  |  | 1257 | 				return NULL;
 | 
        
           |  |  | 1258 | 			}
 | 
        
           |  |  | 1259 | 			break;
 | 
        
           |  |  | 1260 | 		case SPKFILE_MULTI:
 | 
        
           |  |  | 1261 | 			*error = INSTALLERR_NOMULTI;
 | 
        
           |  |  | 1262 | 			return NULL;
 | 
        
           |  |  | 1263 | 		case SPKFILE_SINGLESHIP:
 | 
        
           |  |  | 1264 | 			installFile = new CXspFile();
 | 
        
           |  |  | 1265 | 			if ( !((CXspFile *)installFile)->ReadFile(file, readtype, progress) )
 | 
        
           |  |  | 1266 | 			{
 | 
        
           |  |  | 1267 | 				delete installFile;
 | 
        
           |  |  | 1268 | 				return NULL;
 | 
        
           |  |  | 1269 | 			}
 | 
        
           |  |  | 1270 | 			break;
 | 
        
           |  |  | 1271 |   | 
        
           |  |  | 1272 | 		default:
 | 
        
           |  |  | 1273 | 			*error = INSTALLERR_UNKNOWN;
 | 
        
           |  |  | 1274 | 			return NULL;
 | 
        
           |  |  | 1275 | 	}
 | 
        
           |  |  | 1276 |   | 
        
           |  |  | 1277 | 	if ( progress )
 | 
        
           |  |  | 1278 | 		progress->SecondHalf();
 | 
        
           |  |  | 1279 |   | 
        
           |  |  | 1280 | 	// now uncomress all files
 | 
        
           |  |  | 1281 | 	if ( !(flags & READFLAG_NOUNCOMPRESS) )
 | 
        
           |  |  | 1282 | 		installFile->UncompressAllFiles(progress);
 | 
        
           |  |  | 1283 |   | 
        
           |  |  | 1284 | 	this->ConvertOldPackage (installFile);
 | 
        
           |  |  | 1285 |   | 
        
           |  |  | 1286 | 	return installFile;
 | 
        
           |  |  | 1287 | }
 | 
        
           |  |  | 1288 |   | 
        
           |  |  | 1289 | void CPackages::PurgeUninstallScripts(CBaseFile *package, CyStringList *errors)
 | 
        
           |  |  | 1290 | {
 | 
        
           |  |  | 1291 | 	for ( CListNode<C_File> *fNode = m_lUninstallFiles.Front(); fNode; fNode = fNode->next() )
 | 
        
           |  |  | 1292 | 	{
 | 
        
           |  |  | 1293 | 		C_File *uf = fNode->Data();
 | 
        
           |  |  | 1294 | 		// check against any script files
 | 
        
           |  |  | 1295 | 		for ( CListNode<C_File> *checkNode = package->GetFileList()->Front(); checkNode; checkNode = checkNode->next() )
 | 
        
           |  |  | 1296 | 		{
 | 
        
           |  |  | 1297 | 			C_File *checkFile = checkNode->Data();
 | 
        
           |  |  | 1298 | 			if ( !checkFile ) continue;
 | 
        
           |  |  | 1299 |   | 
        
           |  |  | 1300 | 			if ( checkFile->GetFileType() != FILETYPE_UNINSTALL && checkFile->GetFileType() != FILETYPE_SCRIPT )
 | 
        
           |  |  | 1301 | 				continue;
 | 
        
           |  |  | 1302 |   | 
        
           |  |  | 1303 | 			if ( uf->GetFilename().Compare(checkFile->GetFilename()) )
 | 
        
           |  |  | 1304 | 			{
 | 
        
           |  |  | 1305 | 				if ( RemoveUninstallFile(uf, errors) )
 | 
        
           |  |  | 1306 | 					fNode->DeleteData();
 | 
        
           |  |  | 1307 | 				break;
 | 
        
           |  |  | 1308 | 			}
 | 
        
           |  |  | 1309 | 		}
 | 
        
           |  |  | 1310 | 	}
 | 
        
           |  |  | 1311 |   | 
        
           |  |  | 1312 | 	m_lUninstallFiles.RemoveEmpty();
 | 
        
           |  |  | 1313 |   | 
        
           |  |  | 1314 | 	this->WriteData();
 | 
        
           |  |  | 1315 | }
 | 
        
           |  |  | 1316 |   | 
        
           |  |  | 1317 | int CPackages::InstallPreparedPackages(CyStringList *errors, CProgressInfo *progress, CLinkList<CBaseFile> *errored, CLinkList<CBaseFile> *installedList)
 | 
        
           |  |  | 1318 | {
 | 
        
           |  |  | 1319 | 	if ( m_lInstallList.empty() ) return false;
 | 
        
           |  |  | 1320 |   | 
        
           |  |  | 1321 | 	int installed = 0;
 | 
        
           |  |  | 1322 | 	for ( CListNode<CBaseFile> *node = m_lInstallList.Front(); node; node = node->next() )
 | 
        
           |  |  | 1323 | 	{
 | 
        
           |  |  | 1324 | 		CBaseFile *p = node->Data();
 | 
        
           |  |  | 1325 | 		if ( this->InstallPackage(p, errors, progress, !p->IsEnabled()) )
 | 
        
           |  |  | 1326 | 		{
 | 
        
           |  |  | 1327 | 			++installed;
 | 
        
           |  |  | 1328 | 			if ( installedList )
 | 
        
           |  |  | 1329 | 				installedList->push_back(p);
 | 
        
           |  |  | 1330 | 		}
 | 
        
           |  |  | 1331 | 		else if ( errored )
 | 
        
           |  |  | 1332 | 		{
 | 
        
           |  |  | 1333 | 			m_lPackages.remove(p);
 | 
        
           |  |  | 1334 | 			errored->push_back(p);
 | 
        
           |  |  | 1335 | 		}
 | 
        
           |  |  | 1336 | 	}
 | 
        
           |  |  | 1337 |   | 
        
           |  |  | 1338 | 	m_lInstallList.clear();
 | 
        
           |  |  | 1339 |   | 
        
           |  |  | 1340 | 	this->WriteData();
 | 
        
           |  |  | 1341 |   | 
        
           |  |  | 1342 | 	return installed;
 | 
        
           |  |  | 1343 | }
 | 
        
           |  |  | 1344 |   | 
        
           |  |  | 1345 | bool CPackages::InstallPackage ( CBaseFile *package, CyStringList *errors, CProgressInfo *progress, bool disabled )
 | 
        
           |  |  | 1346 | {
 | 
        
           |  |  | 1347 | 	// first check if we are installed a mod
 | 
        
           |  |  | 1348 | 	bool prevDisabled = disabled;
 | 
        
           |  |  | 1349 | 	if ( package->IsMod() && m_pEnabledMod && !m_bForceModInstall )
 | 
        
           |  |  | 1350 | 		disabled = true;
 | 
        
           |  |  | 1351 | 	// if vanilla nad package aint signed
 | 
        
           |  |  | 1352 | 	if ( m_bVanilla && !package->IsSigned() )
 | 
        
           |  |  | 1353 | 		disabled = true;
 | 
        
           |  |  | 1354 |   | 
        
           |  |  | 1355 | 	// check any depancies
 | 
        
           |  |  | 1356 | 	if ( !disabled && !this->CheckEnabledDependacy(package) )
 | 
        
           |  |  | 1357 | 		disabled = true;
 | 
        
           |  |  | 1358 |   | 
        
           |  |  | 1359 | 	// search for an old version
 | 
        
           |  |  | 1360 | 	CBaseFile *oldPackage = FindPackage(package);
 | 
        
           |  |  | 1361 | 	if ( oldPackage && oldPackage == m_pEnabledMod && disabled )
 | 
        
           |  |  | 1362 | 		disabled = prevDisabled;
 | 
        
           |  |  | 1363 |   | 
        
           |  |  | 1364 | 	// update packages must have an old package installed already (should have been checked for already)
 | 
        
           |  |  | 1365 | 	if ( package->GetType() == TYPE_SPK )
 | 
        
           |  |  | 1366 | 	{
 | 
        
           |  |  | 1367 | 		if ( ((CSpkFile *)package)->IsPackageUpdate() )
 | 
        
           |  |  | 1368 | 		{
 | 
        
           |  |  | 1369 | 			if ( !oldPackage )
 | 
        
           |  |  | 1370 | 				return false;
 | 
        
           |  |  | 1371 | 			// change any mods to temp ones
 | 
        
           |  |  | 1372 | 			for ( CListNode<C_File> *f = package->GetFileList()->Front(); f; f = f->next() )
 | 
        
           |  |  | 1373 | 			{
 | 
        
           |  |  | 1374 | 				if ( f->Data()->GetFileType() != FILETYPE_MOD )
 | 
        
           |  |  | 1375 | 					continue;
 | 
        
           |  |  | 1376 |   | 
        
           |  |  | 1377 | 				f->Data()->SetDir("temp");
 | 
        
           |  |  | 1378 | 				if ( f->Data()->IsFakePatch() )
 | 
        
           |  |  | 1379 | 					f->Data()->SetName(CyString("Fake_") + f->Data()->GetName());
 | 
        
           |  |  | 1380 | 			}
 | 
        
           |  |  | 1381 | 		}
 | 
        
           |  |  | 1382 | 	}
 | 
        
           |  |  | 1383 |   | 
        
           |  |  | 1384 | 	// no need to backup if we're disabling them
 | 
        
           |  |  | 1385 | 	if ( !disabled )
 | 
        
           |  |  | 1386 | 	{
 | 
        
           |  |  | 1387 | 		// find any uninstall files and remove them
 | 
        
           |  |  | 1388 | 		this->PurgeUninstallScripts(package, errors);
 | 
        
           |  |  | 1389 |   | 
        
           |  |  | 1390 | 		// backup any original files before installing
 | 
        
           |  |  | 1391 | 		CDirIO oDir(m_sCurrentDir + "/PluginManager/Original");
 | 
        
           |  |  | 1392 | 		for ( CListNode<C_File> *oNode = m_lOriginalFiles.Front(); oNode; oNode = oNode->next() )
 | 
        
           |  |  | 1393 | 		{
 | 
        
           |  |  | 1394 | 			C_File *of = oNode->Data();
 | 
        
           |  |  | 1395 | 			for ( CListNode<C_File> *checkNode = package->GetFileList()->Front(); checkNode; checkNode = checkNode->next() )
 | 
        
           |  |  | 1396 | 			{
 | 
        
           |  |  | 1397 | 				C_File *f = checkNode->Data();
 | 
        
           |  |  | 1398 |   | 
        
           |  |  | 1399 | 				// match the same filetype
 | 
        
           |  |  | 1400 | 				if ( of->GetFileType() != f->GetFileType() )
 | 
        
           |  |  | 1401 | 					continue;
 | 
        
           |  |  | 1402 |   | 
        
           |  |  | 1403 | 				// same file
 | 
        
           |  |  | 1404 | 				if ( of->GetFilename().Compare(f->GetFilename()) )
 | 
        
           |  |  | 1405 | 				{
 | 
        
           |  |  | 1406 | 					// check if original file already exists (assume already backed up)
 | 
        
           |  |  | 1407 | 					if ( !BackupOriginalFile(of, errors) )
 | 
        
           |  |  | 1408 | 						continue;
 | 
        
           |  |  | 1409 | 					break;
 | 
        
           |  |  | 1410 | 				}
 | 
        
           |  |  | 1411 | 			}
 | 
        
           |  |  | 1412 | 		}
 | 
        
           |  |  | 1413 | 	}
 | 
        
           |  |  | 1414 |   | 
        
           |  |  | 1415 | 	// install all the files
 | 
        
           |  |  | 1416 | 	if ( oldPackage )
 | 
        
           |  |  | 1417 | 	{
 | 
        
           |  |  | 1418 | 		CLinkList<CBaseFile> excludeList;
 | 
        
           |  |  | 1419 | 		excludeList.push_back(oldPackage);
 | 
        
           |  |  | 1420 | 		this->UpdateUsedFiles(&excludeList, true);
 | 
        
           |  |  | 1421 | 	}
 | 
        
           |  |  | 1422 | 	else
 | 
        
           |  |  | 1423 | 		this->UpdateUsedFiles(0, true);
 | 
        
           |  |  | 1424 |   | 
        
           |  |  | 1425 | 	package->ReadAllFilesToMemory();
 | 
        
           |  |  | 1426 | 	if ( !package->InstallFiles (m_sCurrentDir, progress, &m_lFiles, errors, !disabled, this) )
 | 
        
           |  |  | 1427 | 	{
 | 
        
           |  |  | 1428 | 		// TODO: clear up installed files
 | 
        
           |  |  | 1429 | 		return false;
 | 
        
           |  |  | 1430 | 	}
 | 
        
           |  |  | 1431 |   | 
        
           |  |  | 1432 | 	// if we're installing an addon, lets use the fake patch method for object files
 | 
        
           |  |  | 1433 | 	if ( m_iGameFlags & EXEFLAG_ADDON ) {
 | 
        
           |  |  | 1434 | 		CCatFile cat;
 | 
        
           |  |  | 1435 | 		if ( CCatFile::Opened(cat.Open(m_sCurrentDir + "/PluginManager/PlugMan_Fake.cat", this->GetAddonDir(), CATREAD_DAT)) ) {
 | 
        
           |  |  | 1436 | 			for ( CListNode<C_File> *f = package->GetFileList()->Front(); f; f = f->next() ) {
 | 
        
           |  |  | 1437 | 				if ( f->Data()->GetFileType() != FILETYPE_SHIPSCENE && f->Data()->GetFileType() != FILETYPE_COCKPITSCENE && f->Data()->GetFileType() != FILETYPE_SHIPMODEL && f->Data()->GetFileType() != FILETYPE_SHIPOTHER )
 | 
        
           |  |  | 1438 | 					continue;
 | 
        
           |  |  | 1439 | 				if ( CCatFile::IsAddonDir(f->Data()->GetNameDirectory(package)) )
 | 
        
           |  |  | 1440 | 					continue;
 | 
        
           |  |  | 1441 | 				if ( cat.AppendFile(f->Data()->GetFilePointer(), f->Data()->GetNameDirectory(package), true, (m_iGameFlags & EXEFLAG_NOXOR) ? false : true) ) {
 | 
        
           |  |  | 1442 | 					CFileIO(f->Data()->GetFilePointer()).Remove();
 | 
        
           |  |  | 1443 | 					f->Data()->SetFilename(m_sCurrentDir + "/PluginManager/PlugMan_Fake.cat::" + f->Data()->GetNameDirectory(package));
 | 
        
           |  |  | 1444 | 				}
 | 
        
           |  |  | 1445 | 			}
 | 
        
           | 14 | cycrow | 1446 |   | 
        
           | 1 | cycrow | 1447 | 		}
 | 
        
           |  |  | 1448 | 	}
 | 
        
           |  |  | 1449 |   | 
        
           |  |  | 1450 | 	bool shuffle = false;
 | 
        
           |  |  | 1451 |   | 
        
           |  |  | 1452 | 	// merge the update into the old package
 | 
        
           |  |  | 1453 | 	bool dontAdd = false;
 | 
        
           |  |  | 1454 | 	if ( package->GetType() == TYPE_SPK )
 | 
        
           |  |  | 1455 | 	{
 | 
        
           |  |  | 1456 | 		if ( ((CSpkFile *)package)->IsPackageUpdate() )
 | 
        
           |  |  | 1457 | 		{
 | 
        
           |  |  | 1458 | 			// now copy any files from a mod
 | 
        
           |  |  | 1459 | 			for ( CListNode<C_File> *f = package->GetFileList()->Front(); f; f = f->next() )
 | 
        
           |  |  | 1460 | 			{
 | 
        
           |  |  | 1461 | 				if ( !f->Data() )
 | 
        
           |  |  | 1462 | 					continue;
 | 
        
           |  |  | 1463 | 				if ( f->Data()->GetFileType() != FILETYPE_MOD )
 | 
        
           |  |  | 1464 | 					continue;
 | 
        
           |  |  | 1465 | 				// we only need the cat file
 | 
        
           |  |  | 1466 | 				if ( !f->Data()->CheckFileExt("cat") )
 | 
        
           |  |  | 1467 | 					continue;
 | 
        
           |  |  | 1468 |   | 
        
           |  |  | 1469 | 				// if fake patch, find first fake patch in package
 | 
        
           |  |  | 1470 | 				C_File *findMatching = NULL;
 | 
        
           |  |  | 1471 | 				if ( f->Data()->GetBaseName().Left(5).Compare("fake_") )
 | 
        
           |  |  | 1472 | 				{
 | 
        
           |  |  | 1473 | 					for ( CListNode<C_File> *node = oldPackage->GetFileList()->Front(); node; node = node->next() )
 | 
        
           |  |  | 1474 | 					{
 | 
        
           |  |  | 1475 | 						if ( !node->Data() )
 | 
        
           |  |  | 1476 | 							continue;
 | 
        
           |  |  | 1477 | 						if ( node->Data()->GetFileType() != FILETYPE_MOD )
 | 
        
           |  |  | 1478 | 							continue;
 | 
        
           |  |  | 1479 | 						// we only need the cat file
 | 
        
           |  |  | 1480 | 						if ( !node->Data()->CheckFileExt("cat") )
 | 
        
           |  |  | 1481 | 							continue;
 | 
        
           |  |  | 1482 | 						if ( !node->Data()->IsFakePatch() )
 | 
        
           |  |  | 1483 | 							continue;
 | 
        
           |  |  | 1484 |   | 
        
           |  |  | 1485 | 						findMatching = node->Data();
 | 
        
           |  |  | 1486 | 						break;
 | 
        
           |  |  | 1487 | 					}
 | 
        
           |  |  | 1488 | 				}
 | 
        
           |  |  | 1489 | 				// otherwise, just add to the mod of the same name
 | 
        
           |  |  | 1490 | 				else
 | 
        
           |  |  | 1491 | 				{
 | 
        
           |  |  | 1492 | 					for ( CListNode<C_File> *node = oldPackage->GetFileList()->Front(); node; node = node->next() )
 | 
        
           |  |  | 1493 | 					{
 | 
        
           |  |  | 1494 | 						if ( !node->Data() )
 | 
        
           |  |  | 1495 | 							continue;
 | 
        
           |  |  | 1496 | 						if ( node->Data()->GetFileType() != FILETYPE_MOD )
 | 
        
           |  |  | 1497 | 							continue;
 | 
        
           |  |  | 1498 | 						// we only need the cat file
 | 
        
           |  |  | 1499 | 						if ( !node->Data()->CheckFileExt("cat") )
 | 
        
           |  |  | 1500 | 							continue;
 | 
        
           |  |  | 1501 |   | 
        
           |  |  | 1502 | 						if ( node->Data()->GetName().Compare(f->Data()->GetName()) )
 | 
        
           |  |  | 1503 | 						{
 | 
        
           |  |  | 1504 | 							findMatching = node->Data();
 | 
        
           |  |  | 1505 | 							break;
 | 
        
           |  |  | 1506 | 						}
 | 
        
           |  |  | 1507 | 					}
 | 
        
           |  |  | 1508 | 				}
 | 
        
           |  |  | 1509 |   | 
        
           |  |  | 1510 | 				if ( findMatching )
 | 
        
           |  |  | 1511 | 				{
 | 
        
           |  |  | 1512 | 					// copy accross all mods
 | 
        
           |  |  | 1513 | 					CCatFile catTo, catFrom;
 | 
        
           |  |  | 1514 | 					if ( catFrom.Open(f->Data()->GetFilePointer(), this->GetAddonDir(), CATREAD_CATDECRYPT, false) == CATERR_NONE )
 | 
        
           |  |  | 1515 | 					{
 | 
        
           |  |  | 1516 | 						if ( catTo.Open(findMatching->GetFilePointer(), this->GetAddonDir(), CATREAD_CATDECRYPT, false) == CATERR_NONE )
 | 
        
           |  |  | 1517 | 						{
 | 
        
           |  |  | 1518 | 							for ( int i = 0; i < catFrom.GetNumFiles(); i++ )
 | 
        
           |  |  | 1519 | 							{
 | 
        
           |  |  | 1520 | 								SInCatFile *c = catFrom.GetFile(i);								 
 | 
        
           |  |  | 1521 | 								catTo.AppendFile(f->Data()->GetFilePointer() + "::" + c->sFile, c->sFile);
 | 
        
           |  |  | 1522 | 							}
 | 
        
           |  |  | 1523 | 						}
 | 
        
           |  |  | 1524 | 					}
 | 
        
           |  |  | 1525 |   | 
        
           |  |  | 1526 | 					// now remove the files
 | 
        
           |  |  | 1527 | 					C_File *m = package->FindMatchingMod(f->Data());
 | 
        
           |  |  | 1528 | 					RemoveFile(f->Data(), errors);
 | 
        
           |  |  | 1529 | 					m_lFiles.remove(f->Data());
 | 
        
           |  |  | 1530 | 					f->ChangeData(NULL);
 | 
        
           |  |  | 1531 | 					if ( m )
 | 
        
           |  |  | 1532 | 					{
 | 
        
           |  |  | 1533 | 						int pos = package->GetFileList()->FindPos(m);
 | 
        
           |  |  | 1534 | 						RemoveFile(m, errors);
 | 
        
           |  |  | 1535 | 						m_lFiles.remove(m);
 | 
        
           |  |  | 1536 | 						if ( pos != -1 )
 | 
        
           |  |  | 1537 | 							package->GetFileList()->GetNode(pos)->ChangeData(NULL);
 | 
        
           |  |  | 1538 | 					}
 | 
        
           |  |  | 1539 | 				}
 | 
        
           |  |  | 1540 | 				// no matching file, then we shall just renaming back
 | 
        
           |  |  | 1541 | 				else
 | 
        
           |  |  | 1542 | 				{
 | 
        
           |  |  | 1543 | 					if ( f->Data()->GetBaseName().Left(5).Compare("fake_") )
 | 
        
           |  |  | 1544 | 					{
 | 
        
           |  |  | 1545 | 						shuffle = true;
 | 
        
           |  |  | 1546 | 						C_File *match = package->FindMatchingMod(f->Data());
 | 
        
           |  |  | 1547 | 						CyString next = CyString::Number(this->FindNextFakePatch()).PadNumber(2);
 | 
        
           |  |  | 1548 |   | 
        
           |  |  | 1549 | 						CyString oldFilePointer = f->Data()->GetFilePointer();
 | 
        
           |  |  | 1550 | 						f->Data()->SetDir("");
 | 
        
           |  |  | 1551 | 						f->Data()->ChangeBaseName(next);
 | 
        
           |  |  | 1552 | 						if ( CFileIO(oldFilePointer).Rename(m_sCurrentDir + "/" + f->Data()->GetNameDirectory(package)) )
 | 
        
           |  |  | 1553 | 							f->Data()->SetFilename(m_sCurrentDir + "/" + f->Data()->GetNameDirectory(package));
 | 
        
           |  |  | 1554 |   | 
        
           |  |  | 1555 | 						if ( match )
 | 
        
           |  |  | 1556 | 						{
 | 
        
           |  |  | 1557 | 							CyString oldFilePointer = match->GetFilePointer();
 | 
        
           |  |  | 1558 | 							match->SetDir("");
 | 
        
           |  |  | 1559 | 							match->ChangeBaseName(next);
 | 
        
           |  |  | 1560 | 							if ( CFileIO(oldFilePointer).Rename(m_sCurrentDir + "/" + match->GetNameDirectory(package)) )
 | 
        
           |  |  | 1561 | 								match->SetFilename(m_sCurrentDir + "/" + match->GetNameDirectory(package));
 | 
        
           |  |  | 1562 | 						}
 | 
        
           |  |  | 1563 | 					}
 | 
        
           |  |  | 1564 | 					else
 | 
        
           |  |  | 1565 | 					{
 | 
        
           |  |  | 1566 | 						C_File *match = package->FindMatchingMod(f->Data());
 | 
        
           |  |  | 1567 |   | 
        
           |  |  | 1568 | 						f->Data()->SetDir("");
 | 
        
           |  |  | 1569 | 						if ( CFileIO(f->Data()->GetFilePointer()).Rename(m_sCurrentDir + "/" + f->Data()->GetNameDirectory(package)) )
 | 
        
           |  |  | 1570 | 							f->Data()->SetFilename(m_sCurrentDir + "/" + f->Data()->GetNameDirectory(package));
 | 
        
           |  |  | 1571 | 						if ( match )
 | 
        
           |  |  | 1572 | 						{
 | 
        
           |  |  | 1573 | 							match->SetDir("");
 | 
        
           |  |  | 1574 | 							if ( CFileIO(match->GetFilePointer()).Rename(m_sCurrentDir + "/" + match->GetNameDirectory(package)) )
 | 
        
           |  |  | 1575 | 								match->SetFilename(m_sCurrentDir + "/" + match->GetNameDirectory(package));
 | 
        
           |  |  | 1576 | 						}
 | 
        
           |  |  | 1577 | 					}
 | 
        
           |  |  | 1578 | 				}
 | 
        
           |  |  | 1579 | 			}
 | 
        
           |  |  | 1580 |   | 
        
           |  |  | 1581 | 			package->GetFileList()->RemoveEmpty();
 | 
        
           |  |  | 1582 | 			((CSpkFile *)oldPackage)->MergePackage(package);
 | 
        
           |  |  | 1583 | 			delete package;
 | 
        
           |  |  | 1584 | 			package = oldPackage;
 | 
        
           |  |  | 1585 | 			oldPackage = false;
 | 
        
           |  |  | 1586 | 			dontAdd = true;
 | 
        
           |  |  | 1587 |   | 
        
           |  |  | 1588 | 			CDirIO(m_sCurrentDir).RemoveDir("temp");
 | 
        
           |  |  | 1589 | 			CDirIO(m_sCurrentDir).RemoveDir("Mods/temp");
 | 
        
           |  |  | 1590 | 		}
 | 
        
           |  |  | 1591 | 	}
 | 
        
           |  |  | 1592 |   | 
        
           |  |  | 1593 | 	// if theres an icon, write it
 | 
        
           |  |  | 1594 | 	if ( package->GetIcon() )
 | 
        
           |  |  | 1595 | 	{
 | 
        
           |  |  | 1596 | 		C_File *icon = package->GetIcon();
 | 
        
           |  |  | 1597 | 		if ( !icon->GetData() || !icon->GetDataSize() )
 | 
        
           |  |  | 1598 | 			package->SetIcon(NULL, "");
 | 
        
           |  |  | 1599 | 		else
 | 
        
           |  |  | 1600 | 		{
 | 
        
           |  |  | 1601 | 			CDirIO Dir(m_sCurrentDir);
 | 
        
           |  |  | 1602 | 			bool ready = true;
 | 
        
           |  |  | 1603 | 			if ( !Dir.Exists("PluginManager") )
 | 
        
           |  |  | 1604 | 			{
 | 
        
           |  |  | 1605 | 				if ( !Dir.Create("PluginManager") )
 | 
        
           |  |  | 1606 | 					ready = false;
 | 
        
           |  |  | 1607 | 			}
 | 
        
           |  |  | 1608 | 			if ( ready && !Dir.Exists("PluginManager/Icons") )
 | 
        
           |  |  | 1609 | 			{
 | 
        
           |  |  | 1610 | 				if ( !Dir.Create("PluginManager/Icons") )
 | 
        
           |  |  | 1611 | 					ready = false;
 | 
        
           |  |  | 1612 | 			}
 | 
        
           |  |  | 1613 |   | 
        
           |  |  | 1614 | 			if ( ready )
 | 
        
           |  |  | 1615 | 			{
 | 
        
           |  |  | 1616 | 				if ( !icon->UncompressData() )
 | 
        
           |  |  | 1617 | 					package->SetIcon(NULL, "");
 | 
        
           |  |  | 1618 | 				else
 | 
        
           |  |  | 1619 | 				{
 | 
        
           |  |  | 1620 | 					CFileIO iconFile(m_sCurrentDir + "/PluginManager/Icons/" + package->GetAuthor() + "_" + package->GetName() + "." + package->GetIconExt());
 | 
        
           |  |  | 1621 | 					if ( iconFile.WriteData((const char *)icon->GetData(), icon->GetDataSize()) )
 | 
        
           |  |  | 1622 | 					{
 | 
        
           |  |  | 1623 | 						icon->SetFilename(package->GetAuthor() + "_" + package->GetName() + "." + package->GetIconExt());
 | 
        
           |  |  | 1624 | 						icon->SetFullDir(m_sCurrentDir + "/PluginManager/Icons");
 | 
        
           |  |  | 1625 | 					}
 | 
        
           |  |  | 1626 | 					else
 | 
        
           |  |  | 1627 | 						package->SetIcon(NULL, "");
 | 
        
           |  |  | 1628 | 				}
 | 
        
           |  |  | 1629 | 			}
 | 
        
           |  |  | 1630 |   | 
        
           |  |  | 1631 | 			if ( package->GetIcon() )
 | 
        
           |  |  | 1632 | 				package->GetIcon()->DeleteData();
 | 
        
           |  |  | 1633 | 		}
 | 
        
           |  |  | 1634 | 	}
 | 
        
           |  |  | 1635 |   | 
        
           |  |  | 1636 | 	// remove all data
 | 
        
           |  |  | 1637 | 	package->ClearFileData();
 | 
        
           |  |  | 1638 |   | 
        
           |  |  | 1639 | 	// add to list
 | 
        
           |  |  | 1640 | 	if ( !dontAdd )
 | 
        
           |  |  | 1641 | 	{
 | 
        
           |  |  | 1642 | 		if ( oldPackage )
 | 
        
           |  |  | 1643 | 		{
 | 
        
           |  |  | 1644 | 			m_lPackages.insert(oldPackage, package);
 | 
        
           |  |  | 1645 | 			m_lPackages.remove(oldPackage, false);
 | 
        
           |  |  | 1646 | 		}
 | 
        
           |  |  | 1647 | 		else
 | 
        
           |  |  | 1648 | 			m_lPackages.push_back (package);
 | 
        
           |  |  | 1649 | 	}
 | 
        
           |  |  | 1650 |   | 
        
           |  |  | 1651 | 	UpdateUsedFiles();
 | 
        
           |  |  | 1652 |   | 
        
           |  |  | 1653 | 	if ( disabled )
 | 
        
           |  |  | 1654 | 		package->SetEnabled(false);
 | 
        
           |  |  | 1655 |   | 
        
           |  |  | 1656 | 	// remove any files no longer used by old package
 | 
        
           |  |  | 1657 | 	if ( oldPackage )
 | 
        
           |  |  | 1658 | 	{
 | 
        
           |  |  | 1659 | 		CListNode<C_File> *fnode = oldPackage->GetFileList()->Front();
 | 
        
           |  |  | 1660 | 		while ( fnode )
 | 
        
           |  |  | 1661 | 		{
 | 
        
           |  |  | 1662 | 			C_File *f = fnode->Data();
 | 
        
           |  |  | 1663 |   | 
        
           |  |  | 1664 | 			// no longer used
 | 
        
           |  |  | 1665 | 			if ( !f->GetUsed() )
 | 
        
           |  |  | 1666 | 			{
 | 
        
           |  |  | 1667 | 				// remove from file list
 | 
        
           |  |  | 1668 | 				m_lFiles.remove(f, false);
 | 
        
           |  |  | 1669 |   | 
        
           |  |  | 1670 | 				// remove from hard drive
 | 
        
           |  |  | 1671 | 				if ( RemoveFile(f, errors) )
 | 
        
           |  |  | 1672 | 				{
 | 
        
           |  |  | 1673 | 					// if a fake patch, we need to shufle
 | 
        
           |  |  | 1674 | 					if ( f->IsFakePatch() )
 | 
        
           |  |  | 1675 | 						shuffle = true;
 | 
        
           |  |  | 1676 | 					else if ( f->IsAutoTextFile() )
 | 
        
           |  |  | 1677 | 						shuffle = true;
 | 
        
           |  |  | 1678 | 				}
 | 
        
           |  |  | 1679 | 			}
 | 
        
           |  |  | 1680 |   | 
        
           |  |  | 1681 | 			fnode = fnode->next();
 | 
        
           |  |  | 1682 | 		}
 | 
        
           |  |  | 1683 |   | 
        
           |  |  | 1684 | 	}
 | 
        
           |  |  | 1685 |   | 
        
           |  |  | 1686 | 	if ( shuffle )
 | 
        
           |  |  | 1687 | 	{
 | 
        
           |  |  | 1688 | 		ShuffleFakePatches(errors);
 | 
        
           |  |  | 1689 | 		ShuffleTextFiles(errors);
 | 
        
           |  |  | 1690 | 	}
 | 
        
           |  |  | 1691 |   | 
        
           |  |  | 1692 | 	// now we need to link any child/parent packages
 | 
        
           |  |  | 1693 | 	if ( package->GetType() == TYPE_SPK )
 | 
        
           |  |  | 1694 | 	{
 | 
        
           |  |  | 1695 | 		CSpkFile *spk = (CSpkFile *)package;
 | 
        
           |  |  | 1696 | 		if ( spk->IsAnotherMod() )
 | 
        
           |  |  | 1697 | 			spk->SetParent((CSpkFile *)FindSpkPackage(spk->GetOtherName(), spk->GetOtherAuthor()));
 | 
        
           |  |  | 1698 | 	}
 | 
        
           |  |  | 1699 |   | 
        
           |  |  | 1700 | 	// store enabled mod
 | 
        
           |  |  | 1701 | 	if ( package->IsMod() && !disabled )
 | 
        
           |  |  | 1702 | 		m_pEnabledMod = package;
 | 
        
           |  |  | 1703 |   | 
        
           |  |  | 1704 | 	m_bRemoveDir = true;
 | 
        
           |  |  | 1705 |   | 
        
           |  |  | 1706 | 	this->WriteData();
 | 
        
           |  |  | 1707 |   | 
        
           |  |  | 1708 | 	return true;
 | 
        
           |  |  | 1709 | }
 | 
        
           |  |  | 1710 |   | 
        
           |  |  | 1711 | bool CPackages::UninstallPreparedPackages(CyStringList *errors, CProgressInfo *progress, CLinkList<CBaseFile> *uninstalledPackages, CLinkList<CBaseFile> *disabledPackages)
 | 
        
           |  |  | 1712 | {
 | 
        
           |  |  | 1713 | 	if ( m_lInstallList.empty() ) return false;
 | 
        
           |  |  | 1714 |   | 
        
           |  |  | 1715 | 	// update the used status, excluding all packages we are about to remove
 | 
        
           |  |  | 1716 | 	UpdateUsedFiles(&m_lInstallList);
 | 
        
           |  |  | 1717 |   | 
        
           |  |  | 1718 | 	CyStringList removeDirs;
 | 
        
           |  |  | 1719 | 	CLinkList<C_File> uninstallFiles;
 | 
        
           |  |  | 1720 | 	CLinkList<C_File> fileList;
 | 
        
           |  |  | 1721 | 	bool readme = false, original = false, shuffle = false;
 | 
        
           |  |  | 1722 |   | 
        
           |  |  | 1723 | 	// find all files that need to be removed
 | 
        
           |  |  | 1724 | 	int maxFiles = 0;
 | 
        
           |  |  | 1725 | 	for ( CListNode<CBaseFile> *node = m_lInstallList.Front(); node; node = node->next() )
 | 
        
           |  |  | 1726 | 	{
 | 
        
           |  |  | 1727 | 		CBaseFile *p = node->Data();
 | 
        
           |  |  | 1728 | 		maxFiles += this->GetAllPackageFiles(p, &fileList, true);
 | 
        
           |  |  | 1729 |   | 
        
           |  |  | 1730 | 		// disable any dependants
 | 
        
           |  |  | 1731 | 		if ( p->GetType() == TYPE_SPK && ((CSpkFile *)p)->IsLibrary() )
 | 
        
           |  |  | 1732 | 		{
 | 
        
           |  |  | 1733 | 			CLinkList<CBaseFile> depList;
 | 
        
           |  |  | 1734 | 			if ( this->GetDependacyList(p, &depList) )
 | 
        
           |  |  | 1735 | 			{
 | 
        
           |  |  | 1736 | 				for ( CBaseFile *depP = depList.First(); depP; depP = depList.Next() )
 | 
        
           |  |  | 1737 | 				{
 | 
        
           |  |  | 1738 | 					if ( depP->IsEnabled() )
 | 
        
           |  |  | 1739 | 						this->PrepareDisablePackage(depP);
 | 
        
           |  |  | 1740 | 				}
 | 
        
           |  |  | 1741 |   | 
        
           |  |  | 1742 | 				if ( m_lDisableList.size() )
 | 
        
           |  |  | 1743 | 					this->DisablePreparedPackages(errors, progress, disabledPackages);
 | 
        
           |  |  | 1744 | 			}
 | 
        
           |  |  | 1745 | 		}
 | 
        
           |  |  | 1746 | 	}
 | 
        
           |  |  | 1747 |   | 
        
           |  |  | 1748 | 	// interate through all the files in the package
 | 
        
           |  |  | 1749 | 	int fileCount = 0;
 | 
        
           |  |  | 1750 | 	for ( CListNode<C_File> *node = fileList.Front(); node; node = node->next() )
 | 
        
           |  |  | 1751 | 	{
 | 
        
           |  |  | 1752 | 		C_File *f = node->Data();
 | 
        
           |  |  | 1753 |   | 
        
           |  |  | 1754 | 		// display progress if needed
 | 
        
           |  |  | 1755 | 		if ( progress )
 | 
        
           |  |  | 1756 | 		{
 | 
        
           |  |  | 1757 | 			progress->UpdateProgress(fileCount++, maxFiles);
 | 
        
           |  |  | 1758 | 			progress->UpdateFile(f);
 | 
        
           |  |  | 1759 | 		}
 | 
        
           |  |  | 1760 |   | 
        
           |  |  | 1761 | 		// skip uninstall files
 | 
        
           |  |  | 1762 | 		if ( f->GetFileType() == FILETYPE_UNINSTALL )
 | 
        
           |  |  | 1763 | 		{
 | 
        
           |  |  | 1764 | 			uninstallFiles.push_back(f);
 | 
        
           |  |  | 1765 | 			continue;
 | 
        
           |  |  | 1766 | 		}
 | 
        
           |  |  | 1767 |   | 
        
           |  |  | 1768 | 		// only delete files that are not used
 | 
        
           |  |  | 1769 | 		// if its a shared file, we skip it
 | 
        
           |  |  | 1770 | 		if ( f->GetUsed() || f->IsShared() )
 | 
        
           |  |  | 1771 | 			continue;
 | 
        
           |  |  | 1772 |   | 
        
           |  |  | 1773 | 		if ( f->GetFileType() == FILETYPE_README )
 | 
        
           |  |  | 1774 | 			readme = true;
 | 
        
           |  |  | 1775 | 		else if ( f->GetFileType() == FILETYPE_UNINSTALL || f->GetFileType() == FILETYPE_MAP || f->GetFileType() == FILETYPE_SOUND || f->GetFileType() == FILETYPE_EXTRA || f->GetFileType() == FILETYPE_SHIPSCENE || f->GetFileType() == FILETYPE_COCKPITSCENE || f->GetFileType() == FILETYPE_SHIPOTHER || f->GetFileType() == FILETYPE_SHIPMODEL || f->GetFileType() == FILETYPE_ADVERT )
 | 
        
           |  |  | 1776 | 		{
 | 
        
           |  |  | 1777 | 			CyString dir = f->GetDirectory(NULL);
 | 
        
           |  |  | 1778 | 			removeDirs.PushBack(dir, true);
 | 
        
           |  |  | 1779 | 			dir = dir.FindReplace("\\", "/");
 | 
        
           |  |  | 1780 | 			if ( dir.IsIn("/") )
 | 
        
           |  |  | 1781 | 			{
 | 
        
           |  |  | 1782 | 				for ( int i = dir.NumToken("/"); i; i-- )
 | 
        
           |  |  | 1783 | 				{
 | 
        
           |  |  | 1784 | 					CyString remDir = dir.GetToken("/", 1, i);
 | 
        
           |  |  | 1785 | 					removeDirs.PushBack(remDir, true);
 | 
        
           |  |  | 1786 | 				}
 | 
        
           |  |  | 1787 | 			}
 | 
        
           |  |  | 1788 | 		}
 | 
        
           |  |  | 1789 |   | 
        
           |  |  | 1790 | 		if ( f->GetFileType() == FILETYPE_EXTRA && f->GetDir().Left(6).lower() == "extras" )
 | 
        
           |  |  | 1791 | 			removeDirs.PushBack("Extras", true);
 | 
        
           |  |  | 1792 |   | 
        
           |  |  | 1793 | 		if ( RemoveFile(f, errors) )
 | 
        
           |  |  | 1794 | 		{
 | 
        
           |  |  | 1795 | 			// check if its an original file and restore
 | 
        
           |  |  | 1796 | 			if ( IsOriginalFile(f) )
 | 
        
           |  |  | 1797 | 			{
 | 
        
           |  |  | 1798 | 				CFileIO of(m_sCurrentDir + "/PluginManager/Original/" + f->GetNameDirectory(NULL));
 | 
        
           |  |  | 1799 | 				if ( of.Exists() )
 | 
        
           |  |  | 1800 | 				{
 | 
        
           |  |  | 1801 | 					original = true;
 | 
        
           |  |  | 1802 | 					if ( of.Rename(m_sCurrentDir + "/" + f->GetNameDirectory(NULL)) )
 | 
        
           |  |  | 1803 | 						this->AddLogEntry(SPKINSTALL_ORIGINAL_RESTORE, f->GetNameDirectory(NULL), errors);
 | 
        
           |  |  | 1804 | 					else
 | 
        
           |  |  | 1805 | 						this->AddLogEntry(SPKINSTALL_ORIGINAL_RESTORE_FAIL, f->GetNameDirectory(NULL), errors);
 | 
        
           |  |  | 1806 | 				}
 | 
        
           |  |  | 1807 | 			}
 | 
        
           |  |  | 1808 | 		}
 | 
        
           |  |  | 1809 | 		else // problem removeing (try when the program closes)
 | 
        
           |  |  | 1810 | 			m_lNonRemovedFiles.PushBack(f->GetFilePointer());
 | 
        
           |  |  | 1811 |   | 
        
           |  |  | 1812 | 		// check for fake patchs
 | 
        
           |  |  | 1813 | 		if ( f->IsFakePatch() )
 | 
        
           |  |  | 1814 | 			shuffle = true;
 | 
        
           |  |  | 1815 | 		else if ( f->IsAutoTextFile() )
 | 
        
           |  |  | 1816 | 			shuffle = true;
 | 
        
           |  |  | 1817 |   | 
        
           |  |  | 1818 | 		// remove the file from the main list as swell
 | 
        
           |  |  | 1819 | 		m_lFiles.remove(f, false);
 | 
        
           |  |  | 1820 | 		delete f;
 | 
        
           |  |  | 1821 | 	}
 | 
        
           |  |  | 1822 |   | 
        
           |  |  | 1823 | 	// remove all the packages from memory
 | 
        
           |  |  | 1824 | 	for ( CListNode<CBaseFile> *node = m_lInstallList.Front(); node; node = node->next() )
 | 
        
           |  |  | 1825 | 	{
 | 
        
           |  |  | 1826 | 		CBaseFile *p = node->Data();
 | 
        
           |  |  | 1827 | 		p->GetFileList()->clear();
 | 
        
           |  |  | 1828 | 		m_lPackages.remove(p);
 | 
        
           |  |  | 1829 |   | 
        
           |  |  | 1830 | 		if ( p == m_pEnabledMod )
 | 
        
           |  |  | 1831 | 			m_pEnabledMod = NULL;
 | 
        
           |  |  | 1832 |   | 
        
           |  |  | 1833 | 		if ( uninstalledPackages )
 | 
        
           |  |  | 1834 | 			uninstalledPackages->push_back(p);
 | 
        
           |  |  | 1835 | 		else
 | 
        
           |  |  | 1836 | 			delete p;
 | 
        
           |  |  | 1837 | 	}
 | 
        
           |  |  | 1838 |   | 
        
           |  |  | 1839 | 	m_lInstallList.clear();
 | 
        
           |  |  | 1840 |   | 
        
           |  |  | 1841 | 	// check unistall files
 | 
        
           |  |  | 1842 | 	if ( !uninstallFiles.empty() )
 | 
        
           |  |  | 1843 | 	{
 | 
        
           |  |  | 1844 | 		removeDirs.PushBack(CyString("PluginManager/Uninstall"));
 | 
        
           |  |  | 1845 |   | 
        
           |  |  | 1846 | 		// make sure the scripts directory is created, even thou it should always be there anyways
 | 
        
           |  |  | 1847 | 		CDirIO scriptDir(m_sCurrentDir);
 | 
        
           |  |  | 1848 | 		if ( !scriptDir.Exists("scripts") )
 | 
        
           |  |  | 1849 | 		{
 | 
        
           |  |  | 1850 | 			if ( scriptDir.Create("Scripts") )
 | 
        
           |  |  | 1851 | 				this->AddLogEntry(SPKINSTALL_CREATEDIRECTORY, "Scripts", errors);
 | 
        
           |  |  | 1852 | 			else
 | 
        
           |  |  | 1853 | 				this->AddLogEntry(SPKINSTALL_CREATEDIRECTORY_FAIL, "Scripts", errors);
 | 
        
           |  |  | 1854 | 		}
 | 
        
           |  |  | 1855 |   | 
        
           |  |  | 1856 | 		for ( C_File *uf = uninstallFiles.First(); uf; uf = uninstallFiles.Next() )
 | 
        
           |  |  | 1857 | 		{
 | 
        
           |  |  | 1858 | 			C_File *newFile = new C_File();
 | 
        
           |  |  | 1859 | 			newFile->SetFileType(FILETYPE_SCRIPT);
 | 
        
           |  |  | 1860 | 			newFile->SetFilename(uf->GetFilename());
 | 
        
           |  |  | 1861 | 			newFile->SetCreationTime(uf->GetCreationTime());
 | 
        
           |  |  | 1862 |   | 
        
           |  |  | 1863 | 			// other installed packages use this file as well, copy it
 | 
        
           |  |  | 1864 | 			CyString newFilename = m_sCurrentDir + "/" + newFile->GetNameDirectory(NULL);
 | 
        
           |  |  | 1865 | 			CFileIO file(uf->GetFilePointer());
 | 
        
           |  |  | 1866 |   | 
        
           |  |  | 1867 | 			if ( uf->GetUsed() )
 | 
        
           |  |  | 1868 | 			{
 | 
        
           |  |  | 1869 | 				if ( file.Copy(newFilename) )
 | 
        
           |  |  | 1870 | 					this->AddLogEntry(SPKINSTALL_UNINSTALL_COPY, newFile->GetNameDirectory(NULL), errors);
 | 
        
           |  |  | 1871 | 				else
 | 
        
           |  |  | 1872 | 				{
 | 
        
           |  |  | 1873 | 					this->AddLogEntry(SPKINSTALL_UNINSTALL_COPY_FAIL, newFile->GetNameDirectory(NULL), errors);
 | 
        
           |  |  | 1874 | 					delete newFile;
 | 
        
           |  |  | 1875 | 					newFile = NULL;
 | 
        
           |  |  | 1876 | 				}
 | 
        
           |  |  | 1877 | 			}
 | 
        
           |  |  | 1878 | 			// otherwise just move it
 | 
        
           |  |  | 1879 | 			else
 | 
        
           |  |  | 1880 | 			{
 | 
        
           |  |  | 1881 | 				if ( file.Rename(newFilename) )
 | 
        
           |  |  | 1882 | 					this->AddLogEntry(SPKINSTALL_UNINSTALL_MOVE, newFile->GetNameDirectory(NULL), errors);
 | 
        
           |  |  | 1883 | 				else
 | 
        
           |  |  | 1884 | 				{
 | 
        
           |  |  | 1885 | 					this->AddLogEntry(SPKINSTALL_UNINSTALL_MOVE_FAIL, newFile->GetNameDirectory(NULL), errors);
 | 
        
           |  |  | 1886 | 					delete newFile;
 | 
        
           |  |  | 1887 | 					newFile = NULL;
 | 
        
           |  |  | 1888 | 				}
 | 
        
           |  |  | 1889 |   | 
        
           |  |  | 1890 | 				m_lFiles.remove(uf, false);
 | 
        
           |  |  | 1891 | 				delete uf;
 | 
        
           |  |  | 1892 | 			}
 | 
        
           |  |  | 1893 |   | 
        
           |  |  | 1894 | 			// add to the list
 | 
        
           |  |  | 1895 | 			if ( newFile )
 | 
        
           |  |  | 1896 | 			{
 | 
        
           |  |  | 1897 | 				// first check if theres a matching one
 | 
        
           |  |  | 1898 | 				bool found = false;
 | 
        
           |  |  | 1899 | 				for ( CListNode<C_File> *node = m_lUninstallFiles.Front(); node; node = node->next() )
 | 
        
           |  |  | 1900 | 				{
 | 
        
           |  |  | 1901 | 					C_File *checkFile = node->Data();
 | 
        
           |  |  | 1902 | 					if ( checkFile->GetFilename().Compare(newFile->GetFilename()) )
 | 
        
           |  |  | 1903 | 					{
 | 
        
           |  |  | 1904 | 						found = true;
 | 
        
           |  |  | 1905 | 						break;
 | 
        
           |  |  | 1906 | 					}
 | 
        
           |  |  | 1907 | 				}
 | 
        
           |  |  | 1908 |   | 
        
           |  |  | 1909 | 				// not found, so add it
 | 
        
           |  |  | 1910 | 				if ( !found )
 | 
        
           |  |  | 1911 | 					m_lUninstallFiles.push_back(newFile);
 | 
        
           |  |  | 1912 | 				else
 | 
        
           |  |  | 1913 | 					delete newFile;
 | 
        
           |  |  | 1914 | 			}
 | 
        
           |  |  | 1915 | 		}
 | 
        
           |  |  | 1916 | 	}
 | 
        
           |  |  | 1917 | 	uninstallFiles.clear();
 | 
        
           |  |  | 1918 |   | 
        
           |  |  | 1919 | 	// remove all directies that we're not using
 | 
        
           |  |  | 1920 | 	if ( readme )
 | 
        
           |  |  | 1921 | 	{
 | 
        
           |  |  | 1922 | 		removeDirs.PushBack(CyString("PluginManager/Readme"));
 | 
        
           |  |  | 1923 | 		removeDirs.PushBack(CyString("Readme"));
 | 
        
           |  |  | 1924 | 	}
 | 
        
           |  |  | 1925 | 	if ( original )
 | 
        
           |  |  | 1926 | 		removeDirs.PushBack(CyString("PluginManager/Original"));
 | 
        
           |  |  | 1927 | 	removeDirs.PushBack(CyString("PluginManager/Disabled"));
 | 
        
           |  |  | 1928 | 	RemoveUnusedDirectories(removeDirs, errors);
 | 
        
           |  |  | 1929 |   | 
        
           |  |  | 1930 | 	// finally lets shuffle any fake patchs to fill in gaps
 | 
        
           |  |  | 1931 | 	if ( shuffle )
 | 
        
           |  |  | 1932 | 	{
 | 
        
           |  |  | 1933 | 		ShuffleFakePatches(errors);
 | 
        
           |  |  | 1934 | 		ShuffleTextFiles(errors);
 | 
        
           |  |  | 1935 | 	}
 | 
        
           |  |  | 1936 |   | 
        
           |  |  | 1937 | 	this->WriteData();
 | 
        
           |  |  | 1938 |   | 
        
           |  |  | 1939 | 	return true;
 | 
        
           |  |  | 1940 | }
 | 
        
           |  |  | 1941 |   | 
        
           |  |  | 1942 | /**
 | 
        
           |  |  | 1943 |  * Prepares a package to be uninstalled
 | 
        
           |  |  | 1944 |  *
 | 
        
           |  |  | 1945 |  * Adds the package, and all its children onto the uninstall list to be used by UninstallPreparePackages
 | 
        
           |  |  | 1946 |  */
 | 
        
           |  |  | 1947 | void CPackages::PrepareUninstallPackage(CBaseFile *package)
 | 
        
           |  |  | 1948 | {
 | 
        
           |  |  | 1949 | 	// add package to list
 | 
        
           |  |  | 1950 | 	if ( !m_lInstallList.FindData(package) )
 | 
        
           |  |  | 1951 | 		m_lInstallList.push_back(package);
 | 
        
           |  |  | 1952 |   | 
        
           |  |  | 1953 | 	// add all children
 | 
        
           |  |  | 1954 | 	CLinkList<CBaseFile> children;
 | 
        
           |  |  | 1955 | 	if ( this->GetChildPackages(package, &children, true) )
 | 
        
           |  |  | 1956 | 	{
 | 
        
           |  |  | 1957 | 		for ( CBaseFile *p = children.First(); p; p = children.Next() )
 | 
        
           |  |  | 1958 | 		{
 | 
        
           |  |  | 1959 | 			if ( !m_lInstallList.FindData(p) )
 | 
        
           |  |  | 1960 | 				m_lInstallList.push_back(p);
 | 
        
           |  |  | 1961 | 		}
 | 
        
           |  |  | 1962 | 	}
 | 
        
           |  |  | 1963 | }
 | 
        
           |  |  | 1964 |   | 
        
           |  |  | 1965 | bool CPackages::PrepareEnablePackage(CBaseFile *package)
 | 
        
           |  |  | 1966 | {
 | 
        
           |  |  | 1967 | 	ClearError();
 | 
        
           |  |  | 1968 |   | 
        
           |  |  | 1969 | 	if ( package->GetParent() && !package->GetParent()->IsEnabled() )
 | 
        
           |  |  | 1970 | 	{
 | 
        
           |  |  | 1971 | 		m_iError = PKERR_NOPARENT;
 | 
        
           |  |  | 1972 | 		return false;
 | 
        
           |  |  | 1973 | 	}
 | 
        
           |  |  | 1974 |   | 
        
           |  |  | 1975 | 	if ( m_bVanilla && !package->IsSigned() )
 | 
        
           |  |  | 1976 | 	{
 | 
        
           |  |  | 1977 | 		m_iError = PKERR_MODIFIED;
 | 
        
           |  |  | 1978 | 		return false;
 | 
        
           |  |  | 1979 | 	}
 | 
        
           |  |  | 1980 |   | 
        
           |  |  | 1981 | 	// check if it needs depancies
 | 
        
           |  |  | 1982 | 	if ( package->AnyDependacies() )
 | 
        
           |  |  | 1983 | 	{
 | 
        
           |  |  | 1984 | 		if ( this->GetMissingDependacies(package, NULL, true) )
 | 
        
           |  |  | 1985 | 		{
 | 
        
           |  |  | 1986 | 			m_iError = PKERR_MISSINGDEP;
 | 
        
           |  |  | 1987 | 			return false;
 | 
        
           |  |  | 1988 | 		}
 | 
        
           |  |  | 1989 | 	}
 | 
        
           |  |  | 1990 |   | 
        
           |  |  | 1991 | 	if ( !m_lEnableList.FindData(package) )
 | 
        
           |  |  | 1992 | 	{
 | 
        
           |  |  | 1993 | 		if ( !package->IsEnabled() )
 | 
        
           |  |  | 1994 | 			m_lEnableList.push_back(package);
 | 
        
           |  |  | 1995 |   | 
        
           |  |  | 1996 | 		// do all the children as well
 | 
        
           |  |  | 1997 | 		if ( m_bAutoEnableChild )
 | 
        
           |  |  | 1998 | 		{
 | 
        
           |  |  | 1999 | 			CLinkList<CBaseFile> childList;
 | 
        
           |  |  | 2000 | 			this->GetChildPackages(package, &childList, true);
 | 
        
           |  |  | 2001 |   | 
        
           |  |  | 2002 | 			// add all disabled packages to list
 | 
        
           |  |  | 2003 | 			for ( CBaseFile *p = childList.First(); p; p = childList.Next() )
 | 
        
           |  |  | 2004 | 			{
 | 
        
           |  |  | 2005 | 				if ( !p->IsEnabled() )
 | 
        
           |  |  | 2006 | 					m_lEnableList.push_back(p);
 | 
        
           |  |  | 2007 | 			}
 | 
        
           |  |  | 2008 | 		}
 | 
        
           |  |  | 2009 | 	}
 | 
        
           |  |  | 2010 |   | 
        
           |  |  | 2011 | 	m_bRemoveDir = true;
 | 
        
           |  |  | 2012 |   | 
        
           |  |  | 2013 | 	return true;
 | 
        
           |  |  | 2014 | }
 | 
        
           |  |  | 2015 |   | 
        
           |  |  | 2016 | bool CPackages::PrepareDisableForVanilla()
 | 
        
           |  |  | 2017 | {
 | 
        
           |  |  | 2018 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 2019 | 	{
 | 
        
           |  |  | 2020 | 		CBaseFile *p = node->Data();
 | 
        
           |  |  | 2021 | 		if ( !p->IsSigned() && p->IsEnabled() )
 | 
        
           |  |  | 2022 | 		{
 | 
        
           |  |  | 2023 | 			this->PrepareDisablePackage(p);
 | 
        
           |  |  | 2024 | 			m_bDisableVanilla = true;
 | 
        
           |  |  | 2025 | 		}
 | 
        
           |  |  | 2026 | 	}
 | 
        
           |  |  | 2027 |   | 
        
           |  |  | 2028 | 	return true;
 | 
        
           |  |  | 2029 | }
 | 
        
           |  |  | 2030 |   | 
        
           |  |  | 2031 | bool CPackages::PrepareEnableLibrarys()
 | 
        
           |  |  | 2032 | {
 | 
        
           |  |  | 2033 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 2034 | 	{
 | 
        
           |  |  | 2035 | 		CBaseFile *p = node->Data();
 | 
        
           |  |  | 2036 | 		if ( p->GetType() != TYPE_SPK )
 | 
        
           |  |  | 2037 | 			continue;
 | 
        
           |  |  | 2038 |   | 
        
           |  |  | 2039 | 		if ( !p->IsEnabled() && ((CSpkFile *)p)->IsLibrary() )
 | 
        
           |  |  | 2040 | 			this->PrepareEnablePackage(p);
 | 
        
           |  |  | 2041 | 	}
 | 
        
           |  |  | 2042 |   | 
        
           |  |  | 2043 | 	return true;
 | 
        
           |  |  | 2044 | }
 | 
        
           |  |  | 2045 |   | 
        
           |  |  | 2046 | bool CPackages::PrepareEnableFromVanilla()
 | 
        
           |  |  | 2047 | {
 | 
        
           |  |  | 2048 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 2049 | 	{
 | 
        
           |  |  | 2050 | 		CBaseFile *p = node->Data();
 | 
        
           |  |  | 2051 | 		if ( !p->IsEnabled() && p->IsModifiedEnabled() ) {
 | 
        
           |  |  | 2052 | 			this->PrepareEnablePackage(p);
 | 
        
           |  |  | 2053 | 		}
 | 
        
           |  |  | 2054 | 	}
 | 
        
           |  |  | 2055 |   | 
        
           |  |  | 2056 | 	return true;
 | 
        
           |  |  | 2057 | }
 | 
        
           |  |  | 2058 |   | 
        
           |  |  | 2059 | int CPackages::GetDependacyList(CBaseFile *package, CLinkList<CBaseFile> *list)
 | 
        
           |  |  | 2060 | {
 | 
        
           |  |  | 2061 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 2062 | 	{
 | 
        
           |  |  | 2063 | 		CBaseFile *p = node->Data();
 | 
        
           |  |  | 2064 | 		if ( p->IsPackageNeeded(package->GetName(), package->GetAuthor()) )
 | 
        
           |  |  | 2065 | 			list->push_back(p);
 | 
        
           |  |  | 2066 | 	}
 | 
        
           |  |  | 2067 |   | 
        
           |  |  | 2068 | 	return list->size();
 | 
        
           |  |  | 2069 | }
 | 
        
           |  |  | 2070 |   | 
        
           |  |  | 2071 | bool CPackages::PrepareDisablePackage(CBaseFile *package)
 | 
        
           |  |  | 2072 | {
 | 
        
           |  |  | 2073 | 	if ( !m_lDisableList.FindData(package) )
 | 
        
           |  |  | 2074 | 	{
 | 
        
           |  |  | 2075 | 		if ( package->IsEnabled() )
 | 
        
           |  |  | 2076 | 			m_lDisableList.push_back(package);
 | 
        
           |  |  | 2077 |   | 
        
           |  |  | 2078 | 		CLinkList<CBaseFile> childList;
 | 
        
           |  |  | 2079 | 		this->GetChildPackages(package, &childList, true);
 | 
        
           |  |  | 2080 |   | 
        
           |  |  | 2081 | 		// add all disabled packages to list
 | 
        
           |  |  | 2082 | 		for ( CBaseFile *p = childList.First(); p; p = childList.Next() )
 | 
        
           |  |  | 2083 | 		{
 | 
        
           |  |  | 2084 | 			if ( p->IsEnabled() && !m_lDisableList.FindData(p) )
 | 
        
           |  |  | 2085 | 				m_lDisableList.push_back(p);
 | 
        
           |  |  | 2086 | 		}
 | 
        
           |  |  | 2087 |   | 
        
           |  |  | 2088 | 		// if its a library, check for any dependacies
 | 
        
           |  |  | 2089 | 		if ( package->GetType() == TYPE_SPK && ((CSpkFile *)package)->IsLibrary() )
 | 
        
           |  |  | 2090 | 		{
 | 
        
           |  |  | 2091 | 			CLinkList<CBaseFile> depList;
 | 
        
           |  |  | 2092 | 			if ( this->GetDependacyList(package, &depList) )
 | 
        
           |  |  | 2093 | 			{
 | 
        
           |  |  | 2094 | 				for ( CBaseFile *p = depList.First(); p; p = depList.Next() )
 | 
        
           |  |  | 2095 | 				{
 | 
        
           |  |  | 2096 | 					if ( !m_lDisableList.FindData(p) )
 | 
        
           |  |  | 2097 | 						this->PrepareDisablePackage(p);
 | 
        
           |  |  | 2098 | 				}
 | 
        
           |  |  | 2099 | 			}
 | 
        
           |  |  | 2100 | 		}
 | 
        
           |  |  | 2101 | 	}
 | 
        
           |  |  | 2102 | 	return true;
 | 
        
           |  |  | 2103 | }
 | 
        
           |  |  | 2104 |   | 
        
           |  |  | 2105 | /**
 | 
        
           |  |  | 2106 |  * Prepares a package to be installed
 | 
        
           |  |  | 2107 |  */
 | 
        
           |  |  | 2108 | int CPackages::PrepareInstallPackage(CBaseFile *package, bool disabled, bool force, int check)
 | 
        
           |  |  | 2109 | {
 | 
        
           |  |  | 2110 | 	// add package to list
 | 
        
           |  |  | 2111 | 	if ( !m_lInstallList.FindData(package) )
 | 
        
           |  |  | 2112 | 	{
 | 
        
           |  |  | 2113 | 		int error = this->CheckInstallPackage(package, check);
 | 
        
           |  |  | 2114 | 		if ( error == INSTALLCHECK_OK || force )
 | 
        
           |  |  | 2115 | 		{
 | 
        
           |  |  | 2116 | 			if ( disabled )
 | 
        
           |  |  | 2117 | 				package->SetEnabled(false);
 | 
        
           |  |  | 2118 |   | 
        
           |  |  | 2119 | 			bool added = false;
 | 
        
           |  |  | 2120 | 			if ( package->GetType() == TYPE_SPK )
 | 
        
           |  |  | 2121 | 			{
 | 
        
           |  |  | 2122 | 				// find other mods in the currently added list
 | 
        
           |  |  | 2123 | 				CSpkFile *spk = (CSpkFile *)package;
 | 
        
           |  |  | 2124 | 				if ( spk->IsAnotherMod() )
 | 
        
           |  |  | 2125 | 				{
 | 
        
           |  |  | 2126 | 					for ( CListNode<CBaseFile> *node = m_lInstallList.Front(); node; node = node->next() )
 | 
        
           |  |  | 2127 | 					{
 | 
        
           |  |  | 2128 | 						CBaseFile *p = node->Data();
 | 
        
           | 10 | cycrow | 2129 | 						if ( spk->GetOtherName().Compare(p->GetName().ToString()) && spk->GetOtherAuthor().Compare(p->GetAuthor().ToString()) )
 | 
        
           | 1 | cycrow | 2130 | 						{
 | 
        
           |  |  | 2131 | 							m_lInstallList.insert(m_lInstallList.FindPos(p) + 2, package);
 | 
        
           |  |  | 2132 | 							added = true;
 | 
        
           |  |  | 2133 | 							break;
 | 
        
           |  |  | 2134 | 						}
 | 
        
           |  |  | 2135 | 					}
 | 
        
           |  |  | 2136 | 				}
 | 
        
           |  |  | 2137 | 			}
 | 
        
           |  |  | 2138 |   | 
        
           |  |  | 2139 | 			if ( !added )
 | 
        
           |  |  | 2140 | 			{
 | 
        
           |  |  | 2141 | 				// check if we are a parent
 | 
        
           |  |  | 2142 | 				for ( CListNode<CBaseFile> *node = m_lInstallList.Front(); node; node = node->next() )
 | 
        
           |  |  | 2143 | 				{
 | 
        
           |  |  | 2144 | 					if ( node->Data()->GetType() != TYPE_SPK )
 | 
        
           |  |  | 2145 | 						continue;
 | 
        
           |  |  | 2146 |   | 
        
           |  |  | 2147 | 					CSpkFile *spk = (CSpkFile *)node->Data();
 | 
        
           |  |  | 2148 | 					if ( !spk->IsAnotherMod() )
 | 
        
           |  |  | 2149 | 						continue;
 | 
        
           |  |  | 2150 |   | 
        
           | 10 | cycrow | 2151 | 					if ( spk->GetOtherName().Compare(package->GetName().ToString()) && spk->GetOtherAuthor().Compare(package->GetAuthor().ToString()) )
 | 
        
           | 1 | cycrow | 2152 | 					{
 | 
        
           |  |  | 2153 | 						added = true;
 | 
        
           |  |  | 2154 | 						m_lInstallList.insert(node->Data(), package);
 | 
        
           |  |  | 2155 | 						break;
 | 
        
           |  |  | 2156 | 					}
 | 
        
           |  |  | 2157 | 				}
 | 
        
           |  |  | 2158 |   | 
        
           |  |  | 2159 | 				if ( !added )
 | 
        
           |  |  | 2160 | 					m_lInstallList.push_back(package);
 | 
        
           |  |  | 2161 | 			}
 | 
        
           |  |  | 2162 |   | 
        
           |  |  | 2163 | 			return INSTALLCHECK_OK;
 | 
        
           |  |  | 2164 | 		}
 | 
        
           |  |  | 2165 |   | 
        
           |  |  | 2166 | 		package->SetLoadError(error);
 | 
        
           |  |  | 2167 | 		return error;
 | 
        
           |  |  | 2168 | 	}
 | 
        
           |  |  | 2169 |   | 
        
           |  |  | 2170 | 	return INSTALLCHECK_ALREADYQUEUED;
 | 
        
           |  |  | 2171 | }
 | 
        
           |  |  | 2172 |   | 
        
           |  |  | 2173 | void CPackages::RemovePreparedInstall(CBaseFile *package)
 | 
        
           |  |  | 2174 | {
 | 
        
           |  |  | 2175 | 	if ( !package )
 | 
        
           |  |  | 2176 | 	{
 | 
        
           |  |  | 2177 | 		m_lInstallList.MemoryClear();
 | 
        
           |  |  | 2178 | 	}
 | 
        
           |  |  | 2179 | 	else
 | 
        
           |  |  | 2180 | 	{
 | 
        
           |  |  | 2181 | 		if ( m_lInstallList.FindData(package) )
 | 
        
           |  |  | 2182 | 		{
 | 
        
           |  |  | 2183 | 			m_lInstallList.remove(package, true);
 | 
        
           |  |  | 2184 | 		}
 | 
        
           |  |  | 2185 | 	}
 | 
        
           |  |  | 2186 | }
 | 
        
           |  |  | 2187 |   | 
        
           |  |  | 2188 | char CPackages::ConvertWareTypeBack(int w)
 | 
        
           |  |  | 2189 | {
 | 
        
           |  |  | 2190 | 	switch ( w )
 | 
        
           |  |  | 2191 | 	{
 | 
        
           |  |  | 2192 | 		case WARES_BIO:
 | 
        
           |  |  | 2193 | 			return 'b';
 | 
        
           |  |  | 2194 | 		case WARES_ENERGY:
 | 
        
           |  |  | 2195 | 			return 'e';
 | 
        
           |  |  | 2196 | 		case WARES_FOOD:
 | 
        
           |  |  | 2197 | 			return 'f';
 | 
        
           |  |  | 2198 | 		case WARES_MINERAL:
 | 
        
           |  |  | 2199 | 			return 'm';
 | 
        
           |  |  | 2200 | 		case WARES_TECH:
 | 
        
           |  |  | 2201 | 			return 't';
 | 
        
           |  |  | 2202 | 		case WARES_NATURAL:
 | 
        
           |  |  | 2203 | 			return 'n';
 | 
        
           |  |  | 2204 | 	}
 | 
        
           |  |  | 2205 | 	return 't';
 | 
        
           |  |  | 2206 | }
 | 
        
           |  |  | 2207 | int CPackages::ConvertWareType(char w)
 | 
        
           |  |  | 2208 | {
 | 
        
           |  |  | 2209 | 	switch ( LOWER(w) )
 | 
        
           |  |  | 2210 | 	{
 | 
        
           |  |  | 2211 | 		case 'b':
 | 
        
           |  |  | 2212 | 			return WARES_BIO;
 | 
        
           |  |  | 2213 | 		case 'e':
 | 
        
           |  |  | 2214 | 			return WARES_ENERGY;
 | 
        
           |  |  | 2215 | 		case 'f':
 | 
        
           |  |  | 2216 | 			return WARES_FOOD;
 | 
        
           |  |  | 2217 | 		case 'm':
 | 
        
           |  |  | 2218 | 			return WARES_MINERAL;
 | 
        
           |  |  | 2219 | 		case 't':
 | 
        
           |  |  | 2220 | 			return WARES_TECH;
 | 
        
           |  |  | 2221 | 		case 'n':
 | 
        
           |  |  | 2222 | 			return WARES_NATURAL;
 | 
        
           |  |  | 2223 | 	}
 | 
        
           |  |  | 2224 | 	return WARES_TECH;
 | 
        
           |  |  | 2225 | }
 | 
        
           |  |  | 2226 |   | 
        
           |  |  | 2227 | void CPackages::SetupShips()
 | 
        
           |  |  | 2228 | {
 | 
        
           |  |  | 2229 | 	for ( CListNode<SGameShip> *wNode = m_lGameShips.Front(); wNode; wNode = wNode->next() )
 | 
        
           |  |  | 2230 | 	{
 | 
        
           |  |  | 2231 | 		if ( wNode->Data()->iType != WARETYPE_NONE )
 | 
        
           |  |  | 2232 | 			wNode->Data()->iType = WARETYPE_DELETED;
 | 
        
           |  |  | 2233 | 	}
 | 
        
           |  |  | 2234 |   | 
        
           |  |  | 2235 | 	// find any new ships to add to the list
 | 
        
           |  |  | 2236 | 	for ( CListNode<CBaseFile> *pNode = m_lPackages.Front(); pNode; pNode = pNode->next() )
 | 
        
           |  |  | 2237 | 	{
 | 
        
           |  |  | 2238 | 		if ( pNode->Data()->GetType() != TYPE_XSP )
 | 
        
           |  |  | 2239 | 			continue;
 | 
        
           |  |  | 2240 | 		CXspFile *p = (CXspFile *)pNode->Data();
 | 
        
           |  |  | 2241 |   | 
        
           |  |  | 2242 | 		bool found = false;
 | 
        
           |  |  | 2243 | 		for ( CListNode<SGameShip> *wNode = m_lGameShips.Front(); wNode; wNode = wNode->next() )
 | 
        
           |  |  | 2244 | 		{
 | 
        
           | 14 | cycrow | 2245 | 			if ( wNode->Data()->sShipID.Compare(p->GetShipID().c_str()) )
 | 
        
           | 1 | cycrow | 2246 | 			{
 | 
        
           |  |  | 2247 | 				if ( !p->IsEnabled() )
 | 
        
           |  |  | 2248 | 					wNode->Data()->iType = WARETYPE_DISABLED;
 | 
        
           |  |  | 2249 | 				else
 | 
        
           |  |  | 2250 | 					wNode->Data()->iType = WARETYPE_ADDED;
 | 
        
           |  |  | 2251 | 				found = true;
 | 
        
           |  |  | 2252 | 				wNode->Data()->pPackage = p;
 | 
        
           |  |  | 2253 | 				wNode->Data()->sShipClass = p->GetShipClass();
 | 
        
           |  |  | 2254 | 				break;
 | 
        
           |  |  | 2255 | 			}
 | 
        
           |  |  | 2256 | 		}
 | 
        
           |  |  | 2257 |   | 
        
           |  |  | 2258 | 		if ( found || !p->IsEnabled() )
 | 
        
           |  |  | 2259 | 			continue;
 | 
        
           |  |  | 2260 |   | 
        
           |  |  | 2261 | 		// first find any free
 | 
        
           |  |  | 2262 | 		SGameShip *gw = NULL;
 | 
        
           |  |  | 2263 | 		for ( CListNode<SGameShip> *wNode = m_lGameShips.Front(); wNode; wNode = wNode->next() )
 | 
        
           |  |  | 2264 | 		{
 | 
        
           |  |  | 2265 | 			if ( (!gw) && (wNode->Data()->iType == WARETYPE_NONE) )
 | 
        
           |  |  | 2266 | 				gw = wNode->Data();
 | 
        
           |  |  | 2267 | 			// find an old entry for the ware and add it to the same place
 | 
        
           | 14 | cycrow | 2268 | 			if ( wNode->Data()->sShipID.Compare(p->GetShipID().c_str()) )
 | 
        
           | 1 | cycrow | 2269 | 			{
 | 
        
           |  |  | 2270 | 				gw = wNode->Data();
 | 
        
           |  |  | 2271 | 				break;
 | 
        
           |  |  | 2272 | 			}
 | 
        
           |  |  | 2273 | 		}
 | 
        
           |  |  | 2274 |   | 
        
           |  |  | 2275 | 		// none found, create one
 | 
        
           |  |  | 2276 | 		if ( !gw )
 | 
        
           |  |  | 2277 | 		{
 | 
        
           |  |  | 2278 | 			gw = new SGameShip;
 | 
        
           |  |  | 2279 | 			gw->sShipID = p->GetShipID();
 | 
        
           |  |  | 2280 | 			gw->sShipClass = p->GetShipClass();
 | 
        
           |  |  | 2281 | 			gw->pPackage = p;
 | 
        
           |  |  | 2282 | 			m_lGameShips.push_back(gw);
 | 
        
           |  |  | 2283 | 		}
 | 
        
           |  |  | 2284 | 		gw->iType = WARETYPE_ADDED;
 | 
        
           |  |  | 2285 | 	}
 | 
        
           |  |  | 2286 | }
 | 
        
           |  |  | 2287 |   | 
        
           |  |  | 2288 | void CPackages::SetupWares()
 | 
        
           |  |  | 2289 | {
 | 
        
           |  |  | 2290 | 	for ( int i = 0; i < WAREBUFFERS; i++ )
 | 
        
           |  |  | 2291 | 	{
 | 
        
           |  |  | 2292 | 		for ( CListNode<SGameWare> *wNode = m_lGameWares[i].Front(); wNode; wNode = wNode->next() )
 | 
        
           |  |  | 2293 | 		{
 | 
        
           |  |  | 2294 | 			if ( wNode->Data()->iType != WARETYPE_NONE )
 | 
        
           |  |  | 2295 | 				wNode->Data()->iType = WARETYPE_DELETED;
 | 
        
           |  |  | 2296 | 		}
 | 
        
           |  |  | 2297 | 	}
 | 
        
           |  |  | 2298 |   | 
        
           |  |  | 2299 | 	// find any new wares to add to the list
 | 
        
           |  |  | 2300 | 	for ( CListNode<CBaseFile> *pNode = m_lPackages.Front(); pNode; pNode = pNode->next() )
 | 
        
           |  |  | 2301 | 	{
 | 
        
           |  |  | 2302 | 		if ( pNode->Data()->GetType() != TYPE_SPK )
 | 
        
           |  |  | 2303 | 			continue;
 | 
        
           |  |  | 2304 | 		CSpkFile *p = (CSpkFile *)pNode->Data();
 | 
        
           |  |  | 2305 |   | 
        
           |  |  | 2306 | 		for ( CListNode<SWares> *node = p->GetWaresList()->Front(); node; node = node->next() )
 | 
        
           |  |  | 2307 | 		{
 | 
        
           |  |  | 2308 | 			SWares *w = node->Data();
 | 
        
           |  |  | 2309 | 			int wareType = CPackages::ConvertWareType(w->cType);
 | 
        
           |  |  | 2310 |   | 
        
           |  |  | 2311 | 			// check if its on the list
 | 
        
           |  |  | 2312 | 			bool found = false;
 | 
        
           |  |  | 2313 | 			for ( CListNode<SGameWare> *wNode = m_lGameWares[wareType].Front(); wNode; wNode = wNode->next() )
 | 
        
           |  |  | 2314 | 			{
 | 
        
           |  |  | 2315 | 				if ( wNode->Data()->sWareName == w->sID )
 | 
        
           |  |  | 2316 | 				{
 | 
        
           |  |  | 2317 | 					if ( !p->IsEnabled() )
 | 
        
           |  |  | 2318 | 						wNode->Data()->iType = WARETYPE_DISABLED;
 | 
        
           |  |  | 2319 | 					else
 | 
        
           |  |  | 2320 | 						wNode->Data()->iType = WARETYPE_ADDED;
 | 
        
           |  |  | 2321 | 					wNode->Data()->pWare = w;
 | 
        
           |  |  | 2322 | 					found = true;
 | 
        
           |  |  | 2323 | 					break;
 | 
        
           |  |  | 2324 | 				}
 | 
        
           |  |  | 2325 | 			}
 | 
        
           |  |  | 2326 |   | 
        
           |  |  | 2327 | 			if ( found || !p->IsEnabled() )
 | 
        
           |  |  | 2328 | 				continue;
 | 
        
           |  |  | 2329 |   | 
        
           |  |  | 2330 | 			// first find any free
 | 
        
           |  |  | 2331 | 			SGameWare *gw = NULL;
 | 
        
           |  |  | 2332 | 			for ( CListNode<SGameWare> *wNode = m_lGameWares[wareType].Front(); wNode; wNode = wNode->next() )
 | 
        
           |  |  | 2333 | 			{
 | 
        
           |  |  | 2334 | 				if ( (!gw) && (wNode->Data()->iType == WARETYPE_NONE) )
 | 
        
           |  |  | 2335 | 					gw = wNode->Data();
 | 
        
           |  |  | 2336 | 				// find an old entry for the ware and add it to the same place
 | 
        
           |  |  | 2337 | 				if ( wNode->Data()->sWareName == w->sID )
 | 
        
           |  |  | 2338 | 				{
 | 
        
           |  |  | 2339 | 					gw = wNode->Data();
 | 
        
           |  |  | 2340 | 					break;
 | 
        
           |  |  | 2341 | 				}
 | 
        
           |  |  | 2342 | 			}
 | 
        
           |  |  | 2343 |   | 
        
           |  |  | 2344 | 			// none found, create one
 | 
        
           |  |  | 2345 | 			if ( !gw )
 | 
        
           |  |  | 2346 | 			{
 | 
        
           |  |  | 2347 | 				gw = new SGameWare;
 | 
        
           |  |  | 2348 | 				gw->sWareName = w->sID;
 | 
        
           |  |  | 2349 | 				gw->iPos = m_lGameWares[wareType].size();
 | 
        
           |  |  | 2350 | 				gw->pWare = w;
 | 
        
           |  |  | 2351 | 				gw->cType = w->cType;
 | 
        
           |  |  | 2352 | 				m_lGameWares[wareType].push_back(gw);
 | 
        
           |  |  | 2353 | 			}
 | 
        
           |  |  | 2354 | 			gw->iType = WARETYPE_ADDED;
 | 
        
           |  |  | 2355 | 		}
 | 
        
           |  |  | 2356 | 	}
 | 
        
           |  |  | 2357 | }
 | 
        
           |  |  | 2358 |   | 
        
           |  |  | 2359 | /**
 | 
        
           |  |  | 2360 |  * Closing the current directory
 | 
        
           |  |  | 2361 |  *
 | 
        
           |  |  | 2362 |  * When existing, program needs to close the directory
 | 
        
           |  |  | 2363 |  */
 | 
        
           |  |  | 2364 | bool CPackages::CloseDir ( CyStringList *errors, CProgressInfo *progress, bool removedir )
 | 
        
           |  |  | 2365 | {
 | 
        
           |  |  | 2366 | 	if ( m_sCurrentDir.Empty() )
 | 
        
           |  |  | 2367 | 		return true;
 | 
        
           |  |  | 2368 | 	if ( !m_bLoaded )
 | 
        
           |  |  | 2369 | 		return true;
 | 
        
           |  |  | 2370 |   | 
        
           |  |  | 2371 | 	m_sActiveDir = m_sCurrentDir;
 | 
        
           |  |  | 2372 |   | 
        
           |  |  | 2373 | 	if ( m_bRenameText )
 | 
        
           |  |  | 2374 | 		CreateLanguageTextFiles(errors);
 | 
        
           |  |  | 2375 |   | 
        
           |  |  | 2376 | 	this->BackupSaves();
 | 
        
           |  |  | 2377 |   | 
        
           |  |  | 2378 | 	if ( CFileIO(m_sCurrentDir + "/mods/PluginManager.dat").Exists() )
 | 
        
           |  |  | 2379 | 		CFileIO(m_sCurrentDir + "/mods/PluginManager.dat").Remove();
 | 
        
           |  |  | 2380 | 	if ( CFileIO(m_sCurrentDir + "/mods/PluginManager.cat").Exists() )
 | 
        
           |  |  | 2381 | 		CFileIO(m_sCurrentDir + "/mods/PluginManager.cat").Remove();
 | 
        
           |  |  | 2382 |   | 
        
           |  |  | 2383 | 	if ( !m_bVanilla )
 | 
        
           |  |  | 2384 | 	{
 | 
        
           |  |  | 2385 | 		// base mode for Reunion
 | 
        
           |  |  | 2386 | 		if ( m_iGame == GAME_X3 && m_pEnabledMod )
 | 
        
           |  |  | 2387 | 		{
 | 
        
           |  |  | 2388 | 			C_File *fDat = m_pEnabledMod->GetFirstFile(FILETYPE_MOD);
 | 
        
           |  |  | 2389 | 			while ( fDat && !fDat->IsFakePatch() && !fDat->CheckFileExt("dat") )
 | 
        
           |  |  | 2390 | 				fDat = m_pEnabledMod->GetNextFile(fDat);
 | 
        
           |  |  | 2391 |   | 
        
           |  |  | 2392 | 			if ( fDat )
 | 
        
           |  |  | 2393 | 			{
 | 
        
           |  |  | 2394 | 				C_File *fCat = m_pEnabledMod->GetFirstFile(FILETYPE_MOD);
 | 
        
           |  |  | 2395 | 				while ( fCat && !fCat->IsFakePatch() && !fCat->CheckFileExt("cat") && !fCat->GetBaseName().Compare(fDat->GetBaseName()) )
 | 
        
           |  |  | 2396 | 					fCat = m_pEnabledMod->GetNextFile(fCat);
 | 
        
           |  |  | 2397 |   | 
        
           |  |  | 2398 | 				if ( fCat )
 | 
        
           |  |  | 2399 | 				{
 | 
        
           |  |  | 2400 | 					CFileIO(fDat->GetFilePointer()).Copy(m_sCurrentDir + "/mods/PluginManager.dat");
 | 
        
           |  |  | 2401 | 					CFileIO(fCat->GetFilePointer()).Copy(m_sCurrentDir + "/mods/PluginManager.cat");
 | 
        
           |  |  | 2402 | 				}
 | 
        
           |  |  | 2403 | 			}
 | 
        
           |  |  | 2404 | 		}
 | 
        
           |  |  | 2405 | 		else if ( m_iGame == GAME_X3 && !m_sSetMod.Empty() && CFileIO(m_sCurrentDir + "/mods/" + m_sSetMod + ".cat").Exists() && CFileIO(m_sCurrentDir + "/mods/" + m_sSetMod + ".dat").Exists() )
 | 
        
           |  |  | 2406 | 		{
 | 
        
           |  |  | 2407 | 			CFileIO(m_sCurrentDir + "/mods/" + m_sSetMod + ".dat").Copy(m_sCurrentDir + "/mods/PluginManager.dat");
 | 
        
           |  |  | 2408 | 			CFileIO(m_sCurrentDir + "/mods/" + m_sSetMod + ".cat").Copy(m_sCurrentDir + "/mods/PluginManager.cat");
 | 
        
           |  |  | 2409 | 		}
 | 
        
           |  |  | 2410 |   | 
        
           |  |  | 2411 | 		if ( !CDirIO(m_sCurrentDir).Exists("mods") )
 | 
        
           |  |  | 2412 | 			CDirIO(m_sCurrentDir).Create("mods");
 | 
        
           |  |  | 2413 |   | 
        
           |  |  | 2414 | 		SetupWares();
 | 
        
           |  |  | 2415 | 		SetupShips();
 | 
        
           |  |  | 2416 | 		CreateEMPFile();
 | 
        
           |  |  | 2417 | 		CreateWareFiles();
 | 
        
           |  |  | 2418 | 		CreateDummies();
 | 
        
           |  |  | 2419 | 		CreateComponants();
 | 
        
           |  |  | 2420 | 		CreateTShips();
 | 
        
           |  |  | 2421 | 		CreateCutData();
 | 
        
           |  |  | 2422 | 		CreateBodies();
 | 
        
           |  |  | 2423 | 		CreateAnimations();
 | 
        
           |  |  | 2424 | 		CreateCustomStarts();
 | 
        
           |  |  | 2425 | 		CreateGlobals();
 | 
        
           |  |  | 2426 | 		CreatePluginManagerText();
 | 
        
           |  |  | 2427 | 		RestoreFakePatch();
 | 
        
           |  |  | 2428 | 	}
 | 
        
           |  |  | 2429 |   | 
        
           |  |  | 2430 | 	RemoveFailedFiles();
 | 
        
           |  |  | 2431 |   | 
        
           |  |  | 2432 | 	WriteData();
 | 
        
           |  |  | 2433 | 	if ( removedir && m_bRemoveDir )
 | 
        
           |  |  | 2434 | 	{
 | 
        
           |  |  | 2435 | 		m_bRemoveDir = false;
 | 
        
           |  |  | 2436 | 		CyStringList removeDirs;
 | 
        
           |  |  | 2437 | 		removeDirs.PushBack(".");
 | 
        
           |  |  | 2438 | 		RemoveUnusedDirectories(removeDirs, errors);
 | 
        
           |  |  | 2439 | 	}
 | 
        
           |  |  | 2440 |   | 
        
           |  |  | 2441 | 	m_bLoaded = false;
 | 
        
           |  |  | 2442 | 	return true;
 | 
        
           |  |  | 2443 | }
 | 
        
           |  |  | 2444 |   | 
        
           |  |  | 2445 | CyString CPackages::GetModKey()
 | 
        
           |  |  | 2446 | {
 | 
        
           |  |  | 2447 | 	return m_gameExe.GetModKey(m_iGame - 1);
 | 
        
           |  |  | 2448 | }
 | 
        
           |  |  | 2449 | CyString CPackages::GetSelectedModName()
 | 
        
           |  |  | 2450 | {
 | 
        
           |  |  | 2451 | 	if ( !m_pEnabledMod )
 | 
        
           |  |  | 2452 | 	{
 | 
        
           |  |  | 2453 | 		if ( m_sSetMod.Empty() && m_iGame == GAME_X3 )
 | 
        
           |  |  | 2454 | 			return "PluginManager";
 | 
        
           |  |  | 2455 | 		return m_sSetMod;
 | 
        
           |  |  | 2456 | 	}
 | 
        
           |  |  | 2457 |   | 
        
           |  |  | 2458 | 	if ( !m_pEnabledMod->IsEnabled() )
 | 
        
           |  |  | 2459 | 		return m_sSetMod;
 | 
        
           |  |  | 2460 |   | 
        
           |  |  | 2461 | 	C_File *f = m_pEnabledMod->GetFirstFile(FILETYPE_MOD);
 | 
        
           |  |  | 2462 | 	if ( !f )
 | 
        
           |  |  | 2463 | 		return m_sSetMod;
 | 
        
           |  |  | 2464 |   | 
        
           |  |  | 2465 | 	CyString name = f->GetFilename();
 | 
        
           |  |  | 2466 | 	name = name.Left(-4);
 | 
        
           |  |  | 2467 | 	return name;
 | 
        
           |  |  | 2468 |   | 
        
           |  |  | 2469 | }
 | 
        
           |  |  | 2470 |   | 
        
           |  |  | 2471 | bool CPackages::RestoreFakePatch()
 | 
        
           |  |  | 2472 | {
 | 
        
           |  |  | 2473 | 	m_iFakePatch = -1;
 | 
        
           |  |  | 2474 |   | 
        
           |  |  | 2475 | 	CFileIO catFile(m_sCurrentDir + "/PluginManager/PlugMan_Fake.cat");
 | 
        
           |  |  | 2476 | 	CFileIO datFile(m_sCurrentDir + "/PluginManager/PlugMan_Fake.dat");
 | 
        
           |  |  | 2477 |   | 
        
           |  |  | 2478 | 	// if only 1 exists, remove it
 | 
        
           |  |  | 2479 | 	if ( catFile.Exists() && !datFile.Exists() )
 | 
        
           |  |  | 2480 | 	{
 | 
        
           |  |  | 2481 | 		if ( !catFile.Remove() )
 | 
        
           |  |  | 2482 | 			return false;
 | 
        
           |  |  | 2483 | 	}
 | 
        
           |  |  | 2484 | 	else if ( !catFile.Exists() && datFile.Exists() )
 | 
        
           |  |  | 2485 | 	{
 | 
        
           |  |  | 2486 | 		if ( !datFile.Remove() )
 | 
        
           |  |  | 2487 | 			return false;
 | 
        
           |  |  | 2488 | 	}
 | 
        
           |  |  | 2489 |   | 
        
           |  |  | 2490 | 	// if both exists, lets rename them
 | 
        
           |  |  | 2491 | 	if ( catFile.Exists() && datFile.Exists() )
 | 
        
           |  |  | 2492 | 	{
 | 
        
           |  |  | 2493 | 		// we need to add the plugin manager file in
 | 
        
           |  |  | 2494 | 		CyString file = m_sTempDir;
 | 
        
           |  |  | 2495 | 		if ( !file.Empty() )
 | 
        
           |  |  | 2496 | 			file += "/";
 | 
        
           |  |  | 2497 | 		file += "pluginmanagerfake.txt";
 | 
        
           |  |  | 2498 | 		file = file.FindReplace("\\", "/");
 | 
        
           |  |  | 2499 | 		CFileIO fakeFile(file);
 | 
        
           |  |  | 2500 | 		std::vector<CyString> lines;
 | 
        
           |  |  | 2501 | 		lines.push_back("//pluginmanager fake patch");
 | 
        
           |  |  | 2502 | 		fakeFile.WriteFile(&lines);
 | 
        
           |  |  | 2503 |   | 
        
           |  |  | 2504 | 		CCatFile fakePatch;
 | 
        
           |  |  | 2505 | 		if ( fakePatch.Open(m_sCurrentDir + "/PluginManager/PlugMan_Fake.cat", this->GetAddonDir(), CATREAD_DAT, false) == CATERR_NONE )
 | 
        
           |  |  | 2506 | 		{
 | 
        
           |  |  | 2507 | 			if ( fakePatch.AppendFile(file, "PlugMan\\TFake.pck") )
 | 
        
           |  |  | 2508 | 			{
 | 
        
           |  |  | 2509 | 				// find next available fake patch
 | 
        
           |  |  | 2510 | 				m_iFakePatch = this->FindNextFakePatch();
 | 
        
           |  |  | 2511 |   | 
        
           |  |  | 2512 | 				CyString filename = CyString::Number(m_iFakePatch).PadNumber(2);
 | 
        
           |  |  | 2513 | 				if ( catFile.Rename(m_sCurrentDir + "/" + filename + ".cat") )
 | 
        
           |  |  | 2514 | 				{
 | 
        
           |  |  | 2515 | 					if ( datFile.Rename(m_sCurrentDir + "/" + filename + ".dat") )
 | 
        
           |  |  | 2516 | 					{
 | 
        
           |  |  | 2517 | 						fakeFile.Remove();
 | 
        
           |  |  | 2518 | 						return true;
 | 
        
           |  |  | 2519 | 					}
 | 
        
           |  |  | 2520 |   | 
        
           |  |  | 2521 | 					// TODO: restore cat file
 | 
        
           |  |  | 2522 | 				}
 | 
        
           |  |  | 2523 | 			}
 | 
        
           |  |  | 2524 | 		}
 | 
        
           |  |  | 2525 |   | 
        
           |  |  | 2526 | 		fakeFile.Remove();
 | 
        
           |  |  | 2527 | 		return false;
 | 
        
           |  |  | 2528 | 	}
 | 
        
           |  |  | 2529 |   | 
        
           |  |  | 2530 | 	return true;
 | 
        
           |  |  | 2531 | }
 | 
        
           |  |  | 2532 |   | 
        
           |  |  | 2533 |   | 
        
           |  |  | 2534 | /**
 | 
        
           |  |  | 2535 |  * Save package detail to date file
 | 
        
           |  |  | 2536 |  *
 | 
        
           |  |  | 2537 |  * Writes the current package list data into pluginmanager.dat file
 | 
        
           |  |  | 2538 |  */
 | 
        
           |  |  | 2539 | void CPackages::WriteData()
 | 
        
           |  |  | 2540 | {
 | 
        
           |  |  | 2541 | 	if ( m_sCurrentDir.Empty() )
 | 
        
           |  |  | 2542 | 		return;
 | 
        
           |  |  | 2543 |   | 
        
           |  |  | 2544 | 	CyStringList lines;
 | 
        
           |  |  | 2545 | 	CyString version;
 | 
        
           |  |  | 2546 | 	version.FromFloat(GetLibraryVersion(), 2);
 | 
        
           |  |  | 2547 | 	version.Prepend("SpkInstaller: ");
 | 
        
           |  |  | 2548 | 	lines.PushBack(version);
 | 
        
           |  |  | 2549 |   | 
        
           |  |  | 2550 | 	lines.PushBack(CyString("UpdateTime: ") + (long)m_iLastUpdated);
 | 
        
           |  |  | 2551 | 	if ( m_iFakePatch != -1 )
 | 
        
           |  |  | 2552 | 		lines.PushBack(CyString("FakePatch: ") + (long)m_iFakePatch);
 | 
        
           |  |  | 2553 | 	if ( m_iSaveGame != -1 )
 | 
        
           |  |  | 2554 | 		lines.PushBack(CyString("SaveGame: ") + (long)m_iSaveGame);
 | 
        
           |  |  | 2555 | 	lines.PushBack(CyString("SaveGameManager: ") + (long)m_iSaveGameManager);
 | 
        
           |  |  | 2556 | 	if ( !m_bVanilla )
 | 
        
           |  |  | 2557 | 		lines.PushBack("Modified");
 | 
        
           |  |  | 2558 | 	if ( m_bUsedWare )
 | 
        
           |  |  | 2559 | 		lines.PushBack("UsedWare");
 | 
        
           |  |  | 2560 | 	if ( m_bSurpressProtectedWarning )
 | 
        
           |  |  | 2561 | 		lines.PushBack("SurpressProtectedWarning");
 | 
        
           |  |  | 2562 | 	if ( !m_sSetMod.Empty() )
 | 
        
           |  |  | 2563 | 		lines.PushBack(CyString("SetMod: ") + m_sSetMod);
 | 
        
           |  |  | 2564 | 	lines.PushBack(CyString("ShipBuffer: ") + (long)m_iShipBuffer);
 | 
        
           |  |  | 2565 | 	CyString wareBuffer = "WareBuffers:";
 | 
        
           |  |  | 2566 | 	for ( int i = 0; i < WAREBUFFERS; i++ )
 | 
        
           |  |  | 2567 | 		wareBuffer += CyString(" ") + (long)m_iWareBuffer[i];
 | 
        
           |  |  | 2568 | 	lines.PushBack(wareBuffer);
 | 
        
           |  |  | 2569 | 	for ( int i = 0; i < WAREBUFFERS; i++ )
 | 
        
           |  |  | 2570 | 	{
 | 
        
           |  |  | 2571 | 		if ( !m_lGameWares[i].size() )
 | 
        
           |  |  | 2572 | 			continue;
 | 
        
           |  |  | 2573 | 		lines.PushBack(CyString("Wares: ") + (long)i + " " + (long)m_lGameWares[i].size());
 | 
        
           |  |  | 2574 |   | 
        
           |  |  | 2575 | 		for ( CListNode<SGameWare> *node = m_lGameWares[i].Front(); node; node = node->next() )
 | 
        
           |  |  | 2576 | 		{
 | 
        
           |  |  | 2577 | 			SGameWare *gm = node->Data();
 | 
        
           |  |  | 2578 | 			lines.PushBack(CyString((long)gm->iPos) + " " + (long)gm->iType + " " + CyString((char)gm->cType) + " " + gm->sWareName);
 | 
        
           |  |  | 2579 | 		}
 | 
        
           |  |  | 2580 | 	}
 | 
        
           |  |  | 2581 |   | 
        
           |  |  | 2582 | 	for ( SStringList *str = m_lNonRemovedFiles.Head(); str; str = str->next )
 | 
        
           |  |  | 2583 | 		lines.PushBack(CyString("NonRemovedFile: ") + str->str);
 | 
        
           |  |  | 2584 |   | 
        
           |  |  | 2585 | 	if ( m_lGameShips.size() )
 | 
        
           |  |  | 2586 | 	{
 | 
        
           |  |  | 2587 | 		lines.PushBack(CyString("Ships: ") + (long)m_lGameShips.size());
 | 
        
           |  |  | 2588 |   | 
        
           |  |  | 2589 | 		for ( CListNode<SGameShip> *node = m_lGameShips.Front(); node; node = node->next() )
 | 
        
           |  |  | 2590 | 		{
 | 
        
           |  |  | 2591 | 			SGameShip *gm = node->Data();
 | 
        
           |  |  | 2592 | 			lines.PushBack(CyString((long)gm->iType) + " $#C:" + gm->sShipClass + " " + gm->sShipID);
 | 
        
           |  |  | 2593 | 		}
 | 
        
           |  |  | 2594 | 	}
 | 
        
           |  |  | 2595 |   | 
        
           |  |  | 2596 | 	// write created Files
 | 
        
           |  |  | 2597 | 	if ( !m_lCreatedFiles.Empty() )
 | 
        
           |  |  | 2598 | 	{
 | 
        
           |  |  | 2599 | 		for ( SStringList *node = m_lCreatedFiles.Head(); node; node = node->next )
 | 
        
           |  |  | 2600 | 			lines.PushBack(CyString("CreatedFile: ") + node->str.Remove(m_sCurrentDir));
 | 
        
           |  |  | 2601 | 	}
 | 
        
           |  |  | 2602 |   | 
        
           |  |  | 2603 | 	// write uninstall files
 | 
        
           |  |  | 2604 | 	if ( !m_lUninstallFiles.empty() )
 | 
        
           |  |  | 2605 | 	{
 | 
        
           |  |  | 2606 | 		for ( CListNode<C_File> *node = m_lUninstallFiles.Front(); node; node = node->next() )
 | 
        
           |  |  | 2607 | 		{
 | 
        
           |  |  | 2608 | 			C_File *uf = node->Data();
 | 
        
           |  |  | 2609 | 			CyString uString = "Uninstall: ";
 | 
        
           |  |  | 2610 | 			uString += CyString::Number((long)uf->GetCreationTime()) + " ";
 | 
        
           |  |  | 2611 | 			uString += uf->GetFilename();
 | 
        
           |  |  | 2612 | 			lines.PushBack(uString);
 | 
        
           |  |  | 2613 | 		}
 | 
        
           |  |  | 2614 | 	}
 | 
        
           |  |  | 2615 |   | 
        
           |  |  | 2616 | 	// write the original file data
 | 
        
           |  |  | 2617 | 	if ( !m_lOriginalFiles.empty() )
 | 
        
           |  |  | 2618 | 	{
 | 
        
           |  |  | 2619 | 		for ( CListNode<C_File> *node = m_lOriginalFiles.Front(); node; node = node->next() )
 | 
        
           |  |  | 2620 | 		{
 | 
        
           |  |  | 2621 | 			C_File *uf = node->Data();
 | 
        
           |  |  | 2622 | 			CyString uString = "Original: ";
 | 
        
           |  |  | 2623 | 			uString += CyString::Number((long)uf->GetFileType()) + " ";
 | 
        
           |  |  | 2624 | 			uString += uf->GetFilename();
 | 
        
           |  |  | 2625 | 			if ( uf->GetFileType() == FILETYPE_EXTRA && !uf->GetDir().Empty())
 | 
        
           |  |  | 2626 | 			{
 | 
        
           |  |  | 2627 | 				uString += ":";
 | 
        
           |  |  | 2628 | 				uString += uf->GetDir();
 | 
        
           |  |  | 2629 | 			}
 | 
        
           |  |  | 2630 | 			lines.PushBack(uString);
 | 
        
           |  |  | 2631 | 		}
 | 
        
           |  |  | 2632 | 	}
 | 
        
           |  |  | 2633 |   | 
        
           |  |  | 2634 | 	// write the global changes
 | 
        
           |  |  | 2635 | 	if ( !m_lGlobals.Empty() )
 | 
        
           |  |  | 2636 | 	{
 | 
        
           |  |  | 2637 | 		for ( SStringList *str = m_lGlobals.Head(); str; str = str->next )
 | 
        
           |  |  | 2638 | 			lines.PushBack(CyString("GlobalSetting: ") + str->str + ":" + str->data.Remove(";"));
 | 
        
           |  |  | 2639 | 	}
 | 
        
           |  |  | 2640 |   | 
        
           |  |  | 2641 | 	// write the fake patch ordering
 | 
        
           |  |  | 2642 | 	if ( !m_lFakePatchOrder.Empty() )
 | 
        
           |  |  | 2643 | 	{
 | 
        
           |  |  | 2644 | 		for ( SStringList *str = m_lFakePatchOrder.Head(); str; str = str->next )
 | 
        
           |  |  | 2645 | 			lines.PushBack(CyString("FakePatchOrder: ") + str->str + ":" + str->data);
 | 
        
           |  |  | 2646 | 	}
 | 
        
           |  |  | 2647 |   | 
        
           |  |  | 2648 | 	// write the global file list
 | 
        
           |  |  | 2649 | 	lines.PushBack("GlobalFiles:");
 | 
        
           |  |  | 2650 | 	int num = 0;
 | 
        
           |  |  | 2651 | 	for ( CListNode<C_File> *fn = m_lFiles.Front(); fn; fn = fn->next() )
 | 
        
           |  |  | 2652 | 	{
 | 
        
           |  |  | 2653 | 		C_File *f = fn->Data();
 | 
        
           |  |  | 2654 | 		f->SetPos(num++);
 | 
        
           |  |  | 2655 |   | 
        
           |  |  | 2656 | 		CyString line = CyString::Number(f->GetFileType()) + ":" + CyString::Number((long)f->GetCreationTime()) + ":" + f->GetDir() + ":";
 | 
        
           |  |  | 2657 | 		if ( f->IsShared() && !f->IsFakePatch() )
 | 
        
           |  |  | 2658 | 			line += "1:";
 | 
        
           |  |  | 2659 | 		else
 | 
        
           |  |  | 2660 | 			line += "0:";
 | 
        
           |  |  | 2661 |   | 
        
           |  |  | 2662 | 		CyString filename = f->GetFilePointer();
 | 
        
           |  |  | 2663 | 		filename.Remove(m_sCurrentDir);
 | 
        
           |  |  | 2664 |   | 
        
           |  |  | 2665 | 		if ( f->IsDisabled() )
 | 
        
           |  |  | 2666 | 			line += "D#";
 | 
        
           |  |  | 2667 |   | 
        
           |  |  | 2668 | 		line += "G#";
 | 
        
           |  |  | 2669 | 		line += (long)f->GetGame();
 | 
        
           |  |  | 2670 | 		line += "#";
 | 
        
           |  |  | 2671 |   | 
        
           |  |  | 2672 | 		line += filename;
 | 
        
           |  |  | 2673 |   | 
        
           |  |  | 2674 | 		if ( !f->GetOriginalName().Empty() )
 | 
        
           |  |  | 2675 | 		{
 | 
        
           |  |  | 2676 | 			line += "O#";
 | 
        
           |  |  | 2677 | 			line += f->GetOriginalName();
 | 
        
           |  |  | 2678 | 		}
 | 
        
           |  |  | 2679 |   | 
        
           |  |  | 2680 | 		lines.PushBack(line);
 | 
        
           |  |  | 2681 | 	}
 | 
        
           |  |  | 2682 |   | 
        
           |  |  | 2683 | 	// write the package list
 | 
        
           |  |  | 2684 | 	for ( CListNode<CBaseFile> *pn = m_lPackages.Front(); pn; pn = pn->next() )
 | 
        
           |  |  | 2685 | 	{
 | 
        
           |  |  | 2686 | 		CBaseFile *package = pn->Data();
 | 
        
           |  |  | 2687 |   | 
        
           |  |  | 2688 | 		if ( package->GetType() == TYPE_SPK )
 | 
        
           |  |  | 2689 | 			lines.PushBack("<script>");
 | 
        
           |  |  | 2690 | 		else if ( package->GetType() == TYPE_XSP )
 | 
        
           |  |  | 2691 | 			lines.PushBack("<ship>");
 | 
        
           |  |  | 2692 | 		else if ( package->GetType() == TYPE_ARCHIVE )
 | 
        
           |  |  | 2693 | 			lines.PushBack("<archive>");
 | 
        
           |  |  | 2694 | 		else if ( package->GetType() == TYPE_BASE )
 | 
        
           |  |  | 2695 | 			lines.PushBack("<base>");
 | 
        
           |  |  | 2696 | 		else
 | 
        
           |  |  | 2697 | 			continue;
 | 
        
           |  |  | 2698 |   | 
        
           |  |  | 2699 | 		if ( !package->GetFilename().Empty() )
 | 
        
           |  |  | 2700 | 			lines.PushBack(CyString("Installspk: ") + package->GetFilename());
 | 
        
           |  |  | 2701 |   | 
        
           |  |  | 2702 | 		CyString valuesline = package->CreateValuesLine();
 | 
        
           |  |  | 2703 | 		if ( valuesline.Right(1) == '\n' )
 | 
        
           |  |  | 2704 | 			valuesline.Truncate((int)valuesline.Length() - 1);
 | 
        
           |  |  | 2705 | 		lines.PushBack(valuesline);
 | 
        
           |  |  | 2706 |   | 
        
           |  |  | 2707 | 		if ( !package->IsEnabled() )
 | 
        
           |  |  | 2708 | 			lines.PushBack("Disabled");
 | 
        
           |  |  | 2709 | 		if ( !package->IsModifiedEnabled() )
 | 
        
           |  |  | 2710 | 			lines.PushBack("ModifiedDisabled");
 | 
        
           |  |  | 2711 |   | 
        
           |  |  | 2712 | 		if ( package->GetIcon() )
 | 
        
           |  |  | 2713 | 			lines.PushBack(CyString("Icon: ") + package->GetIconExt() + " " + package->GetIcon()->GetFilePointer() );
 | 
        
           |  |  | 2714 |   | 
        
           |  |  | 2715 | 		CyString fileline("Files:");
 | 
        
           |  |  | 2716 | 		for ( CListNode<C_File> *fn = package->GetFileList()->Front(); fn; fn = fn->next() )
 | 
        
           |  |  | 2717 | 		{
 | 
        
           |  |  | 2718 | 			C_File *f = fn->Data();
 | 
        
           |  |  | 2719 | 			fileline += " ";
 | 
        
           |  |  | 2720 | 			fileline += CyString::Number(f->GetPos());
 | 
        
           |  |  | 2721 | 		}
 | 
        
           |  |  | 2722 | 		lines.PushBack(fileline);
 | 
        
           |  |  | 2723 | 	}
 | 
        
           |  |  | 2724 |   | 
        
           |  |  | 2725 | 	lines.PushBack("</scripts>");
 | 
        
           |  |  | 2726 |   | 
        
           |  |  | 2727 | 	CFileIO datFile(m_sCurrentDir + "/PluginManager/PluginManager.dat");
 | 
        
           |  |  | 2728 |   | 
        
           |  |  | 2729 | 	CDirIO Dir(m_sCurrentDir);
 | 
        
           |  |  | 2730 | 	if ( !Dir.Exists("PluginManager") )
 | 
        
           |  |  | 2731 | 		Dir.Create("PluginManager");
 | 
        
           |  |  | 2732 |   | 
        
           |  |  | 2733 |   | 
        
           |  |  | 2734 | 	if ( !datFile.WriteFile(&lines) )
 | 
        
           |  |  | 2735 | 	{
 | 
        
           |  |  | 2736 | 	}
 | 
        
           |  |  | 2737 | }
 | 
        
           |  |  | 2738 |   | 
        
           |  |  | 2739 |   | 
        
           |  |  | 2740 | /**
 | 
        
           |  |  | 2741 |  * Get All Files
 | 
        
           |  |  | 2742 |  *
 | 
        
           |  |  | 2743 |  * Gets a list of all files, includes any child package files
 | 
        
           |  |  | 2744 |  */
 | 
        
           |  |  | 2745 | int CPackages::GetAllPackageFiles(CBaseFile *package, CLinkList<C_File> *fileList, bool includeChild)
 | 
        
           |  |  | 2746 | {
 | 
        
           |  |  | 2747 | 	for ( CListNode<C_File> *node = package->GetFileList()->Front(); node; node = node->next() )
 | 
        
           |  |  | 2748 | 	{
 | 
        
           |  |  | 2749 | 		C_File *f = node->Data();
 | 
        
           |  |  | 2750 | 		if ( !fileList->FindData(f) )
 | 
        
           |  |  | 2751 | 			fileList->push_back(f);
 | 
        
           |  |  | 2752 | 	}
 | 
        
           |  |  | 2753 |   | 
        
           |  |  | 2754 | 	if ( includeChild )
 | 
        
           |  |  | 2755 | 	{
 | 
        
           |  |  | 2756 | 		CLinkList<CBaseFile> childList;
 | 
        
           |  |  | 2757 | 		if ( this->GetChildPackages(package, &childList) )
 | 
        
           |  |  | 2758 | 		{
 | 
        
           |  |  | 2759 | 			for ( CBaseFile *child = childList.First(); child; child = childList.Next() )
 | 
        
           |  |  | 2760 | 				this->GetAllPackageFiles(child, fileList, includeChild);
 | 
        
           |  |  | 2761 | 		}
 | 
        
           |  |  | 2762 | 	}
 | 
        
           |  |  | 2763 |   | 
        
           |  |  | 2764 | 	// disablign for vanilla, make sure we add all files
 | 
        
           |  |  | 2765 | 	if ( m_bDisableVanilla )
 | 
        
           |  |  | 2766 | 	{
 | 
        
           |  |  | 2767 | 		for ( CListNode<C_File> *node = m_lFiles.Front(); node; node = node->next() )
 | 
        
           |  |  | 2768 | 		{
 | 
        
           |  |  | 2769 | 			C_File *f = node->Data();
 | 
        
           |  |  | 2770 | 			if ( !fileList->FindData(f) )
 | 
        
           |  |  | 2771 | 				fileList->push_back(f);
 | 
        
           |  |  | 2772 | 		}
 | 
        
           |  |  | 2773 | 	}
 | 
        
           |  |  | 2774 |   | 
        
           |  |  | 2775 | 	return fileList->size();
 | 
        
           |  |  | 2776 | }
 | 
        
           |  |  | 2777 |   | 
        
           |  |  | 2778 | int CPackages::GetAllPackageFiles(CLinkList<CBaseFile> *list, CLinkList<C_File> *fileList, bool includeChild)
 | 
        
           |  |  | 2779 | {
 | 
        
           |  |  | 2780 | 	for ( CListNode<CBaseFile> *node = list->Front(); node; node = node->next() )
 | 
        
           |  |  | 2781 | 		this->GetAllPackageFiles(node->Data(), fileList, includeChild);
 | 
        
           |  |  | 2782 | 	return fileList->size();
 | 
        
           |  |  | 2783 | }
 | 
        
           |  |  | 2784 |   | 
        
           |  |  | 2785 | /**
 | 
        
           |  |  | 2786 |  * Add Log
 | 
        
           |  |  | 2787 |  *
 | 
        
           |  |  | 2788 |  * Adds a log entry to displayed at end
 | 
        
           |  |  | 2789 |  */
 | 
        
           |  |  | 2790 | void CPackages::AddLogEntry(int type, CyString args, CyStringList *errors)
 | 
        
           |  |  | 2791 | {
 | 
        
           |  |  | 2792 | 	if ( !errors )
 | 
        
           |  |  | 2793 | 		return;
 | 
        
           |  |  | 2794 |   | 
        
           |  |  | 2795 | 	errors->PushBack(args, ERRORLOG(type));
 | 
        
           |  |  | 2796 | }
 | 
        
           |  |  | 2797 |   | 
        
           |  |  | 2798 | /**
 | 
        
           |  |  | 2799 |  * Enable a package
 | 
        
           |  |  | 2800 |  *
 | 
        
           |  |  | 2801 |  * Enables all files in the package, unless they are already enabled, ie, used by other packages
 | 
        
           |  |  | 2802 |  * Backs up any original files before attempting to enable the file
 | 
        
           |  |  | 2803 |  *
 | 
        
           |  |  | 2804 |  * Fake patches are renamed to the next available slot
 | 
        
           |  |  | 2805 |  *
 | 
        
           |  |  | 2806 |  * Clears up the "PluginManager/Disabled" directory
 | 
        
           |  |  | 2807 |  *
 | 
        
           |  |  | 2808 |  * param: package		- The package class to be removed
 | 
        
           |  |  | 2809 |  * param: errors		- The string list for all the status for debugging, ie has an entry for whats happened to every file
 | 
        
           |  |  | 2810 |  * param: progress		- The progress class, updates a progress screen of the derived class
 | 
        
           |  |  | 2811 |  *
 | 
        
           |  |  | 2812 |  * return: boolen - Returns true if the package enabling was successful
 | 
        
           |  |  | 2813 |  */
 | 
        
           |  |  | 2814 | bool CPackages::EnablePackage ( CBaseFile *package, CyStringList *errors, CProgressInfo *progress )
 | 
        
           |  |  | 2815 | {
 | 
        
           |  |  | 2816 | 	ClearError();
 | 
        
           |  |  | 2817 |   | 
        
           |  |  | 2818 | 	// if already enabled, just skip
 | 
        
           |  |  | 2819 | 	if ( package->IsEnabled() )
 | 
        
           |  |  | 2820 | 		return true;
 | 
        
           |  |  | 2821 |   | 
        
           |  |  | 2822 | 	// check if parent is enabled
 | 
        
           |  |  | 2823 | 	if ( package->GetParent() && !package->GetParent()->IsEnabled() )
 | 
        
           |  |  | 2824 | 	{
 | 
        
           |  |  | 2825 | 		m_iError = PKERR_NOPARENT;
 | 
        
           |  |  | 2826 | 		return false;
 | 
        
           |  |  | 2827 | 	}
 | 
        
           |  |  | 2828 |   | 
        
           |  |  | 2829 | 	// check for modified
 | 
        
           |  |  | 2830 | 	if ( m_bVanilla && !package->IsSigned() )
 | 
        
           |  |  | 2831 | 	{
 | 
        
           |  |  | 2832 | 		m_iError = PKERR_MODIFIED;
 | 
        
           |  |  | 2833 | 		return false;
 | 
        
           |  |  | 2834 | 	}
 | 
        
           |  |  | 2835 |   | 
        
           |  |  | 2836 | 	if ( this->PrepareEnablePackage(package) )
 | 
        
           |  |  | 2837 | 		return this->EnablePreparedPackages(errors, progress);
 | 
        
           |  |  | 2838 |   | 
        
           |  |  | 2839 | 	return false;
 | 
        
           |  |  | 2840 | }
 | 
        
           |  |  | 2841 | bool CPackages::EnablePreparedPackages ( CyStringList *errors, CProgressInfo *progress, CLinkList<CBaseFile> *enabledPackages )
 | 
        
           |  |  | 2842 | {
 | 
        
           |  |  | 2843 | 	ClearError();
 | 
        
           |  |  | 2844 |   | 
        
           |  |  | 2845 | 	// get all files, including children
 | 
        
           |  |  | 2846 | 	CLinkList<C_File> fileList;
 | 
        
           |  |  | 2847 | 	int maxFiles = this->GetAllPackageFiles(&m_lEnableList, &fileList, false);
 | 
        
           |  |  | 2848 |   | 
        
           |  |  | 2849 | 	int fileCount = 0;
 | 
        
           |  |  | 2850 | 	// we use this list to match cat and dat files
 | 
        
           |  |  | 2851 | 	CyStringList fakePatches;
 | 
        
           |  |  | 2852 | 	for ( CListNode<C_File> *node = fileList.Front(); node; node = node->next() )
 | 
        
           |  |  | 2853 | 	{
 | 
        
           |  |  | 2854 | 		C_File *f = node->Data();
 | 
        
           |  |  | 2855 | 		if ( f->GetGame() && m_iGame ) {
 | 
        
           |  |  | 2856 | 			if ( f->GetGame() != m_iGame )
 | 
        
           |  |  | 2857 | 				continue;
 | 
        
           |  |  | 2858 | 		}
 | 
        
           |  |  | 2859 | 		CBaseFile *package = NULL;
 | 
        
           |  |  | 2860 | 		for ( CListNode<CBaseFile> *node = m_lEnableList.Front(); node; node = node->next() )
 | 
        
           |  |  | 2861 | 		{
 | 
        
           |  |  | 2862 | 			CBaseFile *p = node->Data();
 | 
        
           |  |  | 2863 | 			if ( p->IsFileAdded(f) )
 | 
        
           |  |  | 2864 | 			{
 | 
        
           |  |  | 2865 | 				package = p;
 | 
        
           |  |  | 2866 | 				break;
 | 
        
           |  |  | 2867 | 			}
 | 
        
           |  |  | 2868 | 		}
 | 
        
           |  |  | 2869 |   | 
        
           |  |  | 2870 | 		if ( progress )
 | 
        
           |  |  | 2871 | 		{
 | 
        
           |  |  | 2872 | 			progress->UpdateProgress(fileCount++, maxFiles);
 | 
        
           |  |  | 2873 | 			progress->UpdateFile(f);
 | 
        
           |  |  | 2874 | 		}
 | 
        
           |  |  | 2875 |   | 
        
           |  |  | 2876 | 		// only move fiels that are disabled
 | 
        
           |  |  | 2877 | 		if ( !f->IsDisabled() )
 | 
        
           |  |  | 2878 | 			continue;
 | 
        
           |  |  | 2879 |   | 
        
           |  |  | 2880 | 		// make the directory if it dont exist
 | 
        
           |  |  | 2881 | 		CDirIO Dir(m_sCurrentDir);
 | 
        
           |  |  | 2882 |   | 
        
           |  |  | 2883 | 		// fake patches are in the root, no need for directory
 | 
        
           |  |  | 2884 | 		if ( !f->IsFakePatch() )
 | 
        
           |  |  | 2885 | 		{
 | 
        
           |  |  | 2886 | 			if ( !Dir.Exists(f->GetDirectory(package)) )
 | 
        
           |  |  | 2887 | 			{
 | 
        
           |  |  | 2888 | 				if ( !Dir.Create(f->GetDirectory(package)) )
 | 
        
           |  |  | 2889 | 				{
 | 
        
           |  |  | 2890 | 					this->AddLogEntry(SPKINSTALL_CREATEDIRECTORY_FAIL, f->GetDirectory(package), errors);
 | 
        
           |  |  | 2891 | 					continue;
 | 
        
           |  |  | 2892 | 				}
 | 
        
           |  |  | 2893 | 				this->AddLogEntry(SPKINSTALL_CREATEDIRECTORY, f->GetDirectory(package), errors);
 | 
        
           |  |  | 2894 | 			}
 | 
        
           |  |  | 2895 | 		}
 | 
        
           |  |  | 2896 |   | 
        
           |  |  | 2897 | 		// check if theres an original file to backup
 | 
        
           |  |  | 2898 | 		C_File *of = GetOriginalFile(f);
 | 
        
           |  |  | 2899 | 		if ( of )
 | 
        
           |  |  | 2900 | 		{
 | 
        
           |  |  | 2901 | 			// check if the orignal file is already backed up
 | 
        
           |  |  | 2902 | 			if ( !CFileIO(m_sCurrentDir + "/PluginManager/Original/" + f->GetNameDirectory(package)).Exists() )
 | 
        
           |  |  | 2903 | 			{
 | 
        
           |  |  | 2904 | 				// lets back up the file now
 | 
        
           |  |  | 2905 | 				BackupOriginalFile(of, errors);
 | 
        
           |  |  | 2906 | 			}
 | 
        
           |  |  | 2907 | 		}
 | 
        
           |  |  | 2908 |   | 
        
           |  |  | 2909 | 		CyString newFilename = f->GetNameDirectory(package);
 | 
        
           |  |  | 2910 |   | 
        
           |  |  | 2911 | 		// fake patches need to be renamed
 | 
        
           |  |  | 2912 | 		if ( f->IsFakePatch() )
 | 
        
           |  |  | 2913 | 		{
 | 
        
           |  |  | 2914 | 			// first check if the matching file has been done already
 | 
        
           |  |  | 2915 | 			SStringList *foundStr = fakePatches.FindString(f->GetBaseName());
 | 
        
           |  |  | 2916 |   | 
        
           |  |  | 2917 | 			// already done one, simply change this to match
 | 
        
           |  |  | 2918 | 			if ( foundStr )
 | 
        
           |  |  | 2919 | 				newFilename = foundStr->data + "." + f->GetFileExt();
 | 
        
           |  |  | 2920 |   | 
        
           |  |  | 2921 | 			// we need to find the next available number instead
 | 
        
           |  |  | 2922 | 			else
 | 
        
           |  |  | 2923 | 			{
 | 
        
           |  |  | 2924 | 				CyString newPos = CyString::Number(FindNextFakePatch()).PadNumber(2);
 | 
        
           |  |  | 2925 | 				newFilename = newPos + "." + f->GetFileExt();
 | 
        
           |  |  | 2926 | 				// and wee need to push this onto the string list so we can adjust the matchign pair
 | 
        
           |  |  | 2927 | 				fakePatches.PushBack(f->GetBaseName(), newPos);
 | 
        
           |  |  | 2928 | 			}
 | 
        
           |  |  | 2929 | 		}
 | 
        
           |  |  | 2930 |   | 
        
           |  |  | 2931 | 		// lets actually move the file back now
 | 
        
           |  |  | 2932 | 		// !!error checking!!
 | 
        
           |  |  | 2933 | 		CFileIO currentFile(f->GetFilePointer());
 | 
        
           |  |  | 2934 | 		CFileIO newFile(m_sCurrentDir + "/" + newFilename);
 | 
        
           |  |  | 2935 | 		if ( !currentFile.Exists() )
 | 
        
           |  |  | 2936 | 		{
 | 
        
           |  |  | 2937 | 			// missing file ??
 | 
        
           |  |  | 2938 | 			if ( !newFile.Exists() )
 | 
        
           |  |  | 2939 | 			{
 | 
        
           |  |  | 2940 | 				this->AddLogEntry(SPKINSTALL_MISSINGFILE, newFilename, errors);
 | 
        
           |  |  | 2941 | 				continue;
 | 
        
           |  |  | 2942 | 			}
 | 
        
           |  |  | 2943 | 		}
 | 
        
           |  |  | 2944 | 		// remove existing file
 | 
        
           |  |  | 2945 | 		// file exists, so lets try to move it
 | 
        
           |  |  | 2946 | 		else
 | 
        
           |  |  | 2947 | 		{
 | 
        
           |  |  | 2948 | 			if ( newFile.Exists() )
 | 
        
           |  |  | 2949 | 				newFile.Remove();
 | 
        
           |  |  | 2950 |   | 
        
           |  |  | 2951 | 			if ( !currentFile.Rename(newFile.GetFullFilename()) )
 | 
        
           |  |  | 2952 | 			{
 | 
        
           |  |  | 2953 | 				this->AddLogEntry(SPKINSTALL_ENABLEFILE_FAIL, newFilename, errors);
 | 
        
           |  |  | 2954 | 				continue;
 | 
        
           |  |  | 2955 | 			}
 | 
        
           |  |  | 2956 | 		}
 | 
        
           |  |  | 2957 |   | 
        
           |  |  | 2958 | 		this->AddLogEntry(SPKINSTALL_ENABLEFILE, newFilename, errors);
 | 
        
           |  |  | 2959 |   | 
        
           |  |  | 2960 | 		// adjust the internal name to match the new filename
 | 
        
           |  |  | 2961 | 		f->SetFilename(m_sCurrentDir + "/" + newFilename);
 | 
        
           |  |  | 2962 | 		// no longer disabled, we need to remove the flag
 | 
        
           |  |  | 2963 | 		f->SetDisabled(false);
 | 
        
           |  |  | 2964 | 	}
 | 
        
           |  |  | 2965 |   | 
        
           |  |  | 2966 | 	// recursive, auto enable all children
 | 
        
           |  |  | 2967 | 	CBaseFile *oldMod = m_pEnabledMod;
 | 
        
           |  |  | 2968 | 	CBaseFile *pMod = NULL;
 | 
        
           |  |  | 2969 |   | 
        
           |  |  | 2970 | 	for ( CListNode<CBaseFile> *node = m_lEnableList.Front(); node; node = node->next() )
 | 
        
           |  |  | 2971 | 	{
 | 
        
           |  |  | 2972 | 		CBaseFile *p = node->Data();
 | 
        
           |  |  | 2973 | 		p->SetEnabled(true);
 | 
        
           |  |  | 2974 | 		if ( p->IsMod() && !pMod )
 | 
        
           |  |  | 2975 | 			pMod = p;
 | 
        
           |  |  | 2976 |   | 
        
           |  |  | 2977 | 		if ( enabledPackages )
 | 
        
           |  |  | 2978 | 			enabledPackages->push_back(p);
 | 
        
           |  |  | 2979 | 	}
 | 
        
           |  |  | 2980 |   | 
        
           |  |  | 2981 | 	if ( pMod )
 | 
        
           |  |  | 2982 | 		m_pEnabledMod = pMod;
 | 
        
           |  |  | 2983 |   | 
        
           |  |  | 2984 | 	// disabled the mod
 | 
        
           |  |  | 2985 | 	if ( oldMod && oldMod != m_pEnabledMod && !m_bForceModInstall )
 | 
        
           |  |  | 2986 | 		this->DisablePackage(oldMod, errors, progress);
 | 
        
           |  |  | 2987 |   | 
        
           |  |  | 2988 | 	// lets remove all the directories we might have left empty
 | 
        
           |  |  | 2989 | 	CyStringList removeDirs;
 | 
        
           |  |  | 2990 | 	removeDirs.PushBack(CyString("PluginManager/Disabled"));
 | 
        
           |  |  | 2991 | 	RemoveUnusedDirectories(removeDirs, errors);
 | 
        
           |  |  | 2992 |   | 
        
           |  |  | 2993 | 	m_lEnableList.clear();
 | 
        
           |  |  | 2994 |   | 
        
           |  |  | 2995 | 	this->WriteData();
 | 
        
           |  |  | 2996 |   | 
        
           |  |  | 2997 | 	return true;
 | 
        
           |  |  | 2998 | }
 | 
        
           |  |  | 2999 |   | 
        
           |  |  | 3000 |   | 
        
           |  |  | 3001 | bool CPackages::DisablePreparedPackages ( CyStringList *errors, CProgressInfo *progress, CLinkList<CBaseFile> *disabledPackages )
 | 
        
           |  |  | 3002 | {
 | 
        
           |  |  | 3003 | 	if ( progress )
 | 
        
           |  |  | 3004 | 		progress->UpdateStatus(PROGRESS_DISABLEFILE);
 | 
        
           |  |  | 3005 |   | 
        
           |  |  | 3006 | 	UpdateUsedFiles(&m_lDisableList, false);
 | 
        
           |  |  | 3007 |   | 
        
           |  |  | 3008 | 	// checks if there are any original files to restore and if any fake patches were disabled to reshuffle
 | 
        
           |  |  | 3009 | 	bool original = false, shuffle = false;
 | 
        
           |  |  | 3010 |   | 
        
           |  |  | 3011 | 	// holds our list of directories that we might need to remove, only empty ones from this list will actually be removed
 | 
        
           |  |  | 3012 | 	CyStringList removeDirs;
 | 
        
           |  |  | 3013 |   | 
        
           |  |  | 3014 | 	// get all files, including children
 | 
        
           |  |  | 3015 | 	CLinkList<C_File> fileList;
 | 
        
           |  |  | 3016 | 	int maxFiles = this->GetAllPackageFiles(&m_lDisableList, &fileList, true);
 | 
        
           |  |  | 3017 |   | 
        
           |  |  | 3018 | 	// interate through all the files in the package
 | 
        
           |  |  | 3019 | 	int fileCount = 0;
 | 
        
           |  |  | 3020 | 	for ( CListNode<C_File> *node = fileList.Front(); node; node = node->next() )
 | 
        
           |  |  | 3021 | 	{
 | 
        
           |  |  | 3022 | 		C_File *f = node->Data();
 | 
        
           |  |  | 3023 | 		CBaseFile *checkPackage = NULL;
 | 
        
           |  |  | 3024 | 		for ( CListNode<CBaseFile> *node = m_lDisableList.Front(); node; node = node->next() )
 | 
        
           |  |  | 3025 | 		{
 | 
        
           |  |  | 3026 | 			CBaseFile *p = node->Data();
 | 
        
           |  |  | 3027 | 			if ( p->IsFileAdded(f) )
 | 
        
           |  |  | 3028 | 			{
 | 
        
           |  |  | 3029 | 				checkPackage = p;
 | 
        
           |  |  | 3030 | 				break;
 | 
        
           |  |  | 3031 | 			}
 | 
        
           |  |  | 3032 | 		}
 | 
        
           |  |  | 3033 |   | 
        
           |  |  | 3034 | 		// update the progress count for the current file
 | 
        
           |  |  | 3035 | 		if ( progress )
 | 
        
           |  |  | 3036 | 		{
 | 
        
           |  |  | 3037 | 			progress->UpdateProgress(++fileCount, maxFiles);
 | 
        
           |  |  | 3038 | 			progress->UpdateFile(f);
 | 
        
           |  |  | 3039 | 		}
 | 
        
           |  |  | 3040 |   | 
        
           |  |  | 3041 | 		// only delete files that are not used by any other enabled packages, counter from UpdateUsedFiles()
 | 
        
           |  |  | 3042 | 		if ( f->GetUsed() || (f->IsShared() && !m_bDisableVanilla) )
 | 
        
           |  |  | 3043 | 			continue;
 | 
        
           |  |  | 3044 |   | 
        
           |  |  | 3045 | 		// file is already disabled, no need to disable again
 | 
        
           |  |  | 3046 | 		if ( f->IsDisabled() )
 | 
        
           |  |  | 3047 | 			continue;
 | 
        
           |  |  | 3048 |   | 
        
           |  |  | 3049 | 		// readmes, uninstall and extra files dont need to be disabled
 | 
        
           |  |  | 3050 | 		// Extra files not in the "Extras" directory could be anywhere, so these should be disabled incase they are game changing files, ie in "types"
 | 
        
           |  |  | 3051 | 		if ( f->GetFileType() == FILETYPE_README || f->GetFileType() == FILETYPE_UNINSTALL || (f->GetFileType() == FILETYPE_EXTRA && f->GetDir().Left(5).lower() == "Extra") )
 | 
        
           |  |  | 3052 | 			continue;
 | 
        
           |  |  | 3053 |   | 
        
           |  |  | 3054 | 		// check if there is a matching uninstall file, ie there the script file is also an uninstall script file for a previously uninstalled package that has yet to be removed
 | 
        
           |  |  | 3055 | 		if ( f->GetFileType() == FILETYPE_SCRIPT )
 | 
        
           |  |  | 3056 | 		{
 | 
        
           |  |  | 3057 | 			bool found = false;
 | 
        
           |  |  | 3058 | 			for ( CListNode<C_File> *uNode = m_lUninstallFiles.Front(); uNode; uNode = uNode->next() )
 | 
        
           |  |  | 3059 | 			{
 | 
        
           |  |  | 3060 | 				C_File *uFile = uNode->Data();
 | 
        
           |  |  | 3061 | 				if ( uFile->GetFilename().Compare(f->GetFilename()) )
 | 
        
           |  |  | 3062 | 				{
 | 
        
           |  |  | 3063 | 					found = true;
 | 
        
           |  |  | 3064 | 					break;
 | 
        
           |  |  | 3065 | 				}
 | 
        
           |  |  | 3066 | 			}
 | 
        
           |  |  | 3067 |   | 
        
           |  |  | 3068 | 			if ( found )
 | 
        
           |  |  | 3069 | 				continue;
 | 
        
           |  |  | 3070 | 		}
 | 
        
           |  |  | 3071 |   | 
        
           |  |  | 3072 | 		if ( f->GetFileType() == FILETYPE_MOD && !f->IsFakePatch() && f->CheckFileExt("cat") )
 | 
        
           |  |  | 3073 | 		{
 | 
        
           |  |  | 3074 | 			if ( f->GetBaseName().Compare(m_sSetMod) )
 | 
        
           |  |  | 3075 | 				m_sSetMod = NullString;
 | 
        
           |  |  | 3076 | 		}
 | 
        
           |  |  | 3077 |   | 
        
           |  |  | 3078 | 		// file is not being used by any enabled package
 | 
        
           |  |  | 3079 | 		// set disabled and move to disabled directory
 | 
        
           |  |  | 3080 | 		CDirIO Dir(m_sCurrentDir);
 | 
        
           |  |  | 3081 | 		CyString newFilename = "PluginManager/Disabled/";
 | 
        
           |  |  | 3082 |   | 
        
           |  |  | 3083 | 		// fake patches have thier own special directory
 | 
        
           |  |  | 3084 | 		if ( f->IsFakePatch() )
 | 
        
           |  |  | 3085 | 			newFilename += "FakePatches";
 | 
        
           |  |  | 3086 | 		// otherwise we put them in thier usual directory structure inside the disabled dir
 | 
        
           |  |  | 3087 | 		else
 | 
        
           |  |  | 3088 | 			newFilename += f->GetDirectory(NULL);
 | 
        
           |  |  | 3089 |   | 
        
           |  |  | 3090 | 		// make sure the directory exists so we can move the file
 | 
        
           |  |  | 3091 | 		if ( !Dir.Exists(newFilename) )
 | 
        
           |  |  | 3092 | 		{
 | 
        
           |  |  | 3093 | 			// we couldn't create the directory for some reason, this is not good
 | 
        
           |  |  | 3094 | 			if ( !Dir.Create(newFilename) )
 | 
        
           |  |  | 3095 | 			{
 | 
        
           |  |  | 3096 | 				this->AddLogEntry(SPKINSTALL_CREATEDIRECTORY_FAIL, newFilename, errors);
 | 
        
           |  |  | 3097 | 				continue;
 | 
        
           |  |  | 3098 | 			}
 | 
        
           |  |  | 3099 | 			this->AddLogEntry(SPKINSTALL_CREATEDIRECTORY, newFilename, errors);
 | 
        
           |  |  | 3100 | 		}
 | 
        
           |  |  | 3101 |   | 
        
           |  |  | 3102 | 		// fake patches need a special directory and filename so they dont overright each other as thier filenames are always changes
 | 
        
           |  |  | 3103 | 		// if a package with a fake patch is installed while another one is disabled, it will fill the gap left by the disabled one
 | 
        
           |  |  | 3104 | 		// they will then end up with the same filename, if it gets disabled they would overright each other, so we change the filename to prevent that from happening
 | 
        
           |  |  | 3105 | 		if ( f->IsFakePatch() )
 | 
        
           |  |  | 3106 | 		{
 | 
        
           |  |  | 3107 | 			// find package the fake patch belongs to
 | 
        
           |  |  | 3108 | 			if ( checkPackage )
 | 
        
           |  |  | 3109 | 			{
 | 
        
           |  |  | 3110 | 				newFilename = m_sCurrentDir + "/PluginManager/Disabled/FakePatches/FakePatch_" + checkPackage->GetNameValidFile() + "_" + checkPackage->GetAuthor() + "_" + f->GetName();
 | 
        
           |  |  | 3111 | 				shuffle = true;
 | 
        
           |  |  | 3112 | 			}
 | 
        
           |  |  | 3113 | 		}
 | 
        
           |  |  | 3114 | 		else if ( f->IsAutoTextFile() )
 | 
        
           |  |  | 3115 | 		{
 | 
        
           |  |  | 3116 | 			if ( checkPackage )
 | 
        
           |  |  | 3117 | 			{
 | 
        
           |  |  | 3118 | 				newFilename = m_sCurrentDir + "/PluginManager/Disabled/TextFiles/Text_" + checkPackage->GetNameValidFile() + "_" + checkPackage->GetAuthor() + "_" + f->GetName();
 | 
        
           |  |  | 3119 | 				shuffle = true;
 | 
        
           |  |  | 3120 | 			}
 | 
        
           |  |  | 3121 | 		}
 | 
        
           |  |  | 3122 | 		// otherwise we can just use the standard filename
 | 
        
           |  |  | 3123 | 		else
 | 
        
           |  |  | 3124 | 			newFilename = m_sCurrentDir + "/PluginManager/Disabled/" + f->GetNameDirectory(checkPackage);
 | 
        
           |  |  | 3125 |   | 
        
           |  |  | 3126 | 		// now to move the file by renameing it to its new location
 | 
        
           |  |  | 3127 | 		// !!error checking!!
 | 
        
           |  |  | 3128 | 		// check the file, if it doesn't exist, and exists as disabled, we should just adjust the setting instead of an error
 | 
        
           |  |  | 3129 | 		CFileIO currentFile(f->GetFilePointer());
 | 
        
           |  |  | 3130 | 		if ( !currentFile.Exists() )
 | 
        
           |  |  | 3131 | 		{
 | 
        
           |  |  | 3132 | 			if ( !CFileIO(newFilename).Exists() )
 | 
        
           |  |  | 3133 | 			{
 | 
        
           |  |  | 3134 | 				this->AddLogEntry(SPKINSTALL_MISSINGFILE, f->GetNameDirectory(checkPackage), errors);
 | 
        
           |  |  | 3135 | 				continue;
 | 
        
           |  |  | 3136 | 			}
 | 
        
           |  |  | 3137 | 		}
 | 
        
           |  |  | 3138 | 		// otherwise the file must exists, so lets move it
 | 
        
           |  |  | 3139 | 		else if ( !currentFile.Rename(newFilename) )
 | 
        
           |  |  | 3140 | 		{
 | 
        
           |  |  | 3141 | 			this->AddLogEntry(SPKINSTALL_DISABLEFILE_FAIL, f->GetNameDirectory(checkPackage), errors);
 | 
        
           |  |  | 3142 | 			continue;
 | 
        
           |  |  | 3143 | 		}
 | 
        
           |  |  | 3144 |   | 
        
           |  |  | 3145 | 		// must have been fine
 | 
        
           |  |  | 3146 | 		this->AddLogEntry(SPKINSTALL_DISABLEFILE, f->GetNameDirectory(checkPackage), errors);
 | 
        
           |  |  | 3147 |   | 
        
           |  |  | 3148 | 		// check if its an original file and restore
 | 
        
           |  |  | 3149 | 		if ( IsOriginalFile(f) )
 | 
        
           |  |  | 3150 | 		{
 | 
        
           |  |  | 3151 | 			CFileIO of(m_sCurrentDir + "/PluginManager/Original/" + f->GetNameDirectory(checkPackage));
 | 
        
           |  |  | 3152 | 			if ( of.Exists() )
 | 
        
           |  |  | 3153 | 			{
 | 
        
           |  |  | 3154 | 				original = true;
 | 
        
           |  |  | 3155 | 				if ( of.Rename(m_sCurrentDir + "/" + f->GetNameDirectory(checkPackage)) )
 | 
        
           |  |  | 3156 | 					this->AddLogEntry(SPKINSTALL_ORIGINAL_RESTORE, f->GetNameDirectory(checkPackage), errors);
 | 
        
           |  |  | 3157 | 				else
 | 
        
           |  |  | 3158 | 					this->AddLogEntry(SPKINSTALL_ORIGINAL_RESTORE_FAIL, f->GetNameDirectory(checkPackage), errors);
 | 
        
           |  |  | 3159 | 			}
 | 
        
           |  |  | 3160 | 		}
 | 
        
           |  |  | 3161 |   | 
        
           |  |  | 3162 | 		// extra file thats not in the extras directory
 | 
        
           |  |  | 3163 | 		if ( f->GetFileType() == FILETYPE_EXTRA || f->GetFileType() == FILETYPE_MAP || f->GetFileType() == FILETYPE_SOUND )
 | 
        
           |  |  | 3164 | 			removeDirs.PushBack(f->GetDirectory(checkPackage), NullString, true);
 | 
        
           |  |  | 3165 |   | 
        
           |  |  | 3166 | 		// change the filename
 | 
        
           |  |  | 3167 | 		f->SetFilename(newFilename);
 | 
        
           |  |  | 3168 |   | 
        
           |  |  | 3169 | 		// finally mark the file as disabled so we know not to try to move it again
 | 
        
           |  |  | 3170 | 		f->SetDisabled(true);
 | 
        
           |  |  | 3171 | 	}
 | 
        
           |  |  | 3172 |   | 
        
           |  |  | 3173 | 	// a fake patch has been disabled, we need to reshuffle the rest to fill in any gaps
 | 
        
           |  |  | 3174 | 	if ( shuffle )
 | 
        
           |  |  | 3175 | 	{
 | 
        
           |  |  | 3176 | 		if ( progress )
 | 
        
           |  |  | 3177 | 			progress->UpdateStatus(PROGRESS_SHUFFLEFAKE);
 | 
        
           |  |  | 3178 | 		ShuffleFakePatches(errors);
 | 
        
           |  |  | 3179 | 		ShuffleTextFiles(errors);
 | 
        
           |  |  | 3180 | 	}
 | 
        
           |  |  | 3181 |   | 
        
           |  |  | 3182 | 	// original files were restored, check to remove the original file directory if its now empty
 | 
        
           |  |  | 3183 | 	if ( original )
 | 
        
           |  |  | 3184 | 		removeDirs.PushBack(CyString("PluginManager/Original"));
 | 
        
           |  |  | 3185 |   | 
        
           |  |  | 3186 | 	// remove any empty directories that we might have left
 | 
        
           |  |  | 3187 | 	if ( !removeDirs.Empty() )
 | 
        
           |  |  | 3188 | 		RemoveUnusedDirectories(removeDirs, errors);
 | 
        
           |  |  | 3189 |   | 
        
           |  |  | 3190 | 	// finally mark the whole package as disabled
 | 
        
           |  |  | 3191 | 	// recursive, we need to disable all children
 | 
        
           |  |  | 3192 | 	for ( CBaseFile *child = m_lDisableList.First(); child; child = m_lDisableList.Next() )
 | 
        
           |  |  | 3193 | 	{
 | 
        
           |  |  | 3194 | 		if ( m_pEnabledMod == child )
 | 
        
           |  |  | 3195 | 			m_pEnabledMod = NULL;
 | 
        
           |  |  | 3196 | 		child->SetEnabled(false);
 | 
        
           |  |  | 3197 |   | 
        
           |  |  | 3198 | 		if ( disabledPackages )
 | 
        
           |  |  | 3199 | 			disabledPackages->push_back(child);
 | 
        
           |  |  | 3200 | 	}
 | 
        
           |  |  | 3201 |   | 
        
           |  |  | 3202 | 	// disabling has completed successfully, we hope
 | 
        
           |  |  | 3203 | 	m_bDisableVanilla = false;
 | 
        
           |  |  | 3204 | 	m_lDisableList.clear();
 | 
        
           |  |  | 3205 |   | 
        
           |  |  | 3206 | 	this->WriteData();
 | 
        
           |  |  | 3207 |   | 
        
           |  |  | 3208 | 	return true;
 | 
        
           |  |  | 3209 | }
 | 
        
           |  |  | 3210 |   | 
        
           |  |  | 3211 | /**
 | 
        
           |  |  | 3212 |  * Disables the selected package
 | 
        
           |  |  | 3213 |  *
 | 
        
           |  |  | 3214 |  * Disables all enabled files that are not being used by any other enabled package
 | 
        
           |  |  | 3215 |  * Any files that are being used by other enabled packages are skipped and left enabled
 | 
        
           |  |  | 3216 |  *
 | 
        
           |  |  | 3217 |  * Original Files are restored when file is disabled
 | 
        
           |  |  | 3218 |  *
 | 
        
           |  |  | 3219 |  * Fake patches are shuffled to fill in any gaps caused by disabling fake patches
 | 
        
           |  |  | 3220 |  *
 | 
        
           |  |  | 3221 |  * All files go into the Plugin/Disabled directory into thier respective directories.
 | 
        
           |  |  | 3222 |  *
 | 
        
           |  |  | 3223 |  * Any directories left empty when disabling files are then removed
 | 
        
           |  |  | 3224 |  *
 | 
        
           |  |  | 3225 |  * param: package	- Package file to be disabled
 | 
        
           |  |  | 3226 |  * param: errors	- A string list used to add the status as it progresses, used in debugging output
 | 
        
           |  |  | 3227 |  * param: progress	- The progress class, updates the progress of the current disabling.  Needs a divered class to report the progress somewhere
 | 
        
           |  |  | 3228 |  *
 | 
        
           |  |  | 3229 |  * return: boolean, true if there was no errors, otherwise false
 | 
        
           |  |  | 3230 |  */
 | 
        
           |  |  | 3231 | bool CPackages::DisablePackage ( CBaseFile *package, CyStringList *errors, CProgressInfo *progress )
 | 
        
           |  |  | 3232 | {
 | 
        
           |  |  | 3233 | 	// if already disabled, just skip
 | 
        
           |  |  | 3234 | 	if ( !package->IsEnabled() )
 | 
        
           |  |  | 3235 | 		return true;
 | 
        
           |  |  | 3236 |   | 
        
           |  |  | 3237 | 	m_lDisableList.clear();
 | 
        
           |  |  | 3238 | 	if ( this->PrepareDisablePackage(package) )
 | 
        
           |  |  | 3239 | 		return this->DisablePreparedPackages(errors, progress);
 | 
        
           |  |  | 3240 |   | 
        
           |  |  | 3241 | 	return false;
 | 
        
           |  |  | 3242 | }
 | 
        
           |  |  | 3243 |   | 
        
           |  |  | 3244 |   | 
        
           |  |  | 3245 | /**
 | 
        
           |  |  | 3246 |  * Find a Package
 | 
        
           |  |  | 3247 |  *
 | 
        
           |  |  | 3248 |  * Finds a matching package so we can find if one is already installed
 | 
        
           |  |  | 3249 |  *
 | 
        
           |  |  | 3250 |  * Uses seperate functions for each package type, ie for SPK and XSP packages
 | 
        
           |  |  | 3251 |  */
 | 
        
           |  |  | 3252 | CBaseFile *CPackages::FindPackage(CBaseFile *package)
 | 
        
           |  |  | 3253 | {
 | 
        
           |  |  | 3254 | 	// no point checking if we've been sent a null pointer
 | 
        
           |  |  | 3255 | 	if ( !package )
 | 
        
           |  |  | 3256 | 		return 0;
 | 
        
           |  |  | 3257 |   | 
        
           |  |  | 3258 | 	// we are checking against a SPK package, so we match the name and author
 | 
        
           |  |  | 3259 | 	if ( package->GetType() == TYPE_SPK )
 | 
        
           |  |  | 3260 | 		return FindSpkPackage(package->GetName(), package->GetAuthor());
 | 
        
           |  |  | 3261 | 	else if ( package->GetType() == TYPE_XSP )
 | 
        
           |  |  | 3262 | 		return FindXspPackage(((CXspFile *)package)->GetShipID());
 | 
        
           |  |  | 3263 | 	else if ( package->GetType() == TYPE_ARCHIVE )
 | 
        
           |  |  | 3264 | 		return FindArchivePackage(package->GetName());
 | 
        
           |  |  | 3265 |   | 
        
           |  |  | 3266 | 	// nothing found obviously
 | 
        
           |  |  | 3267 | 	return 0;
 | 
        
           |  |  | 3268 | }
 | 
        
           |  |  | 3269 |   | 
        
           |  |  | 3270 | CBaseFile *CPackages::FindFirstPackageWithFile(C_File *f)
 | 
        
           |  |  | 3271 | {
 | 
        
           |  |  | 3272 | 	return FindNextPackageWithFile(NULL, f);
 | 
        
           |  |  | 3273 | }
 | 
        
           |  |  | 3274 |   | 
        
           |  |  | 3275 | CBaseFile *CPackages::FindNextPackageWithFile(CBaseFile *p, C_File *f)
 | 
        
           |  |  | 3276 | {
 | 
        
           |  |  | 3277 | 	bool startCheck = (p) ? false : true;
 | 
        
           |  |  | 3278 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 3279 | 	{
 | 
        
           |  |  | 3280 | 		if ( startCheck )
 | 
        
           |  |  | 3281 | 		{
 | 
        
           |  |  | 3282 | 			if ( node->Data()->IsFileAdded(f) )
 | 
        
           |  |  | 3283 | 				return node->Data();
 | 
        
           |  |  | 3284 | 		}
 | 
        
           |  |  | 3285 | 		else if ( p == node->Data() )
 | 
        
           |  |  | 3286 | 			startCheck = true;
 | 
        
           |  |  | 3287 | 	}
 | 
        
           |  |  | 3288 |   | 
        
           |  |  | 3289 | 	return NULL;
 | 
        
           |  |  | 3290 | }
 | 
        
           |  |  | 3291 |   | 
        
           |  |  | 3292 |   | 
        
           |  |  | 3293 | /**
 | 
        
           |  |  | 3294 |  * Find a File
 | 
        
           |  |  | 3295 |  *
 | 
        
           |  |  | 3296 |  * Searches for a file matching the filetype and filename
 | 
        
           |  |  | 3297 |  * Optional dir is used for extras files
 | 
        
           |  |  | 3298 |  */
 | 
        
           |  |  | 3299 | C_File *CPackages::FindFile(int filetype, CyString filename, CyString dir)
 | 
        
           |  |  | 3300 | {
 | 
        
           |  |  | 3301 | 	for ( CListNode<C_File> *node = m_lFiles.Front(); node; node = node->next() )
 | 
        
           |  |  | 3302 | 	{
 | 
        
           |  |  | 3303 | 		C_File *f = node->Data();
 | 
        
           |  |  | 3304 | 		if ( f->GetFileType() != filetype )
 | 
        
           |  |  | 3305 | 			continue;
 | 
        
           |  |  | 3306 |   | 
        
           |  |  | 3307 | 		if ( !f->GetFilename().Compare(filename) )
 | 
        
           |  |  | 3308 | 			continue;
 | 
        
           |  |  | 3309 |   | 
        
           |  |  | 3310 | 		if ( !dir.Empty() && f->GetDir().Compare(dir) )
 | 
        
           |  |  | 3311 | 			continue;
 | 
        
           |  |  | 3312 |   | 
        
           |  |  | 3313 | 		return f;
 | 
        
           |  |  | 3314 | 	}
 | 
        
           |  |  | 3315 |   | 
        
           |  |  | 3316 | 	return NULL;
 | 
        
           |  |  | 3317 | }
 | 
        
           |  |  | 3318 |   | 
        
           |  |  | 3319 | CArchiveFile *CPackages::FindArchivePackage(CyString name)
 | 
        
           |  |  | 3320 | {
 | 
        
           |  |  | 3321 | 	// interate through all packages
 | 
        
           |  |  | 3322 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 3323 | 	{
 | 
        
           |  |  | 3324 | 		CBaseFile *file = node->Data();
 | 
        
           |  |  | 3325 |   | 
        
           |  |  | 3326 | 		// only look for archive packages
 | 
        
           |  |  | 3327 | 		if ( file->GetType() != TYPE_ARCHIVE )
 | 
        
           |  |  | 3328 | 			continue;
 | 
        
           |  |  | 3329 |   | 
        
           |  |  | 3330 | 		// now compare the name and author, "Compare" is a non case senseative check, opposed to ==.
 | 
        
           |  |  | 3331 | 		if ( file->GetName().Compare(name) )
 | 
        
           |  |  | 3332 | 			return (CArchiveFile *)file;
 | 
        
           |  |  | 3333 | 	}
 | 
        
           |  |  | 3334 |   | 
        
           |  |  | 3335 | 	// nothing found
 | 
        
           |  |  | 3336 | 	return 0;
 | 
        
           |  |  | 3337 | }
 | 
        
           |  |  | 3338 |   | 
        
           |  |  | 3339 | /**
 | 
        
           |  |  | 3340 |  * Find a SPK Package
 | 
        
           |  |  | 3341 |  *
 | 
        
           |  |  | 3342 |  * This searching all installed packages for a SPK Package matching the name and author
 | 
        
           |  |  | 3343 |  */
 | 
        
           |  |  | 3344 | CBaseFile *CPackages::FindSpkPackage(CyString name, CyString author)
 | 
        
           |  |  | 3345 | {
 | 
        
           |  |  | 3346 | 	// interate through all packages
 | 
        
           |  |  | 3347 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 3348 | 	{
 | 
        
           |  |  | 3349 | 		CBaseFile *file = node->Data();
 | 
        
           |  |  | 3350 |   | 
        
           |  |  | 3351 | 		// only look for spk packages
 | 
        
           |  |  | 3352 | 		if ( file->GetType() != TYPE_SPK )
 | 
        
           |  |  | 3353 | 			continue;
 | 
        
           |  |  | 3354 |   | 
        
           |  |  | 3355 | 		// now compare the name and author, "Compare" is a non case senseative check, opposed to ==.
 | 
        
           |  |  | 3356 | 		if ( file->GetName().Compare(name) && file->GetAuthor().Compare(author) )
 | 
        
           |  |  | 3357 | 			return file;
 | 
        
           |  |  | 3358 | 	}
 | 
        
           |  |  | 3359 |   | 
        
           |  |  | 3360 | 	// nothing found
 | 
        
           |  |  | 3361 | 	return 0;
 | 
        
           |  |  | 3362 | }
 | 
        
           |  |  | 3363 |   | 
        
           |  |  | 3364 | CBaseFile *CPackages::FindPackage(CyString name, CyString author)
 | 
        
           |  |  | 3365 | {
 | 
        
           |  |  | 3366 | 	// interate through all packages
 | 
        
           |  |  | 3367 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 3368 | 	{
 | 
        
           |  |  | 3369 | 		CBaseFile *file = node->Data();
 | 
        
           |  |  | 3370 |   | 
        
           |  |  | 3371 | 		// now compare the name and author, "Compare" is a non case senseative check, opposed to ==.
 | 
        
           |  |  | 3372 | 		if ( file->GetName().Compare(name) && file->GetAuthor().Compare(author) )
 | 
        
           |  |  | 3373 | 			return file;
 | 
        
           |  |  | 3374 | 	}
 | 
        
           |  |  | 3375 |   | 
        
           |  |  | 3376 | 	// nothing found
 | 
        
           |  |  | 3377 | 	return 0;
 | 
        
           |  |  | 3378 | }
 | 
        
           |  |  | 3379 |   | 
        
           |  |  | 3380 | /**
 | 
        
           |  |  | 3381 |  * Find a XSP Package
 | 
        
           |  |  | 3382 |  *
 | 
        
           |  |  | 3383 |  * This searching all installed packages for a XSP Package matching the object id
 | 
        
           |  |  | 3384 |  */
 | 
        
           |  |  | 3385 | CBaseFile *CPackages::FindXspPackage(CyString id)
 | 
        
           |  |  | 3386 | {
 | 
        
           |  |  | 3387 | 	// interate through all packages
 | 
        
           |  |  | 3388 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 3389 | 	{
 | 
        
           |  |  | 3390 | 		CBaseFile *file = node->Data();
 | 
        
           |  |  | 3391 |   | 
        
           |  |  | 3392 | 		// only look for spk packages
 | 
        
           |  |  | 3393 | 		if ( file->GetType() != TYPE_XSP )
 | 
        
           |  |  | 3394 | 			continue;
 | 
        
           |  |  | 3395 |   | 
        
           |  |  | 3396 | 		// now compare the id, "Compare" is a non case senseative check, opposed to ==.
 | 
        
           | 14 | cycrow | 3397 | 		if ( ((CXspFile *)file)->GetShipID().Compare(id.ToString()) )
 | 
        
           | 1 | cycrow | 3398 | 			return file;
 | 
        
           |  |  | 3399 | 	}
 | 
        
           |  |  | 3400 |   | 
        
           |  |  | 3401 | 	// nothing found
 | 
        
           |  |  | 3402 | 	return 0;
 | 
        
           |  |  | 3403 | }
 | 
        
           |  |  | 3404 |   | 
        
           |  |  | 3405 | /**
 | 
        
           |  |  | 3406 |  * Update the used files count
 | 
        
           |  |  | 3407 |  *
 | 
        
           |  |  | 3408 |  * counts how many packages are currently using the file
 | 
        
           |  |  | 3409 |  */
 | 
        
           |  |  | 3410 | void CPackages::UpdateUsedFiles(CLinkList<CBaseFile> *ignoreList, bool includedisabled)
 | 
        
           |  |  | 3411 | {
 | 
        
           |  |  | 3412 | 	// clear amounts for all files
 | 
        
           |  |  | 3413 | 	CListNode<C_File> *fnode = m_lFiles.Front();
 | 
        
           |  |  | 3414 | 	while ( fnode )
 | 
        
           |  |  | 3415 | 	{
 | 
        
           |  |  | 3416 | 		fnode->Data()->ClearUsed();
 | 
        
           |  |  | 3417 | 		fnode = fnode->next();
 | 
        
           |  |  | 3418 | 	}
 | 
        
           |  |  | 3419 |   | 
        
           |  |  | 3420 | 	// update for all packages
 | 
        
           |  |  | 3421 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node= node->next() )
 | 
        
           |  |  | 3422 | 	{
 | 
        
           |  |  | 3423 | 		CBaseFile *file = node->Data();
 | 
        
           |  |  | 3424 | 		if ( (ignoreList) && (ignoreList->FindData(file)) )
 | 
        
           |  |  | 3425 | 			continue;
 | 
        
           |  |  | 3426 | 		if ( !includedisabled && !file->IsEnabled() )
 | 
        
           |  |  | 3427 | 			continue;
 | 
        
           |  |  | 3428 | 		// now mark all files
 | 
        
           |  |  | 3429 | 		CListNode<C_File> *fnode = file->GetFileList()->Front();
 | 
        
           |  |  | 3430 | 		while ( fnode )
 | 
        
           |  |  | 3431 | 		{
 | 
        
           |  |  | 3432 | 			fnode->Data()->IncUsed();
 | 
        
           |  |  | 3433 | 			fnode = fnode->next();
 | 
        
           |  |  | 3434 | 		}
 | 
        
           |  |  | 3435 | 	}
 | 
        
           |  |  | 3436 | }
 | 
        
           |  |  | 3437 |   | 
        
           |  |  | 3438 | /**
 | 
        
           |  |  | 3439 |  * Removes all empty directories that might have been created
 | 
        
           |  |  | 3440 |  */
 | 
        
           |  |  | 3441 | void CPackages::RemoveUnusedDirectories(CyStringList &dirs, CyStringList *errors)
 | 
        
           |  |  | 3442 | {
 | 
        
           |  |  | 3443 | 	CDirIO Dir(m_sCurrentDir);
 | 
        
           |  |  | 3444 | 	for ( SStringList *str = dirs.Head(); str; str = str->next )
 | 
        
           |  |  | 3445 | 	{
 | 
        
           |  |  | 3446 | 		CyString dir = str->str;
 | 
        
           |  |  | 3447 |   | 
        
           |  |  | 3448 | 		CyStringList removedDir;
 | 
        
           |  |  | 3449 | 		if ( Dir.RemoveDir(dir, false, true, &removedDir) || !removedDir.Empty() )
 | 
        
           |  |  | 3450 | 		{
 | 
        
           |  |  | 3451 | 			for ( SStringList *node = removedDir.Head(); node; node = node->next )
 | 
        
           |  |  | 3452 | 			{
 | 
        
           |  |  | 3453 | 				CyString displayName = node->str;
 | 
        
           |  |  | 3454 | 				displayName = displayName.Remove(m_sCurrentDir);
 | 
        
           |  |  | 3455 | 				this->AddLogEntry(SPKINSTALL_REMOVEDIR, displayName, errors);
 | 
        
           |  |  | 3456 | 			}
 | 
        
           |  |  | 3457 | 		}
 | 
        
           |  |  | 3458 | 	}
 | 
        
           |  |  | 3459 | }
 | 
        
           |  |  | 3460 |   | 
        
           |  |  | 3461 | /**
 | 
        
           |  |  | 3462 |  * Update signed status
 | 
        
           |  |  | 3463 |  *
 | 
        
           |  |  | 3464 |  * Updates the signed status of all packages
 | 
        
           |  |  | 3465 |  */
 | 
        
           |  |  | 3466 | void CPackages::UpdateSigned()
 | 
        
           |  |  | 3467 | {
 | 
        
           |  |  | 3468 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 3469 | 	{
 | 
        
           |  |  | 3470 | 		CBaseFile *p = node->Data();
 | 
        
           |  |  | 3471 |   | 
        
           |  |  | 3472 | 		if ( p->GetType() != TYPE_SPK )
 | 
        
           |  |  | 3473 | 			continue;
 | 
        
           |  |  | 3474 |   | 
        
           |  |  | 3475 | 		((CSpkFile *)p)->UpdateSigned(false);
 | 
        
           |  |  | 3476 | 	}
 | 
        
           |  |  | 3477 | }
 | 
        
           |  |  | 3478 |   | 
        
           |  |  | 3479 | /**
 | 
        
           |  |  | 3480 |  * Check validity of package file
 | 
        
           |  |  | 3481 |  *
 | 
        
           |  |  | 3482 |  * Checks if there is a newer version of the package installed
 | 
        
           |  |  | 3483 |  */
 | 
        
           |  |  | 3484 | int CPackages::CheckInstallPackage(CBaseFile *package, int check)
 | 
        
           |  |  | 3485 | {
 | 
        
           |  |  | 3486 | 	if ( package->GetType() == TYPE_XSP && m_iGame == GAME_X2 )
 | 
        
           |  |  | 3487 | 		return INSTALLCHECK_NOSHIP;
 | 
        
           |  |  | 3488 |   | 
        
           |  |  | 3489 | 	// search for an old version
 | 
        
           |  |  | 3490 | 	CBaseFile *oldPackage = FindPackage(package);
 | 
        
           |  |  | 3491 |   | 
        
           |  |  | 3492 | 	// check versions are newer
 | 
        
           |  |  | 3493 | 	if (oldPackage && (check & IC_OLDVERSION))
 | 
        
           |  |  | 3494 | 	{
 | 
        
           |  |  | 3495 | 		if ( oldPackage->GetVersion().CompareVersion(package->GetVersion()) == COMPARE_OLDER )
 | 
        
           |  |  | 3496 | 			return INSTALLCHECK_OLDVERSION;
 | 
        
           |  |  | 3497 | 	}
 | 
        
           |  |  | 3498 |   | 
        
           |  |  | 3499 | 	// now check for game version
 | 
        
           |  |  | 3500 | 	if ((check & IC_WRONGGAME) || (check & IC_WRONGVERSION))
 | 
        
           |  |  | 3501 | 	{
 | 
        
           |  |  | 3502 | 		if ( package->AnyGameCompatability() )
 | 
        
           |  |  | 3503 | 		{
 | 
        
           |  |  | 3504 | 			if ( (check & IC_WRONGGAME) && (!package->CheckGameCompatability(m_iGame)) )
 | 
        
           |  |  | 3505 | 				return INSTALLCHECK_WRONGGAME;
 | 
        
           |  |  | 3506 | 			else if ( (check & IC_WRONGVERSION) && (!package->CheckGameVersionCompatability(m_iGame, m_sGameVersion, m_iGameVersion)) )
 | 
        
           |  |  | 3507 | 				return INSTALLCHECK_WRONGVERSION;
 | 
        
           |  |  | 3508 | 		}
 | 
        
           |  |  | 3509 | 	}
 | 
        
           |  |  | 3510 |   | 
        
           |  |  | 3511 | 	// check for modified
 | 
        
           |  |  | 3512 | 	if (m_bVanilla && (check & IC_MODIFIED))
 | 
        
           |  |  | 3513 | 	{
 | 
        
           |  |  | 3514 | 		if ( !package->IsSigned() )
 | 
        
           |  |  | 3515 | 			return INSTALLCHECK_MODIFIED;
 | 
        
           |  |  | 3516 | 	}
 | 
        
           |  |  | 3517 |   | 
        
           |  |  | 3518 | 	return INSTALLCHECK_OK;
 | 
        
           |  |  | 3519 | }
 | 
        
           |  |  | 3520 |   | 
        
           |  |  | 3521 | bool CPackages::CheckOtherPackage(CBaseFile *package)
 | 
        
           |  |  | 3522 | {
 | 
        
           |  |  | 3523 | 	// check the need for another mod
 | 
        
           |  |  | 3524 | 	if ( package->GetType() == TYPE_SPK )
 | 
        
           |  |  | 3525 | 	{
 | 
        
           |  |  | 3526 | 		CSpkFile *spk = (CSpkFile *)package;
 | 
        
           |  |  | 3527 | 		if ( spk->IsAnotherMod() )
 | 
        
           |  |  | 3528 | 		{
 | 
        
           |  |  | 3529 | 			if ( !FindSpkPackage(spk->GetOtherName(), spk->GetOtherAuthor()) )
 | 
        
           |  |  | 3530 | 			{
 | 
        
           |  |  | 3531 | 				// check the install list
 | 
        
           |  |  | 3532 | 				if ( m_lInstallList.empty() )
 | 
        
           |  |  | 3533 | 					return false;
 | 
        
           |  |  | 3534 |   | 
        
           |  |  | 3535 | 				bool found = false;
 | 
        
           |  |  | 3536 | 				for ( CListNode<CBaseFile> *node = m_lInstallList.Front(); node; node = node->next() )
 | 
        
           |  |  | 3537 | 				{
 | 
        
           | 10 | cycrow | 3538 | 					if ( spk->GetOtherName().Compare(node->Data()->GetName().ToString()) && spk->GetOtherAuthor().Compare(node->Data()->GetAuthor().ToString()) )
 | 
        
           | 1 | cycrow | 3539 | 					{
 | 
        
           |  |  | 3540 | 						found = true;
 | 
        
           |  |  | 3541 | 						break;
 | 
        
           |  |  | 3542 | 					}
 | 
        
           |  |  | 3543 | 				}
 | 
        
           |  |  | 3544 |   | 
        
           |  |  | 3545 | 				if ( !found )
 | 
        
           |  |  | 3546 | 					return false;
 | 
        
           |  |  | 3547 | 			}
 | 
        
           |  |  | 3548 | 		}
 | 
        
           |  |  | 3549 | 	}
 | 
        
           |  |  | 3550 |   | 
        
           |  |  | 3551 | 	return true;
 | 
        
           |  |  | 3552 | }
 | 
        
           |  |  | 3553 |   | 
        
           |  |  | 3554 | bool CPackages::CheckEnabledDependacy(CBaseFile *p)
 | 
        
           |  |  | 3555 | {
 | 
        
           |  |  | 3556 | 	// check the for another mod
 | 
        
           |  |  | 3557 | 	if ( p->GetType() == TYPE_SPK )
 | 
        
           |  |  | 3558 | 	{
 | 
        
           |  |  | 3559 | 		if ( ((CSpkFile *)p)->IsAnotherMod() )
 | 
        
           |  |  | 3560 | 		{
 | 
        
           |  |  | 3561 | 			CBaseFile *parent = this->FindSpkPackage(((CSpkFile *)p)->GetOtherName(), ((CSpkFile *)p)->GetOtherAuthor());
 | 
        
           |  |  | 3562 | 			if ( parent )
 | 
        
           |  |  | 3563 | 			{
 | 
        
           |  |  | 3564 | 				if ( !parent->IsEnabled() )
 | 
        
           |  |  | 3565 | 					return false;
 | 
        
           |  |  | 3566 | 			}
 | 
        
           |  |  | 3567 | 			else
 | 
        
           |  |  | 3568 | 				return false;
 | 
        
           |  |  | 3569 | 		}
 | 
        
           |  |  | 3570 | 	}
 | 
        
           |  |  | 3571 |   | 
        
           |  |  | 3572 | 	// check any dependacies
 | 
        
           |  |  | 3573 | 	if ( p->AnyDependacies() )
 | 
        
           |  |  | 3574 | 	{
 | 
        
           |  |  | 3575 | 		for ( CListNode<SNeededLibrary> *dNode = p->GetNeededLibraries()->Front(); dNode; dNode = dNode->next() )
 | 
        
           |  |  | 3576 | 		{
 | 
        
           |  |  | 3577 | 			if ( dNode->Data()->sName.Compare("<package>") )
 | 
        
           |  |  | 3578 | 				continue;
 | 
        
           |  |  | 3579 | 			if ( !this->CheckInstalledDependacy(dNode->Data()->sName, dNode->Data()->sAuthor, dNode->Data()->sMinVersion, true, true) )
 | 
        
           |  |  | 3580 | 				return false;
 | 
        
           |  |  | 3581 | 		}
 | 
        
           |  |  | 3582 | 	}
 | 
        
           |  |  | 3583 |   | 
        
           |  |  | 3584 | 	return true;
 | 
        
           |  |  | 3585 | }
 | 
        
           |  |  | 3586 |   | 
        
           |  |  | 3587 | bool CPackages::CheckInstalledDependacy(CyString name, CyString author, CyString version, bool onlyEnabled, bool includePrepared)
 | 
        
           |  |  | 3588 | {
 | 
        
           |  |  | 3589 | 	CBaseFile *p = this->FindSpkPackage(name, author);
 | 
        
           |  |  | 3590 | 	if ( p )
 | 
        
           |  |  | 3591 | 	{
 | 
        
           |  |  | 3592 | 		// now check version
 | 
        
           |  |  | 3593 | 		if ( version.CompareVersion(p->GetVersion()) == COMPARE_OLDER )
 | 
        
           |  |  | 3594 | 			return false;
 | 
        
           |  |  | 3595 |   | 
        
           |  |  | 3596 | 		if ( onlyEnabled && !p->IsEnabled() )
 | 
        
           |  |  | 3597 | 			return false;
 | 
        
           |  |  | 3598 |   | 
        
           |  |  | 3599 | 		return true;
 | 
        
           |  |  | 3600 | 	}
 | 
        
           |  |  | 3601 |   | 
        
           |  |  | 3602 | 	// now check the prepared list
 | 
        
           |  |  | 3603 | 	if ( includePrepared )
 | 
        
           |  |  | 3604 | 	{
 | 
        
           |  |  | 3605 | 		for ( CListNode<CBaseFile> *node = m_lInstallList.Front(); node; node = node->next() )
 | 
        
           |  |  | 3606 | 		{
 | 
        
           |  |  | 3607 | 			p = node->Data();
 | 
        
           |  |  | 3608 | 			if ( !p )
 | 
        
           |  |  | 3609 | 				continue;
 | 
        
           |  |  | 3610 |   | 
        
           |  |  | 3611 | 			if ( p->GetName().Compare(name) && p->GetAuthor().Compare(author) )
 | 
        
           |  |  | 3612 | 			{
 | 
        
           |  |  | 3613 | 				if ( version.CompareVersion(p->GetVersion()) == COMPARE_OLDER )
 | 
        
           |  |  | 3614 | 					continue;
 | 
        
           |  |  | 3615 |   | 
        
           |  |  | 3616 | 				if ( onlyEnabled && !p->IsEnabled() )
 | 
        
           |  |  | 3617 | 					continue;
 | 
        
           |  |  | 3618 |   | 
        
           |  |  | 3619 | 				return true;
 | 
        
           |  |  | 3620 | 			}
 | 
        
           |  |  | 3621 | 		}
 | 
        
           |  |  | 3622 |   | 
        
           |  |  | 3623 | 		m_lInstallList.RemoveEmpty();
 | 
        
           |  |  | 3624 | 	}
 | 
        
           |  |  | 3625 |   | 
        
           |  |  | 3626 | 	return false;
 | 
        
           |  |  | 3627 | }
 | 
        
           |  |  | 3628 |   | 
        
           |  |  | 3629 | int CPackages::GetMissingDependacies(CBaseFile *p, CyStringList *list, bool onlyEnabled, bool includePrepared)
 | 
        
           |  |  | 3630 | {
 | 
        
           |  |  | 3631 | 	int count = 0;
 | 
        
           |  |  | 3632 | 	CLinkList<SNeededLibrary> *neededList = p->GetNeededLibraries();
 | 
        
           |  |  | 3633 | 	if ( neededList )
 | 
        
           |  |  | 3634 | 	{
 | 
        
           |  |  | 3635 | 		for ( CListNode<SNeededLibrary> *node = neededList->Front(); node; node = node->next() )
 | 
        
           |  |  | 3636 | 		{
 | 
        
           |  |  | 3637 | 			SNeededLibrary *nl = node->Data();
 | 
        
           |  |  | 3638 | 			if ( !CheckInstalledDependacy((nl->sName.Compare("<package>")) ? p->GetName() : nl->sName, (nl->sAuthor.Compare("<author>")) ? p->GetAuthor() : nl->sAuthor, nl->sMinVersion, (nl->sName.Compare("<package>")) ? false : onlyEnabled, (nl->sName.Compare("<package>")) ? false : includePrepared) )
 | 
        
           |  |  | 3639 | 			{
 | 
        
           |  |  | 3640 | 				if ( list )
 | 
        
           |  |  | 3641 | 					list->PushBack(((nl->sName.Compare("<package>")) ? p->GetName() : nl->sName) + "|" + nl->sMinVersion, (nl->sAuthor.Compare("<author>")) ? p->GetAuthor() : nl->sAuthor);
 | 
        
           |  |  | 3642 | 				++count;
 | 
        
           |  |  | 3643 | 			}
 | 
        
           |  |  | 3644 | 		}
 | 
        
           |  |  | 3645 | 	}
 | 
        
           |  |  | 3646 |   | 
        
           |  |  | 3647 | 	if ( p->GetType() == TYPE_SPK )
 | 
        
           |  |  | 3648 | 	{
 | 
        
           |  |  | 3649 | 		CSpkFile *spk = (CSpkFile *)p;
 | 
        
           |  |  | 3650 | 		if ( spk->IsAnotherMod() )
 | 
        
           |  |  | 3651 | 		{
 | 
        
           |  |  | 3652 | 			bool found = true;
 | 
        
           |  |  | 3653 | 			if ( !this->FindSpkPackage(spk->GetOtherName(), spk->GetOtherAuthor()) )
 | 
        
           |  |  | 3654 | 			{
 | 
        
           |  |  | 3655 | 				if ( includePrepared )
 | 
        
           |  |  | 3656 | 				{
 | 
        
           |  |  | 3657 | 					found = false;
 | 
        
           |  |  | 3658 | 					for ( CListNode<CBaseFile> *pNode = m_lInstallList.Front(); pNode; pNode = pNode->next() )
 | 
        
           |  |  | 3659 | 					{
 | 
        
           |  |  | 3660 | 						CBaseFile *checkP = pNode->Data();
 | 
        
           |  |  | 3661 | 						if ( p->GetAuthor().Compare(checkP->GetAuthor()) && p->GetName().Compare(checkP->GetName()) )
 | 
        
           |  |  | 3662 | 						{
 | 
        
           |  |  | 3663 | 							found = true;
 | 
        
           |  |  | 3664 | 							break;
 | 
        
           |  |  | 3665 | 						}
 | 
        
           |  |  | 3666 | 					}
 | 
        
           |  |  | 3667 | 				}
 | 
        
           |  |  | 3668 | 				else
 | 
        
           |  |  | 3669 | 					found = false;
 | 
        
           |  |  | 3670 | 			}
 | 
        
           |  |  | 3671 |   | 
        
           |  |  | 3672 | 			if ( !found )
 | 
        
           |  |  | 3673 | 			{
 | 
        
           |  |  | 3674 | 				if ( list )
 | 
        
           | 10 | cycrow | 3675 | 					list->PushBack(CyString(spk->GetOtherName()), CyString(spk->GetOtherAuthor()));
 | 
        
           | 1 | cycrow | 3676 | 				++count;
 | 
        
           |  |  | 3677 | 			}
 | 
        
           |  |  | 3678 | 		}
 | 
        
           |  |  | 3679 | 	}
 | 
        
           |  |  | 3680 |   | 
        
           |  |  | 3681 | 	return count;
 | 
        
           |  |  | 3682 | }
 | 
        
           |  |  | 3683 |   | 
        
           |  |  | 3684 | int CPackages::CheckPreparedInstallRequired(CLinkList<CBaseFile> *list)
 | 
        
           |  |  | 3685 | {
 | 
        
           |  |  | 3686 | 	// loop through all packages
 | 
        
           |  |  | 3687 | 	int count = 0;
 | 
        
           |  |  | 3688 | 	for ( CListNode<CBaseFile> *node = m_lInstallList.Front(); node; node = node->next() )
 | 
        
           |  |  | 3689 | 	{
 | 
        
           |  |  | 3690 | 		CBaseFile *p = node->Data();
 | 
        
           |  |  | 3691 |   | 
        
           |  |  | 3692 | 		// no requirements found, remove from list
 | 
        
           |  |  | 3693 | 		bool missingDep = false;
 | 
        
           |  |  | 3694 | 		if ( !this->CheckOtherPackage(p) )
 | 
        
           |  |  | 3695 | 			missingDep = true;
 | 
        
           |  |  | 3696 | 		else if ( this->GetMissingDependacies(p, NULL, false, true) )
 | 
        
           |  |  | 3697 | 			missingDep = true;
 | 
        
           |  |  | 3698 |   | 
        
           |  |  | 3699 | 		if ( missingDep )
 | 
        
           |  |  | 3700 | 		{
 | 
        
           |  |  | 3701 | 			if ( list )
 | 
        
           |  |  | 3702 | 			{
 | 
        
           |  |  | 3703 | 				node->ChangeData(NULL);
 | 
        
           |  |  | 3704 | 				list->push_back(p);
 | 
        
           |  |  | 3705 | 			}
 | 
        
           |  |  | 3706 | 			else
 | 
        
           |  |  | 3707 | 				node->DeleteData();
 | 
        
           |  |  | 3708 | 			++count;
 | 
        
           |  |  | 3709 | 		}
 | 
        
           |  |  | 3710 | 	}
 | 
        
           |  |  | 3711 |   | 
        
           |  |  | 3712 | 	m_lInstallList.RemoveEmpty();
 | 
        
           |  |  | 3713 |   | 
        
           |  |  | 3714 | 	return count;
 | 
        
           |  |  | 3715 | }
 | 
        
           |  |  | 3716 |   | 
        
           |  |  | 3717 |   | 
        
           |  |  | 3718 | /**
 | 
        
           |  |  | 3719 |  * Remove uninstall file
 | 
        
           |  |  | 3720 |  *
 | 
        
           |  |  | 3721 |  * Removes a single uninstall file
 | 
        
           |  |  | 3722 |  */
 | 
        
           |  |  | 3723 | bool CPackages::RemoveUninstallFile(C_File *file, CyStringList *errors)
 | 
        
           |  |  | 3724 | {
 | 
        
           |  |  | 3725 | 	CFileIO fio(file->GetFilePointer());
 | 
        
           |  |  | 3726 | 	if ( fio.Exists() )
 | 
        
           |  |  | 3727 | 	{
 | 
        
           |  |  | 3728 | 		if ( fio.Remove() )
 | 
        
           |  |  | 3729 | 		{
 | 
        
           |  |  | 3730 | 			this->AddLogEntry(SPKINSTALL_UNINSTALL_REMOVE, file->GetNameDirectory(NULL), errors);
 | 
        
           |  |  | 3731 | 			return true;
 | 
        
           |  |  | 3732 | 		}
 | 
        
           |  |  | 3733 | 		else if ( errors )
 | 
        
           |  |  | 3734 | 			this->AddLogEntry(SPKINSTALL_UNINSTALL_REMOVE_FAIL, file->GetNameDirectory(NULL), errors);
 | 
        
           |  |  | 3735 | 	}
 | 
        
           |  |  | 3736 |   | 
        
           |  |  | 3737 | 	return false;
 | 
        
           |  |  | 3738 | }
 | 
        
           |  |  | 3739 |   | 
        
           |  |  | 3740 | /**
 | 
        
           |  |  | 3741 |  * Remove uninstall scripts
 | 
        
           |  |  | 3742 |  *
 | 
        
           |  |  | 3743 |  * Removes any unused unisntall scripts
 | 
        
           |  |  | 3744 |  * Finds if any scripts are in the current package
 | 
        
           |  |  | 3745 |  */
 | 
        
           |  |  | 3746 | int CPackages::RemoveUninstallScripts(CyStringList *errors, CProgressInfo *progress)
 | 
        
           |  |  | 3747 | {
 | 
        
           |  |  | 3748 | 	if ( m_lUninstallFiles.empty() )
 | 
        
           |  |  | 3749 | 		return 0;
 | 
        
           |  |  | 3750 |   | 
        
           |  |  | 3751 | 	UpdateUsedFiles();
 | 
        
           |  |  | 3752 | 	int files = 0;
 | 
        
           |  |  | 3753 |   | 
        
           |  |  | 3754 | 	for ( CListNode<C_File> *node = m_lUninstallFiles.Back(); node; node = node->prev() )
 | 
        
           |  |  | 3755 | 	{
 | 
        
           |  |  | 3756 | 		if ( progress )
 | 
        
           |  |  | 3757 | 			progress->UpdateProgress(files, m_lUninstallFiles.size());
 | 
        
           |  |  | 3758 | 		files++;
 | 
        
           |  |  | 3759 |   | 
        
           |  |  | 3760 | 		C_File *file = node->Data();
 | 
        
           |  |  | 3761 |   | 
        
           |  |  | 3762 | 		// first check if there is a matching file
 | 
        
           |  |  | 3763 | 		bool found = false;
 | 
        
           |  |  | 3764 | 		for ( CListNode<C_File> *fNode = m_lFiles.Front(); fNode; fNode = fNode->next() )
 | 
        
           |  |  | 3765 | 		{
 | 
        
           |  |  | 3766 | 			C_File *checkFile = fNode->Data();
 | 
        
           |  |  | 3767 | 			if ( checkFile->GetFileType() != FILETYPE_SCRIPT )
 | 
        
           |  |  | 3768 | 				continue;
 | 
        
           |  |  | 3769 |   | 
        
           |  |  | 3770 | 			if ( checkFile->GetFilename().Compare(file->GetFilename()) )
 | 
        
           |  |  | 3771 | 			{
 | 
        
           |  |  | 3772 | 				found = true;
 | 
        
           |  |  | 3773 | 				break;
 | 
        
           |  |  | 3774 | 			}
 | 
        
           |  |  | 3775 | 		}
 | 
        
           |  |  | 3776 |   | 
        
           |  |  | 3777 | 		// not found a matching file, we can safetly remove it
 | 
        
           |  |  | 3778 | 		if ( !found )
 | 
        
           |  |  | 3779 | 		{
 | 
        
           |  |  | 3780 | 			if ( RemoveUninstallFile(file) )
 | 
        
           |  |  | 3781 | 				node->DeleteData();
 | 
        
           |  |  | 3782 | 		}
 | 
        
           |  |  | 3783 | 	}
 | 
        
           |  |  | 3784 |   | 
        
           |  |  | 3785 | 	m_lUninstallFiles.RemoveEmpty();
 | 
        
           |  |  | 3786 |   | 
        
           |  |  | 3787 | 	return files;
 | 
        
           |  |  | 3788 | }
 | 
        
           |  |  | 3789 |   | 
        
           |  |  | 3790 |   | 
        
           |  |  | 3791 | /**
 | 
        
           |  |  | 3792 |  * Remove unused shared file
 | 
        
           |  |  | 3793 |  *
 | 
        
           |  |  | 3794 |  * Removes a single file
 | 
        
           |  |  | 3795 |  */
 | 
        
           |  |  | 3796 | bool CPackages::RemoveSharedFile(C_File *file, CyStringList *errors)
 | 
        
           |  |  | 3797 | {
 | 
        
           |  |  | 3798 | 	CFileIO fio(file->GetFilePointer());
 | 
        
           |  |  | 3799 | 	if ( fio.Exists() )
 | 
        
           |  |  | 3800 | 	{
 | 
        
           |  |  | 3801 | 		if ( fio.Remove() )
 | 
        
           |  |  | 3802 | 		{
 | 
        
           |  |  | 3803 | 			this->AddLogEntry(SPKINSTALL_SHARED, file->GetNameDirectory(NULL), errors);
 | 
        
           |  |  | 3804 | 			delete file;
 | 
        
           |  |  | 3805 | 			return true;
 | 
        
           |  |  | 3806 | 		}
 | 
        
           |  |  | 3807 | 		else if ( errors )
 | 
        
           |  |  | 3808 | 			this->AddLogEntry(SPKINSTALL_SHARED_FAIL, file->GetNameDirectory(NULL), errors);
 | 
        
           |  |  | 3809 | 	}
 | 
        
           |  |  | 3810 |   | 
        
           |  |  | 3811 | 	return false;
 | 
        
           |  |  | 3812 | }
 | 
        
           |  |  | 3813 |   | 
        
           |  |  | 3814 | /**
 | 
        
           |  |  | 3815 |  * Remove Unused Shared Files
 | 
        
           |  |  | 3816 |  *
 | 
        
           |  |  | 3817 |  * Files that have been marked as shared will not be removed or disabled when the last package is removed
 | 
        
           |  |  | 3818 |  * This function will remove any that are no longer connected with packages
 | 
        
           |  |  | 3819 |  *
 | 
        
           |  |  | 3820 |  * Marked shared fiels are mainly used for library scripts that arn't always added to packages
 | 
        
           |  |  | 3821 |  */
 | 
        
           |  |  | 3822 | int CPackages::RemoveUnusedSharedFiles(CyStringList *errors, CProgressInfo *progress)
 | 
        
           |  |  | 3823 | {
 | 
        
           |  |  | 3824 | 	UpdateUsedFiles();
 | 
        
           |  |  | 3825 | 	int files = 0;
 | 
        
           |  |  | 3826 | 	int done = 0;
 | 
        
           |  |  | 3827 |   | 
        
           |  |  | 3828 | 	for ( CListNode<C_File> *node = m_lFiles.Back(); node; node = node->prev() )
 | 
        
           |  |  | 3829 | 	{
 | 
        
           |  |  | 3830 | 		if ( progress )
 | 
        
           |  |  | 3831 | 			progress->UpdateProgress(files, m_lFiles.size());
 | 
        
           |  |  | 3832 | 		files++;
 | 
        
           |  |  | 3833 |   | 
        
           |  |  | 3834 | 		C_File *file = node->Data();
 | 
        
           |  |  | 3835 |   | 
        
           |  |  | 3836 | 		// only do marked shared files
 | 
        
           |  |  | 3837 | 		if ( !file->IsShared() )
 | 
        
           |  |  | 3838 | 			continue;
 | 
        
           |  |  | 3839 |   | 
        
           |  |  | 3840 | 		// only do ones that are no longer needed
 | 
        
           |  |  | 3841 | 		if ( file->GetUsed() )
 | 
        
           |  |  | 3842 | 			continue;
 | 
        
           |  |  | 3843 |   | 
        
           |  |  | 3844 | 		if ( RemoveSharedFile(file, errors) )
 | 
        
           |  |  | 3845 | 			++done;
 | 
        
           |  |  | 3846 | 		node->ChangeData(NULL);
 | 
        
           |  |  | 3847 | 	}
 | 
        
           |  |  | 3848 |   | 
        
           |  |  | 3849 | 	m_lFiles.RemoveEmpty();
 | 
        
           |  |  | 3850 |   | 
        
           |  |  | 3851 | 	return done;
 | 
        
           |  |  | 3852 | }
 | 
        
           |  |  | 3853 |   | 
        
           |  |  | 3854 | /**
 | 
        
           |  |  | 3855 |  * Any Unused Shared
 | 
        
           |  |  | 3856 |  *
 | 
        
           |  |  | 3857 |  * Checks if theres any unused shared files available
 | 
        
           |  |  | 3858 |  *
 | 
        
           |  |  | 3859 |  * Any file thats marked as shared, and is no longer connected to any installed package
 | 
        
           |  |  | 3860 |  */
 | 
        
           |  |  | 3861 | bool CPackages::AnyUnusedShared()
 | 
        
           |  |  | 3862 | {
 | 
        
           |  |  | 3863 | 	UpdateUsedFiles();
 | 
        
           |  |  | 3864 |   | 
        
           |  |  | 3865 | 	for ( CListNode<C_File> *node = m_lFiles.Back(); node; node = node->prev() )
 | 
        
           |  |  | 3866 | 	{
 | 
        
           |  |  | 3867 | 		C_File *file = node->Data();
 | 
        
           |  |  | 3868 |   | 
        
           |  |  | 3869 | 		// only do marked shared files
 | 
        
           |  |  | 3870 | 		if ( !file->IsShared() )
 | 
        
           |  |  | 3871 | 			continue;
 | 
        
           |  |  | 3872 |   | 
        
           |  |  | 3873 | 		// only do ones that are no longer needed
 | 
        
           |  |  | 3874 | 		if ( file->GetUsed() )
 | 
        
           |  |  | 3875 | 			continue;
 | 
        
           |  |  | 3876 |   | 
        
           |  |  | 3877 | 		return true;
 | 
        
           |  |  | 3878 | 	}
 | 
        
           |  |  | 3879 |   | 
        
           |  |  | 3880 | 	return false;
 | 
        
           |  |  | 3881 |   | 
        
           |  |  | 3882 | }
 | 
        
           |  |  | 3883 |   | 
        
           |  |  | 3884 | /**
 | 
        
           |  |  | 3885 |  * Update original files list
 | 
        
           |  |  | 3886 |  *
 | 
        
           |  |  | 3887 |  * Scan the current directory for any fiels that are already there, ie ones that have not been installed
 | 
        
           |  |  | 3888 |  * Original files should be all the scripts/sounds, etc that are in an unmodified game directory
 | 
        
           |  |  | 3889 |  *
 | 
        
           |  |  | 3890 |  * Save list of files and check if any packages overright these files
 | 
        
           |  |  | 3891 |  * Any file that gets overrighten from this list will automatically be backed up, and restored once the packages are removed
 | 
        
           |  |  | 3892 |  */
 | 
        
           |  |  | 3893 | void CPackages::StoreOriginalFiles(int filetype, CyString searchPath)
 | 
        
           |  |  | 3894 | {
 | 
        
           |  |  | 3895 | 	CyString ext = "pck";
 | 
        
           |  |  | 3896 | 	switch ( filetype )
 | 
        
           |  |  | 3897 | 	{
 | 
        
           |  |  | 3898 | 		case FILETYPE_SOUND:
 | 
        
           |  |  | 3899 | 			ext = "mp3";
 | 
        
           |  |  | 3900 | 			break;
 | 
        
           |  |  | 3901 | 	}
 | 
        
           |  |  | 3902 |   | 
        
           |  |  | 3903 | 	CDirIO Dir(m_sCurrentDir + "/" + searchPath);
 | 
        
           |  |  | 3904 |   | 
        
           |  |  | 3905 | 	CyStringList *files = Dir.DirList();
 | 
        
           |  |  | 3906 | 	if ( !files )
 | 
        
           |  |  | 3907 | 		return;
 | 
        
           |  |  | 3908 |   | 
        
           |  |  | 3909 | 	for ( SStringList *node = files->Head(); node; node = node->next )
 | 
        
           |  |  | 3910 | 	{
 | 
        
           |  |  | 3911 | 		CFileIO File(Dir.File(node->str));
 | 
        
           |  |  | 3912 |   | 
        
           |  |  | 3913 | 		if ( File.GetFileExtension().Compare(ext) )
 | 
        
           |  |  | 3914 | 			AddOriginalFile(filetype, File.GetFilename(), searchPath);
 | 
        
           |  |  | 3915 | 	}
 | 
        
           |  |  | 3916 |   | 
        
           |  |  | 3917 | 	delete files;
 | 
        
           |  |  | 3918 | }
 | 
        
           |  |  | 3919 |   | 
        
           |  |  | 3920 | /**
 | 
        
           |  |  | 3921 |  * Adds a file onto the original files list
 | 
        
           |  |  | 3922 |  *
 | 
        
           |  |  | 3923 |  * Checks if it already exists so we dont create multiples
 | 
        
           |  |  | 3924 |  */
 | 
        
           |  |  | 3925 | void CPackages::AddOriginalFile(int filetype, CyString filename, CyString searchPath)
 | 
        
           |  |  | 3926 | {
 | 
        
           |  |  | 3927 | 	// dont add plugin manager as original files
 | 
        
           |  |  | 3928 | 	if ( filetype == FILETYPE_SCRIPT && filename.IsIn("!init.pmanager") )
 | 
        
           |  |  | 3929 | 		return;
 | 
        
           |  |  | 3930 | 	// first check if a matching one exists
 | 
        
           |  |  | 3931 | 	for ( CListNode<C_File> *node = m_lOriginalFiles.Front(); node; node = node->next() )
 | 
        
           |  |  | 3932 | 	{
 | 
        
           |  |  | 3933 | 		C_File *file = node->Data();
 | 
        
           |  |  | 3934 | 		if ( file->GetFileType() != filetype )
 | 
        
           |  |  | 3935 | 			continue;
 | 
        
           |  |  | 3936 |   | 
        
           |  |  | 3937 | 		if ( file->GetFilename().Compare(filename) )
 | 
        
           |  |  | 3938 | 			return;
 | 
        
           |  |  | 3939 | 	}
 | 
        
           |  |  | 3940 |   | 
        
           |  |  | 3941 | 	// check that no packages are currently using them either, not original if being used already
 | 
        
           |  |  | 3942 | 	for ( CListNode<C_File> *node = m_lFiles.Front(); node; node = node->next() )
 | 
        
           |  |  | 3943 | 	{
 | 
        
           |  |  | 3944 | 		C_File *file = node->Data();
 | 
        
           |  |  | 3945 | 		if ( file->GetFileType() != filetype )
 | 
        
           |  |  | 3946 | 			continue;
 | 
        
           |  |  | 3947 |   | 
        
           |  |  | 3948 | 		if ( file->GetFilename().Compare(filename) )
 | 
        
           |  |  | 3949 | 			return;
 | 
        
           |  |  | 3950 | 	}
 | 
        
           |  |  | 3951 |   | 
        
           |  |  | 3952 | 	C_File *of = new C_File(filename);
 | 
        
           |  |  | 3953 | 	of->SetFileType(filetype);
 | 
        
           |  |  | 3954 | 	if ( filetype == FILETYPE_EXTRA )
 | 
        
           |  |  | 3955 | 		of->SetDir(searchPath);
 | 
        
           |  |  | 3956 | 	of->SetFilename(m_sCurrentDir + "/" + of->GetNameDirectory(NULL));
 | 
        
           |  |  | 3957 |   | 
        
           |  |  | 3958 | 	m_lOriginalFiles.push_back(of);
 | 
        
           |  |  | 3959 | }
 | 
        
           |  |  | 3960 |   | 
        
           |  |  | 3961 | /**
 | 
        
           |  |  | 3962 |  * Check for original file
 | 
        
           |  |  | 3963 |  *
 | 
        
           |  |  | 3964 |  * Checks if the file is an original file or not
 | 
        
           |  |  | 3965 |  */
 | 
        
           |  |  | 3966 | bool CPackages::IsOriginalFile(C_File *file)
 | 
        
           |  |  | 3967 | {
 | 
        
           |  |  | 3968 | 	if ( GetOriginalFile(file) )
 | 
        
           |  |  | 3969 | 		return true;
 | 
        
           |  |  | 3970 | 	return false;
 | 
        
           |  |  | 3971 | }
 | 
        
           |  |  | 3972 |   | 
        
           |  |  | 3973 | /**
 | 
        
           |  |  | 3974 |  * Get original file
 | 
        
           |  |  | 3975 |  *
 | 
        
           |  |  | 3976 |  * Finds a matching original file entry and returns it
 | 
        
           |  |  | 3977 |  */
 | 
        
           |  |  | 3978 | C_File *CPackages::GetOriginalFile(C_File *file)
 | 
        
           |  |  | 3979 | {
 | 
        
           |  |  | 3980 | 	if ( !file )
 | 
        
           |  |  | 3981 | 		return NULL;
 | 
        
           |  |  | 3982 |   | 
        
           |  |  | 3983 | 	for ( CListNode<C_File> *node = m_lOriginalFiles.Front(); node; node = node->next() )
 | 
        
           |  |  | 3984 | 	{
 | 
        
           |  |  | 3985 | 		C_File *of = node->Data();
 | 
        
           |  |  | 3986 |   | 
        
           |  |  | 3987 | 		// not of the same file type
 | 
        
           |  |  | 3988 | 		if ( of->GetFileType() != file->GetFileType() )
 | 
        
           |  |  | 3989 | 			continue;
 | 
        
           |  |  | 3990 |   | 
        
           |  |  | 3991 | 		// same file name, must be the same file
 | 
        
           |  |  | 3992 | 		if ( of->GetFilename().Compare(file->GetFilename()) )
 | 
        
           |  |  | 3993 | 			return of;
 | 
        
           |  |  | 3994 | 	}
 | 
        
           |  |  | 3995 |   | 
        
           |  |  | 3996 | 	return NULL;
 | 
        
           |  |  | 3997 | }
 | 
        
           |  |  | 3998 |   | 
        
           |  |  | 3999 | /**
 | 
        
           |  |  | 4000 |  * Backs up an original file
 | 
        
           |  |  | 4001 |  *
 | 
        
           |  |  | 4002 |  * Moves the file into the PluginManager/Original directory so packages dont replace them
 | 
        
           |  |  | 4003 |  * Allows these files to be restored when the package is remove to prevent breaking the game
 | 
        
           |  |  | 4004 |  */
 | 
        
           |  |  | 4005 | bool CPackages::BackupOriginalFile(C_File *f, CyStringList *errors)
 | 
        
           |  |  | 4006 | {
 | 
        
           |  |  | 4007 | 	CyString newDir = CyString("PluginManager/Original/") + f->GetDirectory(NULL);
 | 
        
           |  |  | 4008 | 	CDirIO oDir(m_sCurrentDir);
 | 
        
           |  |  | 4009 | 	if ( oDir.Exists(newDir + "/" + f->GetFilename()) )
 | 
        
           |  |  | 4010 | 		return true;
 | 
        
           |  |  | 4011 |   | 
        
           |  |  | 4012 | 	// make sure the directory exissts
 | 
        
           |  |  | 4013 | 	if ( !oDir.Exists(newDir) )
 | 
        
           |  |  | 4014 | 	{
 | 
        
           |  |  | 4015 | 		if ( !oDir.Create(newDir) )
 | 
        
           |  |  | 4016 | 		{
 | 
        
           |  |  | 4017 | 			this->AddLogEntry(SPKINSTALL_CREATEDIRECTORY_FAIL, newDir, errors);
 | 
        
           |  |  | 4018 | 			return false;
 | 
        
           |  |  | 4019 | 		}
 | 
        
           |  |  | 4020 |   | 
        
           |  |  | 4021 | 		this->AddLogEntry(SPKINSTALL_CREATEDIRECTORY, newDir, errors);
 | 
        
           |  |  | 4022 | 	}
 | 
        
           |  |  | 4023 |   | 
        
           |  |  | 4024 | 	// now lets copy the file
 | 
        
           |  |  | 4025 | 	CFileIO CopyFile(f->GetFilePointer());
 | 
        
           |  |  | 4026 | 	if ( CopyFile.Copy(oDir.File(newDir + "/" + f->GetFilename())) )
 | 
        
           |  |  | 4027 | 	{
 | 
        
           |  |  | 4028 | 		this->AddLogEntry(SPKINSTALL_ORIGINAL_BACKUP, f->GetNameDirectory(NULL), errors);
 | 
        
           |  |  | 4029 | 		return true;
 | 
        
           |  |  | 4030 | 	}
 | 
        
           |  |  | 4031 | 	else
 | 
        
           |  |  | 4032 | 	{
 | 
        
           |  |  | 4033 | 		this->AddLogEntry(SPKINSTALL_ORIGINAL_BACKUP_FAIL, f->GetNameDirectory(NULL), errors);
 | 
        
           |  |  | 4034 | 		return false;
 | 
        
           |  |  | 4035 | 	}
 | 
        
           |  |  | 4036 | }
 | 
        
           |  |  | 4037 |   | 
        
           |  |  | 4038 | void CPackages::ShuffleTextFiles(CyStringList *errors)
 | 
        
           |  |  | 4039 | {
 | 
        
           |  |  | 4040 | 	for ( CListNode<C_File> *node = m_lFiles.Front(); node; node = node->next() )
 | 
        
           |  |  | 4041 | 	{
 | 
        
           |  |  | 4042 | 		C_File *f = node->Data();
 | 
        
           |  |  | 4043 | 		// only do files that are enabled
 | 
        
           |  |  | 4044 | 		if ( f->IsDisabled() )
 | 
        
           |  |  | 4045 | 			continue;
 | 
        
           |  |  | 4046 |   | 
        
           |  |  | 4047 | 		if ( f->GetFileType() != FILETYPE_TEXT )
 | 
        
           |  |  | 4048 | 			continue;
 | 
        
           |  |  | 4049 |   | 
        
           |  |  | 4050 | 		// check if the file is an auto text file
 | 
        
           |  |  | 4051 | 		if ( !f->IsAutoTextFile() )
 | 
        
           |  |  | 4052 | 			continue;
 | 
        
           |  |  | 4053 |   | 
        
           |  |  | 4054 | 		// we need to rename it
 | 
        
           |  |  | 4055 | 		int current = FindNextTextFile();
 | 
        
           |  |  | 4056 | 		if ( current < f->GetTextFileID() )
 | 
        
           |  |  | 4057 | 		{
 | 
        
           |  |  | 4058 | 			CFileIO moveFile(f->GetFilePointer());
 | 
        
           |  |  | 4059 |   | 
        
           |  |  | 4060 | 			CyString newName = SPK::FormatTextName(current, m_iLanguage, (m_iGameFlags & EXEFLAG_TCTEXT)) + "." + moveFile.GetFileExtension();
 | 
        
           |  |  | 4061 | 			if ( moveFile.Rename(m_sCurrentDir + "/t/" + newName) )
 | 
        
           |  |  | 4062 | 			{
 | 
        
           |  |  | 4063 | 				this->AddLogEntry(SPKINSTALL_AUTOTEXT, f->GetName() + "~" + newName, errors);
 | 
        
           |  |  | 4064 | 				f->SetName(newName);
 | 
        
           |  |  | 4065 | 			}
 | 
        
           |  |  | 4066 | 			else
 | 
        
           |  |  | 4067 | 				this->AddLogEntry(SPKINSTALL_AUTOTEXT_FAIL, f->GetName() + "~" + newName, errors);
 | 
        
           |  |  | 4068 | 		}
 | 
        
           |  |  | 4069 | 	}
 | 
        
           |  |  | 4070 | }
 | 
        
           |  |  | 4071 |   | 
        
           |  |  | 4072 | /**
 | 
        
           |  |  | 4073 |  * Shuffle Fake Patches
 | 
        
           |  |  | 4074 |  *
 | 
        
           |  |  | 4075 |  * Rename the fake patches so they are always in sequence to be loaded into the game
 | 
        
           |  |  | 4076 |  *
 | 
        
           |  |  | 4077 |  * IE, when one is removed, the rest need to be shuffled down so theres no gaps
 | 
        
           |  |  | 4078 |  */
 | 
        
           |  |  | 4079 | void CPackages::ShuffleFakePatches(CyStringList *errors)
 | 
        
           |  |  | 4080 | {
 | 
        
           |  |  | 4081 | 	int check = FindNextFakePatch();
 | 
        
           |  |  | 4082 |   | 
        
           |  |  | 4083 | 	// lets make sure our order is correct
 | 
        
           |  |  | 4084 | 	// find Lowest Fake Patch Installed
 | 
        
           |  |  | 4085 | 	CLinkList<C_File> doneList;
 | 
        
           |  |  | 4086 | 	int lowest = FindLowestFakePatchInstalled();
 | 
        
           |  |  | 4087 | 	if ( check < lowest ) lowest = check; // gap at the beginning, lets use that
 | 
        
           |  |  | 4088 |   | 
        
           |  |  | 4089 | 	// lets define the order
 | 
        
           |  |  | 4090 | 	CyStringList fakePatchOrder;
 | 
        
           |  |  | 4091 | 	for ( SStringList *str = m_lFakePatchOrder.Head(); str; str = str->next )
 | 
        
           |  |  | 4092 | 		fakePatchOrder.PushBack(str->str, str->data);
 | 
        
           |  |  | 4093 |   | 
        
           |  |  | 4094 | 	// add any other packages that need to be ordered
 | 
        
           |  |  | 4095 | 	// we need to work out the correct order
 | 
        
           |  |  | 4096 | 	CLinkList<CBaseFile> packages;
 | 
        
           |  |  | 4097 | 	for ( CListNode<CBaseFile> *pNode = m_lPackages.Front(); pNode; pNode = pNode->next() )
 | 
        
           |  |  | 4098 | 	{
 | 
        
           |  |  | 4099 | 		CBaseFile *p = pNode->Data();
 | 
        
           |  |  | 4100 | 		// search for any fake patches in package
 | 
        
           |  |  | 4101 | 		if ( !p->IsEnabled() ) continue;
 | 
        
           |  |  | 4102 | 		if ( !p->AnyFileType(FILETYPE_MOD) ) continue;
 | 
        
           |  |  | 4103 |   | 
        
           |  |  | 4104 | 		// must have an order define
 | 
        
           |  |  | 4105 | 		if ( !p->AnyFakePatchOrder() ) continue;
 | 
        
           |  |  | 4106 |   | 
        
           |  |  | 4107 | 		// check if theres any already ordered (manual)
 | 
        
           |  |  | 4108 | 		bool added = false;
 | 
        
           |  |  | 4109 | 		for ( SStringList *sCheck = fakePatchOrder.Head(); sCheck; sCheck = sCheck->next )
 | 
        
           |  |  | 4110 | 		{
 | 
        
           |  |  | 4111 | 			if ( sCheck->str.Compare(p->GetName()) && sCheck->data.Compare(p->GetAuthor()) )
 | 
        
           |  |  | 4112 | 			{
 | 
        
           |  |  | 4113 | 				added = true;
 | 
        
           |  |  | 4114 | 				break;
 | 
        
           |  |  | 4115 | 			}
 | 
        
           |  |  | 4116 | 		}
 | 
        
           |  |  | 4117 |   | 
        
           |  |  | 4118 | 		if ( added ) continue;
 | 
        
           |  |  | 4119 |   | 
        
           |  |  | 4120 | 		bool anyFound = false;
 | 
        
           |  |  | 4121 | 		for ( C_File *file = p->GetFirstFile(FILETYPE_MOD); file; file = p->GetNextFile(file) )
 | 
        
           |  |  | 4122 | 		{
 | 
        
           |  |  | 4123 | 			if ( !file->IsFakePatch() ) continue;
 | 
        
           |  |  | 4124 | 			if ( !file->CheckFileExt("cat") ) continue;
 | 
        
           |  |  | 4125 | 			if ( doneList.FindData(file) ) 	continue;
 | 
        
           |  |  | 4126 | 			anyFound = true;
 | 
        
           |  |  | 4127 | 			break;
 | 
        
           |  |  | 4128 | 		}
 | 
        
           |  |  | 4129 |   | 
        
           |  |  | 4130 | 		// we have some fake patches that need to be shuffled
 | 
        
           |  |  | 4131 | 		if ( anyFound )
 | 
        
           |  |  | 4132 | 			packages.push_back(p);
 | 
        
           |  |  | 4133 | 	}
 | 
        
           |  |  | 4134 |   | 
        
           |  |  | 4135 | 	// lets adjust the order (only if theres more than 1
 | 
        
           |  |  | 4136 | 	if ( packages.size() > 1 )
 | 
        
           |  |  | 4137 | 	{
 | 
        
           |  |  | 4138 | 		CLinkList<CBaseFile> sortedPackages;
 | 
        
           |  |  | 4139 |   | 
        
           |  |  | 4140 | 		// first add all the packages that dont need to be installed after
 | 
        
           |  |  | 4141 | 		for ( CListNode<CBaseFile> *pNode = packages.Front(); pNode; pNode = pNode->next() )
 | 
        
           |  |  | 4142 | 		{
 | 
        
           |  |  | 4143 | 			CBaseFile *p = pNode->Data();
 | 
        
           |  |  | 4144 | 			// we have a before and not after
 | 
        
           |  |  | 4145 | 			if ( !p->GetFakePatchBeforeOrder().Empty() && p->GetFakePatchAfterOrder().Empty() )
 | 
        
           |  |  | 4146 | 			{
 | 
        
           |  |  | 4147 | 				// if we have to install before, check if any on the list
 | 
        
           |  |  | 4148 | 				int earliestPos = -1;
 | 
        
           |  |  | 4149 | 				bool notAdded = true;
 | 
        
           |  |  | 4150 | 				for ( SStringList *str = p->GetFakePatchBeforeOrder().Head(); str; str = str->next )
 | 
        
           |  |  | 4151 | 				{
 | 
        
           |  |  | 4152 | 					int pos = 0;
 | 
        
           |  |  | 4153 | 					for ( CListNode<CBaseFile> *sNode = sortedPackages.Front(); sNode; sNode = sNode->next() )
 | 
        
           |  |  | 4154 | 					{
 | 
        
           |  |  | 4155 | 						if ( str->str.Compare(sNode->Data()->GetName()) && str->data.Compare(sNode->Data()->GetAuthor()) )
 | 
        
           |  |  | 4156 | 						{
 | 
        
           |  |  | 4157 | 							if ( earliestPos == -1 || pos < earliestPos )
 | 
        
           |  |  | 4158 | 								earliestPos = pos;
 | 
        
           |  |  | 4159 | 							break;
 | 
        
           |  |  | 4160 | 						}
 | 
        
           |  |  | 4161 | 						++pos;
 | 
        
           |  |  | 4162 | 					}					
 | 
        
           |  |  | 4163 | 				}
 | 
        
           |  |  | 4164 |   | 
        
           |  |  | 4165 | 				if ( earliestPos > -1 )
 | 
        
           |  |  | 4166 | 					sortedPackages.insert(earliestPos, p);
 | 
        
           |  |  | 4167 | 				// otherwise just add it at the back
 | 
        
           |  |  | 4168 | 				else
 | 
        
           |  |  | 4169 | 					sortedPackages.push_back(p);
 | 
        
           |  |  | 4170 |   | 
        
           |  |  | 4171 | 				// remove from the list
 | 
        
           |  |  | 4172 | 				pNode->ChangeData(NULL);
 | 
        
           |  |  | 4173 | 			}
 | 
        
           |  |  | 4174 | 		}
 | 
        
           |  |  | 4175 |   | 
        
           |  |  | 4176 | 		// now do the packages that have both before and after
 | 
        
           |  |  | 4177 | 		packages.RemoveEmpty();
 | 
        
           |  |  | 4178 | 		for ( CListNode<CBaseFile> *pNode = packages.Front(); pNode; pNode = pNode->next() )
 | 
        
           |  |  | 4179 | 		{
 | 
        
           |  |  | 4180 | 			CBaseFile *p = pNode->Data();
 | 
        
           |  |  | 4181 | 			if ( !p->GetFakePatchBeforeOrder().Empty() && !p->GetFakePatchAfterOrder().Empty() )
 | 
        
           |  |  | 4182 | 			{
 | 
        
           |  |  | 4183 | 			}
 | 
        
           |  |  | 4184 | 		}
 | 
        
           |  |  | 4185 |   | 
        
           |  |  | 4186 | 		// add them onto the list
 | 
        
           |  |  | 4187 | 		for ( CListNode<CBaseFile> *pNode = sortedPackages.Front(); pNode; pNode = pNode->next() )
 | 
        
           |  |  | 4188 | 			fakePatchOrder.PushBack(pNode->Data()->GetName(), pNode->Data()->GetAuthor());
 | 
        
           |  |  | 4189 | 	}
 | 
        
           |  |  | 4190 |   | 
        
           |  |  | 4191 | 	// now add to do list
 | 
        
           |  |  | 4192 | 	for ( CListNode<CBaseFile> *pNode = packages.Front(); pNode; pNode = pNode->next() )
 | 
        
           |  |  | 4193 | 		fakePatchOrder.PushBack(pNode->Data()->GetName(), pNode->Data()->GetAuthor());
 | 
        
           |  |  | 4194 |   | 
        
           |  |  | 4195 | 	for ( SStringList *str = fakePatchOrder.Head(); str; str = str->next )
 | 
        
           |  |  | 4196 | 	{
 | 
        
           |  |  | 4197 | 		CBaseFile *package = FindPackage(str->str, str->data);
 | 
        
           |  |  | 4198 | 		if ( package )
 | 
        
           |  |  | 4199 | 		{
 | 
        
           |  |  | 4200 | 			// might have more than 1 fake patch for the file, so we'll need the lowest
 | 
        
           |  |  | 4201 | 			while ( true )
 | 
        
           |  |  | 4202 | 			{
 | 
        
           |  |  | 4203 | 				C_File *lowestFile = NULL;
 | 
        
           |  |  | 4204 | 				for ( C_File *file = package->GetFirstFile(FILETYPE_MOD); file; file = package->GetNextFile(file) )
 | 
        
           |  |  | 4205 | 				{
 | 
        
           |  |  | 4206 | 					if ( !file->IsFakePatch() ) continue;
 | 
        
           |  |  | 4207 | 					if ( !file->CheckFileExt("cat") ) continue; // only do the cat file, we can shuffle the dat file to match later
 | 
        
           |  |  | 4208 | 					if ( doneList.FindData(file) ) continue; // already done?
 | 
        
           |  |  | 4209 |   | 
        
           |  |  | 4210 | 					if ( !lowestFile )
 | 
        
           |  |  | 4211 | 						lowestFile = file;
 | 
        
           |  |  | 4212 | 					else
 | 
        
           |  |  | 4213 | 					{
 | 
        
           |  |  | 4214 | 						if ( file->GetBaseName().ToInt() < lowestFile->GetBaseName().ToInt() )
 | 
        
           |  |  | 4215 | 							lowestFile = file;
 | 
        
           |  |  | 4216 | 					}
 | 
        
           |  |  | 4217 | 				}
 | 
        
           |  |  | 4218 |   | 
        
           |  |  | 4219 | 				if ( !lowestFile ) // no more files ?
 | 
        
           |  |  | 4220 | 					break;
 | 
        
           |  |  | 4221 |   | 
        
           |  |  | 4222 | 				// check its filename, it might already be in the correct place
 | 
        
           |  |  | 4223 | 				if ( lowestFile->GetBaseName().ToInt() != lowest )
 | 
        
           |  |  | 4224 | 				{
 | 
        
           |  |  | 4225 | 					// if the file already exists, we need to move it elsewhere
 | 
        
           |  |  | 4226 | 					CyString nextName = CyString::Number(lowest).PadNumber(2);
 | 
        
           |  |  | 4227 | 					if ( CFileIO(m_sCurrentDir + "/" + nextName + ".cat").Exists() )
 | 
        
           |  |  | 4228 | 					{
 | 
        
           |  |  | 4229 | 						// find the file in our internal file list
 | 
        
           |  |  | 4230 | 						C_File *moveFile = FindFile(FILETYPE_MOD, nextName + ".cat");
 | 
        
           |  |  | 4231 | 						if ( !moveFile ) // must not have it in our list ? lets move to the next
 | 
        
           |  |  | 4232 | 						{
 | 
        
           |  |  | 4233 | 							lowest++;
 | 
        
           |  |  | 4234 | 							continue;
 | 
        
           |  |  | 4235 | 						}
 | 
        
           |  |  | 4236 |   | 
        
           |  |  | 4237 | 						// now we can move the the cat/dat file elsewhere, lets shuffle it to the highest free number
 | 
        
           |  |  | 4238 | 						ShufflePatchTo(moveFile, FindLastFakePatch(), errors);
 | 
        
           |  |  | 4239 | 					}
 | 
        
           |  |  | 4240 |   | 
        
           |  |  | 4241 | 					// space should be free, now lets shuffle it
 | 
        
           |  |  | 4242 | 					ShufflePatchTo(lowestFile, lowest, errors);
 | 
        
           |  |  | 4243 | 				}
 | 
        
           |  |  | 4244 |   | 
        
           |  |  | 4245 | 				doneList.push_back(lowestFile); // we've done this file now
 | 
        
           |  |  | 4246 | 				lowest++; // move up the lowest ready for the next patch
 | 
        
           |  |  | 4247 | 			}
 | 
        
           |  |  | 4248 | 		}
 | 
        
           |  |  | 4249 | 	}
 | 
        
           |  |  | 4250 |   | 
        
           |  |  | 4251 | 	// now lets shuffle the rest
 | 
        
           |  |  | 4252 | 	// now find any packages with greater fake patchs and fill the gaps
 | 
        
           |  |  | 4253 | 	for ( CListNode<C_File> *node = m_lFiles.Front(); node; node = node->next() )
 | 
        
           |  |  | 4254 | 	{
 | 
        
           |  |  | 4255 | 		C_File *f = node->Data();
 | 
        
           |  |  | 4256 | 		// already done?
 | 
        
           |  |  | 4257 | 		if ( doneList.FindData(f) ) 
 | 
        
           |  |  | 4258 | 			continue;
 | 
        
           |  |  | 4259 |   | 
        
           |  |  | 4260 | 		// only do files that are enabled
 | 
        
           |  |  | 4261 | 		if ( f->IsDisabled() )
 | 
        
           |  |  | 4262 | 			continue;
 | 
        
           |  |  | 4263 |   | 
        
           |  |  | 4264 | 		// check if the file is a fake patch
 | 
        
           |  |  | 4265 | 		if ( !f->IsFakePatch() )
 | 
        
           |  |  | 4266 | 			continue;
 | 
        
           |  |  | 4267 |   | 
        
           |  |  | 4268 | 		// we only want cat and dat files, all fake patchs should be, but incase theres an error in the package somewhere we can check
 | 
        
           |  |  | 4269 | 		if ( !f->CheckFileExt("cat") )
 | 
        
           |  |  | 4270 | 			continue;
 | 
        
           |  |  | 4271 |   | 
        
           |  |  | 4272 | 		// now lets check if its greater than our gap
 | 
        
           |  |  | 4273 | 		int check = FindNextFakePatch();
 | 
        
           |  |  | 4274 | 		int patchNum = f->GetFilename().GetToken(".", 1, 1).ToInt();
 | 
        
           |  |  | 4275 | 		if ( patchNum <= check )
 | 
        
           |  |  | 4276 | 			continue;
 | 
        
           |  |  | 4277 |   | 
        
           |  |  | 4278 | 		ShufflePatchTo(f, check, errors);
 | 
        
           |  |  | 4279 | 	}
 | 
        
           |  |  | 4280 | }
 | 
        
           |  |  | 4281 |   | 
        
           |  |  | 4282 | void CPackages::ShufflePatchTo(C_File *file, int to, CyStringList *errors)
 | 
        
           |  |  | 4283 | {
 | 
        
           |  |  | 4284 | 	// it is, we need to shift this to fill the gap
 | 
        
           |  |  | 4285 | 	CyString newName = CyString::Number(to).PadNumber(2) + "." + file->GetFileExt();
 | 
        
           |  |  | 4286 |   | 
        
           |  |  | 4287 | 	// now rename the file
 | 
        
           |  |  | 4288 | 	CFileIO moveFile(file->GetFilePointer());
 | 
        
           |  |  | 4289 | 	if ( moveFile.Rename(m_sCurrentDir + "/" + newName) )
 | 
        
           |  |  | 4290 | 	{
 | 
        
           |  |  | 4291 | 		// display moveing
 | 
        
           |  |  | 4292 | 		this->AddLogEntry(SPKINSTALL_FAKEPATCH, file->GetName() + "~" + newName, errors);
 | 
        
           |  |  | 4293 |   | 
        
           |  |  | 4294 | 		// now find the matching pairing if it exists
 | 
        
           |  |  | 4295 | 		for ( CListNode<C_File> *node2 = m_lFiles.Front(); node2; node2 = node2->next() )
 | 
        
           |  |  | 4296 | 		{
 | 
        
           |  |  | 4297 | 			C_File *f2 = node2->Data();
 | 
        
           |  |  | 4298 |   | 
        
           |  |  | 4299 | 			if ( f2->IsDisabled() || !f2->IsFakePatch() || f2->CheckFileExt(file->GetFileExt()) )
 | 
        
           |  |  | 4300 | 				continue;
 | 
        
           |  |  | 4301 |   | 
        
           |  |  | 4302 | 			// needs to be the same file
 | 
        
           |  |  | 4303 | 			if ( f2->GetBaseName() != file->GetBaseName() )
 | 
        
           |  |  | 4304 | 				continue;
 | 
        
           |  |  | 4305 |   | 
        
           |  |  | 4306 | 			CyString newName2 = CyString::Number(to).PadNumber(2) + "." + f2->GetFileExt();
 | 
        
           |  |  | 4307 | 			CFileIO moveFile(f2->GetFilePointer());
 | 
        
           |  |  | 4308 | 			if ( moveFile.Rename(m_sCurrentDir + "/" + newName2) )
 | 
        
           |  |  | 4309 | 			{
 | 
        
           |  |  | 4310 | 				this->AddLogEntry(SPKINSTALL_FAKEPATCH, f2->GetName() + "~" + newName2, errors);
 | 
        
           |  |  | 4311 | 				f2->SetName(newName2);
 | 
        
           |  |  | 4312 | 			}
 | 
        
           |  |  | 4313 | 			else
 | 
        
           |  |  | 4314 | 				this->AddLogEntry(SPKINSTALL_FAKEPATCH_FAIL, f2->GetName() + "~" + newName2, errors);
 | 
        
           |  |  | 4315 | 		}
 | 
        
           |  |  | 4316 |   | 
        
           |  |  | 4317 | 		// finally make sure the internal name matches the new one
 | 
        
           |  |  | 4318 | 		file->SetName(newName);
 | 
        
           |  |  | 4319 | 	}
 | 
        
           |  |  | 4320 | 	else
 | 
        
           |  |  | 4321 | 		this->AddLogEntry(SPKINSTALL_FAKEPATCH_FAIL, file->GetName() + "~" + newName, errors);
 | 
        
           |  |  | 4322 | }
 | 
        
           |  |  | 4323 |   | 
        
           |  |  | 4324 | int CPackages::FindLowestFakePatchInstalled()
 | 
        
           |  |  | 4325 | {
 | 
        
           |  |  | 4326 | 	int lowest = 99;
 | 
        
           |  |  | 4327 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 4328 | 	{
 | 
        
           |  |  | 4329 | 		CBaseFile *p = node->Data();
 | 
        
           |  |  | 4330 | 		if ( !p->IsEnabled() ) continue;
 | 
        
           |  |  | 4331 | 		if ( !p->AnyFileType(FILETYPE_MOD) ) continue;
 | 
        
           |  |  | 4332 |   | 
        
           |  |  | 4333 | 		// now get all fake patches
 | 
        
           |  |  | 4334 | 		for ( C_File *file = p->GetFirstFile(FILETYPE_MOD); file; file = p->GetNextFile(file) )
 | 
        
           |  |  | 4335 | 		{
 | 
        
           |  |  | 4336 | 			if ( !file->IsFakePatch() ) continue;
 | 
        
           |  |  | 4337 | 			if ( file->CheckFileExt("dat") ) continue;
 | 
        
           |  |  | 4338 | 			int check = file->GetBaseName().ToInt();
 | 
        
           |  |  | 4339 | 			if ( check < lowest )
 | 
        
           |  |  | 4340 | 				lowest = check;
 | 
        
           |  |  | 4341 | 		}
 | 
        
           |  |  | 4342 | 	}
 | 
        
           |  |  | 4343 |   | 
        
           |  |  | 4344 | 	return lowest;
 | 
        
           |  |  | 4345 | }
 | 
        
           |  |  | 4346 |   | 
        
           |  |  | 4347 | int CPackages::FindLastFakePatch(int start, CyString dir)
 | 
        
           |  |  | 4348 | {
 | 
        
           |  |  | 4349 | 	CDirIO Dir((dir.Empty()) ? m_sCurrentDir : dir);
 | 
        
           |  |  | 4350 |   | 
        
           |  |  | 4351 | 	int check = start;
 | 
        
           |  |  | 4352 | 	while ( check > 0 )
 | 
        
           |  |  | 4353 | 	{
 | 
        
           |  |  | 4354 | 		CyString checkStr = CyString::Number(check).PadNumber(2);
 | 
        
           |  |  | 4355 |   | 
        
           |  |  | 4356 | 		// check if a cat file exists
 | 
        
           |  |  | 4357 | 		if ( !Dir.Exists(checkStr + ".cat") )
 | 
        
           |  |  | 4358 | 		{
 | 
        
           |  |  | 4359 | 			// it doen't, check if theres a dat file (incase of package error)
 | 
        
           |  |  | 4360 | 			if ( !Dir.Exists(checkStr + ".dat") )
 | 
        
           |  |  | 4361 | 				break;
 | 
        
           |  |  | 4362 | 		}
 | 
        
           |  |  | 4363 | 		--check;
 | 
        
           |  |  | 4364 | 	}
 | 
        
           |  |  | 4365 |   | 
        
           |  |  | 4366 | 	return check;
 | 
        
           |  |  | 4367 | }
 | 
        
           |  |  | 4368 |   | 
        
           |  |  | 4369 | /**
 | 
        
           |  |  | 4370 |  * Find next fake patch
 | 
        
           |  |  | 4371 |  *
 | 
        
           |  |  | 4372 |  * Searching for the next gap in patches, starting with 01.cat to 99.cat
 | 
        
           |  |  | 4373 |  */
 | 
        
           |  |  | 4374 | int CPackages::FindNextFakePatch(int start, CyString dir)
 | 
        
           |  |  | 4375 | {
 | 
        
           |  |  | 4376 | 	CDirIO Dir((dir.Empty()) ? m_sCurrentDir : dir);
 | 
        
           |  |  | 4377 |   | 
        
           |  |  | 4378 | 	int check = start;
 | 
        
           |  |  | 4379 | 	while ( check < 99 )
 | 
        
           |  |  | 4380 | 	{
 | 
        
           |  |  | 4381 | 		++check;
 | 
        
           |  |  | 4382 | 		CyString checkStr = CyString::Number(check).PadNumber(2);
 | 
        
           |  |  | 4383 |   | 
        
           |  |  | 4384 | 		// check if a cat file exists
 | 
        
           |  |  | 4385 | 		if ( !Dir.Exists(checkStr + ".cat") )
 | 
        
           |  |  | 4386 | 		{
 | 
        
           |  |  | 4387 | 			// it doen't, check if theres a dat file (incase of package error)
 | 
        
           |  |  | 4388 | 			if ( !Dir.Exists(checkStr + ".dat") )
 | 
        
           |  |  | 4389 | 				break;
 | 
        
           |  |  | 4390 | 		}
 | 
        
           |  |  | 4391 | 	}
 | 
        
           |  |  | 4392 |   | 
        
           |  |  | 4393 | 	return check;
 | 
        
           |  |  | 4394 | }
 | 
        
           |  |  | 4395 |   | 
        
           |  |  | 4396 | /**
 | 
        
           |  |  | 4397 |  * Find next text file
 | 
        
           |  |  | 4398 |  *
 | 
        
           |  |  | 4399 |  * Searching for the next gap in automatic text files, start with 0003-LXXX or XX0003
 | 
        
           |  |  | 4400 |  */
 | 
        
           |  |  | 4401 | int CPackages::FindNextTextFile(int start, CyString dir)
 | 
        
           |  |  | 4402 | {
 | 
        
           |  |  | 4403 | 	CDirIO Dir((dir.Empty()) ? m_sCurrentDir : dir);
 | 
        
           |  |  | 4404 | 	Dir.cd("t");
 | 
        
           |  |  | 4405 |   | 
        
           |  |  | 4406 | 	int check = start;
 | 
        
           |  |  | 4407 | 	if ( check < 2 ) check = 2;
 | 
        
           |  |  | 4408 | 	while ( check < 9999 )
 | 
        
           |  |  | 4409 | 	{
 | 
        
           |  |  | 4410 | 		++check;
 | 
        
           |  |  | 4411 | 		CyString newFilename = SPK::FormatTextName(check, m_iLanguage, (m_iGameFlags & EXEFLAG_TCTEXT));
 | 
        
           |  |  | 4412 |   | 
        
           |  |  | 4413 | 		// check if a packed file exists
 | 
        
           |  |  | 4414 | 		if ( !Dir.Exists(newFilename + ".pck") )
 | 
        
           |  |  | 4415 | 		{
 | 
        
           |  |  | 4416 | 			// it doen't, check if theres an unpacked file
 | 
        
           |  |  | 4417 | 			if ( !Dir.Exists(newFilename + ".xml") )
 | 
        
           |  |  | 4418 | 				break;
 | 
        
           |  |  | 4419 | 		}
 | 
        
           |  |  | 4420 | 	}
 | 
        
           |  |  | 4421 |   | 
        
           |  |  | 4422 | 	return check;
 | 
        
           |  |  | 4423 | }
 | 
        
           |  |  | 4424 |   | 
        
           |  |  | 4425 | int CPackages::FindLastTextFile(int start, CyString dir)
 | 
        
           |  |  | 4426 | {
 | 
        
           |  |  | 4427 | 	CDirIO Dir((dir.Empty()) ? m_sCurrentDir : dir);
 | 
        
           |  |  | 4428 | 	Dir.cd("t");
 | 
        
           |  |  | 4429 |   | 
        
           |  |  | 4430 | 	int check = start;
 | 
        
           |  |  | 4431 | 	while ( check < 9999 )
 | 
        
           |  |  | 4432 | 	{
 | 
        
           |  |  | 4433 | 		++check;
 | 
        
           |  |  | 4434 | 		CyString newFilename = SPK::FormatTextName(check, m_iLanguage, (m_iGameFlags & EXEFLAG_TCTEXT));
 | 
        
           |  |  | 4435 |   | 
        
           |  |  | 4436 | 		// check if a packed file exists
 | 
        
           |  |  | 4437 | 		if ( !Dir.Exists(newFilename + ".pck") )
 | 
        
           |  |  | 4438 | 		{
 | 
        
           |  |  | 4439 | 			// it doen't, check if theres an unpacked file
 | 
        
           |  |  | 4440 | 			if ( !Dir.Exists(newFilename + ".xml") )
 | 
        
           |  |  | 4441 | 				break;
 | 
        
           |  |  | 4442 | 		}
 | 
        
           |  |  | 4443 | 	}
 | 
        
           |  |  | 4444 |   | 
        
           |  |  | 4445 | 	return check;
 | 
        
           |  |  | 4446 | }
 | 
        
           |  |  | 4447 |   | 
        
           |  |  | 4448 | /**
 | 
        
           |  |  | 4449 |  * Read game language
 | 
        
           |  |  | 4450 |  *
 | 
        
           |  |  | 4451 |  * Reads the lang.dat file from the game directory for the language id
 | 
        
           |  |  | 4452 |  */
 | 
        
           |  |  | 4453 | void CPackages::ReadGameLanguage(bool force)
 | 
        
           |  |  | 4454 | {
 | 
        
           |  |  | 4455 | 	// check if lauguage is already set
 | 
        
           |  |  | 4456 | 	if ( !force && m_iLanguage )
 | 
        
           |  |  | 4457 | 		return;
 | 
        
           |  |  | 4458 |   | 
        
           |  |  | 4459 | 	CDirIO Dir(m_sCurrentDir);
 | 
        
           |  |  | 4460 |   | 
        
           |  |  | 4461 | 	// check for lang.dat file
 | 
        
           |  |  | 4462 | 	if ( Dir.Exists("lang.dat") )
 | 
        
           |  |  | 4463 | 	{
 | 
        
           |  |  | 4464 | 		CFileIO File(Dir.File("lang.dat"));
 | 
        
           |  |  | 4465 |   | 
        
           |  |  | 4466 | 		size_t size;
 | 
        
           |  |  | 4467 | 		char *data = File.ReadToData(&size);
 | 
        
           |  |  | 4468 |   | 
        
           |  |  | 4469 | 		if ( data )
 | 
        
           |  |  | 4470 | 		{
 | 
        
           |  |  | 4471 | 			CyString str(data);
 | 
        
           |  |  | 4472 | 			m_iLanguage = str.GetToken("\n", 1, 1).GetToken(" ", 1, 1).ToInt();
 | 
        
           |  |  | 4473 | 		}
 | 
        
           |  |  | 4474 | 	}
 | 
        
           |  |  | 4475 | }
 | 
        
           |  |  | 4476 |   | 
        
           |  |  | 4477 | /**
 | 
        
           |  |  | 4478 |  * Create Language Text File
 | 
        
           |  |  | 4479 |  *
 | 
        
           |  |  | 4480 |  * Creates text files for all packages into the correct language
 | 
        
           |  |  | 4481 |  */
 | 
        
           |  |  | 4482 | void CPackages::CreateLanguageTextFiles(CyStringList *errors)
 | 
        
           |  |  | 4483 | {
 | 
        
           |  |  | 4484 | 	// no need to create them if theres no language to use
 | 
        
           |  |  | 4485 | 	if ( !m_iLanguage )
 | 
        
           |  |  | 4486 | 		return;
 | 
        
           |  |  | 4487 |   | 
        
           |  |  | 4488 | 	// find all text files
 | 
        
           |  |  | 4489 | 	CyStringList ids;
 | 
        
           |  |  | 4490 |   | 
        
           |  |  | 4491 | 	for ( CListNode<C_File> *node = m_lFiles.Front(); node; node = node->next() )
 | 
        
           |  |  | 4492 | 	{
 | 
        
           |  |  | 4493 | 		C_File *f = node->Data();
 | 
        
           |  |  | 4494 | 		// only do text fiels
 | 
        
           |  |  | 4495 | 		if ( f->GetFileType() != FILETYPE_TEXT )
 | 
        
           |  |  | 4496 | 			continue;
 | 
        
           |  |  | 4497 |   | 
        
           |  |  | 4498 | 		CyString id, lang;
 | 
        
           |  |  | 4499 | 		if ( m_iGameFlags & EXEFLAG_TCTEXT )
 | 
        
           |  |  | 4500 | 		{
 | 
        
           |  |  | 4501 | 			id = f->GetBaseName().GetToken("-", 1, 1);
 | 
        
           |  |  | 4502 | 			lang = f->GetBaseName().GetToken("-", 2, 2);
 | 
        
           |  |  | 4503 | 			if ( lang.Empty() )
 | 
        
           |  |  | 4504 | 				lang = "NULL";
 | 
        
           |  |  | 4505 | 			else
 | 
        
           |  |  | 4506 | 				lang = lang.Erase(0, 1);  // remove the "L"
 | 
        
           |  |  | 4507 | 		}
 | 
        
           |  |  | 4508 | 		else
 | 
        
           |  |  | 4509 | 		{
 | 
        
           |  |  | 4510 | 			lang = f->GetBaseName().Left((int)f->GetBaseName().Length() - 4).PadNumber(3);
 | 
        
           |  |  | 4511 | 			id = f->GetBaseName().Mid(((int)f->GetBaseName().Length() - 4) + 1, 4);
 | 
        
           |  |  | 4512 | 		}
 | 
        
           |  |  | 4513 |   | 
        
           |  |  | 4514 | 		SStringList *strList = ids.FindString(id);
 | 
        
           |  |  | 4515 |   | 
        
           |  |  | 4516 | 		// not added, add a new one
 | 
        
           |  |  | 4517 | 		if ( !strList )
 | 
        
           |  |  | 4518 | 			strList = ids.PushBack(id, lang);
 | 
        
           |  |  | 4519 | 		else
 | 
        
           |  |  | 4520 | 		{
 | 
        
           |  |  | 4521 | 			if ( strList->data.Empty() )
 | 
        
           |  |  | 4522 | 				strList->data = lang;
 | 
        
           |  |  | 4523 | 			else
 | 
        
           |  |  | 4524 | 			{
 | 
        
           |  |  | 4525 | 				strList->data += ":";
 | 
        
           |  |  | 4526 | 				strList->data += lang;
 | 
        
           |  |  | 4527 | 			}
 | 
        
           |  |  | 4528 | 		}
 | 
        
           |  |  | 4529 | 	}
 | 
        
           |  |  | 4530 |   | 
        
           |  |  | 4531 | 	// we should now have a list of all text files, we need to remove those that have a matching language
 | 
        
           |  |  | 4532 | 	for ( SStringList *sNode = ids.Head(); sNode; sNode = sNode->next )
 | 
        
           |  |  | 4533 | 	{
 | 
        
           |  |  | 4534 | 		int size = 0;
 | 
        
           |  |  | 4535 | 		CyString *data = sNode->data.SplitToken(':', &size);
 | 
        
           |  |  | 4536 |   | 
        
           |  |  | 4537 | 		// huh ? we shouldn't have this
 | 
        
           |  |  | 4538 | 		if ( !size )
 | 
        
           |  |  | 4539 | 			continue;
 | 
        
           |  |  | 4540 |   | 
        
           |  |  | 4541 | 		// lets search for a matching id
 | 
        
           |  |  | 4542 | 		int useId = 0;
 | 
        
           |  |  | 4543 | 		bool found = false;
 | 
        
           |  |  | 4544 | 		for ( int i = 0; i < size; i++ )
 | 
        
           |  |  | 4545 | 		{
 | 
        
           |  |  | 4546 | 			if ( data[i] == "NULL" )
 | 
        
           |  |  | 4547 | 				useId = -1;
 | 
        
           |  |  | 4548 | 			else
 | 
        
           |  |  | 4549 | 			{
 | 
        
           |  |  | 4550 | 				int num = data[i].ToInt();
 | 
        
           |  |  | 4551 | 				if ( num == m_iLanguage )
 | 
        
           |  |  | 4552 | 				{
 | 
        
           |  |  | 4553 | 					found = true;
 | 
        
           |  |  | 4554 | 					useId = m_iLanguage;
 | 
        
           |  |  | 4555 | 					break;
 | 
        
           |  |  | 4556 | 				}
 | 
        
           |  |  | 4557 | 				// prioities the text file to use, no language first, then 44, then 49, otherwise, we pick the first available
 | 
        
           |  |  | 4558 | 				else if ( num == 44 && useId != -1)
 | 
        
           |  |  | 4559 | 					useId = 44;
 | 
        
           |  |  | 4560 | 				// if we have a german language, and its not yet found english or null
 | 
        
           |  |  | 4561 | 				else if ( num == 49 && useId != 44 && useId != -1 )
 | 
        
           |  |  | 4562 | 					useId = 49;
 | 
        
           |  |  | 4563 | 				// if we have not found a valid language yet, we will use this one
 | 
        
           |  |  | 4564 | 				else if ( !useId )
 | 
        
           |  |  | 4565 | 					useId = num;
 | 
        
           |  |  | 4566 | 			}
 | 
        
           |  |  | 4567 | 		}
 | 
        
           |  |  | 4568 |   | 
        
           |  |  | 4569 | 		if ( found )
 | 
        
           |  |  | 4570 | 			continue;
 | 
        
           |  |  | 4571 |   | 
        
           |  |  | 4572 | 		if ( !useId )
 | 
        
           |  |  | 4573 | 			useId = data[0].ToInt();
 | 
        
           |  |  | 4574 | 		if ( !useId )
 | 
        
           |  |  | 4575 | 			useId = -1;
 | 
        
           |  |  | 4576 |   | 
        
           |  |  | 4577 | 		CLEANSPLIT(data, size);
 | 
        
           |  |  | 4578 |   | 
        
           |  |  | 4579 | 		RenameTextFile(sNode->str, useId, errors);
 | 
        
           |  |  | 4580 | 	}
 | 
        
           |  |  | 4581 | }
 | 
        
           |  |  | 4582 |   | 
        
           |  |  | 4583 | /**
 | 
        
           |  |  | 4584 |  * Rename a text file
 | 
        
           |  |  | 4585 |  *
 | 
        
           |  |  | 4586 |  * Creates a new text file and copies an existing one
 | 
        
           |  |  | 4587 |  */
 | 
        
           |  |  | 4588 | bool CPackages::RenameTextFile(CyString textid, int languageid, CyStringList *errors)
 | 
        
           |  |  | 4589 | {
 | 
        
           |  |  | 4590 | 	// lets check if the file already exists
 | 
        
           |  |  | 4591 | 	CyString newFilename = SPK::FormatTextName(textid.ToInt(), m_iLanguage, (m_iGameFlags & EXEFLAG_TCTEXT));
 | 
        
           |  |  | 4592 | 	C_File *addFile = FindFile(FILETYPE_TEXT, newFilename + ".xml");
 | 
        
           |  |  | 4593 | 	if ( !addFile )
 | 
        
           |  |  | 4594 | 		addFile = FindFile(FILETYPE_TEXT, newFilename + ".pck");
 | 
        
           |  |  | 4595 |   | 
        
           |  |  | 4596 | 	// we have found the file, lets just add it to our scripts
 | 
        
           |  |  | 4597 | 	if ( addFile )
 | 
        
           |  |  | 4598 | 	{
 | 
        
           |  |  | 4599 | 		AddTextFileToScripts(addFile, textid);
 | 
        
           |  |  | 4600 | 		return true;
 | 
        
           |  |  | 4601 | 	}
 | 
        
           |  |  | 4602 |   | 
        
           |  |  | 4603 | 	// first we need to find our text file
 | 
        
           |  |  | 4604 | 	CyString filename;
 | 
        
           |  |  | 4605 | 	if ( languageid != -1 )
 | 
        
           |  |  | 4606 | 		filename = SPK::FormatTextName(textid.ToInt(), languageid, (m_iGameFlags & EXEFLAG_TCTEXT));
 | 
        
           |  |  | 4607 | 	else
 | 
        
           |  |  | 4608 | 		filename = textid;
 | 
        
           |  |  | 4609 |   | 
        
           |  |  | 4610 | 	C_File *textFile = FindFile(FILETYPE_TEXT, filename + ".xml");
 | 
        
           |  |  | 4611 | 	if ( !textFile )
 | 
        
           |  |  | 4612 | 	{
 | 
        
           |  |  | 4613 | 		textFile = FindFile(FILETYPE_TEXT, filename + ".pck");
 | 
        
           |  |  | 4614 | 		if ( !textFile )
 | 
        
           |  |  | 4615 | 			return false;
 | 
        
           |  |  | 4616 | 	}
 | 
        
           |  |  | 4617 |   | 
        
           |  |  | 4618 | 	// now lets create out new text file
 | 
        
           |  |  | 4619 | 	CFileIO readFile(textFile->GetFilePointer());
 | 
        
           |  |  | 4620 | 	std::vector<CyString> *lines = readFile.ReadLines();
 | 
        
           |  |  | 4621 |   | 
        
           |  |  | 4622 | 	// find the language id in the lines
 | 
        
           |  |  | 4623 | 	std::vector<CyString> frontLines;
 | 
        
           |  |  | 4624 | 	for(std::vector<CyString>::iterator it = lines->begin(); it != lines->end(); ++it)
 | 
        
           |  |  | 4625 | 	{
 | 
        
           |  |  | 4626 | 		CyString line = *it;
 | 
        
           |  |  | 4627 | 		int pos = line.FindPos("<language id");
 | 
        
           |  |  | 4628 | 		if ( pos != -1)
 | 
        
           |  |  | 4629 | 		{
 | 
        
           |  |  | 4630 | 			CyString newLine = "<language id=\"";
 | 
        
           |  |  | 4631 | 			newLine += CyString::Number(m_iLanguage);
 | 
        
           |  |  | 4632 | 			newLine += "\">";
 | 
        
           |  |  | 4633 | 			newLine += line.GetToken(">", 2);
 | 
        
           |  |  | 4634 |   | 
        
           |  |  | 4635 | 			frontLines.insert(frontLines.begin(), newLine);
 | 
        
           |  |  | 4636 |   | 
        
           |  |  | 4637 | 			lines->erase(lines->begin(), ++it);
 | 
        
           |  |  | 4638 | 			break;
 | 
        
           |  |  | 4639 | 		}
 | 
        
           |  |  | 4640 | 		frontLines.insert(frontLines.begin(), line);
 | 
        
           |  |  | 4641 | 	}
 | 
        
           |  |  | 4642 |   | 
        
           |  |  | 4643 | 	for(std::vector<CyString>::iterator it = frontLines.begin(); it != frontLines.end(); ++it)
 | 
        
           |  |  | 4644 | 		lines->insert(lines->begin(), *it);
 | 
        
           |  |  | 4645 |   | 
        
           |  |  | 4646 | 	addFile = new C_File(newFilename + ".xml");
 | 
        
           |  |  | 4647 | 	addFile->SetFileType(FILETYPE_TEXT);
 | 
        
           |  |  | 4648 |   | 
        
           |  |  | 4649 | 	CFileIO writeFile(m_sCurrentDir + "/" + addFile->GetNameDirectory(NULL));
 | 
        
           |  |  | 4650 | 	if ( writeFile.WriteFile(lines) )
 | 
        
           |  |  | 4651 | 	{
 | 
        
           |  |  | 4652 | 		this->AddLogEntry(SPKINSTALL_WRITEFILE, addFile->GetNameDirectory(NULL), errors);
 | 
        
           |  |  | 4653 |   | 
        
           |  |  | 4654 | 		addFile->SetFilename(m_sCurrentDir + "/" + addFile->GetNameDirectory(NULL));
 | 
        
           |  |  | 4655 | 		// now we have the file wrriten, we need to add it to all scripts that need it
 | 
        
           |  |  | 4656 | 		// first we add it to the global list
 | 
        
           |  |  | 4657 | 		m_lFiles.push_back(addFile);
 | 
        
           |  |  | 4658 |   | 
        
           |  |  | 4659 | 		// now add it to the scripts
 | 
        
           |  |  | 4660 | 		AddTextFileToScripts(addFile, textid);
 | 
        
           |  |  | 4661 | 	}
 | 
        
           |  |  | 4662 | 	else
 | 
        
           |  |  | 4663 | 	{
 | 
        
           |  |  | 4664 | 		this->AddLogEntry(SPKINSTALL_WRITEFILE_FAIL, addFile->GetNameDirectory(NULL), errors);
 | 
        
           |  |  | 4665 | 		if ( lines )
 | 
        
           |  |  | 4666 | 			delete lines;
 | 
        
           |  |  | 4667 | 		return false;
 | 
        
           |  |  | 4668 | 	}
 | 
        
           |  |  | 4669 |   | 
        
           |  |  | 4670 | 	if ( lines )
 | 
        
           |  |  | 4671 | 		delete lines;
 | 
        
           |  |  | 4672 |   | 
        
           |  |  | 4673 |   | 
        
           |  |  | 4674 | 	return true;
 | 
        
           |  |  | 4675 | }
 | 
        
           |  |  | 4676 |   | 
        
           |  |  | 4677 | /**
 | 
        
           |  |  | 4678 |  * Add file to scripts
 | 
        
           |  |  | 4679 |  *
 | 
        
           |  |  | 4680 |  * Adds a file to all scripts that need it
 | 
        
           |  |  | 4681 |  */
 | 
        
           |  |  | 4682 | void CPackages::AddTextFileToScripts(C_File *file, CyString textid)
 | 
        
           |  |  | 4683 | {
 | 
        
           |  |  | 4684 | 	// now we need to find all scripts that have a matching file and add this to the list
 | 
        
           |  |  | 4685 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 4686 | 	{
 | 
        
           |  |  | 4687 | 		CBaseFile *package = node->Data();
 | 
        
           |  |  | 4688 |   | 
        
           |  |  | 4689 | 		// first make sure it doesn't already exist
 | 
        
           |  |  | 4690 | 		if ( package->GetFileList()->FindData(file) )
 | 
        
           |  |  | 4691 | 			continue;
 | 
        
           |  |  | 4692 |   | 
        
           |  |  | 4693 | 		bool found = false;
 | 
        
           |  |  | 4694 | 		for ( CListNode<C_File> *fNode = package->GetFileList()->Front(); fNode; fNode = fNode->next() )
 | 
        
           |  |  | 4695 | 		{
 | 
        
           |  |  | 4696 | 			C_File *tFile = fNode->Data();
 | 
        
           |  |  | 4697 | 			if ( tFile->GetFileType() != FILETYPE_TEXT )
 | 
        
           |  |  | 4698 | 				continue;
 | 
        
           |  |  | 4699 |   | 
        
           |  |  | 4700 | 			CyString id = tFile->GetBaseName().GetToken("-", 1, 1);
 | 
        
           |  |  | 4701 | 			if ( id == textid )
 | 
        
           |  |  | 4702 | 			{
 | 
        
           |  |  | 4703 | 				found = true;
 | 
        
           |  |  | 4704 | 				break;
 | 
        
           |  |  | 4705 | 			}
 | 
        
           |  |  | 4706 | 		}
 | 
        
           |  |  | 4707 |   | 
        
           |  |  | 4708 | 		if ( found )
 | 
        
           |  |  | 4709 | 			package->GetFileList()->push_back(file);
 | 
        
           |  |  | 4710 | 	}
 | 
        
           |  |  | 4711 | }
 | 
        
           |  |  | 4712 |   | 
        
           |  |  | 4713 | bool CPackages::RemoveFile(C_File *file, CyStringList *errors)
 | 
        
           |  |  | 4714 | {
 | 
        
           |  |  | 4715 | 	if ( !file )
 | 
        
           |  |  | 4716 | 		return true;
 | 
        
           |  |  | 4717 |   | 
        
           |  |  | 4718 | 	CyString remFileStr = file->GetFilePointer();
 | 
        
           |  |  | 4719 | 	remFileStr.FindReplace(m_sCurrentDir, "");
 | 
        
           |  |  | 4720 |   | 
        
           |  |  | 4721 | 	if ( file->GetFilePointer().IsIn("::") ) {
 | 
        
           |  |  | 4722 | 		CFileIO CatFile(file->GetFilePointer().GetToken("::", 1, 1));
 | 
        
           |  |  | 4723 | 		if ( CatFile.Exists() ) {
 | 
        
           |  |  | 4724 | 			CCatFile cat;
 | 
        
           |  |  | 4725 | 			if ( cat.Open(CatFile.GetFullFilename(), this->GetAddonDir(), CATREAD_DAT, false) == CATERR_NONE ) {
 | 
        
           |  |  | 4726 | 				CyString fileName = file->GetFilePointer().GetToken("::", 2, 2);
 | 
        
           |  |  | 4727 | 				if ( cat.FindData(fileName) ) {
 | 
        
           |  |  | 4728 | 					if ( cat.RemoveFile(fileName) ) {
 | 
        
           |  |  | 4729 | 						this->AddLogEntry(SPKINSTALL_DELETEFILE, remFileStr, errors);
 | 
        
           |  |  | 4730 | 					}
 | 
        
           |  |  | 4731 | 					else {
 | 
        
           |  |  | 4732 | 						this->AddLogEntry(SPKINSTALL_DELETEFILE_FAIL, remFileStr, errors);
 | 
        
           |  |  | 4733 | 						return false;
 | 
        
           |  |  | 4734 | 					}
 | 
        
           |  |  | 4735 | 				}
 | 
        
           |  |  | 4736 | 			}
 | 
        
           |  |  | 4737 | 		}
 | 
        
           |  |  | 4738 | 	}
 | 
        
           |  |  | 4739 | 	else {
 | 
        
           |  |  | 4740 | 		CFileIO f(file->GetFilePointer());
 | 
        
           |  |  | 4741 | 		if ( f.Exists() )
 | 
        
           |  |  | 4742 | 		{
 | 
        
           |  |  | 4743 | 			if ( f.Remove() )
 | 
        
           |  |  | 4744 | 				this->AddLogEntry(SPKINSTALL_DELETEFILE, remFileStr, errors);
 | 
        
           |  |  | 4745 | 			else if ( errors )
 | 
        
           |  |  | 4746 | 			{
 | 
        
           |  |  | 4747 | 				this->AddLogEntry(SPKINSTALL_DELETEFILE_FAIL, remFileStr, errors);
 | 
        
           |  |  | 4748 | 				return false;
 | 
        
           |  |  | 4749 | 			}
 | 
        
           |  |  | 4750 | 			else
 | 
        
           |  |  | 4751 | 				return false;
 | 
        
           |  |  | 4752 | 		}
 | 
        
           |  |  | 4753 | 	}
 | 
        
           |  |  | 4754 |   | 
        
           |  |  | 4755 | 	return true;
 | 
        
           |  |  | 4756 | }
 | 
        
           |  |  | 4757 |   | 
        
           |  |  | 4758 | int CPackages::RemoveAllPackages(CyStringList *errors, CProgressInfo *progress)
 | 
        
           |  |  | 4759 | {
 | 
        
           |  |  | 4760 | 	int files = 0;
 | 
        
           |  |  | 4761 |   | 
        
           |  |  | 4762 | 	// remove all files
 | 
        
           |  |  | 4763 | 	int max = m_lFiles.size() + m_lOriginalFiles.size() + m_lUninstallFiles.size();
 | 
        
           |  |  | 4764 | 	for ( CListNode<C_File> *node = m_lFiles.Front(); node; node = node->next() )
 | 
        
           |  |  | 4765 | 	{
 | 
        
           |  |  | 4766 | 		// update the progress
 | 
        
           |  |  | 4767 | 		if ( progress )
 | 
        
           |  |  | 4768 | 			progress->UpdateProgress(files, max);
 | 
        
           |  |  | 4769 | 		++files;
 | 
        
           |  |  | 4770 |   | 
        
           |  |  | 4771 | 		RemoveFile(node->Data());
 | 
        
           |  |  | 4772 | 		delete node->Data();
 | 
        
           |  |  | 4773 | 	}
 | 
        
           |  |  | 4774 | 	m_lFiles.clear();
 | 
        
           |  |  | 4775 |   | 
        
           |  |  | 4776 | 	// restore any original files that are backed up
 | 
        
           |  |  | 4777 | 	for ( CListNode<C_File> *oNode = m_lOriginalFiles.Front(); oNode; oNode = oNode->next() )
 | 
        
           |  |  | 4778 | 	{
 | 
        
           |  |  | 4779 | 		// update the progress
 | 
        
           |  |  | 4780 | 		if ( progress )
 | 
        
           |  |  | 4781 | 			progress->UpdateProgress(files, max);
 | 
        
           |  |  | 4782 | 		++files;
 | 
        
           |  |  | 4783 |   | 
        
           |  |  | 4784 | 		C_File *f = oNode->Data();
 | 
        
           |  |  | 4785 | 		CFileIO of(m_sCurrentDir + "/PluginManager/Original/" + f->GetNameDirectory(NULL));
 | 
        
           |  |  | 4786 | 		if ( of.Exists() )
 | 
        
           |  |  | 4787 | 			of.Rename(m_sCurrentDir + "/" + f->GetNameDirectory(NULL));
 | 
        
           |  |  | 4788 |   | 
        
           |  |  | 4789 | 		//RemoveFile(oNode->Data());
 | 
        
           |  |  | 4790 | 		delete oNode->Data();
 | 
        
           |  |  | 4791 | 	}
 | 
        
           |  |  | 4792 | 	m_lOriginalFiles.clear();
 | 
        
           |  |  | 4793 |   | 
        
           |  |  | 4794 | 	// remove any uninstall files that remain
 | 
        
           |  |  | 4795 | 	for ( CListNode<C_File> *uNode = m_lUninstallFiles.Front(); uNode; uNode = uNode->next() )
 | 
        
           |  |  | 4796 | 	{
 | 
        
           |  |  | 4797 | 		// update the progress
 | 
        
           |  |  | 4798 | 		if ( progress )
 | 
        
           |  |  | 4799 | 			progress->UpdateProgress(files, max);
 | 
        
           |  |  | 4800 | 		++files;
 | 
        
           |  |  | 4801 |   | 
        
           |  |  | 4802 | 		RemoveFile(uNode->Data());
 | 
        
           |  |  | 4803 | 		delete uNode->Data();
 | 
        
           |  |  | 4804 | 	}
 | 
        
           |  |  | 4805 | 	m_lUninstallFiles.clear();
 | 
        
           |  |  | 4806 |   | 
        
           |  |  | 4807 | 	// delete all packages
 | 
        
           |  |  | 4808 | 	for ( CListNode<CBaseFile> *pNode = m_lPackages.Front(); pNode; pNode = pNode->next() )
 | 
        
           |  |  | 4809 | 	{
 | 
        
           |  |  | 4810 | 		// clear file list as we have removed them already
 | 
        
           |  |  | 4811 | 		pNode->Data()->GetFileList()->clear();
 | 
        
           |  |  | 4812 | 		// delete the memory for the package
 | 
        
           |  |  | 4813 | 		delete pNode->Data();
 | 
        
           |  |  | 4814 | 	}
 | 
        
           |  |  | 4815 | 	m_lPackages.clear();
 | 
        
           |  |  | 4816 |   | 
        
           |  |  | 4817 | 	return files;
 | 
        
           |  |  | 4818 | }
 | 
        
           |  |  | 4819 |   | 
        
           |  |  | 4820 | /**
 | 
        
           |  |  | 4821 |  * Get Install Before Text
 | 
        
           |  |  | 4822 |  *
 | 
        
           |  |  | 4823 |  * Returns the install before text for the package in the correct language
 | 
        
           |  |  | 4824 |  */
 | 
        
           |  |  | 4825 | CyString CPackages::GetInstallBeforeText(CBaseFile *package)
 | 
        
           |  |  | 4826 | {
 | 
        
           |  |  | 4827 | 	if ( !package->IsThereInstallText() )
 | 
        
           |  |  | 4828 | 		return NullString;
 | 
        
           |  |  | 4829 |   | 
        
           |  |  | 4830 | 	return package->GetInstallBeforeText(m_iLanguage);
 | 
        
           |  |  | 4831 | }
 | 
        
           |  |  | 4832 | CyString CPackages::GetInstallAfterText(CBaseFile *package)
 | 
        
           |  |  | 4833 | {
 | 
        
           |  |  | 4834 | 	if ( !package->IsThereInstallText() )
 | 
        
           |  |  | 4835 | 		return NullString;
 | 
        
           |  |  | 4836 |   | 
        
           |  |  | 4837 | 	return package->GetInstallAfterText(m_iLanguage);
 | 
        
           |  |  | 4838 | }
 | 
        
           |  |  | 4839 | CyString CPackages::GetUninstallBeforeText(CBaseFile *package)
 | 
        
           |  |  | 4840 | {
 | 
        
           |  |  | 4841 | 	if ( !package->IsThereUninstallText() )
 | 
        
           |  |  | 4842 | 		return NullString;
 | 
        
           |  |  | 4843 |   | 
        
           |  |  | 4844 | 	return package->GetUninstallBeforeText(m_iLanguage);
 | 
        
           |  |  | 4845 | }
 | 
        
           |  |  | 4846 | CyString CPackages::GetUninstallAfterText(CBaseFile *package)
 | 
        
           |  |  | 4847 | {
 | 
        
           |  |  | 4848 | 	if ( !package->IsThereUninstallText() )
 | 
        
           |  |  | 4849 | 		return NullString;
 | 
        
           |  |  | 4850 |   | 
        
           |  |  | 4851 | 	return package->GetUninstallAfterText(m_iLanguage);
 | 
        
           |  |  | 4852 | }
 | 
        
           |  |  | 4853 |   | 
        
           |  |  | 4854 | int CPackages::GetChildPackages(CBaseFile *package, CLinkList<CBaseFile> *children, bool recursive)
 | 
        
           |  |  | 4855 | {
 | 
        
           |  |  | 4856 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 4857 | 	{
 | 
        
           |  |  | 4858 | 		CBaseFile *p = node->Data();
 | 
        
           |  |  | 4859 | 		if ( p->GetParent() == package )
 | 
        
           |  |  | 4860 | 		{
 | 
        
           |  |  | 4861 | 			children->push_back(p);
 | 
        
           |  |  | 4862 |   | 
        
           |  |  | 4863 | 			if ( recursive )
 | 
        
           |  |  | 4864 | 				this->GetChildPackages(p, children, recursive);
 | 
        
           |  |  | 4865 | 		}
 | 
        
           |  |  | 4866 | 	}
 | 
        
           |  |  | 4867 |   | 
        
           |  |  | 4868 | 	return children->size();
 | 
        
           |  |  | 4869 | }
 | 
        
           |  |  | 4870 |   | 
        
           |  |  | 4871 | void CPackages::AssignPackageNumbers()
 | 
        
           |  |  | 4872 | {
 | 
        
           |  |  | 4873 | 	int num = 0;
 | 
        
           |  |  | 4874 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 4875 | 		node->Data()->SetNum(num++);
 | 
        
           |  |  | 4876 | }
 | 
        
           |  |  | 4877 |   | 
        
           |  |  | 4878 | CyString CPackages::FindDataDir(CyString dir, CyString file)
 | 
        
           |  |  | 4879 | {
 | 
        
           |  |  | 4880 | 	CDirIO Dir(dir);
 | 
        
           |  |  | 4881 | 	// data files could be in 4 places depending on what program is used, check for all of these
 | 
        
           |  |  | 4882 | 	if ( Dir.Exists(file) )
 | 
        
           |  |  | 4883 | 		return Dir.File(file);
 | 
        
           |  |  | 4884 | 	else if ( Dir.Exists(CyString("Data/") + file) )
 | 
        
           |  |  | 4885 | 		return Dir.File(CyString("Data/") + file);
 | 
        
           |  |  | 4886 | 	else if ( Dir.Exists(CyString("../") + file) )
 | 
        
           |  |  | 4887 | 		return Dir.File(CyString("../") + file);
 | 
        
           |  |  | 4888 | 	else if ( Dir.Exists(CyString("../Data/") + file) )
 | 
        
           |  |  | 4889 | 		return Dir.File(CyString("../Data/") + file);
 | 
        
           |  |  | 4890 |   | 
        
           |  |  | 4891 | 	return NullString;
 | 
        
           |  |  | 4892 | }
 | 
        
           |  |  | 4893 |   | 
        
           |  |  | 4894 | void CPackages::Startup(CyString dir, CyString tempDir, CyString myDoc, CyString mod)
 | 
        
           |  |  | 4895 | {
 | 
        
           |  |  | 4896 | 	this->SetTempDirectory(tempDir);
 | 
        
           |  |  | 4897 | 	this->SetMyDocuments(myDoc);
 | 
        
           |  |  | 4898 |   | 
        
           |  |  | 4899 | 	m_sSetMod = mod;
 | 
        
           |  |  | 4900 |   | 
        
           |  |  | 4901 | 	// need to read the game exe versions
 | 
        
           |  |  | 4902 | 	m_gameExe.Reset();
 | 
        
           |  |  | 4903 |   | 
        
           |  |  | 4904 | 	CyString exeFile = this->FindDataDir(dir, "exe");
 | 
        
           |  |  | 4905 |   | 
        
           |  |  | 4906 | 	// if file exists, read it, otherwise, just add
 | 
        
           |  |  | 4907 | 	if ( !exeFile.Empty() && CFileIO(exeFile).Exists() )
 | 
        
           |  |  | 4908 | 		m_gameExe.ReadFile(exeFile);
 | 
        
           |  |  | 4909 | 	else
 | 
        
           |  |  | 4910 | 	{
 | 
        
           |  |  | 4911 | 		m_gameExe.ParseExe("x2.exe:5:NOSAVESUBDIR:HKCU/Software/EgoSoftware/X2/ModName:X2 The Threat:!GAMEDIR!:2:1604608!2150400:1.4 Artifical Life:1974272:1.5 Uplink");
 | 
        
           |  |  | 4912 | 		m_gameExe.ParseExe("x3.exe:5:0:HKCU/Software/Egosoft/X3/ModName:X3 Reunion:Egosoft/X3:2:2347008:2.0 Bala Gi:2367488!2375680:2.5 Uplink");
 | 
        
           |  |  | 4913 | 		m_gameExe.ParseExe("x3tc.exe:5:NO_XOR|TC_TEXT|MYDOCLOG:HKCU/Software/Egosoft/X3TC/ModName:X3 Terran Conflict:Egosoft/X3TC:3:1933464!1933520:2.0 Aldrin Expansion:-1:2.5 A New Home (Superbox):-1:3.0 Balance of Power");
 | 
        
           |  |  | 4914 | 		m_gameExe.ParseExe("x3ap.exe:2:NO_XOR|TC_TEXT|MYDOCLOG|ADDON:HKCU/Software/Egosoft/X3AP/ModName:X3 Albion Prelude:Egosoft/X3AP:addon!x3tc.exe:0");
 | 
        
           |  |  | 4915 | 	}
 | 
        
           |  |  | 4916 | }
 | 
        
           |  |  | 4917 |   | 
        
           |  |  | 4918 | int CPackages::GetGameLanguage(CyString dir)
 | 
        
           |  |  | 4919 | {
 | 
        
           |  |  | 4920 | 	if ( dir.Empty() )
 | 
        
           |  |  | 4921 | 		dir = m_sCurrentDir;
 | 
        
           |  |  | 4922 |   | 
        
           |  |  | 4923 | 	CDirIO Dir(dir);
 | 
        
           |  |  | 4924 |   | 
        
           |  |  | 4925 | 	// check for lang.dat file
 | 
        
           |  |  | 4926 | 	if ( Dir.Exists("lang.dat") )
 | 
        
           |  |  | 4927 | 	{
 | 
        
           |  |  | 4928 | 		CFileIO File(Dir.File("lang.dat"));
 | 
        
           |  |  | 4929 |   | 
        
           |  |  | 4930 | 		size_t size;
 | 
        
           |  |  | 4931 | 		char *data = File.ReadToData(&size);
 | 
        
           |  |  | 4932 |   | 
        
           |  |  | 4933 | 		if ( data )
 | 
        
           |  |  | 4934 | 		{
 | 
        
           |  |  | 4935 | 			CyString str(data);
 | 
        
           |  |  | 4936 | 			return str.GetToken("\n", 1, 1).GetToken(" ", 1, 1).ToInt();
 | 
        
           |  |  | 4937 | 		}
 | 
        
           |  |  | 4938 | 	}
 | 
        
           |  |  | 4939 |   | 
        
           |  |  | 4940 | 	return 0;
 | 
        
           |  |  | 4941 | }
 | 
        
           |  |  | 4942 | CyString CPackages::GetGameRunExe(CyString dir)
 | 
        
           |  |  | 4943 | {
 | 
        
           |  |  | 4944 | 	return m_gameExe.GetGameRunExe((dir.Empty()) ? m_sCurrentDir : dir);
 | 
        
           |  |  | 4945 | }
 | 
        
           |  |  | 4946 |   | 
        
           |  |  | 4947 | CyString CPackages::GetGameNameFromType(int game)
 | 
        
           |  |  | 4948 | {
 | 
        
           |  |  | 4949 | 	return m_gameExe.GetGameNameFromType(game - 1);
 | 
        
           |  |  | 4950 | }
 | 
        
           |  |  | 4951 | CyString CPackages::GetGameName(CyString dir)
 | 
        
           |  |  | 4952 | {
 | 
        
           |  |  | 4953 | 	return m_gameExe.GetGameName((dir.Empty()) ? m_sCurrentDir : dir);
 | 
        
           |  |  | 4954 | }
 | 
        
           |  |  | 4955 | CyString CPackages::GetProperDir(CyString dir)
 | 
        
           |  |  | 4956 | {
 | 
        
           |  |  | 4957 | 	return m_gameExe.GetProperDir((dir.Empty()) ? m_sCurrentDir : dir);
 | 
        
           |  |  | 4958 | }
 | 
        
           |  |  | 4959 | CyString CPackages::GetAddonDir(CyString dir)
 | 
        
           |  |  | 4960 | {
 | 
        
           |  |  | 4961 | 	return m_gameExe.GetAddonDir((dir.Empty()) ? m_sCurrentDir : dir);
 | 
        
           |  |  | 4962 | }
 | 
        
           |  |  | 4963 | int CPackages::GetGameAddons(CyStringList &exes, CyString dir)
 | 
        
           |  |  | 4964 | {
 | 
        
           |  |  | 4965 | 	return m_gameExe.GetGameAddons((dir.Empty()) ? m_sCurrentDir : dir, exes);
 | 
        
           |  |  | 4966 | }
 | 
        
           |  |  | 4967 |   | 
        
           |  |  | 4968 | CyString CPackages::GetGameTypesString(CBaseFile *package, bool includeVersion)
 | 
        
           |  |  | 4969 | {
 | 
        
           |  |  | 4970 | 	if ( !package->AnyGameCompatability() )
 | 
        
           |  |  | 4971 | 		return NullString;
 | 
        
           |  |  | 4972 |   | 
        
           |  |  | 4973 | 	CyString sGames;
 | 
        
           |  |  | 4974 | 	for ( CListNode<SGameCompat> *gNode = package->GetGameCompatabilityList()->Front(); gNode; gNode = gNode->next() ) {
 | 
        
           |  |  | 4975 | 		if ( !sGames.Empty() )
 | 
        
           |  |  | 4976 | 			sGames += ", ";
 | 
        
           |  |  | 4977 | 		sGames += m_gameExe.GetGameNameFromType(gNode->Data()->iGame - 1);
 | 
        
           |  |  | 4978 | 		if ( includeVersion ) {
 | 
        
           |  |  | 4979 | 			sGames += " (";
 | 
        
           |  |  | 4980 | 			sGames += m_gameExe.GetGameVersionFromType(gNode->Data()->iGame - 1, gNode->Data()->iVersion - 1, gNode->Data()->sVersion);
 | 
        
           |  |  | 4981 | 			sGames += ")";
 | 
        
           |  |  | 4982 | 		}
 | 
        
           |  |  | 4983 | 	}
 | 
        
           |  |  | 4984 | 	return sGames;
 | 
        
           |  |  | 4985 | }
 | 
        
           |  |  | 4986 |   | 
        
           |  |  | 4987 | CyString CPackages::GetGameVersionString(CBaseFile *package)
 | 
        
           |  |  | 4988 | {
 | 
        
           |  |  | 4989 | 	for ( CListNode<SGameCompat> *gNode = package->GetGameCompatabilityList()->Front(); gNode; gNode = gNode->next() ) {
 | 
        
           |  |  | 4990 | 		if ( gNode->Data()->iGame == m_iGame ) {
 | 
        
           |  |  | 4991 | 			return m_gameExe.GetGameVersionFromType(m_iGame - 1, gNode->Data()->iVersion - 1, gNode->Data()->sVersion);
 | 
        
           |  |  | 4992 | 		}
 | 
        
           |  |  | 4993 | 	}
 | 
        
           |  |  | 4994 |   | 
        
           |  |  | 4995 | 	return NullString;
 | 
        
           |  |  | 4996 | }
 | 
        
           |  |  | 4997 |   | 
        
           |  |  | 4998 | CyString CPackages::GetGameVersionFromType(int game, int version, CyString sVersion)
 | 
        
           |  |  | 4999 | {
 | 
        
           |  |  | 5000 | 	return m_gameExe.GetGameVersionFromType(game - 1, version - 1, sVersion);
 | 
        
           |  |  | 5001 | }
 | 
        
           |  |  | 5002 |   | 
        
           |  |  | 5003 | int CPackages::CountBuiltInPackages(bool onlyEnabled)
 | 
        
           |  |  | 5004 | {
 | 
        
           |  |  | 5005 | 	int count = 0;
 | 
        
           |  |  | 5006 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 5007 | 	{
 | 
        
           |  |  | 5008 | 		if ( !node->Data()->CheckGameCompatability(m_iGame) )
 | 
        
           |  |  | 5009 | 			continue;
 | 
        
           |  |  | 5010 | 		if ( onlyEnabled && !node->Data()->IsEnabled() )
 | 
        
           |  |  | 5011 | 			continue;
 | 
        
           |  |  | 5012 | 		if ( node->Data()->GetAuthor().Compare("PluginManager") )
 | 
        
           |  |  | 5013 | 			++count;
 | 
        
           |  |  | 5014 | 	}
 | 
        
           |  |  | 5015 |   | 
        
           |  |  | 5016 | 	return count;
 | 
        
           |  |  | 5017 | }
 | 
        
           |  |  | 5018 |   | 
        
           |  |  | 5019 | int CPackages::CountPackages(int type, bool onlyEnabled)
 | 
        
           |  |  | 5020 | {
 | 
        
           |  |  | 5021 | 	int count = 0;
 | 
        
           |  |  | 5022 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 5023 | 	{
 | 
        
           |  |  | 5024 | 		CBaseFile *p = node->Data();
 | 
        
           |  |  | 5025 |   | 
        
           |  |  | 5026 | 		if ( (type != TYPE_BASE) && (p->GetType() != type) )
 | 
        
           |  |  | 5027 | 			continue;
 | 
        
           |  |  | 5028 |   | 
        
           |  |  | 5029 | 		if ( (onlyEnabled) && (!p->IsEnabled()) )
 | 
        
           |  |  | 5030 | 			continue;
 | 
        
           |  |  | 5031 |   | 
        
           |  |  | 5032 | 		++count;
 | 
        
           |  |  | 5033 | 	}
 | 
        
           |  |  | 5034 |   | 
        
           |  |  | 5035 | 	return count;
 | 
        
           |  |  | 5036 | }
 | 
        
           |  |  | 5037 |   | 
        
           |  |  | 5038 | int CPackages::ExtractGameFile(CyString aFilename, CyString aTo, CyString dir, CyString addon)
 | 
        
           |  |  | 5039 | {
 | 
        
           |  |  | 5040 | 	// first check the enabled mod
 | 
        
           |  |  | 5041 | 	if ( dir.Empty() )
 | 
        
           |  |  | 5042 | 		dir = m_sCurrentDir;
 | 
        
           |  |  | 5043 |   | 
        
           |  |  | 5044 | 	CyString addonDir = addon;
 | 
        
           |  |  | 5045 | 	if ( addonDir.Empty() ) addonDir = this->GetAddonDir(dir);
 | 
        
           |  |  | 5046 |   | 
        
           |  |  | 5047 | 	if ( m_pEnabledMod && m_pEnabledMod->AnyFileType(FILETYPE_MOD) )
 | 
        
           |  |  | 5048 | 	{
 | 
        
           |  |  | 5049 | 		for ( C_File *file = m_pEnabledMod->GetFirstFile(FILETYPE_MOD); file; file = m_pEnabledMod->GetNextFile(file) )
 | 
        
           |  |  | 5050 | 		{
 | 
        
           |  |  | 5051 | 			if ( !file->CheckFileExt("cat") )
 | 
        
           |  |  | 5052 | 				continue;
 | 
        
           |  |  | 5053 |   | 
        
           |  |  | 5054 | 			CCatFile catFile;
 | 
        
           |  |  | 5055 | 			if ( catFile.Open(file->GetFilePointer(), addonDir, CATREAD_CATDECRYPT, false) == CATERR_NONE )
 | 
        
           |  |  | 5056 | 			{
 | 
        
           |  |  | 5057 | 				if ( catFile.ExtractFile(aFilename, aTo) )
 | 
        
           |  |  | 5058 | 					return 1;
 | 
        
           |  |  | 5059 | 				if ( catFile.Error() == CATERR_INVALIDDEST || catFile.Error() == CATERR_CANTCREATEDIR )
 | 
        
           |  |  | 5060 | 				{
 | 
        
           |  |  | 5061 | 					if ( catFile.ExtractFile(aFilename) )
 | 
        
           |  |  | 5062 | 						return -1;
 | 
        
           |  |  | 5063 | 				}
 | 
        
           |  |  | 5064 |   | 
        
           |  |  | 5065 | 			}
 | 
        
           |  |  | 5066 | 		}
 | 
        
           |  |  | 5067 | 	}
 | 
        
           |  |  | 5068 | 	else if ( !m_sSetMod.Empty() )
 | 
        
           |  |  | 5069 | 	{
 | 
        
           |  |  | 5070 | 		if ( CFileIO(m_sCurrentDir + "/mods/" + m_sSetMod + ".cat").Exists() )
 | 
        
           |  |  | 5071 | 		{
 | 
        
           |  |  | 5072 | 			CCatFile catFile;
 | 
        
           |  |  | 5073 | 			if ( catFile.Open(m_sCurrentDir + "/mods/" + m_sSetMod + ".cat", addonDir, CATREAD_CATDECRYPT, false) == CATERR_NONE )
 | 
        
           |  |  | 5074 | 			{
 | 
        
           |  |  | 5075 | 				if ( catFile.ExtractFile(aFilename, aTo) )
 | 
        
           |  |  | 5076 | 					return 1;
 | 
        
           |  |  | 5077 | 				if ( catFile.Error() == CATERR_INVALIDDEST || catFile.Error() == CATERR_CANTCREATEDIR )
 | 
        
           |  |  | 5078 | 				{
 | 
        
           |  |  | 5079 | 					if ( catFile.ExtractFile(aFilename) )
 | 
        
           |  |  | 5080 | 						return -1;
 | 
        
           |  |  | 5081 | 				}
 | 
        
           |  |  | 5082 | 			}
 | 
        
           |  |  | 5083 | 		}
 | 
        
           |  |  | 5084 | 	}
 | 
        
           |  |  | 5085 |   | 
        
           |  |  | 5086 | 	// find the highest cat number
 | 
        
           |  |  | 5087 | 	int catNumber = 1;
 | 
        
           |  |  | 5088 | 	while ( CFileIO(dir + "/" + CyString::Number(catNumber).PadNumber(2) + ".cat").Exists() && catNumber < 99 )
 | 
        
           |  |  | 5089 | 		++catNumber;
 | 
        
           |  |  | 5090 |   | 
        
           |  |  | 5091 | 	// get the last one, not the next free one
 | 
        
           |  |  | 5092 | 	--catNumber;
 | 
        
           |  |  | 5093 |   | 
        
           |  |  | 5094 | 	// work backwards until we find the file
 | 
        
           |  |  | 5095 | 	for ( ; catNumber; catNumber-- )
 | 
        
           |  |  | 5096 | 	{
 | 
        
           |  |  | 5097 | 		CCatFile catFile;
 | 
        
           |  |  | 5098 | 		if ( catFile.Open(dir + "/" + CyString::Number(catNumber).PadNumber(2) + ".cat", addonDir, CATREAD_CATDECRYPT, false) == CATERR_NONE )
 | 
        
           |  |  | 5099 | 		{
 | 
        
           |  |  | 5100 | 			// check for the file
 | 
        
           |  |  | 5101 | 			if ( catFile.ExtractFile(aFilename, aTo) )
 | 
        
           |  |  | 5102 | 				return 1;
 | 
        
           |  |  | 5103 | 			if ( catFile.Error() == CATERR_INVALIDDEST || catFile.Error() == CATERR_CANTCREATEDIR )
 | 
        
           |  |  | 5104 | 			{
 | 
        
           |  |  | 5105 | 				if ( catFile.ExtractFile(aFilename) )
 | 
        
           |  |  | 5106 | 					return -1;
 | 
        
           |  |  | 5107 | 			}
 | 
        
           |  |  | 5108 | 		}
 | 
        
           |  |  | 5109 | 	}
 | 
        
           |  |  | 5110 |   | 
        
           |  |  | 5111 | 	return 0;
 | 
        
           |  |  | 5112 | }
 | 
        
           |  |  | 5113 |   | 
        
           |  |  | 5114 | void CPackages::CreateWareFiles()
 | 
        
           |  |  | 5115 | {
 | 
        
           |  |  | 5116 | 	// do each ware
 | 
        
           |  |  | 5117 | 	int wareTextID = WARETEXTSTART;
 | 
        
           |  |  | 5118 | 	for ( int i = 0; i < WAREBUFFERS; i++ )
 | 
        
           |  |  | 5119 | 	{
 | 
        
           |  |  | 5120 | 		// its empty, no need to create ware files
 | 
        
           |  |  | 5121 | 		if ( !m_lGameWares[i].size() )
 | 
        
           |  |  | 5122 | 			continue;
 | 
        
           |  |  | 5123 |   | 
        
           |  |  | 5124 | 		// lets extract the ware file
 | 
        
           |  |  | 5125 | 		char wareType = CPackages::ConvertWareTypeBack(i);
 | 
        
           |  |  | 5126 | 		CyString wareFile = "TWare";
 | 
        
           |  |  | 5127 | 		wareFile += (char)UPPER(wareType);
 | 
        
           |  |  | 5128 |   | 
        
           |  |  | 5129 | 		CyString openFile;
 | 
        
           |  |  | 5130 |   | 
        
           |  |  | 5131 | 		int e;
 | 
        
           |  |  | 5132 | 		if ( i == WARES_TECH && CFileIO(m_sTempDir + "/TWareT.txt").Exists() )
 | 
        
           |  |  | 5133 | 			openFile = m_sTempDir + "/TWareT.txt";
 | 
        
           |  |  | 5134 | 		else {
 | 
        
           |  |  | 5135 | 			e = ExtractGameFile(CyString("types/") + wareFile + ".pck", m_sTempDir + "/" + wareFile + ".txt");
 | 
        
           |  |  | 5136 | 			if ( e == 1 )
 | 
        
           |  |  | 5137 | 				openFile = m_sTempDir + "/" + wareFile + ".txt";
 | 
        
           |  |  | 5138 | 			else if ( e == -2 )
 | 
        
           |  |  | 5139 | 				openFile = wareFile + ".txt";
 | 
        
           |  |  | 5140 | 		}
 | 
        
           |  |  | 5141 |   | 
        
           |  |  | 5142 | 		if ( !openFile.Empty() )
 | 
        
           |  |  | 5143 | 		{
 | 
        
           |  |  | 5144 | 			// read the file into memory
 | 
        
           |  |  | 5145 | 			CyStringList wareLines;
 | 
        
           |  |  | 5146 | 			int oldSize = -1;
 | 
        
           |  |  | 5147 | 			int version = -1;
 | 
        
           |  |  | 5148 |   | 
        
           |  |  | 5149 | 			// read first number
 | 
        
           |  |  | 5150 | 			CFileIO readFile(m_sTempDir + "/" + wareFile + ".txt");
 | 
        
           |  |  | 5151 | 			CyStringList *lines = readFile.ReadLinesStr();
 | 
        
           |  |  | 5152 | 			if ( lines )
 | 
        
           |  |  | 5153 | 			{
 | 
        
           |  |  | 5154 | 				for ( SStringList *str = lines->Head(); str; str = str->next )
 | 
        
           |  |  | 5155 | 				{
 | 
        
           |  |  | 5156 | 					CyString line(str->str);
 | 
        
           |  |  | 5157 | 					line.RemoveFirstSpace();
 | 
        
           |  |  | 5158 | 					line.RemoveChar(9);
 | 
        
           |  |  | 5159 | 					line.RemoveChar('\r');
 | 
        
           |  |  | 5160 | 					if ( line.Empty() )
 | 
        
           |  |  | 5161 | 						continue;
 | 
        
           |  |  | 5162 | 					if ( line[0] == '/' )
 | 
        
           |  |  | 5163 | 						continue;
 | 
        
           |  |  | 5164 |   | 
        
           |  |  | 5165 | 					if ( oldSize == -1 )
 | 
        
           |  |  | 5166 | 					{
 | 
        
           |  |  | 5167 | 						version = line.GetToken(";", 1, 1).ToInt();
 | 
        
           |  |  | 5168 | 						oldSize = line.GetToken(";", 2, 2).ToInt();
 | 
        
           |  |  | 5169 | 					}
 | 
        
           |  |  | 5170 | 					else
 | 
        
           |  |  | 5171 | 					{
 | 
        
           |  |  | 5172 | 						line.RemoveEndSpace();
 | 
        
           |  |  | 5173 | 						if ( line.Right(1) != ';' )
 | 
        
           |  |  | 5174 | 							line += ";";
 | 
        
           |  |  | 5175 | 						wareLines.PushBack(line);
 | 
        
           |  |  | 5176 | 						if ( wareLines.Count() >= oldSize )
 | 
        
           |  |  | 5177 | 							break;
 | 
        
           |  |  | 5178 | 					}
 | 
        
           |  |  | 5179 | 				}
 | 
        
           |  |  | 5180 |   | 
        
           |  |  | 5181 | 				delete lines;
 | 
        
           |  |  | 5182 |   | 
        
           |  |  | 5183 | 				// apply the buffer
 | 
        
           |  |  | 5184 | 				if ( m_iWareBuffer[i] <= 0 )
 | 
        
           |  |  | 5185 | 					m_iWareBuffer[i] = wareLines.Count() + 10;
 | 
        
           |  |  | 5186 | 				// last resort, readjust the buffer
 | 
        
           |  |  | 5187 | 				else if ( wareLines.Count() > m_iWareBuffer[i] )
 | 
        
           |  |  | 5188 | 					m_iWareBuffer[i] = wareLines.Count();
 | 
        
           |  |  | 5189 |   | 
        
           |  |  | 5190 | 				// add the buffers
 | 
        
           |  |  | 5191 | 				while ( wareLines.Count() < m_iWareBuffer[i] )
 | 
        
           |  |  | 5192 | 					wareLines.PushBack("27;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;SS_WARE_FILLER;");
 | 
        
           |  |  | 5193 |   | 
        
           |  |  | 5194 | 				// add the ware lines
 | 
        
           |  |  | 5195 | 				bool create = false;
 | 
        
           |  |  | 5196 | 				for ( CListNode<SGameWare> *node = m_lGameWares[i].Front(); node; node = node->next() )
 | 
        
           |  |  | 5197 | 				{
 | 
        
           |  |  | 5198 | 					SGameWare *w = node->Data();
 | 
        
           |  |  | 5199 |   | 
        
           |  |  | 5200 | 					if ( w->iType == WARETYPE_NONE )
 | 
        
           |  |  | 5201 | 						continue;
 | 
        
           |  |  | 5202 | 					else if ( w->iType == WARETYPE_DISABLED )
 | 
        
           |  |  | 5203 | 					{
 | 
        
           |  |  | 5204 | 						create = true;
 | 
        
           |  |  | 5205 | 						wareLines.PushBack(CyString("27;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;") + w->sWareName + "_DISABLED;");
 | 
        
           |  |  | 5206 | 					}
 | 
        
           |  |  | 5207 | 					else if ( w->iType == WARETYPE_DELETED || !w->pWare )
 | 
        
           |  |  | 5208 | 					{
 | 
        
           |  |  | 5209 | 						create = true;
 | 
        
           |  |  | 5210 | 						wareLines.PushBack("27;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;SS_WARE_DELETED;");
 | 
        
           |  |  | 5211 | 					}
 | 
        
           |  |  | 5212 | 					else if ( w->iType == WARETYPE_ADDED )
 | 
        
           |  |  | 5213 | 					{
 | 
        
           |  |  | 5214 | 						create = true;
 | 
        
           |  |  | 5215 | 						w->pWare->iDescID = wareTextID;
 | 
        
           |  |  | 5216 | 						w->iText = wareTextID;
 | 
        
           |  |  | 5217 | 						wareTextID += 10;
 | 
        
           |  |  | 5218 | 						w->iPos = wareLines.Count();
 | 
        
           |  |  | 5219 | 						wareLines.PushBack(CyString("28;0;0;0;0;") + (long)wareLines.Count() + ";" + (long)(w->iText + 3) + ";" + (long)w->pWare->iVolumn + ";" + (long)w->pWare->iPrice + ";1;1;" + (long)w->pWare->iSize + ";" + (long)w->pWare->iPrice + ";" + (long)w->pWare->iNotority + ";0;0;" + w->sWareName.ToUpper() + ";");
 | 
        
           |  |  | 5220 | 					}
 | 
        
           |  |  | 5221 | 				}
 | 
        
           |  |  | 5222 |   | 
        
           |  |  | 5223 | 				if ( create )
 | 
        
           |  |  | 5224 | 				{
 | 
        
           |  |  | 5225 | 					wareLines.PushFront(CyString::Number(version) + ";" + CyString::Number(wareLines.Count()) + ";", NullString);
 | 
        
           |  |  | 5226 | 					CyString strV;
 | 
        
           |  |  | 5227 | 					strV.FromFloat(GetLibraryVersion(), 2);
 | 
        
           |  |  | 5228 | 					wareLines.PushFront(CyString("// Created by SPKInstaller Libraries V") + strV, NullString);
 | 
        
           |  |  | 5229 | 					if ( readFile.WriteFile(&wareLines) )
 | 
        
           |  |  | 5230 | 						this->PackFile(&readFile, CyString("types\\") + wareFile + ".pck");
 | 
        
           |  |  | 5231 | 				}
 | 
        
           |  |  | 5232 | 			}
 | 
        
           |  |  | 5233 | 			readFile.Remove();
 | 
        
           |  |  | 5234 | 		}
 | 
        
           |  |  | 5235 | 	}
 | 
        
           |  |  | 5236 | }
 | 
        
           |  |  | 5237 |   | 
        
           |  |  | 5238 | void CPackages::CreateEMPFile(CyString progDir)
 | 
        
           |  |  | 5239 | {
 | 
        
           |  |  | 5240 | 	// do emp wares
 | 
        
           |  |  | 5241 | 	int maxsize = 0;
 | 
        
           |  |  | 5242 | 	CyString empWares;
 | 
        
           |  |  | 5243 |   | 
        
           |  |  | 5244 | 	if ( m_iGame == GAME_X3TC )
 | 
        
           |  |  | 5245 | 	{
 | 
        
           |  |  | 5246 | 		maxsize = EMP_X3TC;
 | 
        
           |  |  | 5247 | 		empWares = GetX3TCEmp();
 | 
        
           |  |  | 5248 | 	}
 | 
        
           |  |  | 5249 | 	else if ( m_iGame == GAME_X3AP )
 | 
        
           |  |  | 5250 | 	{
 | 
        
           |  |  | 5251 | 		maxsize = EMP_X3AP;
 | 
        
           |  |  | 5252 | 		empWares = GetX3TCEmp();
 | 
        
           |  |  | 5253 | 	}
 | 
        
           |  |  | 5254 | 	else if ( m_iGame == GAME_X3 )
 | 
        
           |  |  | 5255 | 	{
 | 
        
           |  |  | 5256 | 		maxsize = EMP_X3;
 | 
        
           |  |  | 5257 | 		empWares = GetX3Emp();
 | 
        
           |  |  | 5258 | 	}
 | 
        
           |  |  | 5259 |   | 
        
           |  |  | 5260 | 	if ( maxsize )
 | 
        
           |  |  | 5261 | 	{
 | 
        
           |  |  | 5262 | 		int e = ExtractGameFile("types/TWareT.pck", m_sTempDir + "/TWareT.txt");
 | 
        
           |  |  | 5263 | 		if ( e )
 | 
        
           |  |  | 5264 | 		{
 | 
        
           |  |  | 5265 | 			// read the file into memory
 | 
        
           |  |  | 5266 | 			CyStringList wareLines;
 | 
        
           |  |  | 5267 | 			int oldSize = -1;
 | 
        
           |  |  | 5268 | 			int version = -1;
 | 
        
           |  |  | 5269 |   | 
        
           |  |  | 5270 | 			// read first number
 | 
        
           |  |  | 5271 | 			CFileIO readFile((e == -1) ? "TWareT.txt" : m_sTempDir + "/TWareT.txt");
 | 
        
           |  |  | 5272 | 			std::vector<CyString> *lines = readFile.ReadLines();
 | 
        
           |  |  | 5273 | 			if ( lines )
 | 
        
           |  |  | 5274 | 			{
 | 
        
           |  |  | 5275 | 				for ( int i = 0; i < (int)lines->size(); i++ )
 | 
        
           |  |  | 5276 | 				{
 | 
        
           |  |  | 5277 | 					CyString line(lines->at(i));
 | 
        
           |  |  | 5278 | 					line.RemoveFirstSpace();
 | 
        
           |  |  | 5279 | 					line.RemoveChar('\r');
 | 
        
           |  |  | 5280 | 					line.RemoveChar(9);
 | 
        
           |  |  | 5281 | 					if ( line[0] == '/' )
 | 
        
           |  |  | 5282 | 						continue;
 | 
        
           |  |  | 5283 |   | 
        
           |  |  | 5284 | 					if ( oldSize == -1 )
 | 
        
           |  |  | 5285 | 					{
 | 
        
           |  |  | 5286 | 						version = line.GetToken(";", 1, 1).ToInt();
 | 
        
           |  |  | 5287 | 						oldSize = line.GetToken(";", 2, 2).ToInt();
 | 
        
           |  |  | 5288 | 					}
 | 
        
           |  |  | 5289 | 					else
 | 
        
           |  |  | 5290 | 					{
 | 
        
           |  |  | 5291 | 						line.RemoveEndSpace();
 | 
        
           |  |  | 5292 | 						if ( line.Right(1) != ";" )
 | 
        
           |  |  | 5293 | 							line += ";";
 | 
        
           |  |  | 5294 | 						wareLines.PushBack(line);
 | 
        
           |  |  | 5295 | 						if ( wareLines.Count() >= oldSize )
 | 
        
           |  |  | 5296 | 							break;
 | 
        
           |  |  | 5297 | 					}
 | 
        
           |  |  | 5298 | 				}
 | 
        
           |  |  | 5299 |   | 
        
           |  |  | 5300 | 				delete lines;
 | 
        
           |  |  | 5301 | 			}
 | 
        
           |  |  | 5302 |   | 
        
           |  |  | 5303 | 			// now we too add/remove entries to match
 | 
        
           |  |  | 5304 | 			// need filler entries
 | 
        
           |  |  | 5305 | 			while ( wareLines.Count() < maxsize )
 | 
        
           |  |  | 5306 | 				wareLines.PushBack("27;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;SS_WARE_FILLER;");
 | 
        
           |  |  | 5307 |   | 
        
           |  |  | 5308 | 			int empEntries = 0;
 | 
        
           |  |  | 5309 | 			CyString *empStr = empWares.SplitToken("\n", &empEntries);
 | 
        
           |  |  | 5310 |   | 
        
           |  |  | 5311 | 			if ( empEntries && empStr )
 | 
        
           |  |  | 5312 | 			{
 | 
        
           |  |  | 5313 | 				// remove any empty end entries
 | 
        
           |  |  | 5314 | 				while ( empStr[empEntries - 1].Empty() )
 | 
        
           |  |  | 5315 | 					--empEntries;
 | 
        
           |  |  | 5316 |   | 
        
           |  |  | 5317 | 				CyStringList addAfter;
 | 
        
           |  |  | 5318 | 				if ( wareLines.Count() > maxsize )
 | 
        
           |  |  | 5319 | 				{
 | 
        
           |  |  | 5320 | 					// force emp, remove entries to allow them to be added
 | 
        
           |  |  | 5321 | 					if ( m_bForceEMP )
 | 
        
           |  |  | 5322 | 					{
 | 
        
           |  |  | 5323 | 						// more after emp
 | 
        
           |  |  | 5324 | 						if ( wareLines.Count() > (maxsize + empEntries) )
 | 
        
           |  |  | 5325 | 						{
 | 
        
           |  |  | 5326 | 							SStringList *node = wareLines.GetAt(maxsize + empEntries);
 | 
        
           |  |  | 5327 | 							while ( node )
 | 
        
           |  |  | 5328 | 							{
 | 
        
           |  |  | 5329 | 								addAfter.PushBack(node->str);
 | 
        
           |  |  | 5330 | 								node = node->next;
 | 
        
           |  |  | 5331 | 							}
 | 
        
           |  |  | 5332 | 						}
 | 
        
           |  |  | 5333 |   | 
        
           |  |  | 5334 | 						// no remove them all
 | 
        
           |  |  | 5335 | 						wareLines.DeleteFrom(maxsize);
 | 
        
           |  |  | 5336 | 					}
 | 
        
           |  |  | 5337 | 					else if ( m_iGame == GAME_X3TC || m_iGame == GAME_X3AP ) // check if old emp is included, and convert it
 | 
        
           |  |  | 5338 | 					{
 | 
        
           |  |  | 5339 | 						if ( wareLines.Count() > 128 )
 | 
        
           |  |  | 5340 | 						{
 | 
        
           |  |  | 5341 | 							CyString test = wareLines.GetAt(128)->str;
 | 
        
           |  |  | 5342 | 							if ( test.GetToken(";", -2).Compare("SS_WARE_SW_CUSTOM16_1;") )
 | 
        
           |  |  | 5343 | 							{
 | 
        
           |  |  | 5344 | 								// if theres any at the end, remove the last emp entry
 | 
        
           |  |  | 5345 | 								if ( wareLines.Count() > (maxsize + empEntries - 1) )
 | 
        
           |  |  | 5346 | 								{
 | 
        
           |  |  | 5347 | 									SStringList *node = wareLines.GetAt(maxsize + empEntries - 2);
 | 
        
           |  |  | 5348 | 									if ( node )
 | 
        
           |  |  | 5349 | 										node->remove = true;
 | 
        
           |  |  | 5350 | 								}
 | 
        
           |  |  | 5351 | 								wareLines.Insert(128, "0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;128;");
 | 
        
           |  |  | 5352 | 								wareLines.RemoveMarked();
 | 
        
           |  |  | 5353 | 							}
 | 
        
           |  |  | 5354 | 						}
 | 
        
           |  |  | 5355 | 					}
 | 
        
           |  |  | 5356 | 				}
 | 
        
           |  |  | 5357 |   | 
        
           |  |  | 5358 | 				// too many entries, need to remove the first set of EMP wares
 | 
        
           |  |  | 5359 | 				int i = 0;
 | 
        
           |  |  | 5360 | 				if ( wareLines.Count() > maxsize )
 | 
        
           |  |  | 5361 | 					i = wareLines.Count() - maxsize;
 | 
        
           |  |  | 5362 |   | 
        
           |  |  | 5363 | 				for ( ; i < empEntries; i++ )
 | 
        
           |  |  | 5364 | 				{
 | 
        
           |  |  | 5365 | 					CyString str = empStr[i];
 | 
        
           |  |  | 5366 | 					str.RemoveEndSpace();
 | 
        
           |  |  | 5367 | 					str.RemoveChar(9);
 | 
        
           |  |  | 5368 | 					str.RemoveChar('\r');
 | 
        
           |  |  | 5369 | 					if ( str.Empty() )
 | 
        
           |  |  | 5370 | 						continue;
 | 
        
           |  |  | 5371 | 					if ( str.Right(1) != ";" )
 | 
        
           |  |  | 5372 | 						str += ";";
 | 
        
           |  |  | 5373 | 					wareLines.PushBack(str);
 | 
        
           |  |  | 5374 | 				}
 | 
        
           |  |  | 5375 |   | 
        
           |  |  | 5376 | 				for ( SStringList *afterNode = addAfter.Head(); afterNode; afterNode = afterNode->next )
 | 
        
           |  |  | 5377 | 					wareLines.PushBack(afterNode->str);
 | 
        
           |  |  | 5378 |   | 
        
           |  |  | 5379 | 				// finally we write the whole file
 | 
        
           |  |  | 5380 | 				wareLines.PushFront(CyString::Number(version) + ";" + CyString::Number(wareLines.Count()) + ";", NullString);
 | 
        
           |  |  | 5381 | 				CyString strV;
 | 
        
           |  |  | 5382 | 				strV.FromFloat(GetLibraryVersion(), 2);
 | 
        
           |  |  | 5383 | 				wareLines.PushFront(CyString("// Created by SPKInstaller Libraries V") + strV, NullString);
 | 
        
           |  |  | 5384 | 				if ( readFile.WriteFile(&wareLines) )
 | 
        
           |  |  | 5385 | 					this->PackFile(&readFile, "types\\TWareT.pck");
 | 
        
           |  |  | 5386 | 			}
 | 
        
           |  |  | 5387 | 			CLEANSPLIT(empStr, empEntries);
 | 
        
           |  |  | 5388 | 		}
 | 
        
           |  |  | 5389 | 	}
 | 
        
           |  |  | 5390 | }
 | 
        
           |  |  | 5391 |   | 
        
           |  |  | 5392 | CyString CPackages::ConvertTextString(CyString text)
 | 
        
           |  |  | 5393 | {
 | 
        
           |  |  | 5394 | 	text = text.FindReplace("(", "\\(");
 | 
        
           |  |  | 5395 | 	text = text.FindReplace(")", "\\)");
 | 
        
           |  |  | 5396 | 	text = text.FindReplace("[", "{");
 | 
        
           |  |  | 5397 | 	text = text.FindReplace("]", "}");
 | 
        
           |  |  | 5398 | 	text = text.FindReplace(">", ">");
 | 
        
           |  |  | 5399 | 	text = text.FindReplace("<", "<");
 | 
        
           |  |  | 5400 | 	text = text.FindReplace("&", "&");
 | 
        
           |  |  | 5401 | 	return text;
 | 
        
           |  |  | 5402 | }
 | 
        
           |  |  | 5403 |   | 
        
           |  |  | 5404 | void CPackages::CreatePluginManagerText()
 | 
        
           |  |  | 5405 | {
 | 
        
           |  |  | 5406 | 	int gameNumber = 0;
 | 
        
           |  |  | 5407 | 	if ( m_iGame == GAME_X3 )
 | 
        
           |  |  | 5408 | 		gameNumber = 30;
 | 
        
           |  |  | 5409 | 	else if ( m_iGame == GAME_X3TC )
 | 
        
           |  |  | 5410 | 		gameNumber = 35;
 | 
        
           |  |  | 5411 | 	else if ( m_iGame == GAME_X3AP )
 | 
        
           |  |  | 5412 | 		gameNumber = 38;
 | 
        
           |  |  | 5413 |   | 
        
           |  |  | 5414 | 	int lang = m_iLanguage;
 | 
        
           |  |  | 5415 | 	if ( !lang || lang < 0 )
 | 
        
           |  |  | 5416 | 		lang = 44;
 | 
        
           |  |  | 5417 |   | 
        
           |  |  | 5418 | 	CDirIO Dir(m_sCurrentDir);
 | 
        
           |  |  | 5419 | 	if ( !Dir.Exists("t") )
 | 
        
           |  |  | 5420 | 		Dir.Create("t");
 | 
        
           |  |  | 5421 |   | 
        
           |  |  | 5422 | 	m_iLastUpdated = (int)time(NULL);
 | 
        
           |  |  | 5423 |   | 
        
           |  |  | 5424 | 	CyString filename = SPK::FormatTextName(PMTEXTFILE, lang, (m_iGameFlags & EXEFLAG_TCTEXT));
 | 
        
           |  |  | 5425 | 	CFileIO textFile(m_sCurrentDir + "/t/" + filename + ".xml");
 | 
        
           |  |  | 5426 |   | 
        
           |  |  | 5427 | 	std::vector<CyString> writeData;
 | 
        
           |  |  | 5428 |   | 
        
           |  |  | 5429 | 	CLinkList<SGameWare> lWares;
 | 
        
           |  |  | 5430 | 	CLinkList<SGameShip> lShips;
 | 
        
           |  |  | 5431 | 	for ( int i = 0; i < WAREBUFFERS; i++ )
 | 
        
           |  |  | 5432 | 	{
 | 
        
           |  |  | 5433 | 		for ( CListNode<SGameWare> *node = m_lGameWares[i].Front(); node; node = node->next() )
 | 
        
           |  |  | 5434 | 		{
 | 
        
           |  |  | 5435 | 			SGameWare *w = node->Data();
 | 
        
           |  |  | 5436 | 			if ( w->iType == WARETYPE_NONE )
 | 
        
           |  |  | 5437 | 				continue;
 | 
        
           |  |  | 5438 | 			lWares.push_back(w);
 | 
        
           |  |  | 5439 | 		}
 | 
        
           |  |  | 5440 | 	}
 | 
        
           |  |  | 5441 | 	for ( CListNode<SGameShip> *node = m_lGameShips.Front(); node; node = node->next() )
 | 
        
           |  |  | 5442 | 	{
 | 
        
           |  |  | 5443 | 		if ( node->Data()->iType == WARETYPE_NONE )
 | 
        
           |  |  | 5444 | 			continue;
 | 
        
           |  |  | 5445 | 		lShips.push_back(node->Data());
 | 
        
           |  |  | 5446 | 	}
 | 
        
           |  |  | 5447 |   | 
        
           |  |  | 5448 | 	writeData.push_back(CyString("<?xml version=\"1.0\" encoding=\"UTF-8\" ?>"));
 | 
        
           |  |  | 5449 | 	writeData.push_back(CyString("<language id=\"") + CyString::Number(lang) + "\">");
 | 
        
           |  |  | 5450 |   | 
        
           |  |  | 5451 | 	if ( !gameNumber )
 | 
        
           |  |  | 5452 | 		writeData.push_back(CyString("	<page id=\"") + CyString::Number(PMTEXTFILE) + "\" title=\"Plugin Manager Text File\" descr=\"Contains text used for the plugin manager, packages, settings, wares, ship, etc\">");
 | 
        
           |  |  | 5453 | 	else
 | 
        
           |  |  | 5454 | 		writeData.push_back(CyString("	<page id=\"") + (long)gameNumber + CyString::Number(PMTEXTFILE).PadNumber(4) + "\" title=\"Plugin Manager Text File\" descr=\"Contains text used for the plugin manager, packages, settings, wares, ship, etc\">");
 | 
        
           |  |  | 5455 |   | 
        
           |  |  | 5456 | 	// write the heading
 | 
        
           |  |  | 5457 | 	int start = 10000;
 | 
        
           |  |  | 5458 | 	writeData.push_back(CyString("		<t id=\"1\">") + CyString::Number(m_iLastUpdated) + "</t>");
 | 
        
           |  |  | 5459 | 	writeData.push_back(CyString("		<t id=\"2\">") + CyString::Number(this->CountPackages(TYPE_SPK, true)) + "</t>");
 | 
        
           |  |  | 5460 | 	writeData.push_back(CyString("		<t id=\"3\">") + CyString::Number(start) + "</t>");
 | 
        
           |  |  | 5461 | 	writeData.push_back(CyString("		<t id=\"4\">") + CyString::Number(lWares.size()) + "</t>");
 | 
        
           |  |  | 5462 | 	writeData.push_back(CyString("		<t id=\"6\">") + CyString::Number(lShips.size()) + "</t>");
 | 
        
           |  |  | 5463 |   | 
        
           |  |  | 5464 | 	// write some generic texts
 | 
        
           |  |  | 5465 | 	writeData.push_back(CyString("		<t id=\"110\">") + (long)m_iLanguage + "</t>");
 | 
        
           |  |  | 5466 | 	writeData.push_back(CyString("		<t id=\"109\">Plugin Manager: \\033GPoll Gui Data\\033X</t>"));
 | 
        
           |  |  | 5467 | 	writeData.push_back(CyString("		<t id=\"107\">Plugin Manager: \\033GExport Game Data\\033X </t>"));
 | 
        
           |  |  | 5468 | 	writeData.push_back(CyString("		<t id=\"100\">\\n</t>"));
 | 
        
           |  |  | 5469 | 	writeData.push_back(CyString("		<t id=\"101\">\\033B</t>"));
 | 
        
           |  |  | 5470 | 	writeData.push_back(CyString("		<t id=\"102\">\\033G</t>"));
 | 
        
           |  |  | 5471 | 	writeData.push_back(CyString("		<t id=\"103\">\\033B</t>"));
 | 
        
           |  |  | 5472 | 	writeData.push_back(CyString("		<t id=\"104\">\\033X</t>"));
 | 
        
           |  |  | 5473 | 	writeData.push_back(CyString("		<t id=\"105\">\\033Y</t>"));
 | 
        
           |  |  | 5474 | 	writeData.push_back(CyString("		<t id=\"106\">\\033C</t>"));
 | 
        
           |  |  | 5475 | 	writeData.push_back(CyString("		<t id=\"108\">\\033</t>"));
 | 
        
           |  |  | 5476 | 	// now write each package
 | 
        
           |  |  | 5477 | 	int settingStart = 100000;
 | 
        
           |  |  | 5478 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 5479 | 	{
 | 
        
           |  |  | 5480 | 		CBaseFile *p = node->Data();
 | 
        
           |  |  | 5481 | 		if ( !p->IsEnabled() )
 | 
        
           |  |  | 5482 | 			continue;
 | 
        
           |  |  | 5483 |   | 
        
           |  |  | 5484 | 		if ( p->GetType() != TYPE_SPK )
 | 
        
           |  |  | 5485 | 			continue;
 | 
        
           |  |  | 5486 |   | 
        
           |  |  | 5487 | 		CSpkFile *spk = (CSpkFile *)p;
 | 
        
           |  |  | 5488 |   | 
        
           |  |  | 5489 | 		// count text files
 | 
        
           |  |  | 5490 | 		CyString textEntries;
 | 
        
           |  |  | 5491 | 		int textCount = 0;
 | 
        
           |  |  | 5492 | 		C_File *f = p->GetFirstFile(FILETYPE_TEXT);
 | 
        
           |  |  | 5493 | 		while ( f )
 | 
        
           |  |  | 5494 | 		{
 | 
        
           |  |  | 5495 | 			CyString sLang;
 | 
        
           |  |  | 5496 | 			CyString id;
 | 
        
           |  |  | 5497 | 			if ( m_iGameFlags & EXEFLAG_TCTEXT )
 | 
        
           |  |  | 5498 | 			{
 | 
        
           |  |  | 5499 | 				id = f->GetBaseName().GetToken("-", 1, 1);
 | 
        
           |  |  | 5500 | 				sLang = f->GetBaseName().GetToken("-", 2, 2);
 | 
        
           |  |  | 5501 | 				if ( sLang.Empty() )
 | 
        
           |  |  | 5502 | 					sLang = "NULL";
 | 
        
           |  |  | 5503 | 				else
 | 
        
           |  |  | 5504 | 					sLang = sLang.Erase(0, 1);  // remove the "L"
 | 
        
           |  |  | 5505 | 			}
 | 
        
           |  |  | 5506 | 			else
 | 
        
           |  |  | 5507 | 			{
 | 
        
           |  |  | 5508 | 				sLang = f->GetBaseName().Left((int)f->GetBaseName().Length() - 4).PadNumber(3);
 | 
        
           |  |  | 5509 | 				id = f->GetBaseName().Mid(((int)f->GetBaseName().Length() - 4) + 1, 4);
 | 
        
           |  |  | 5510 | 			}
 | 
        
           |  |  | 5511 |   | 
        
           |  |  | 5512 | 			if ( sLang != "NULL" )
 | 
        
           |  |  | 5513 | 			{
 | 
        
           |  |  | 5514 | 				if ( sLang.ToInt() == lang )
 | 
        
           |  |  | 5515 | 				{
 | 
        
           |  |  | 5516 | 					++textCount;
 | 
        
           |  |  | 5517 | 					if ( !textEntries.Empty() )
 | 
        
           |  |  | 5518 | 						textEntries += " ";
 | 
        
           |  |  | 5519 | 					textEntries += id;
 | 
        
           |  |  | 5520 | 				}
 | 
        
           |  |  | 5521 | 			}
 | 
        
           |  |  | 5522 | 			f = p->GetNextFile(f);
 | 
        
           |  |  | 5523 | 		}
 | 
        
           |  |  | 5524 |   | 
        
           |  |  | 5525 | 		CyString sTextCount((long)textCount);
 | 
        
           |  |  | 5526 | 		writeData.push_back(CyString("		<t id=\"") + (long)start + "\">" + this->ConvertTextString(p->GetName()) + "</t>");
 | 
        
           |  |  | 5527 | 		writeData.push_back(CyString("		<t id=\"") + (long)(start + 1) + "\">" + this->ConvertTextString(p->GetAuthor()) + "</t>");
 | 
        
           |  |  | 5528 | 		writeData.push_back(CyString("		<t id=\"") + (long)(start + 2) + "\">" + this->ConvertTextString(p->GetVersion()) + "</t>");
 | 
        
           |  |  | 5529 | 		writeData.push_back(CyString("		<t id=\"") + (long)(start + 3) + "\">" + this->ConvertTextString(p->GetLanguageName(lang)) + "</t>");
 | 
        
           |  |  | 5530 |   | 
        
           | 14 | cycrow | 5531 | 		CLinkList<SSettingType> *settings = spk->GetSettingsList();
 | 
        
           | 1 | cycrow | 5532 | 		if ( settings && settings->size() )
 | 
        
           |  |  | 5533 | 		{
 | 
        
           |  |  | 5534 | 			writeData.push_back(CyString("		<t id=\"") + (long)(start + 4) + "\">" + (long)settings->size() + "</t>");
 | 
        
           |  |  | 5535 | 			writeData.push_back(CyString("		<t id=\"") + (long)(start + 5) + "\">" + (long)settingStart + "</t>");
 | 
        
           |  |  | 5536 |   | 
        
           | 14 | cycrow | 5537 | 			for ( CListNode<SSettingType> *sNode = settings->Front(); sNode; sNode = sNode->next() )
 | 
        
           | 1 | cycrow | 5538 | 			{
 | 
        
           | 14 | cycrow | 5539 | 				SSettingType *st = sNode->Data();
 | 
        
           | 1 | cycrow | 5540 | 				writeData.push_back(CyString("		<t id=\"") + (long)(settingStart++) + "\">" + st->sKey + "</t>");
 | 
        
           |  |  | 5541 | 				writeData.push_back(CyString("		<t id=\"") + (long)(settingStart++) + "\">" + spk->GetSetting(st) + "</t>");
 | 
        
           |  |  | 5542 | 			}
 | 
        
           |  |  | 5543 | 		}
 | 
        
           |  |  | 5544 | 		else
 | 
        
           |  |  | 5545 | 			writeData.push_back(CyString("		<t id=\"") + (long)(start + 4) + "\">0</t>");
 | 
        
           |  |  | 5546 |   | 
        
           |  |  | 5547 | 		writeData.push_back(CyString("		<t id=\"") + (long)(start + 6) + "\">" + sTextCount + "</t>");
 | 
        
           |  |  | 5548 | 		if ( textCount )
 | 
        
           |  |  | 5549 | 			writeData.push_back(CyString("		<t id=\"") + (long)(start + 7) + "\">" + textEntries + "</t>");
 | 
        
           |  |  | 5550 |   | 
        
           |  |  | 5551 | 		start += 10;
 | 
        
           |  |  | 5552 | 	}
 | 
        
           |  |  | 5553 |   | 
        
           |  |  | 5554 | 	// write ware names
 | 
        
           |  |  | 5555 | 	if ( lWares.size() )
 | 
        
           |  |  | 5556 | 	{
 | 
        
           |  |  | 5557 | 		writeData.push_back(CyString("		<t id=\"5\">") + CyString::Number(start) + "</t>");
 | 
        
           |  |  | 5558 | 		for ( CListNode<SGameWare> *node = lWares.Front(); node; node = node->next() )
 | 
        
           |  |  | 5559 | 		{
 | 
        
           |  |  | 5560 | 			SGameWare *w = node->Data();
 | 
        
           |  |  | 5561 | 			if ( w->pWare && w->iType == WARETYPE_ADDED )
 | 
        
           |  |  | 5562 | 				writeData.push_back(CyString("		<t id=\"") + (long)start + "\">" + w->sWareName + "</t>");
 | 
        
           |  |  | 5563 | 			else
 | 
        
           |  |  | 5564 | 				writeData.push_back(CyString("		<t id=\"") + (long)start + "\">-1</t>");
 | 
        
           |  |  | 5565 | 			writeData.push_back(CyString("		<t id=\"") + (long)(start + 1) + "\">" + CyString((char)w->cType) + "</t>");
 | 
        
           |  |  | 5566 | 			writeData.push_back(CyString("		<t id=\"") + (long)(start + 2) + "\">" + (long)w->iPos + "</t>");
 | 
        
           |  |  | 5567 | 			start += 10;
 | 
        
           |  |  | 5568 | 		}
 | 
        
           |  |  | 5569 | 	}
 | 
        
           |  |  | 5570 |   | 
        
           |  |  | 5571 | 	if ( lShips.size() )
 | 
        
           |  |  | 5572 | 	{
 | 
        
           |  |  | 5573 | 		writeData.push_back(CyString("		<t id=\"7\">") + CyString::Number(start) + "</t>");
 | 
        
           |  |  | 5574 | 		for ( CListNode<SGameShip> *node = lShips.Front(); node; node = node->next() )
 | 
        
           |  |  | 5575 | 		{
 | 
        
           |  |  | 5576 | 			SGameShip *gs = node->Data();
 | 
        
           |  |  | 5577 | 			if ( gs->iType == WARETYPE_NONE )
 | 
        
           |  |  | 5578 | 				continue;
 | 
        
           |  |  | 5579 | 			if ( gs->pPackage && gs->iType == WARETYPE_ADDED )
 | 
        
           |  |  | 5580 | 				writeData.push_back(CyString("		<t id=\"") + (long)start + "\">" + gs->sShipID + "</t>");
 | 
        
           |  |  | 5581 | 			else
 | 
        
           |  |  | 5582 | 				writeData.push_back(CyString("		<t id=\"") + (long)start + "\">-1</t>");
 | 
        
           |  |  | 5583 | 			writeData.push_back(CyString("		<t id=\"") + (long)(start + 1) + "\">" + (long)gs->iPos + "</t>");
 | 
        
           |  |  | 5584 | 			writeData.push_back(CyString("		<t id=\"") + (long)(start + 2) + "\">Ship</t>");
 | 
        
           |  |  | 5585 |   | 
        
           |  |  | 5586 | 			// write shipyard info
 | 
        
           |  |  | 5587 | 			if ( gs->pPackage )
 | 
        
           |  |  | 5588 | 			{
 | 
        
           |  |  | 5589 | 				int doStart = start + 5;
 | 
        
           |  |  | 5590 | 				for ( int i = SHIPYARD_ARGON; i <= SHIPYARD_MAX; i *= 2 )
 | 
        
           |  |  | 5591 | 				{
 | 
        
           |  |  | 5592 | 					writeData.push_back(CyString("		<t id=\"") + (long)(doStart) + "\">" + ((gs->pPackage->IsShipyard(i)) ? CyString::Number(1) : CyString::Number(0)) + "</t>");
 | 
        
           |  |  | 5593 | 					++doStart;
 | 
        
           |  |  | 5594 | 				}
 | 
        
           |  |  | 5595 | 			}
 | 
        
           |  |  | 5596 |   | 
        
           |  |  | 5597 | 			start += 20;
 | 
        
           |  |  | 5598 | 		}
 | 
        
           |  |  | 5599 | 	}
 | 
        
           |  |  | 5600 |   | 
        
           |  |  | 5601 | 	writeData.push_back(CyString("	</page>"));
 | 
        
           |  |  | 5602 |   | 
        
           |  |  | 5603 | 	// wares
 | 
        
           |  |  | 5604 | 	if ( m_iGame == GAME_X3AP || m_iGame == GAME_X3TC || m_iGame == GAME_X3 || lWares.size() || lShips.size() )
 | 
        
           |  |  | 5605 | 	{
 | 
        
           |  |  | 5606 | 		if ( !gameNumber )
 | 
        
           |  |  | 5607 | 			writeData.push_back(CyString("  <page id=\"17\" title=\"Plugin Manager Objects\">"));
 | 
        
           |  |  | 5608 | 		else
 | 
        
           |  |  | 5609 | 			writeData.push_back(CyString("  <page id=\"") + (long)gameNumber + "0017\" title=\"Plugin Manager Objects\">");
 | 
        
           |  |  | 5610 |   | 
        
           |  |  | 5611 | 		writeData.push_back(CyString("		<t id=\"") + (long)(SHIPSTARTTEXT - 1) + "\">ZZ_BLANKSHIP</t>");
 | 
        
           |  |  | 5612 | 		// do emp
 | 
        
           |  |  | 5613 | 		if ( m_iGame == GAME_X3TC || m_iGame == GAME_X3 || m_iGame == GAME_X3AP )
 | 
        
           |  |  | 5614 | 			writeData.push_back(GetEMPText());
 | 
        
           |  |  | 5615 |   | 
        
           |  |  | 5616 | 		// object names
 | 
        
           |  |  | 5617 | 		for ( CListNode<SGameWare> *node = lWares.Front(); node; node = node->next() )
 | 
        
           |  |  | 5618 | 		{
 | 
        
           |  |  | 5619 | 			SGameWare *w = node->Data();
 | 
        
           |  |  | 5620 | 			if ( !w->pWare || w->iType != WARETYPE_ADDED )
 | 
        
           |  |  | 5621 | 				continue;
 | 
        
           |  |  | 5622 |   | 
        
           |  |  | 5623 | 			// find the correct text for the language
 | 
        
           |  |  | 5624 | 			CyString name = CSpkFile::GetWareText(w->pWare, m_iLanguage);
 | 
        
           |  |  | 5625 | 			CyString desc = CSpkFile::GetWareDesc(w->pWare, m_iLanguage);
 | 
        
           |  |  | 5626 | 			if ( !name.Empty() )
 | 
        
           |  |  | 5627 | 				writeData.push_back(CyString("		<t id=\"") + (long)(w->iText + 3) + "\">" + name + "</t>");
 | 
        
           |  |  | 5628 | 			if ( !desc.Empty() )
 | 
        
           |  |  | 5629 | 				writeData.push_back(CyString("		<t id=\"") + (long)(w->iText + 4) + "\">" + desc + "</t>");
 | 
        
           |  |  | 5630 | 		}
 | 
        
           |  |  | 5631 | 		for ( CListNode<SGameShip> *node = m_lGameShips.Front(); node; node = node->next() )
 | 
        
           |  |  | 5632 | 		{
 | 
        
           |  |  | 5633 | 			SGameShip *s = node->Data();
 | 
        
           |  |  | 5634 | 			if ( !s->pPackage || s->iType != WARETYPE_ADDED )
 | 
        
           |  |  | 5635 | 				continue;
 | 
        
           |  |  | 5636 | 			if ( s->pPackage->GetOriginalDescription() )
 | 
        
           |  |  | 5637 | 				continue;
 | 
        
           |  |  | 5638 |   | 
        
           |  |  | 5639 | 			CyString name = s->pPackage->GetTextName(m_iLanguage);
 | 
        
           |  |  | 5640 | 			CyString desc = s->pPackage->GetTextDescription(m_iLanguage);
 | 
        
           |  |  | 5641 | 			if ( !name.Empty() )
 | 
        
           |  |  | 5642 | 				writeData.push_back(CyString("		<t id=\"") + (long)s->iText + "\">" + name + "</t>");
 | 
        
           |  |  | 5643 | 			if ( !desc.Empty() )
 | 
        
           |  |  | 5644 | 				writeData.push_back(CyString("		<t id=\"") + (long)(s->iText + 1) + "\">" + desc + "</t>");
 | 
        
           |  |  | 5645 | 		}
 | 
        
           |  |  | 5646 | 		writeData.push_back(CyString("  </page>"));
 | 
        
           |  |  | 5647 | 	}
 | 
        
           |  |  | 5648 | 	writeData.push_back(CyString("</language>"));
 | 
        
           |  |  | 5649 | 	textFile.WriteFileUTF(&writeData);
 | 
        
           |  |  | 5650 |   | 
        
           |  |  | 5651 | 	size_t fileSize;
 | 
        
           |  |  | 5652 | 	char *fileData = CFileIO(textFile.GetFullFilename()).ReadToData(&fileSize);
 | 
        
           |  |  | 5653 |   | 
        
           |  |  | 5654 | 	if ( fileData && fileSize)
 | 
        
           |  |  | 5655 | 	{
 | 
        
           |  |  | 5656 | 		size_t newFileSize;
 | 
        
           |  |  | 5657 | 		unsigned char *pckData = PCKData((unsigned char *)fileData, fileSize, &newFileSize, true);
 | 
        
           |  |  | 5658 | 		if ( pckData )
 | 
        
           |  |  | 5659 | 		{
 | 
        
           |  |  | 5660 | 			CFileIO pckFile(m_sCurrentDir + "/t/" + filename + ".pck");
 | 
        
           |  |  | 5661 | 			pckFile.WriteData((char *)pckData, newFileSize);
 | 
        
           |  |  | 5662 | 			this->AddCreatedFile(pckFile.GetFullFilename());
 | 
        
           |  |  | 5663 | 		}
 | 
        
           |  |  | 5664 | 	}
 | 
        
           |  |  | 5665 | 	textFile.Remove();
 | 
        
           |  |  | 5666 | }
 | 
        
           |  |  | 5667 |   | 
        
           |  |  | 5668 | bool CPackages::IsCurrentDir(CyString dir)
 | 
        
           |  |  | 5669 | {
 | 
        
           |  |  | 5670 | 	if ( dir.Compare(m_sCurrentDir) )
 | 
        
           |  |  | 5671 | 		return true;
 | 
        
           |  |  | 5672 |   | 
        
           |  |  | 5673 | 	CyString checkDir = m_sCurrentDir;
 | 
        
           |  |  | 5674 | 	checkDir = checkDir.FindReplace("/", "\\");
 | 
        
           |  |  | 5675 | 	if ( checkDir.Compare(dir) )
 | 
        
           |  |  | 5676 | 		return true;
 | 
        
           |  |  | 5677 |   | 
        
           |  |  | 5678 | 	checkDir = checkDir.FindReplace("\\", "/");
 | 
        
           |  |  | 5679 | 	if ( checkDir.Compare(dir) )
 | 
        
           |  |  | 5680 | 		return true;
 | 
        
           |  |  | 5681 |   | 
        
           |  |  | 5682 | 	return false;
 | 
        
           |  |  | 5683 | }
 | 
        
           |  |  | 5684 |   | 
        
           |  |  | 5685 | void CPackages::BackupSaves(bool vanilla)
 | 
        
           |  |  | 5686 | {
 | 
        
           |  |  | 5687 | 	// copy any saves into the vanilla directory
 | 
        
           |  |  | 5688 | 	CyString dir = (vanilla) ? "Vanilla" : "Modified";
 | 
        
           |  |  | 5689 |   | 
        
           |  |  | 5690 | 	// make sure the directory exists
 | 
        
           |  |  | 5691 | 	CDirIO saveDir(this->GetSaveDirectory());
 | 
        
           |  |  | 5692 | 	CDirIO gameSaveDir(m_sCurrentDir);
 | 
        
           |  |  | 5693 | 	if ( !gameSaveDir.Exists("PluginManager") )
 | 
        
           |  |  | 5694 | 		gameSaveDir.Create("PluginManager");
 | 
        
           |  |  | 5695 | 	gameSaveDir.cd("PluginManager");
 | 
        
           |  |  | 5696 | 	if ( !gameSaveDir.Exists("Saves") )
 | 
        
           |  |  | 5697 | 		gameSaveDir.Create("Saves");
 | 
        
           |  |  | 5698 | 	gameSaveDir.cd("Saves");
 | 
        
           |  |  | 5699 | 	if ( !gameSaveDir.Exists(dir) )
 | 
        
           |  |  | 5700 | 		gameSaveDir.Create(dir);
 | 
        
           |  |  | 5701 | 	gameSaveDir.cd(dir);
 | 
        
           |  |  | 5702 |   | 
        
           |  |  | 5703 | 	// backup the saves
 | 
        
           |  |  | 5704 | 	CyStringList *dirs = saveDir.DirList();
 | 
        
           |  |  | 5705 | 	if ( dirs )
 | 
        
           |  |  | 5706 | 	{
 | 
        
           |  |  | 5707 | 		for ( SStringList *node = dirs->Head(); node; node = node->next )
 | 
        
           |  |  | 5708 | 		{
 | 
        
           |  |  | 5709 | 			CFileIO File(saveDir.File(node->str));
 | 
        
           |  |  | 5710 | 			if ( !File.CheckFileExtension("sav") )
 | 
        
           |  |  | 5711 | 				continue;
 | 
        
           |  |  | 5712 | 			// remove the file if already exists
 | 
        
           |  |  | 5713 | 			if ( gameSaveDir.Exists(node->str) )
 | 
        
           |  |  | 5714 | 				CFileIO(gameSaveDir.File(node->str)).Remove();
 | 
        
           |  |  | 5715 |   | 
        
           |  |  | 5716 | 			// copy the file into the games save dir for backup
 | 
        
           |  |  | 5717 | 			File.Copy(gameSaveDir.File(File.GetFilename()), true);
 | 
        
           |  |  | 5718 | 		}
 | 
        
           |  |  | 5719 |   | 
        
           |  |  | 5720 | 		delete dirs;
 | 
        
           |  |  | 5721 | 	}
 | 
        
           |  |  | 5722 |   | 
        
           |  |  | 5723 | }
 | 
        
           |  |  | 5724 |   | 
        
           |  |  | 5725 | void CPackages::RestoreSaves(bool vanilla)
 | 
        
           |  |  | 5726 | {
 | 
        
           |  |  | 5727 | 	// get dir to restore from
 | 
        
           |  |  | 5728 | 	CyString dir = (vanilla) ? "Vanilla" : "Modified";
 | 
        
           |  |  | 5729 | 	CDirIO restoreDir(m_sCurrentDir + "/PluginManager/Saves/" + dir);
 | 
        
           |  |  | 5730 | 	CDirIO toDir(this->GetSaveDirectory());
 | 
        
           |  |  | 5731 |   | 
        
           |  |  | 5732 | 	CyStringList *dirs = restoreDir.DirList();
 | 
        
           |  |  | 5733 | 	if ( dirs )
 | 
        
           |  |  | 5734 | 	{
 | 
        
           |  |  | 5735 | 		for ( SStringList *node = dirs->Head(); node; node = node->next )
 | 
        
           |  |  | 5736 | 		{
 | 
        
           |  |  | 5737 | 			CFileIO File(restoreDir.File(node->str));
 | 
        
           |  |  | 5738 | 			// remove the file if already exists
 | 
        
           |  |  | 5739 | 			if ( toDir.Exists(node->str) )
 | 
        
           |  |  | 5740 | 				CFileIO(toDir.File(node->str)).Remove();
 | 
        
           |  |  | 5741 |   | 
        
           |  |  | 5742 | 			// move file over
 | 
        
           |  |  | 5743 | 			File.Copy(toDir.File(node->str), true);
 | 
        
           |  |  | 5744 | 		}
 | 
        
           |  |  | 5745 |   | 
        
           |  |  | 5746 | 		delete dirs;
 | 
        
           |  |  | 5747 | 	}
 | 
        
           |  |  | 5748 |   | 
        
           |  |  | 5749 | }
 | 
        
           |  |  | 5750 |   | 
        
           |  |  | 5751 | bool CPackages::RemoveCurrentDirectory()
 | 
        
           |  |  | 5752 | {
 | 
        
           |  |  | 5753 | 	if ( !m_bLoaded )
 | 
        
           |  |  | 5754 | 		return false;
 | 
        
           |  |  | 5755 |   | 
        
           |  |  | 5756 | 	// remove all package files
 | 
        
           |  |  | 5757 | 	this->RemoveAllPackages();
 | 
        
           |  |  | 5758 |   | 
        
           |  |  | 5759 | 	// remove all plugin manager files
 | 
        
           |  |  | 5760 | 	this->RemoveCreatedFiles();
 | 
        
           |  |  | 5761 |   | 
        
           |  |  | 5762 | 	// restore any vanilla saves
 | 
        
           |  |  | 5763 | 	/*
 | 
        
           |  |  | 5764 | 	if ( !m_bVanilla )
 | 
        
           |  |  | 5765 | 	{
 | 
        
           |  |  | 5766 | 		this->BackupSaves();
 | 
        
           |  |  | 5767 | 		m_bVanilla = true;
 | 
        
           |  |  | 5768 | 		this->RestoreSaves();
 | 
        
           |  |  | 5769 | 	}*/
 | 
        
           |  |  | 5770 |   | 
        
           |  |  | 5771 | 	this->Reset();
 | 
        
           |  |  | 5772 | 	m_bLoaded = false;
 | 
        
           |  |  | 5773 |   | 
        
           |  |  | 5774 | 	// clear the plugin manager directory
 | 
        
           |  |  | 5775 | 	CDirIO Dir(m_sCurrentDir);
 | 
        
           |  |  | 5776 | 	Dir.RemoveDir("PluginManager", true, true, 0);
 | 
        
           |  |  | 5777 | 	Dir.RemoveDir("dds", false, true, 0);
 | 
        
           |  |  | 5778 | 	Dir.RemoveDir("objects", false, true, 0);
 | 
        
           |  |  | 5779 | 	Dir.RemoveDir("types", false, true, 0);
 | 
        
           |  |  | 5780 | 	Dir.RemoveDir("textures", false, true, 0);
 | 
        
           |  |  | 5781 |   | 
        
           |  |  | 5782 | 	// remove the plugin manager mod files
 | 
        
           |  |  | 5783 | 	if ( Dir.Exists("mods/PluginManager.cat") )
 | 
        
           |  |  | 5784 | 		CFileIO(Dir.File("mods/PluginManager.cat")).Remove();
 | 
        
           |  |  | 5785 | 	if ( Dir.Exists("mods/PluginManager.dat") )
 | 
        
           |  |  | 5786 | 		CFileIO(Dir.File("mods/PluginManager.dat")).Remove();
 | 
        
           |  |  | 5787 |   | 
        
           |  |  | 5788 | 	return true;
 | 
        
           |  |  | 5789 | }
 | 
        
           |  |  | 5790 |   | 
        
           |  |  | 5791 | void CPackages::CreateDummies()
 | 
        
           |  |  | 5792 | {
 | 
        
           |  |  | 5793 | 	// first check we have any ships
 | 
        
           |  |  | 5794 | 	if ( m_lGameShips.empty() || !this->CountPackages(TYPE_XSP, true) )
 | 
        
           |  |  | 5795 | 		return;
 | 
        
           |  |  | 5796 |   | 
        
           |  |  | 5797 | 	CLinkList<SDummyEntry> dummyList;
 | 
        
           |  |  | 5798 |   | 
        
           |  |  | 5799 | 	// now extract the existing dummies
 | 
        
           |  |  | 5800 | 	int e = ExtractGameFile("types/Dummies.pck", m_sTempDir + "/Dummies.txt");
 | 
        
           |  |  | 5801 | 	if ( e )
 | 
        
           |  |  | 5802 | 	{
 | 
        
           |  |  | 5803 | 		// read the dummies
 | 
        
           |  |  | 5804 | 		CFileIO File;
 | 
        
           |  |  | 5805 | 		if ( File.Open((e == -1) ? "Dummies.txt" : m_sTempDir + "/Dummies.txt") )
 | 
        
           |  |  | 5806 | 		{
 | 
        
           |  |  | 5807 | 			std::vector<CyString> *lines = File.ReadLines();
 | 
        
           |  |  | 5808 | 			if ( lines )
 | 
        
           |  |  | 5809 | 			{
 | 
        
           |  |  | 5810 | 				int insection = 0;
 | 
        
           |  |  | 5811 | 				SDummyEntry *currentSection = NULL;
 | 
        
           |  |  | 5812 | 				for ( int j = 0; j < (int)lines->size(); j++ )
 | 
        
           |  |  | 5813 | 				{
 | 
        
           |  |  | 5814 | 					CyString line(lines->at(j));
 | 
        
           |  |  | 5815 | 					line.RemoveChar(9);
 | 
        
           |  |  | 5816 | 					line.RemoveChar('\r');
 | 
        
           |  |  | 5817 | 					line.RemoveFirstSpace();
 | 
        
           |  |  | 5818 | 					if ( line.Empty() )
 | 
        
           |  |  | 5819 | 						continue;
 | 
        
           |  |  | 5820 | 					if ( line[0] == '/' )
 | 
        
           |  |  | 5821 | 						continue;
 | 
        
           |  |  | 5822 |   | 
        
           |  |  | 5823 | 					// read the section, first entry is section, second is size
 | 
        
           |  |  | 5824 | 					while ( !line.Empty() )
 | 
        
           |  |  | 5825 | 					{
 | 
        
           |  |  | 5826 | 						if ( !insection )
 | 
        
           |  |  | 5827 | 						{
 | 
        
           |  |  | 5828 | 							CyString section = line.GetToken(";", 1, 1);
 | 
        
           |  |  | 5829 | 							insection = line.GetToken(";", 2, 2).ToInt();
 | 
        
           |  |  | 5830 |   | 
        
           |  |  | 5831 | 							// search for the sections
 | 
        
           |  |  | 5832 | 							currentSection = NULL;
 | 
        
           |  |  | 5833 | 							for ( CListNode<SDummyEntry> *node = dummyList.Front(); node; node = node->next() )
 | 
        
           |  |  | 5834 | 							{
 | 
        
           |  |  | 5835 | 								SDummyEntry *d = node->Data();
 | 
        
           |  |  | 5836 | 								if ( d->sSection.Compare(section) )
 | 
        
           |  |  | 5837 | 								{
 | 
        
           |  |  | 5838 | 									currentSection = node->Data();
 | 
        
           |  |  | 5839 | 									break;
 | 
        
           |  |  | 5840 | 								}
 | 
        
           |  |  | 5841 | 							}
 | 
        
           |  |  | 5842 |   | 
        
           |  |  | 5843 | 							if ( !currentSection )
 | 
        
           |  |  | 5844 | 							{
 | 
        
           |  |  | 5845 | 								currentSection = new struct SDummyEntry;
 | 
        
           |  |  | 5846 | 								currentSection->sSection = section;
 | 
        
           |  |  | 5847 | 								dummyList.push_back(currentSection);
 | 
        
           |  |  | 5848 | 							}
 | 
        
           |  |  | 5849 |   | 
        
           |  |  | 5850 | 							// we have some more ?
 | 
        
           |  |  | 5851 | 							line = line.DelToken(";", 1, 2);
 | 
        
           |  |  | 5852 | 						}
 | 
        
           |  |  | 5853 | 						else
 | 
        
           |  |  | 5854 | 						{
 | 
        
           |  |  | 5855 | 							--insection;
 | 
        
           |  |  | 5856 | 							// check the last entry for number of states
 | 
        
           |  |  | 5857 | 							if ( currentSection->sSection.Compare("SDTYPE_GUN") )
 | 
        
           |  |  | 5858 | 							{
 | 
        
           |  |  | 5859 | 								int states = line.GetToken(";", 3, 3).ToInt();
 | 
        
           |  |  | 5860 | 								int parts = line.GetToken(";", 4 + (states * 2), 4 + (states * 2)).ToInt();
 | 
        
           |  |  | 5861 | 								CyString data = line.GetToken(";", 1, 4 + (states * 2) + (parts * 2)) + ";";
 | 
        
           |  |  | 5862 | 								currentSection->lEntries.PushBack(data);
 | 
        
           |  |  | 5863 |   | 
        
           |  |  | 5864 | 								// remove done
 | 
        
           |  |  | 5865 | 								line = line.DelToken(";", 1, 4 + (states * 2) + (parts * 2));
 | 
        
           |  |  | 5866 | 							}
 | 
        
           |  |  | 5867 | 							else
 | 
        
           |  |  | 5868 | 							{
 | 
        
           |  |  | 5869 | 								int states = line.GetToken(";", 3, 3).ToInt();
 | 
        
           |  |  | 5870 | 								CyString data = line.GetToken(";", 1, 3 + (states * 2)) + ";";
 | 
        
           |  |  | 5871 | 								currentSection->lEntries.PushBack(data);
 | 
        
           |  |  | 5872 |   | 
        
           |  |  | 5873 | 								// remove done
 | 
        
           |  |  | 5874 | 								line = line.DelToken(";", 1, 3 + (states * 2));
 | 
        
           |  |  | 5875 | 							}
 | 
        
           |  |  | 5876 | 						}
 | 
        
           |  |  | 5877 | 					}
 | 
        
           |  |  | 5878 | 				}
 | 
        
           |  |  | 5879 |   | 
        
           |  |  | 5880 | 				delete lines;
 | 
        
           |  |  | 5881 | 			}
 | 
        
           |  |  | 5882 |   | 
        
           |  |  | 5883 | 			File.Remove();
 | 
        
           |  |  | 5884 | 		}
 | 
        
           |  |  | 5885 |   | 
        
           |  |  | 5886 | 		// add the new entries for the ships
 | 
        
           |  |  | 5887 | 		for ( CListNode<SGameShip> *node = m_lGameShips.Front(); node; node = node->next() )
 | 
        
           |  |  | 5888 | 		{
 | 
        
           |  |  | 5889 | 			SGameShip *s = node->Data();
 | 
        
           |  |  | 5890 | 			if ( s->iType != WARETYPE_ADDED || !s->pPackage )
 | 
        
           |  |  | 5891 | 				continue;
 | 
        
           |  |  | 5892 |   | 
        
           |  |  | 5893 | 			// no dummies to add?
 | 
        
           |  |  | 5894 | 			if ( !s->pPackage->AnyDummies() )
 | 
        
           |  |  | 5895 | 				continue;
 | 
        
           |  |  | 5896 |   | 
        
           |  |  | 5897 | 			// add each dummy to list
 | 
        
           |  |  | 5898 | 			for ( CListNode<SDummy> *dNode = s->pPackage->GetDummies()->Front(); dNode; dNode = dNode->next() )
 | 
        
           |  |  | 5899 | 			{
 | 
        
           |  |  | 5900 | 				SDummy *dummy = dNode->Data();
 | 
        
           |  |  | 5901 | 				SDummyEntry *found = NULL;
 | 
        
           |  |  | 5902 | 				for ( CListNode<SDummyEntry> *eNode = dummyList.Front(); eNode; eNode = eNode->next() )
 | 
        
           |  |  | 5903 | 				{
 | 
        
           |  |  | 5904 | 					if ( eNode->Data()->sSection.Compare(dummy->sSection) )
 | 
        
           |  |  | 5905 | 					{
 | 
        
           |  |  | 5906 | 						found = eNode->Data();
 | 
        
           |  |  | 5907 | 						break;
 | 
        
           |  |  | 5908 | 					}
 | 
        
           |  |  | 5909 | 				}
 | 
        
           |  |  | 5910 | 				if ( !found )
 | 
        
           |  |  | 5911 | 				{
 | 
        
           |  |  | 5912 | 					found = new SDummyEntry;
 | 
        
           |  |  | 5913 | 					found->sSection = dummy->sSection;
 | 
        
           |  |  | 5914 | 					dummyList.push_back(found);
 | 
        
           |  |  | 5915 | 				}
 | 
        
           |  |  | 5916 | 				// check if its already on the list
 | 
        
           |  |  | 5917 | 				else
 | 
        
           |  |  | 5918 | 				{
 | 
        
           |  |  | 5919 | 					bool f = false;
 | 
        
           |  |  | 5920 | 					for ( SStringList *strNode = found->lEntries.Head(); strNode; strNode = strNode->next )
 | 
        
           |  |  | 5921 | 					{
 | 
        
           |  |  | 5922 | 						if ( strNode->str.GetToken(";", 1, 1).Compare(dummy->sData.GetToken(";", 1, 1)) )
 | 
        
           |  |  | 5923 | 						{
 | 
        
           |  |  | 5924 | 							f = true;
 | 
        
           |  |  | 5925 | 							break;
 | 
        
           |  |  | 5926 | 						}
 | 
        
           |  |  | 5927 | 					}
 | 
        
           |  |  | 5928 |   | 
        
           |  |  | 5929 | 					if ( f )
 | 
        
           |  |  | 5930 | 						continue;
 | 
        
           |  |  | 5931 | 				}
 | 
        
           |  |  | 5932 |   | 
        
           |  |  | 5933 | 				found->lEntries.PushBack(dummy->sData);
 | 
        
           |  |  | 5934 | 			}
 | 
        
           |  |  | 5935 | 		}
 | 
        
           |  |  | 5936 |   | 
        
           |  |  | 5937 | 		// finally, write the file
 | 
        
           |  |  | 5938 | 		std::vector<CyString> lines;
 | 
        
           |  |  | 5939 | 		lines.push_back(CyString("// Dummies file, created by SPK Libraries V") + CyString::CreateFromFloat(GetLibraryVersion(), 2));
 | 
        
           |  |  | 5940 | 		for ( SDummyEntry *dummy = dummyList.First(); dummy; dummy = dummyList.Next() )
 | 
        
           |  |  | 5941 | 		{
 | 
        
           |  |  | 5942 | 			lines.push_back("");
 | 
        
           |  |  | 5943 | 			lines.push_back(CyString("// Section: ") + dummy->sSection + " Entries: " + (long)dummy->lEntries.Count());
 | 
        
           |  |  | 5944 | 			lines.push_back(dummy->sSection + ";" + CyString::Number(dummy->lEntries.Count()) + ";");
 | 
        
           |  |  | 5945 | 			for ( SStringList *str = dummy->lEntries.Head(); str; str = str->next )
 | 
        
           |  |  | 5946 | 			{
 | 
        
           |  |  | 5947 | 				CyString strLine = str->str;
 | 
        
           |  |  | 5948 | 				strLine.RemoveChar(9);
 | 
        
           |  |  | 5949 | 				strLine.RemoveChar('\r');
 | 
        
           |  |  | 5950 | 				strLine.RemoveEndSpace();
 | 
        
           |  |  | 5951 | 				strLine.RemoveFirstSpace();
 | 
        
           |  |  | 5952 | 				strLine = strLine.FindReplace("<::PiPe::>", "|");
 | 
        
           |  |  | 5953 | 				if ( strLine.Right(1) != ";" )
 | 
        
           |  |  | 5954 | 					strLine += ";";
 | 
        
           |  |  | 5955 | 				lines.push_back(strLine);
 | 
        
           |  |  | 5956 | 			}
 | 
        
           |  |  | 5957 | 		}
 | 
        
           |  |  | 5958 | 		lines.push_back("");
 | 
        
           |  |  | 5959 |   | 
        
           |  |  | 5960 | 		// write the file to disk
 | 
        
           |  |  | 5961 | 		CFileIO WriteFile(m_sTempDir + "/dummies.txt");
 | 
        
           |  |  | 5962 | 		if ( WriteFile.WriteFile(&lines) )
 | 
        
           |  |  | 5963 | 		{
 | 
        
           |  |  | 5964 | 			this->PackFile(&WriteFile, "types\\dummies.pck");
 | 
        
           |  |  | 5965 | 			WriteFile.Remove();
 | 
        
           |  |  | 5966 | 		}
 | 
        
           |  |  | 5967 | 	}
 | 
        
           |  |  | 5968 | }
 | 
        
           |  |  | 5969 |   | 
        
           |  |  | 5970 | void CPackages::CreateCutData()
 | 
        
           |  |  | 5971 | {
 | 
        
           |  |  | 5972 | 	// first check we have any ships
 | 
        
           |  |  | 5973 | 	if ( m_lGameShips.empty() || !this->CountPackages(TYPE_XSP, true) )
 | 
        
           |  |  | 5974 | 		return;
 | 
        
           |  |  | 5975 |   | 
        
           |  |  | 5976 | 	bool found = false;
 | 
        
           |  |  | 5977 | 	for ( CListNode<SGameShip> *node = m_lGameShips.Front(); node; node = node->next() )
 | 
        
           |  |  | 5978 | 	{
 | 
        
           |  |  | 5979 | 		SGameShip *s = node->Data();
 | 
        
           |  |  | 5980 | 		if ( s->iType != WARETYPE_ADDED || !s->pPackage )
 | 
        
           |  |  | 5981 | 			continue;
 | 
        
           |  |  | 5982 |   | 
        
           |  |  | 5983 | 		// no dummies to add?
 | 
        
           |  |  | 5984 | 		if ( !s->pPackage->AnyCutData() )
 | 
        
           |  |  | 5985 | 			continue;
 | 
        
           |  |  | 5986 | 		found = true;
 | 
        
           |  |  | 5987 | 		break;
 | 
        
           |  |  | 5988 | 	}
 | 
        
           |  |  | 5989 |   | 
        
           |  |  | 5990 | 	if ( !found )
 | 
        
           |  |  | 5991 | 		return;
 | 
        
           |  |  | 5992 |   | 
        
           |  |  | 5993 | 	CyStringList cutList;
 | 
        
           |  |  | 5994 | 	int e = ExtractGameFile("types/CutData.pck", m_sTempDir + "/CutData.txt");
 | 
        
           |  |  | 5995 | 	if ( e )
 | 
        
           |  |  | 5996 | 	{
 | 
        
           |  |  | 5997 | 		CFileIO File;
 | 
        
           |  |  | 5998 | 		if ( File.Open((e == -1) ? "CutData.txt" : m_sTempDir + "/CutData.txt") )
 | 
        
           |  |  | 5999 | 		{
 | 
        
           |  |  | 6000 | 			std::vector<CyString> *lines = File.ReadLines();
 | 
        
           |  |  | 6001 | 			if ( lines )
 | 
        
           |  |  | 6002 | 			{
 | 
        
           |  |  | 6003 | 				int entries = -1;
 | 
        
           |  |  | 6004 | 				for ( int j = 0; j < (int)lines->size(); j++ )
 | 
        
           |  |  | 6005 | 				{
 | 
        
           |  |  | 6006 | 					CyString line(lines->at(j));
 | 
        
           |  |  | 6007 | 					line.RemoveChar(9);
 | 
        
           |  |  | 6008 | 					line.RemoveChar('\r');
 | 
        
           |  |  | 6009 | 					line.RemoveChar(' ');
 | 
        
           |  |  | 6010 | 					if ( line.Empty() || line[0] == '/' )
 | 
        
           |  |  | 6011 | 						continue;
 | 
        
           |  |  | 6012 | 					if ( entries == -1 )
 | 
        
           |  |  | 6013 | 						entries = line.GetToken(";", 1, 1).ToInt();
 | 
        
           |  |  | 6014 | 					else
 | 
        
           |  |  | 6015 | 					{
 | 
        
           |  |  | 6016 | 						if ( line.Right(1) != ";" )
 | 
        
           |  |  | 6017 | 							line += ";";
 | 
        
           |  |  | 6018 | 						cutList.PushBack(line);
 | 
        
           |  |  | 6019 | 						if ( cutList.Count() == entries )
 | 
        
           |  |  | 6020 | 							break;
 | 
        
           |  |  | 6021 | 					}
 | 
        
           |  |  | 6022 | 				}
 | 
        
           |  |  | 6023 |   | 
        
           |  |  | 6024 | 				delete lines;
 | 
        
           |  |  | 6025 | 			}
 | 
        
           |  |  | 6026 |   | 
        
           |  |  | 6027 | 			File.Remove();
 | 
        
           |  |  | 6028 | 		}
 | 
        
           |  |  | 6029 | 	}
 | 
        
           |  |  | 6030 |   | 
        
           |  |  | 6031 | 	for ( CListNode<SGameShip> *node = m_lGameShips.Front(); node; node = node->next() )
 | 
        
           |  |  | 6032 | 	{
 | 
        
           |  |  | 6033 | 		SGameShip *s = node->Data();
 | 
        
           |  |  | 6034 | 		if ( s->iType != WARETYPE_ADDED || !s->pPackage )
 | 
        
           |  |  | 6035 | 			continue;
 | 
        
           |  |  | 6036 |   | 
        
           |  |  | 6037 | 		// no dummies to add?
 | 
        
           |  |  | 6038 | 		if ( !s->pPackage->AnyCutData() )
 | 
        
           |  |  | 6039 | 			continue;
 | 
        
           |  |  | 6040 |   | 
        
           |  |  | 6041 | 		// add each dummy to list
 | 
        
           |  |  | 6042 | 		for ( SStringList *strNode = s->pPackage->GetCutData()->Head(); strNode; strNode = strNode->next )
 | 
        
           |  |  | 6043 | 		{
 | 
        
           |  |  | 6044 | 			CyString str = strNode->str;
 | 
        
           |  |  | 6045 | 			str.RemoveChar(' ');
 | 
        
           |  |  | 6046 | 			if ( str.Right(1) != ";" )
 | 
        
           |  |  | 6047 | 				str += ";";
 | 
        
           |  |  | 6048 | 			cutList.PushBack(str, true);
 | 
        
           |  |  | 6049 | 		}
 | 
        
           |  |  | 6050 | 	}
 | 
        
           |  |  | 6051 |   | 
        
           |  |  | 6052 | 	cutList.PushFront(CyString::Number(cutList.Count()) + ";");
 | 
        
           |  |  | 6053 | 	cutList.PushFront("/cut id;filename (leave blank to use id)");
 | 
        
           |  |  | 6054 | 	cutList.PushFront(CyString("// Cut Data file, created by SPK Libraries V") + CyString::CreateFromFloat(GetLibraryVersion(), 2));
 | 
        
           |  |  | 6055 |   | 
        
           |  |  | 6056 | 	// write the file to disk
 | 
        
           |  |  | 6057 | 	CFileIO WriteFile(m_sTempDir + "/CutData.txt");
 | 
        
           |  |  | 6058 | 	if ( WriteFile.WriteFile(&cutList) )
 | 
        
           |  |  | 6059 | 	{
 | 
        
           |  |  | 6060 | 		this->PackFile(&WriteFile, "types\\CutData.pck");
 | 
        
           |  |  | 6061 | 		WriteFile.Remove();
 | 
        
           |  |  | 6062 | 	}
 | 
        
           |  |  | 6063 | }
 | 
        
           |  |  | 6064 |   | 
        
           |  |  | 6065 | void CPackages::CreateAnimations()
 | 
        
           |  |  | 6066 | {
 | 
        
           |  |  | 6067 | 	// first check we have any ships
 | 
        
           |  |  | 6068 | 	if ( m_lGameShips.empty() || !this->CountPackages(TYPE_XSP, true) )
 | 
        
           |  |  | 6069 | 		return;
 | 
        
           |  |  | 6070 |   | 
        
           |  |  | 6071 | 	bool found = false;
 | 
        
           |  |  | 6072 | 	for ( CListNode<SGameShip> *node = m_lGameShips.Front(); node; node = node->next() )
 | 
        
           |  |  | 6073 | 	{
 | 
        
           |  |  | 6074 | 		SGameShip *s = node->Data();
 | 
        
           |  |  | 6075 | 		if ( s->iType != WARETYPE_ADDED || !s->pPackage )
 | 
        
           |  |  | 6076 | 			continue;
 | 
        
           |  |  | 6077 |   | 
        
           |  |  | 6078 | 		// no dummies to add?
 | 
        
           |  |  | 6079 | 		if ( !s->pPackage->AnyAnimations() )
 | 
        
           |  |  | 6080 | 			continue;
 | 
        
           |  |  | 6081 | 		found = true;
 | 
        
           |  |  | 6082 | 		break;
 | 
        
           |  |  | 6083 | 	}
 | 
        
           |  |  | 6084 |   | 
        
           |  |  | 6085 | 	if ( !found )
 | 
        
           |  |  | 6086 | 		return;
 | 
        
           |  |  | 6087 |   | 
        
           |  |  | 6088 | 	CyStringList aniList;
 | 
        
           |  |  | 6089 | 	int e = ExtractGameFile("types/Animations.pck", m_sTempDir + "/Animations.txt");
 | 
        
           |  |  | 6090 | 	if ( e )
 | 
        
           |  |  | 6091 | 	{
 | 
        
           |  |  | 6092 | 		CFileIO File;
 | 
        
           |  |  | 6093 | 		if ( File.Open((e == -1) ? "Animations.txt" : m_sTempDir + "/Animations.txt") )
 | 
        
           |  |  | 6094 | 		{
 | 
        
           |  |  | 6095 | 			std::vector<CyString> *lines = File.ReadLines();
 | 
        
           |  |  | 6096 | 			if ( lines )
 | 
        
           |  |  | 6097 | 			{
 | 
        
           |  |  | 6098 | 				for ( int j = 0; j < (int)lines->size(); j++ )
 | 
        
           |  |  | 6099 | 				{
 | 
        
           |  |  | 6100 | 					CyString line(lines->at(j));
 | 
        
           |  |  | 6101 | 					aniList.PushBack(line);
 | 
        
           |  |  | 6102 | 				}
 | 
        
           |  |  | 6103 |   | 
        
           |  |  | 6104 | 				delete lines;
 | 
        
           |  |  | 6105 | 			}
 | 
        
           |  |  | 6106 |   | 
        
           |  |  | 6107 | 			File.Remove();
 | 
        
           |  |  | 6108 | 		}
 | 
        
           |  |  | 6109 | 	}
 | 
        
           |  |  | 6110 |   | 
        
           |  |  | 6111 | 	CyStringList parsedAniList;
 | 
        
           |  |  | 6112 | 	CXspFile::ReadAnimations(&aniList, &parsedAniList, 0);
 | 
        
           |  |  | 6113 |   | 
        
           |  |  | 6114 | 	for ( CListNode<SGameShip> *node = m_lGameShips.Front(); node; node = node->next() )
 | 
        
           |  |  | 6115 | 	{
 | 
        
           |  |  | 6116 | 		SGameShip *s = node->Data();
 | 
        
           |  |  | 6117 | 		if ( s->iType != WARETYPE_ADDED || !s->pPackage )
 | 
        
           |  |  | 6118 | 			continue;
 | 
        
           |  |  | 6119 |   | 
        
           |  |  | 6120 | 		// no dummies to add?
 | 
        
           |  |  | 6121 | 		if ( !s->pPackage->AnyAnimations() )
 | 
        
           |  |  | 6122 | 			continue;
 | 
        
           |  |  | 6123 |   | 
        
           |  |  | 6124 | 		// add each dummy to list
 | 
        
           |  |  | 6125 | 		for ( SStringList *strNode = s->pPackage->GetAnimations()->Head(); strNode; strNode = strNode->next )
 | 
        
           |  |  | 6126 | 			parsedAniList.PushBack(strNode->str);
 | 
        
           |  |  | 6127 | 	}
 | 
        
           |  |  | 6128 |   | 
        
           |  |  | 6129 | 	// format the list with added spaces
 | 
        
           |  |  | 6130 | 	CyStringList formatedAniList;
 | 
        
           |  |  | 6131 | 	int lineCount = -1;
 | 
        
           |  |  | 6132 | 	for ( SStringList *strNode = parsedAniList.Head(); strNode; strNode = strNode->next )
 | 
        
           |  |  | 6133 | 	{
 | 
        
           |  |  | 6134 | 		// format the comment to match the line number
 | 
        
           |  |  | 6135 | 		lineCount++;
 | 
        
           |  |  | 6136 | 		CyString oldComment = strNode->str.GetToken("//", 2);
 | 
        
           |  |  | 6137 | 		CyString comment = CyString("//") + CyString::Number(lineCount);
 | 
        
           |  |  | 6138 | 		if ( !oldComment.Empty() )
 | 
        
           |  |  | 6139 | 		{
 | 
        
           |  |  | 6140 | 			comment += " ";
 | 
        
           |  |  | 6141 | 			oldComment.RemoveFirstSpace();
 | 
        
           |  |  | 6142 | 			if ( oldComment.GetToken(" ", 1, 1).IsNumber() )
 | 
        
           |  |  | 6143 | 				comment += oldComment.GetToken(" ", 2);
 | 
        
           |  |  | 6144 | 			else
 | 
        
           |  |  | 6145 | 				comment += oldComment;
 | 
        
           |  |  | 6146 | 		}
 | 
        
           |  |  | 6147 | 		CyString line = strNode->str.GetToken("//", 1, 1);
 | 
        
           |  |  | 6148 |   | 
        
           |  |  | 6149 | 		// split into seperate lines
 | 
        
           |  |  | 6150 | 		CyString first = line.GetToken(";", 1, 1);
 | 
        
           |  |  | 6151 | 		if ( first.Compare("TAT_TAGSINGLESTEP") )
 | 
        
           |  |  | 6152 | 		{
 | 
        
           |  |  | 6153 | 			formatedAniList.PushBack(line.GetToken(";", 1, 5) + ";");
 | 
        
           |  |  | 6154 | 			int max;
 | 
        
           |  |  | 6155 | 			CyString *sLines = line.GetToken(";", 6).SplitToken(";", &max);
 | 
        
           |  |  | 6156 | 			if ( max && sLines )
 | 
        
           |  |  | 6157 | 			{
 | 
        
           |  |  | 6158 | 				if ( sLines[max - 1].Empty() )
 | 
        
           |  |  | 6159 | 					--max; // remove the last ";"
 | 
        
           |  |  | 6160 |   | 
        
           |  |  | 6161 | 				for ( int i = 0; i < max; i++ )
 | 
        
           |  |  | 6162 | 				{
 | 
        
           |  |  | 6163 | 					CyString l = CyString("\t") + sLines[i] + ";";
 | 
        
           |  |  | 6164 | 					if ( i == (max - 1) )
 | 
        
           |  |  | 6165 | 						formatedAniList.PushBack(l + comment);
 | 
        
           |  |  | 6166 | 					else
 | 
        
           |  |  | 6167 | 						formatedAniList.PushBack(l);
 | 
        
           |  |  | 6168 | 				}
 | 
        
           |  |  | 6169 | 			}
 | 
        
           |  |  | 6170 | 			CLEANSPLIT(sLines, max);
 | 
        
           |  |  | 6171 | 		}
 | 
        
           |  |  | 6172 | 		else if ( (first.Compare("TAT_TAGONESHOT") || first.Compare("TAT_TAGLOOP")) && (line.IsIn("TATF_COORDS")) )
 | 
        
           |  |  | 6173 | 		{
 | 
        
           |  |  | 6174 | 			formatedAniList.PushBack(line.GetToken(";", 1, 5) + ";");
 | 
        
           |  |  | 6175 | 			int max;
 | 
        
           |  |  | 6176 | 			CyString *sLines = line.GetToken(";", 6).SplitToken(";", &max);
 | 
        
           |  |  | 6177 | 			if ( max && sLines )
 | 
        
           |  |  | 6178 | 			{
 | 
        
           |  |  | 6179 | 				if ( sLines[max - 1].Empty() )
 | 
        
           |  |  | 6180 | 					--max; // remove the last ";"
 | 
        
           |  |  | 6181 |   | 
        
           |  |  | 6182 | 				CyString prevLine;
 | 
        
           |  |  | 6183 | 				for ( int i = 0; i < max; i++ )
 | 
        
           |  |  | 6184 | 				{
 | 
        
           |  |  | 6185 | 					CyString l = sLines[i] + ";";
 | 
        
           |  |  | 6186 | 					if ( l.IsIn("TATF_COORDS") && !prevLine.Empty() )
 | 
        
           |  |  | 6187 | 					{
 | 
        
           |  |  | 6188 | 						formatedAniList.PushBack(CyString("\t") + prevLine);
 | 
        
           |  |  | 6189 | 						prevLine = "";
 | 
        
           |  |  | 6190 | 					}
 | 
        
           |  |  | 6191 | 					prevLine += l;
 | 
        
           |  |  | 6192 | 				}
 | 
        
           |  |  | 6193 |   | 
        
           |  |  | 6194 | 				if ( !prevLine.Empty() )
 | 
        
           |  |  | 6195 | 					formatedAniList.PushBack(CyString("\t") + prevLine + comment);
 | 
        
           |  |  | 6196 |   | 
        
           |  |  | 6197 | 			}
 | 
        
           |  |  | 6198 | 			CLEANSPLIT(sLines, max);
 | 
        
           |  |  | 6199 | 		}
 | 
        
           |  |  | 6200 | 		else
 | 
        
           |  |  | 6201 | 			formatedAniList.PushBack(line + comment);
 | 
        
           |  |  | 6202 | 	}
 | 
        
           |  |  | 6203 |   | 
        
           |  |  | 6204 | 	formatedAniList.PushFront(CyString::Number(parsedAniList.Count()) + ";");
 | 
        
           |  |  | 6205 | 	formatedAniList.PushFront(CyString("// Animations, created by SPK Libraries V") + CyString::CreateFromFloat(GetLibraryVersion(), 2));
 | 
        
           |  |  | 6206 |   | 
        
           |  |  | 6207 | 	// write the file to disk
 | 
        
           |  |  | 6208 | 	CFileIO WriteFile(m_sTempDir + "/Animations.txt");
 | 
        
           |  |  | 6209 | 	if ( WriteFile.WriteFile(&formatedAniList) )
 | 
        
           |  |  | 6210 | 	{
 | 
        
           |  |  | 6211 | 		this->PackFile(&WriteFile, "types\\Animations.pck");
 | 
        
           |  |  | 6212 | 		WriteFile.Remove();
 | 
        
           |  |  | 6213 | 	}
 | 
        
           |  |  | 6214 | }
 | 
        
           |  |  | 6215 |   | 
        
           |  |  | 6216 | void CPackages::CreateBodies()
 | 
        
           |  |  | 6217 | {
 | 
        
           |  |  | 6218 | 	// first check we have any ships
 | 
        
           |  |  | 6219 | 	if ( m_lGameShips.empty() || !this->CountPackages(TYPE_XSP, true) )
 | 
        
           |  |  | 6220 | 		return;
 | 
        
           |  |  | 6221 |   | 
        
           |  |  | 6222 | 	bool found = false;
 | 
        
           |  |  | 6223 | 	for ( CListNode<SGameShip> *node = m_lGameShips.Front(); node; node = node->next() )
 | 
        
           |  |  | 6224 | 	{
 | 
        
           |  |  | 6225 | 		SGameShip *s = node->Data();
 | 
        
           |  |  | 6226 | 		if ( s->iType != WARETYPE_ADDED || !s->pPackage )
 | 
        
           |  |  | 6227 | 			continue;
 | 
        
           |  |  | 6228 |   | 
        
           |  |  | 6229 | 		// no dummies to add?
 | 
        
           |  |  | 6230 | 		if ( !s->pPackage->AnyBodies() )
 | 
        
           |  |  | 6231 | 			continue;
 | 
        
           |  |  | 6232 | 		found = true;
 | 
        
           |  |  | 6233 | 		break;
 | 
        
           |  |  | 6234 | 	}
 | 
        
           |  |  | 6235 |   | 
        
           |  |  | 6236 | 	if ( !found )
 | 
        
           |  |  | 6237 | 		return;
 | 
        
           |  |  | 6238 |   | 
        
           |  |  | 6239 | 	// lets read our current bodies file
 | 
        
           |  |  | 6240 | 	CLinkList<SBodies> bodiesList;
 | 
        
           |  |  | 6241 | 	SBodies *currentSection = NULL;
 | 
        
           |  |  | 6242 | 	int e = ExtractGameFile("types/Bodies.pck", m_sTempDir + "/Bodies.txt");
 | 
        
           |  |  | 6243 | 	if ( e )
 | 
        
           |  |  | 6244 | 	{
 | 
        
           |  |  | 6245 | 		CFileIO File;
 | 
        
           |  |  | 6246 | 		if ( File.Open((e == -1) ? "Bodies.txt" : m_sTempDir + "/Bodies.txt") )
 | 
        
           |  |  | 6247 | 		{
 | 
        
           |  |  | 6248 | 			std::vector<CyString> *lines = File.ReadLines();
 | 
        
           |  |  | 6249 | 			if ( lines )
 | 
        
           |  |  | 6250 | 			{
 | 
        
           |  |  | 6251 | 				int entries = 0;
 | 
        
           |  |  | 6252 | 				for ( int j = 0; j < (int)lines->size(); j++ )
 | 
        
           |  |  | 6253 | 				{
 | 
        
           |  |  | 6254 | 					CyString line(lines->at(j));
 | 
        
           |  |  | 6255 | 					line.RemoveChar(' ');
 | 
        
           |  |  | 6256 | 					line.RemoveChar(9);
 | 
        
           |  |  | 6257 | 					if ( line.Empty() || line[0] == '/' )
 | 
        
           |  |  | 6258 | 						continue;
 | 
        
           |  |  | 6259 | 					if ( entries <= 0 )
 | 
        
           |  |  | 6260 | 					{
 | 
        
           |  |  | 6261 | 						entries = line.GetToken(";", 2, 2).ToInt();
 | 
        
           |  |  | 6262 | 						currentSection = new SBodies;
 | 
        
           |  |  | 6263 | 						currentSection->sSection = line.GetToken(";", 1, 1);
 | 
        
           |  |  | 6264 | 						bodiesList.push_back(currentSection);
 | 
        
           |  |  | 6265 | 					}
 | 
        
           |  |  | 6266 | 					else if ( currentSection )
 | 
        
           |  |  | 6267 | 					{
 | 
        
           |  |  | 6268 | 						int num;
 | 
        
           |  |  | 6269 | 						CyString *strs = line.SplitToken(";", &num);
 | 
        
           |  |  | 6270 | 						if ( num && strs )
 | 
        
           |  |  | 6271 | 						{
 | 
        
           |  |  | 6272 | 							for ( int i = 0; i < num; i++ )
 | 
        
           |  |  | 6273 | 							{
 | 
        
           |  |  | 6274 | 								if ( strs[i].Empty() )
 | 
        
           |  |  | 6275 | 									continue;
 | 
        
           |  |  | 6276 | 								currentSection->lEntries.PushBack(strs[i] + ";", true);
 | 
        
           |  |  | 6277 | 								--entries;
 | 
        
           |  |  | 6278 | 							}
 | 
        
           |  |  | 6279 | 						}
 | 
        
           |  |  | 6280 | 						CLEANSPLIT(strs, num);
 | 
        
           |  |  | 6281 | 					}
 | 
        
           |  |  | 6282 | 				}
 | 
        
           |  |  | 6283 |   | 
        
           |  |  | 6284 | 				delete lines;
 | 
        
           |  |  | 6285 | 			}
 | 
        
           |  |  | 6286 | 			File.Remove();
 | 
        
           |  |  | 6287 | 		}
 | 
        
           |  |  | 6288 | 	}
 | 
        
           |  |  | 6289 |   | 
        
           |  |  | 6290 | 	// lets now add any new entries
 | 
        
           |  |  | 6291 | 	for ( CListNode<SGameShip> *node = m_lGameShips.Front(); node; node = node->next() )
 | 
        
           |  |  | 6292 | 	{
 | 
        
           |  |  | 6293 | 		SGameShip *s = node->Data();
 | 
        
           |  |  | 6294 | 		if ( s->iType != WARETYPE_ADDED || !s->pPackage )
 | 
        
           |  |  | 6295 | 			continue;
 | 
        
           |  |  | 6296 |   | 
        
           |  |  | 6297 | 		// no dummies to add?
 | 
        
           |  |  | 6298 | 		if ( !s->pPackage->AnyBodies() )
 | 
        
           |  |  | 6299 | 			continue;
 | 
        
           |  |  | 6300 |   | 
        
           |  |  | 6301 | 		// add each dummy to list
 | 
        
           |  |  | 6302 | 		for ( SStringList *strNode = s->pPackage->GetBodies()->Head(); strNode; strNode = strNode->next )
 | 
        
           |  |  | 6303 | 		{
 | 
        
           |  |  | 6304 | 			CyString section = strNode->str.GetToken(";", 1, 1);
 | 
        
           |  |  | 6305 | 			CyString body = strNode->str.GetToken(";", 2).Remove(' ');
 | 
        
           |  |  | 6306 | 			if ( body.Right(1) != ";" )
 | 
        
           |  |  | 6307 | 				body += ";";
 | 
        
           |  |  | 6308 |   | 
        
           |  |  | 6309 | 			// find the section to add into
 | 
        
           |  |  | 6310 | 			SBodies *foundSection = NULL;
 | 
        
           |  |  | 6311 | 			for ( CListNode<SBodies> *checkBody = bodiesList.Front(); checkBody; checkBody = checkBody->next() )
 | 
        
           |  |  | 6312 | 			{
 | 
        
           |  |  | 6313 | 				if ( checkBody->Data()->sSection.Compare(section) )
 | 
        
           |  |  | 6314 | 				{
 | 
        
           |  |  | 6315 | 					foundSection = checkBody->Data();
 | 
        
           |  |  | 6316 | 					break;
 | 
        
           |  |  | 6317 | 				}
 | 
        
           |  |  | 6318 | 			}
 | 
        
           |  |  | 6319 |   | 
        
           |  |  | 6320 | 			if ( !foundSection )
 | 
        
           |  |  | 6321 | 			{
 | 
        
           |  |  | 6322 | 				foundSection = new SBodies;
 | 
        
           |  |  | 6323 | 				foundSection->sSection = section;
 | 
        
           |  |  | 6324 | 				bodiesList.push_back(foundSection);
 | 
        
           |  |  | 6325 | 			}
 | 
        
           |  |  | 6326 | 			foundSection->lEntries.PushBack(body, true);
 | 
        
           |  |  | 6327 | 		}
 | 
        
           |  |  | 6328 | 	}
 | 
        
           |  |  | 6329 |   | 
        
           |  |  | 6330 | 	// now write the file
 | 
        
           |  |  | 6331 | 	CyStringList writeList;
 | 
        
           |  |  | 6332 | 	// the header first
 | 
        
           |  |  | 6333 | 	writeList.PushBack(CyString("// Bodies file, created by SPK Libraries V") + CyString::CreateFromFloat(GetLibraryVersion(), 2));
 | 
        
           |  |  | 6334 | 	writeList.PushBack("//body type;num bodies;");
 | 
        
           |  |  | 6335 | 	writeList.PushBack("//[body id/name]");
 | 
        
           |  |  | 6336 |   | 
        
           |  |  | 6337 | 	// now our sections
 | 
        
           |  |  | 6338 | 	for ( SBodies *bSection = bodiesList.First(); bSection; bSection = bodiesList.Next() )
 | 
        
           |  |  | 6339 | 	{
 | 
        
           |  |  | 6340 | 		writeList.PushBack("");
 | 
        
           |  |  | 6341 | 		writeList.PushBack(CyString("// Section: ") + bSection->sSection);
 | 
        
           |  |  | 6342 | 		writeList.PushBack(bSection->sSection + ";" + CyString::Number(bSection->lEntries.Count()) + ";");
 | 
        
           |  |  | 6343 | 		for ( SStringList *strNode = bSection->lEntries.Head(); strNode; strNode = strNode->next )
 | 
        
           |  |  | 6344 | 		{
 | 
        
           |  |  | 6345 | 			CyString str = strNode->str;
 | 
        
           |  |  | 6346 | 			str.RemoveChar(9);
 | 
        
           |  |  | 6347 | 			str.RemoveChar(' ');
 | 
        
           |  |  | 6348 | 			if ( str.Right(1) != ";" )
 | 
        
           |  |  | 6349 | 				str += ";";
 | 
        
           |  |  | 6350 | 			writeList.PushBack(str);
 | 
        
           |  |  | 6351 | 		}
 | 
        
           |  |  | 6352 | 	}
 | 
        
           |  |  | 6353 |   | 
        
           |  |  | 6354 | 	// write the file to disk
 | 
        
           |  |  | 6355 | 	CFileIO WriteFile(m_sTempDir + "/Bodies.txt");
 | 
        
           |  |  | 6356 | 	if ( WriteFile.WriteFile(&writeList) )
 | 
        
           |  |  | 6357 | 	{
 | 
        
           |  |  | 6358 | 		this->PackFile(&WriteFile, "types\\Bodies.pck");
 | 
        
           |  |  | 6359 | 		WriteFile.Remove();
 | 
        
           |  |  | 6360 | 	}
 | 
        
           |  |  | 6361 | }
 | 
        
           |  |  | 6362 |   | 
        
           |  |  | 6363 | void CPackages::CreateCustomStarts()
 | 
        
           |  |  | 6364 | {
 | 
        
           |  |  | 6365 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 6366 | 	{
 | 
        
           |  |  | 6367 | 		// find all spk files (only ones that can be custom starts
 | 
        
           |  |  | 6368 | 		if ( node->Data()->GetType() != TYPE_SPK )
 | 
        
           |  |  | 6369 | 			continue;
 | 
        
           |  |  | 6370 |   | 
        
           |  |  | 6371 | 		CSpkFile *p = (CSpkFile *)node->Data();
 | 
        
           |  |  | 6372 |   | 
        
           |  |  | 6373 | 		// only use custom starts
 | 
        
           |  |  | 6374 | 		if ( !p->IsCustomStart() )
 | 
        
           |  |  | 6375 | 			continue;
 | 
        
           |  |  | 6376 |   | 
        
           |  |  | 6377 | 		// get the name of the start to use
 | 
        
           |  |  | 6378 | 		CyString name = p->GetCustomStartName();
 | 
        
           |  |  | 6379 | 		if ( name.Empty() )
 | 
        
           |  |  | 6380 | 			continue;
 | 
        
           |  |  | 6381 |   | 
        
           |  |  | 6382 | 		// find if maps file exists
 | 
        
           |  |  | 6383 | 		CyStringList createFiles;
 | 
        
           |  |  | 6384 | 		createFiles.PushBack(name, "maps/x3_universe");
 | 
        
           |  |  | 6385 | 		createFiles.PushBack(name, "types/Jobs");
 | 
        
           |  |  | 6386 | 		createFiles.PushBack(name, "types/JobWings");
 | 
        
           |  |  | 6387 |   | 
        
           |  |  | 6388 | 		for ( SStringList *str = createFiles.Head(); str; str = str->next )
 | 
        
           |  |  | 6389 | 		{
 | 
        
           |  |  | 6390 | 			CyString dir = CFileIO(str->data).GetDir();
 | 
        
           |  |  | 6391 | 			int type = FILETYPE_EXTRA;
 | 
        
           |  |  | 6392 | 			if ( dir.Compare("maps") )
 | 
        
           |  |  | 6393 | 				type = FILETYPE_MAP;
 | 
        
           |  |  | 6394 |   | 
        
           |  |  | 6395 | 			if ( !p->FindFile(str->str + ".xml", type) && !p->FindFile(str->str + ".pck", type) )
 | 
        
           |  |  | 6396 | 			{
 | 
        
           |  |  | 6397 | 				// create a maps files
 | 
        
           |  |  | 6398 | 				int e = this->ExtractGameFile(str->data + ".pck", m_sTempDir + "/" + str->data + ".pck");
 | 
        
           |  |  | 6399 | 				if ( e )
 | 
        
           |  |  | 6400 | 				{
 | 
        
           |  |  | 6401 | 					CFileIO File((e == -1) ? (str->data + ".pck") : (m_sTempDir + "/" + str->data + ".pck"));
 | 
        
           |  |  | 6402 | 					if ( File.Exists() )
 | 
        
           |  |  | 6403 | 					{
 | 
        
           |  |  | 6404 | 						File.Rename(m_sCurrentDir + "/" + dir + "/" + str->str + ".pck");
 | 
        
           |  |  | 6405 | 						this->AddCreatedFile(dir + "/" + str->str + ".pck");
 | 
        
           |  |  | 6406 | 					}
 | 
        
           |  |  | 6407 | 				}
 | 
        
           |  |  | 6408 | 			}
 | 
        
           |  |  | 6409 | 		}
 | 
        
           |  |  | 6410 | 	}
 | 
        
           |  |  | 6411 | }
 | 
        
           |  |  | 6412 |   | 
        
           |  |  | 6413 | void CPackages::AddCreatedFile(CyString file)
 | 
        
           |  |  | 6414 | {
 | 
        
           |  |  | 6415 | 	file = file.Remove(m_sCurrentDir);
 | 
        
           |  |  | 6416 | 	while ( file[0] == '/' )
 | 
        
           |  |  | 6417 | 		file.Erase(0, 1);
 | 
        
           |  |  | 6418 | 	while ( file[0] == '\\' )
 | 
        
           |  |  | 6419 | 		file.Erase(0, 1);
 | 
        
           |  |  | 6420 |   | 
        
           |  |  | 6421 | 	m_lCreatedFiles.PushBack(file, true);
 | 
        
           |  |  | 6422 | }
 | 
        
           |  |  | 6423 |   | 
        
           |  |  | 6424 | void CPackages::CreateComponants()
 | 
        
           |  |  | 6425 | {
 | 
        
           |  |  | 6426 | 	// first check we have any ships
 | 
        
           |  |  | 6427 | 	if ( m_lGameShips.empty() || !this->CountPackages(TYPE_XSP, true) )
 | 
        
           |  |  | 6428 | 		return;
 | 
        
           |  |  | 6429 |   | 
        
           |  |  | 6430 | 	CLinkList<SComponantEntry> dummyList;
 | 
        
           |  |  | 6431 |   | 
        
           |  |  | 6432 | 	// now extract the existing dummies
 | 
        
           |  |  | 6433 | 	int e = ExtractGameFile("types/Components.pck", m_sTempDir + "/Components.txt");
 | 
        
           |  |  | 6434 | 	if ( e )
 | 
        
           |  |  | 6435 | 	{
 | 
        
           |  |  | 6436 | 		// read the dummies
 | 
        
           |  |  | 6437 | 		CFileIO File;
 | 
        
           |  |  | 6438 | 		if ( File.Open((e == -1) ? "Components.txt" : m_sTempDir + "/Components.txt") )
 | 
        
           |  |  | 6439 | 		{
 | 
        
           |  |  | 6440 | 			std::vector<CyString> *lines = File.ReadLines();
 | 
        
           |  |  | 6441 | 			if ( lines )
 | 
        
           |  |  | 6442 | 			{
 | 
        
           |  |  | 6443 | 				int insection = 0;
 | 
        
           |  |  | 6444 | 				int insubsection = 0;
 | 
        
           |  |  | 6445 | 				SComponantEntry *currentSection = NULL;
 | 
        
           |  |  | 6446 | 				SComponantEntry2 *currentSubSection = NULL;
 | 
        
           |  |  | 6447 | 				for ( int j = 0; j < (int)lines->size(); j++ )
 | 
        
           |  |  | 6448 | 				{
 | 
        
           |  |  | 6449 | 					CyString line(lines->at(j));
 | 
        
           |  |  | 6450 | 					if ( line[0] == '/' )
 | 
        
           |  |  | 6451 | 						continue;
 | 
        
           |  |  | 6452 | 					line.RemoveChar('\r');
 | 
        
           |  |  | 6453 | 					line = line.RemoveFirstSpace();
 | 
        
           |  |  | 6454 | 					line = line.RemoveEndSpace();
 | 
        
           |  |  | 6455 | 					if ( line.Empty() )
 | 
        
           |  |  | 6456 | 						continue;
 | 
        
           |  |  | 6457 |   | 
        
           |  |  | 6458 |   | 
        
           |  |  | 6459 | 					// read the section, first entry is section, second is size
 | 
        
           |  |  | 6460 | 					while ( !line.Empty() )
 | 
        
           |  |  | 6461 | 					{
 | 
        
           |  |  | 6462 | 						line = line.RemoveFirstSpace();
 | 
        
           |  |  | 6463 | 						if ( line.Empty() )
 | 
        
           |  |  | 6464 | 							break;
 | 
        
           |  |  | 6465 |   | 
        
           |  |  | 6466 | 						if ( !insection && !insubsection )
 | 
        
           |  |  | 6467 | 						{
 | 
        
           |  |  | 6468 | 							CyString section = line.GetToken(";", 1, 1);
 | 
        
           |  |  | 6469 | 							insection = line.GetToken(";", 2, 2).ToInt();
 | 
        
           |  |  | 6470 |   | 
        
           |  |  | 6471 | 							// search for the sections
 | 
        
           |  |  | 6472 | 							currentSection = NULL;
 | 
        
           |  |  | 6473 | 							for ( CListNode<SComponantEntry> *node = dummyList.Front(); node; node = node->next() )
 | 
        
           |  |  | 6474 | 							{
 | 
        
           |  |  | 6475 | 								SComponantEntry *d = node->Data();
 | 
        
           |  |  | 6476 | 								if ( d->sSection.Compare(section) )
 | 
        
           |  |  | 6477 | 								{
 | 
        
           |  |  | 6478 | 									currentSection = node->Data();
 | 
        
           |  |  | 6479 | 									break;
 | 
        
           |  |  | 6480 | 								}
 | 
        
           |  |  | 6481 | 							}
 | 
        
           |  |  | 6482 |   | 
        
           |  |  | 6483 | 							if ( !currentSection )
 | 
        
           |  |  | 6484 | 							{
 | 
        
           |  |  | 6485 | 								currentSection = new SComponantEntry;
 | 
        
           |  |  | 6486 | 								currentSection->sSection = section;
 | 
        
           |  |  | 6487 | 								dummyList.push_back(currentSection);
 | 
        
           |  |  | 6488 | 							}
 | 
        
           |  |  | 6489 |   | 
        
           |  |  | 6490 | 							// we have some more ?
 | 
        
           |  |  | 6491 | 							line = line.DelToken(";", 1, 2);
 | 
        
           |  |  | 6492 | 						}
 | 
        
           |  |  | 6493 | 						else if ( !insubsection )
 | 
        
           |  |  | 6494 | 						{
 | 
        
           |  |  | 6495 | 							--insection;
 | 
        
           |  |  | 6496 | 							CyString section = line.GetToken(";", 1, 1);
 | 
        
           |  |  | 6497 | 							insubsection = line.GetToken(";", 2, 2).ToInt();
 | 
        
           |  |  | 6498 |   | 
        
           |  |  | 6499 | 							currentSubSection = new SComponantEntry2;
 | 
        
           |  |  | 6500 | 							currentSubSection->sSection = section;
 | 
        
           |  |  | 6501 | 							currentSection->lEntries.push_back(currentSubSection);
 | 
        
           |  |  | 6502 |   | 
        
           |  |  | 6503 | 							line = line.DelToken(";", 1, 2);
 | 
        
           |  |  | 6504 | 						}
 | 
        
           |  |  | 6505 | 						else
 | 
        
           |  |  | 6506 | 						{
 | 
        
           |  |  | 6507 | 							--insubsection;
 | 
        
           |  |  | 6508 | 							currentSubSection->lEntries.PushBack(line.Remove(' '), true);
 | 
        
           |  |  | 6509 | 							line = "";
 | 
        
           |  |  | 6510 | 						}
 | 
        
           |  |  | 6511 | 					}
 | 
        
           |  |  | 6512 | 				}
 | 
        
           |  |  | 6513 |   | 
        
           |  |  | 6514 | 				delete lines;
 | 
        
           |  |  | 6515 | 			}
 | 
        
           |  |  | 6516 |   | 
        
           |  |  | 6517 | 			File.Remove();
 | 
        
           |  |  | 6518 | 		}
 | 
        
           |  |  | 6519 |   | 
        
           |  |  | 6520 | 		// add the new entries for the ships
 | 
        
           |  |  | 6521 | 		for ( CListNode<SGameShip> *node = m_lGameShips.Front(); node; node = node->next() )
 | 
        
           |  |  | 6522 | 		{
 | 
        
           |  |  | 6523 | 			SGameShip *s = node->Data();
 | 
        
           |  |  | 6524 | 			if ( s->iType != WARETYPE_ADDED || !s->pPackage )
 | 
        
           |  |  | 6525 | 				continue;
 | 
        
           |  |  | 6526 |   | 
        
           |  |  | 6527 | 			// no dummies to add?
 | 
        
           |  |  | 6528 | 			if ( !s->pPackage->AnyComponents() )
 | 
        
           |  |  | 6529 | 				continue;
 | 
        
           |  |  | 6530 |   | 
        
           |  |  | 6531 | 			// add each dummy to list
 | 
        
           |  |  | 6532 | 			for ( CListNode<SComponent> *dNode = s->pPackage->GetComponents()->Front(); dNode; dNode = dNode->next() )
 | 
        
           |  |  | 6533 | 			{
 | 
        
           |  |  | 6534 | 				SComponent *dummy = dNode->Data();
 | 
        
           |  |  | 6535 | 				SComponantEntry *found = NULL;
 | 
        
           |  |  | 6536 | 				SComponantEntry2 *found2 = NULL;
 | 
        
           |  |  | 6537 | 				for ( CListNode<SComponantEntry> *eNode = dummyList.Front(); eNode; eNode = eNode->next() )
 | 
        
           |  |  | 6538 | 				{
 | 
        
           |  |  | 6539 | 					if ( eNode->Data()->sSection.Compare(dummy->sSection) )
 | 
        
           |  |  | 6540 | 					{
 | 
        
           |  |  | 6541 | 						found = eNode->Data();
 | 
        
           |  |  | 6542 | 						break;
 | 
        
           |  |  | 6543 | 					}
 | 
        
           |  |  | 6544 | 				}
 | 
        
           |  |  | 6545 | 				if ( !found )
 | 
        
           |  |  | 6546 | 				{
 | 
        
           |  |  | 6547 | 					found = new SComponantEntry;
 | 
        
           |  |  | 6548 | 					found->sSection = dummy->sSection;
 | 
        
           |  |  | 6549 | 					dummyList.push_back(found);
 | 
        
           |  |  | 6550 | 					found2 = new SComponantEntry2;
 | 
        
           |  |  | 6551 | 					found2->sSection = dummy->sSection2;
 | 
        
           |  |  | 6552 | 					found->lEntries.push_back(found2);
 | 
        
           |  |  | 6553 | 				}
 | 
        
           |  |  | 6554 | 				// else check for the 2nd section
 | 
        
           |  |  | 6555 | 				else
 | 
        
           |  |  | 6556 | 				{
 | 
        
           |  |  | 6557 | 					for ( CListNode<SComponantEntry2> *cNode = found->lEntries.Front(); cNode; cNode = cNode->next() )
 | 
        
           |  |  | 6558 | 					{
 | 
        
           |  |  | 6559 | 						if ( cNode->Data()->sSection.Compare(dummy->sSection2) )
 | 
        
           |  |  | 6560 | 						{
 | 
        
           |  |  | 6561 | 							found2 = cNode->Data();
 | 
        
           |  |  | 6562 | 							break;
 | 
        
           |  |  | 6563 | 						}
 | 
        
           |  |  | 6564 | 					}
 | 
        
           |  |  | 6565 |   | 
        
           |  |  | 6566 | 					if ( !found2 )
 | 
        
           |  |  | 6567 | 					{
 | 
        
           |  |  | 6568 | 						found2 = new SComponantEntry2;
 | 
        
           |  |  | 6569 | 						found2->sSection = dummy->sSection2;
 | 
        
           |  |  | 6570 | 						found->lEntries.push_back(found2);
 | 
        
           |  |  | 6571 | 					}
 | 
        
           |  |  | 6572 | 					else
 | 
        
           |  |  | 6573 | 					{
 | 
        
           |  |  | 6574 | 						bool f = false;
 | 
        
           |  |  | 6575 | 						for ( SStringList *strNode = found2->lEntries.Head(); strNode; strNode = strNode->next )
 | 
        
           |  |  | 6576 | 						{
 | 
        
           |  |  | 6577 | 							if ( dummy->sData.Remove(' ').Compare(strNode->str) )
 | 
        
           |  |  | 6578 | 							{
 | 
        
           |  |  | 6579 | 								f = true;
 | 
        
           |  |  | 6580 | 								break;
 | 
        
           |  |  | 6581 | 							}
 | 
        
           |  |  | 6582 | 						}
 | 
        
           |  |  | 6583 |   | 
        
           |  |  | 6584 | 						if ( f )
 | 
        
           |  |  | 6585 | 							continue;
 | 
        
           |  |  | 6586 | 					}
 | 
        
           |  |  | 6587 | 				}
 | 
        
           |  |  | 6588 |   | 
        
           |  |  | 6589 | 				found2->lEntries.PushBack(dummy->sData.Remove(' '));
 | 
        
           |  |  | 6590 | 			}
 | 
        
           |  |  | 6591 | 		}
 | 
        
           |  |  | 6592 |   | 
        
           |  |  | 6593 | 		// finally, write the file
 | 
        
           |  |  | 6594 | 		std::vector<CyString> lines;
 | 
        
           |  |  | 6595 | 		lines.push_back(CyString("// Components file, created by SPK Libraries V") + CyString::CreateFromFloat(GetLibraryVersion(), 2));
 | 
        
           |  |  | 6596 | 		for ( SComponantEntry *dummy = dummyList.First(); dummy; dummy = dummyList.Next() )
 | 
        
           |  |  | 6597 | 		{
 | 
        
           |  |  | 6598 | 			lines.push_back("");
 | 
        
           |  |  | 6599 | 			lines.push_back(CyString("// Section: ") + dummy->sSection + " Entries: " + (long)dummy->lEntries.size());
 | 
        
           |  |  | 6600 | 			lines.push_back(dummy->sSection + ";" + CyString::Number(dummy->lEntries.size()) + ";");
 | 
        
           |  |  | 6601 | 			for ( CListNode<SComponantEntry2> *comp = dummy->lEntries.Front(); comp; comp = comp->next() )
 | 
        
           |  |  | 6602 | 			{
 | 
        
           |  |  | 6603 | 				lines.push_back(comp->Data()->sSection + ";" + (long)comp->Data()->lEntries.Count() + ";");
 | 
        
           |  |  | 6604 | 				for ( SStringList *str = comp->Data()->lEntries.Head(); str; str = str->next )
 | 
        
           |  |  | 6605 | 				{
 | 
        
           |  |  | 6606 | 					CyString cStr = str->str;
 | 
        
           |  |  | 6607 | 					cStr.RemoveEndSpace();
 | 
        
           |  |  | 6608 | 					cStr.RemoveChar(9);
 | 
        
           |  |  | 6609 | 					cStr.RemoveChar('\r');
 | 
        
           |  |  | 6610 | 					if ( cStr.Right(1) != ";" )
 | 
        
           |  |  | 6611 | 						cStr += ";";
 | 
        
           |  |  | 6612 | 					lines.push_back(cStr);
 | 
        
           |  |  | 6613 | 				}
 | 
        
           |  |  | 6614 | 			}
 | 
        
           |  |  | 6615 | 		}
 | 
        
           |  |  | 6616 |   | 
        
           |  |  | 6617 | 		// write the file to disk
 | 
        
           |  |  | 6618 | 		CFileIO WriteFile(m_sTempDir + "/Components.txt");
 | 
        
           |  |  | 6619 | 		if ( WriteFile.WriteFile(&lines) )
 | 
        
           |  |  | 6620 | 		{
 | 
        
           |  |  | 6621 | 			this->PackFile(&WriteFile, "types\\Components.pck");
 | 
        
           |  |  | 6622 | 			WriteFile.Remove();
 | 
        
           |  |  | 6623 | 		}
 | 
        
           |  |  | 6624 | 	}
 | 
        
           |  |  | 6625 | }
 | 
        
           |  |  | 6626 |   | 
        
           |  |  | 6627 | bool CPackages::ReadGlobals(CyStringList &globals)
 | 
        
           |  |  | 6628 | {
 | 
        
           |  |  | 6629 | 	int e = ExtractGameFile("types/Globals.pck", m_sTempDir);
 | 
        
           |  |  | 6630 | 	if ( e )
 | 
        
           |  |  | 6631 | 	{
 | 
        
           |  |  | 6632 | 		CFileIO File(((e == -1) ? "." : m_sTempDir) + "/Globals.txt");
 | 
        
           |  |  | 6633 | 		if ( File.Exists() )
 | 
        
           |  |  | 6634 | 		{
 | 
        
           |  |  | 6635 | 			CyStringList *lines = File.ReadLinesStr();
 | 
        
           |  |  | 6636 | 			if ( lines )
 | 
        
           |  |  | 6637 | 			{
 | 
        
           |  |  | 6638 | 				int entries = -1;
 | 
        
           |  |  | 6639 | 				for ( SStringList *str = lines->Head(); str; str = str->next )
 | 
        
           |  |  | 6640 | 				{
 | 
        
           |  |  | 6641 | 					str->str.RemoveChar('\r');
 | 
        
           |  |  | 6642 | 					str->str.RemoveChar(9);
 | 
        
           |  |  | 6643 | 					str->str.RemoveFirstSpace();
 | 
        
           |  |  | 6644 |   | 
        
           |  |  | 6645 | 					if ( str->str.Empty() )
 | 
        
           |  |  | 6646 | 						continue;
 | 
        
           |  |  | 6647 | 					if ( str->str[0] == '/' )
 | 
        
           |  |  | 6648 | 						continue;
 | 
        
           |  |  | 6649 |   | 
        
           |  |  | 6650 | 					// remove comments
 | 
        
           |  |  | 6651 | 					CyString l = str->str;
 | 
        
           |  |  | 6652 | 					if ( l.IsIn("/") ) 
 | 
        
           |  |  | 6653 | 						l = l.GetToken("/", 1, 1);
 | 
        
           |  |  | 6654 |   | 
        
           |  |  | 6655 | 					if ( entries == -1 )
 | 
        
           |  |  | 6656 | 						entries = l.GetToken(";", 1, 1).ToInt();
 | 
        
           |  |  | 6657 | 					else
 | 
        
           |  |  | 6658 | 						globals.PushBack(l.GetToken(";", 1, 1), l.GetToken(";", 2, 2));
 | 
        
           |  |  | 6659 | 				}
 | 
        
           |  |  | 6660 |   | 
        
           |  |  | 6661 | 				delete lines;
 | 
        
           |  |  | 6662 |   | 
        
           |  |  | 6663 | 				return true;
 | 
        
           |  |  | 6664 | 			}
 | 
        
           |  |  | 6665 | 		}
 | 
        
           |  |  | 6666 | 	}
 | 
        
           |  |  | 6667 |   | 
        
           |  |  | 6668 | 	return false;
 | 
        
           |  |  | 6669 | }
 | 
        
           |  |  | 6670 |   | 
        
           |  |  | 6671 | void CPackages::CreateGlobals()
 | 
        
           |  |  | 6672 | {
 | 
        
           |  |  | 6673 | 	if ( m_lGlobals.Empty() )
 | 
        
           |  |  | 6674 | 		return; // no global settings
 | 
        
           |  |  | 6675 |   | 
        
           |  |  | 6676 | 	CyStringList globals;
 | 
        
           |  |  | 6677 | 	if ( ReadGlobals(globals) )
 | 
        
           |  |  | 6678 | 	{
 | 
        
           |  |  | 6679 | 		// apply out settings
 | 
        
           |  |  | 6680 | 		for ( SStringList *str = m_lGlobals.Head(); str; str = str->next )
 | 
        
           |  |  | 6681 | 		{
 | 
        
           |  |  | 6682 | 			SStringList *found = globals.FindString(str->str);
 | 
        
           |  |  | 6683 | 			if ( found )
 | 
        
           |  |  | 6684 | 				found->data = str->data;
 | 
        
           |  |  | 6685 | 		}
 | 
        
           |  |  | 6686 |   | 
        
           |  |  | 6687 | 		// now write it
 | 
        
           |  |  | 6688 | 		CyStringList writeList;
 | 
        
           |  |  | 6689 | 		for ( SStringList *str = globals.Head(); str; str = str->next )
 | 
        
           |  |  | 6690 | 			writeList.PushBack(str->str + ";" + str->data + ";");
 | 
        
           |  |  | 6691 |   | 
        
           |  |  | 6692 | 		// finally, write the file
 | 
        
           |  |  | 6693 | 		writeList.PushFront(CyString::Number(writeList.Count()) + "; /globals amount", "");
 | 
        
           |  |  | 6694 | 		writeList.PushFront(CyString("// Globals file, created by SPK Libraries V") + CyString::CreateFromFloat(GetLibraryVersion(), 2), "");
 | 
        
           |  |  | 6695 |   | 
        
           |  |  | 6696 | 		CFileIO WriteFile(m_sTempDir + "/Globals.txt");
 | 
        
           |  |  | 6697 | 		if ( WriteFile.WriteFile(&writeList) )
 | 
        
           |  |  | 6698 | 		{
 | 
        
           |  |  | 6699 | 			this->PackFile(&WriteFile, "types/Globals.pck");
 | 
        
           |  |  | 6700 | 			WriteFile.Remove();
 | 
        
           |  |  | 6701 | 		}
 | 
        
           |  |  | 6702 | 	}
 | 
        
           |  |  | 6703 | }
 | 
        
           |  |  | 6704 |   | 
        
           |  |  | 6705 | void CPackages::CreateTShips()
 | 
        
           |  |  | 6706 | {
 | 
        
           |  |  | 6707 | 	// no ships ?
 | 
        
           |  |  | 6708 | 	if ( m_lGameShips.empty() )
 | 
        
           |  |  | 6709 | 		return;
 | 
        
           |  |  | 6710 |   | 
        
           |  |  | 6711 | 	// get the cockpit list to match with ships turrets
 | 
        
           |  |  | 6712 | 	CyStringList Cockpits;
 | 
        
           |  |  | 6713 | 	CyStringList *cockpitList = this->CreateCockpits();
 | 
        
           |  |  | 6714 | 	if ( cockpitList )
 | 
        
           |  |  | 6715 | 	{
 | 
        
           |  |  | 6716 | 		for ( SStringList *str = cockpitList->Head(); str; str = str->next )
 | 
        
           |  |  | 6717 | 		{
 | 
        
           |  |  | 6718 | 			CyString id = str->str.GetToken(";", 19, 19);
 | 
        
           |  |  | 6719 | 			Cockpits.PushBack(id);
 | 
        
           |  |  | 6720 | 		}
 | 
        
           |  |  | 6721 |   | 
        
           |  |  | 6722 | 		delete cockpitList;
 | 
        
           |  |  | 6723 | 	}
 | 
        
           |  |  | 6724 |   | 
        
           |  |  | 6725 | 	CLinkList<SGameShip> shipOverrides;
 | 
        
           |  |  | 6726 | 	for ( CListNode<SGameShip> *node = m_lGameShips.Front(); node; node = node->next() )
 | 
        
           |  |  | 6727 | 	{
 | 
        
           |  |  | 6728 | 		if ( node->Data()->iType != WARETYPE_ADDED || !node->Data()->pPackage )
 | 
        
           |  |  | 6729 | 			continue;		
 | 
        
           |  |  | 6730 | 		if ( !node->Data()->pPackage->IsExistingShip() )
 | 
        
           |  |  | 6731 | 			continue;
 | 
        
           |  |  | 6732 | 		shipOverrides.push_back(node->Data());
 | 
        
           |  |  | 6733 | 	}
 | 
        
           |  |  | 6734 |   | 
        
           |  |  | 6735 | 	// read the existing tships file
 | 
        
           |  |  | 6736 | 	int e = ExtractGameFile("types/TShips.pck", m_sTempDir + "/TShips.txt");
 | 
        
           |  |  | 6737 | 	if ( e )
 | 
        
           |  |  | 6738 | 	{
 | 
        
           |  |  | 6739 | 		int fileType = 51;
 | 
        
           |  |  | 6740 | 		CyStringList tshipsList;
 | 
        
           |  |  | 6741 |   | 
        
           |  |  | 6742 | 		// if we have no buffer, lets create one
 | 
        
           |  |  | 6743 | 		CFileIO File;
 | 
        
           |  |  | 6744 | 		if ( File.Open((e == -1) ? "TShips.txt" : m_sTempDir + "/TShips.txt") )
 | 
        
           |  |  | 6745 | 		{
 | 
        
           |  |  | 6746 | 			int shiptext = SHIPSTARTTEXT;
 | 
        
           |  |  | 6747 |   | 
        
           |  |  | 6748 | 			std::vector<CyString> *lines = File.ReadLines();
 | 
        
           |  |  | 6749 | 			if ( lines )
 | 
        
           |  |  | 6750 | 			{
 | 
        
           |  |  | 6751 | 				int count = -1;
 | 
        
           |  |  | 6752 | 				for ( int j = 0; j < (int)lines->size(); j++ )
 | 
        
           |  |  | 6753 | 				{
 | 
        
           |  |  | 6754 | 					CyString line(lines->at(j));
 | 
        
           |  |  | 6755 | 					if ( line[0] == '/' )
 | 
        
           |  |  | 6756 | 						continue;
 | 
        
           |  |  | 6757 | 					line.RemoveChar('\r');
 | 
        
           |  |  | 6758 | 					line.RemoveChar(9);
 | 
        
           |  |  | 6759 | 					line = line.RemoveFirstSpace();
 | 
        
           |  |  | 6760 | 					line = line.RemoveEndSpace();
 | 
        
           |  |  | 6761 | 					if ( line.Empty() )
 | 
        
           |  |  | 6762 | 						continue;
 | 
        
           |  |  | 6763 |   | 
        
           |  |  | 6764 | 					if ( count == -1 )
 | 
        
           |  |  | 6765 | 					{
 | 
        
           |  |  | 6766 | 						fileType = line.GetToken(";", 1, 1).ToInt();
 | 
        
           |  |  | 6767 | 						count = line.GetToken(";", 2, 2).ToInt();
 | 
        
           |  |  | 6768 | 					}
 | 
        
           |  |  | 6769 | 					else
 | 
        
           |  |  | 6770 | 					{
 | 
        
           |  |  | 6771 | 						if ( line.Right(1) != ";" )
 | 
        
           |  |  | 6772 | 							line += ";";
 | 
        
           |  |  | 6773 |   | 
        
           |  |  | 6774 | 						// check for any ship overrides
 | 
        
           |  |  | 6775 | 						bool added = false;
 | 
        
           |  |  | 6776 | 						if ( !shipOverrides.empty() )
 | 
        
           |  |  | 6777 | 						{
 | 
        
           |  |  | 6778 | 							CShipData shipData;
 | 
        
           |  |  | 6779 | 							if ( shipData.ReadShipData(line) )
 | 
        
           |  |  | 6780 | 							{
 | 
        
           |  |  | 6781 | 								for ( CListNode<SGameShip> *node = shipOverrides.Front(); node; node = node->next() )
 | 
        
           |  |  | 6782 | 								{
 | 
        
           |  |  | 6783 | 									SGameShip *s = node->Data();
 | 
        
           | 14 | cycrow | 6784 | 									if ( !s->pPackage->GetShipID().Compare(shipData.sID.ToString()) )
 | 
        
           | 1 | cycrow | 6785 | 										continue;
 | 
        
           |  |  | 6786 | 									s->iText = shiptext;
 | 
        
           |  |  | 6787 | 									if ( !s->pPackage->GetOriginalDescription() )
 | 
        
           |  |  | 6788 | 										shiptext += 2;
 | 
        
           |  |  | 6789 | 									s->iPos = tshipsList.Count();
 | 
        
           |  |  | 6790 | 									added = true;
 | 
        
           |  |  | 6791 | 									tshipsList.PushBack(s->pPackage->FormatShipData(&Cockpits, &s->iText, m_iGame));
 | 
        
           |  |  | 6792 | 									shipOverrides.remove(node);
 | 
        
           |  |  | 6793 | 									break;
 | 
        
           |  |  | 6794 | 								}
 | 
        
           |  |  | 6795 | 							}
 | 
        
           |  |  | 6796 | 						}
 | 
        
           |  |  | 6797 |   | 
        
           |  |  | 6798 | 						if ( !added )
 | 
        
           |  |  | 6799 | 							tshipsList.PushBack(line);
 | 
        
           |  |  | 6800 | 						--count;
 | 
        
           |  |  | 6801 | 						if ( count < 0 )
 | 
        
           |  |  | 6802 | 							break;
 | 
        
           |  |  | 6803 | 					}
 | 
        
           |  |  | 6804 | 				}
 | 
        
           |  |  | 6805 |   | 
        
           |  |  | 6806 | 				delete lines;
 | 
        
           |  |  | 6807 |   | 
        
           |  |  | 6808 | 			}
 | 
        
           |  |  | 6809 |   | 
        
           |  |  | 6810 | 			File.Remove();
 | 
        
           |  |  | 6811 |   | 
        
           |  |  | 6812 | 			// assign the ship buffer
 | 
        
           |  |  | 6813 | 			if ( !m_iShipBuffer )
 | 
        
           |  |  | 6814 | 				m_iShipBuffer = tshipsList.Count() + 15;
 | 
        
           |  |  | 6815 | 			// there seems to be too many additional entries, we have no choise but to change the buffer
 | 
        
           |  |  | 6816 | 			else if ( m_iShipBuffer <= tshipsList.Count() )
 | 
        
           |  |  | 6817 | 				m_iShipBuffer = tshipsList.Count() + 15;
 | 
        
           |  |  | 6818 |   | 
        
           |  |  | 6819 | 			CyString bufferStart;
 | 
        
           |  |  | 6820 | 			if ( m_iGame == GAME_X3 )
 | 
        
           |  |  | 6821 | 				bufferStart = "0;0;0;0;0;2;499999;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0.049988;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;4;1;0;0;0;0;0;0;2092;1;1;-1;0;0;1;1;0;1;1;1;0;0;0;;-1;0;0;0;0;0;0;0;0;0;";
 | 
        
           |  |  | 6822 | 			else
 | 
        
           |  |  | 6823 | 				bufferStart = "0;0;0;0;0;SG_SH_M5;499999;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0.049988;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;4;1;0;0;0;0;0;0;OBJ_BEACON;1;1;-1;0;0;1;1;0;1;1;1;0;0;0;;-1;0;0;0;0;0;0;0;0;0;";
 | 
        
           |  |  | 6824 | 			// add the buffers now
 | 
        
           |  |  | 6825 | 			for ( int i = tshipsList.Count(); i < m_iShipBuffer; i++ )
 | 
        
           |  |  | 6826 | 				tshipsList.PushBack(bufferStart + "SHIP_BUFFER;");
 | 
        
           |  |  | 6827 |   | 
        
           |  |  | 6828 | 			// now lets add our tships line
 | 
        
           |  |  | 6829 | 			for ( CListNode<SGameShip> *node = m_lGameShips.Front(); node; node = node->next() )
 | 
        
           |  |  | 6830 | 			{
 | 
        
           |  |  | 6831 | 				SGameShip *s = node->Data();
 | 
        
           |  |  | 6832 | 				if ( s->pPackage && s->pPackage->IsExistingShip() )
 | 
        
           |  |  | 6833 | 					continue;
 | 
        
           |  |  | 6834 | 				s->iPos = tshipsList.Count();
 | 
        
           |  |  | 6835 | 				if ( s->iType == WARETYPE_ADDED && s->pPackage )
 | 
        
           |  |  | 6836 | 				{
 | 
        
           |  |  | 6837 | 					s->iText = shiptext;
 | 
        
           |  |  | 6838 | 					if ( !s->pPackage->GetOriginalDescription() )
 | 
        
           |  |  | 6839 | 						shiptext += 2;
 | 
        
           |  |  | 6840 |   | 
        
           |  |  | 6841 | 					tshipsList.PushBack(s->pPackage->FormatShipData(&Cockpits, &s->iText, m_iGame));
 | 
        
           |  |  | 6842 | 				}
 | 
        
           |  |  | 6843 | 				else if ( s->iType == WARETYPE_DELETED )
 | 
        
           |  |  | 6844 | 					tshipsList.PushBack(bufferStart + "SHIP_DELETED;");
 | 
        
           |  |  | 6845 | 				else if ( s->iType == WARETYPE_DISABLED )
 | 
        
           |  |  | 6846 | 					tshipsList.PushBack(bufferStart + "SHIP_DISABLED;");
 | 
        
           |  |  | 6847 | 				else
 | 
        
           |  |  | 6848 | 					tshipsList.PushBack(bufferStart + "SHIP_SPACER;");
 | 
        
           |  |  | 6849 | 			}
 | 
        
           |  |  | 6850 |   | 
        
           |  |  | 6851 | 			// finally, write the file
 | 
        
           |  |  | 6852 | 			tshipsList.PushFront(CyString::Number(fileType) + ";" + CyString::Number(tshipsList.Count()) + ";", "");
 | 
        
           |  |  | 6853 | 			tshipsList.PushFront(CyString("// TShips file, created by SPK Libraries V") + CyString::CreateFromFloat(GetLibraryVersion(), 2), "");
 | 
        
           |  |  | 6854 |   | 
        
           |  |  | 6855 | 			CFileIO WriteFile(m_sTempDir + "/TShips.txt");
 | 
        
           |  |  | 6856 | 			if ( WriteFile.WriteFile(&tshipsList) )
 | 
        
           |  |  | 6857 | 			{
 | 
        
           |  |  | 6858 | 				this->PackFile(&WriteFile, "types/TShips.pck");
 | 
        
           |  |  | 6859 | 				WriteFile.Remove();
 | 
        
           |  |  | 6860 | 			}
 | 
        
           |  |  | 6861 | 		}
 | 
        
           |  |  | 6862 | 	}
 | 
        
           |  |  | 6863 |   | 
        
           |  |  | 6864 | }
 | 
        
           |  |  | 6865 |   | 
        
           |  |  | 6866 | bool CPackages::PackFile(CyString filename)
 | 
        
           |  |  | 6867 | {
 | 
        
           |  |  | 6868 | 	// compress the file
 | 
        
           |  |  | 6869 | 	CFileIO File(filename);
 | 
        
           |  |  | 6870 | 	size_t fileSize;
 | 
        
           |  |  | 6871 | 	char *fileData = File.ReadToData(&fileSize);
 | 
        
           |  |  | 6872 |   | 
        
           |  |  | 6873 | 	if ( fileData && fileSize)
 | 
        
           |  |  | 6874 | 	{
 | 
        
           |  |  | 6875 | 		size_t newFileSize;
 | 
        
           |  |  | 6876 | 		unsigned char *pckData = PCKData((unsigned char *)fileData, fileSize, &newFileSize, true);
 | 
        
           |  |  | 6877 | 		if ( pckData )
 | 
        
           |  |  | 6878 | 		{
 | 
        
           |  |  | 6879 | 			CyString ext = "pck";
 | 
        
           |  |  | 6880 | 			if ( File.CheckFileExtension("bob") )
 | 
        
           |  |  | 6881 | 				ext = "pbb";
 | 
        
           |  |  | 6882 | 			else if ( File.CheckFileExtension("bod") )
 | 
        
           |  |  | 6883 | 				ext = "pbd";
 | 
        
           |  |  | 6884 | 			CFileIO pckFile(File.ChangeFileExtension(ext));
 | 
        
           |  |  | 6885 | 			if ( !CDirIO(pckFile.GetDir()).Exists() )
 | 
        
           |  |  | 6886 | 				CDirIO(pckFile.GetDir()).Create();
 | 
        
           |  |  | 6887 | 			pckFile.WriteData((char *)pckData, newFileSize);
 | 
        
           |  |  | 6888 | 			return true;
 | 
        
           |  |  | 6889 | 		}
 | 
        
           |  |  | 6890 | 	}
 | 
        
           |  |  | 6891 |   | 
        
           |  |  | 6892 | 	return false;
 | 
        
           |  |  | 6893 | }
 | 
        
           |  |  | 6894 |   | 
        
           |  |  | 6895 | bool CPackages::UnPackFile(CyString filename, bool checkxml)
 | 
        
           |  |  | 6896 | {
 | 
        
           |  |  | 6897 | 	// compress the file
 | 
        
           |  |  | 6898 | 	CFileIO File(filename);
 | 
        
           |  |  | 6899 | 	size_t fileSize;
 | 
        
           |  |  | 6900 | 	char *fileData = File.ReadToData(&fileSize);
 | 
        
           |  |  | 6901 |   | 
        
           |  |  | 6902 | 	if ( fileData && fileSize)
 | 
        
           |  |  | 6903 | 	{
 | 
        
           |  |  | 6904 | 		size_t newFileSize;
 | 
        
           |  |  | 6905 | 		unsigned char *pckData = UnPCKData((unsigned char *)fileData, fileSize, &newFileSize, true);
 | 
        
           |  |  | 6906 | 		if ( pckData )
 | 
        
           |  |  | 6907 | 		{
 | 
        
           |  |  | 6908 | 			CyString ext = "txt";
 | 
        
           |  |  | 6909 | 			if ( File.CheckFileExtension("pbb") )
 | 
        
           |  |  | 6910 | 				ext = "bob";
 | 
        
           |  |  | 6911 | 			else if ( File.CheckFileExtension("pbd") )
 | 
        
           |  |  | 6912 | 				ext = "bod";
 | 
        
           |  |  | 6913 | 			CFileIO pckFile(File.ChangeFileExtension(ext));
 | 
        
           |  |  | 6914 | 			if ( !CDirIO(pckFile.GetDir()).Exists() )
 | 
        
           |  |  | 6915 | 				CDirIO(pckFile.GetDir()).Create();
 | 
        
           |  |  | 6916 | 			pckFile.WriteData((char *)pckData, newFileSize);
 | 
        
           |  |  | 6917 |   | 
        
           |  |  | 6918 | 			// check for xml and rename
 | 
        
           |  |  | 6919 | 			if ( checkxml )
 | 
        
           |  |  | 6920 | 			{
 | 
        
           |  |  | 6921 | 				int readmaxlines = 20;
 | 
        
           |  |  | 6922 | 				bool isxml = false;
 | 
        
           |  |  | 6923 | 				do {
 | 
        
           |  |  | 6924 | 					CyString line = pckFile.ReadToEndLine(true);
 | 
        
           |  |  | 6925 | 					if ( line.IsIn("<language id=") )
 | 
        
           |  |  | 6926 | 					{
 | 
        
           |  |  | 6927 | 						isxml = true;
 | 
        
           |  |  | 6928 | 						break;
 | 
        
           |  |  | 6929 | 					}
 | 
        
           |  |  | 6930 | 					else if ( line.IsIn("<page id=") )
 | 
        
           |  |  | 6931 | 					{
 | 
        
           |  |  | 6932 | 						isxml = true;
 | 
        
           |  |  | 6933 | 						break;
 | 
        
           |  |  | 6934 | 					}
 | 
        
           |  |  | 6935 | 					else if ( line.IsIn("<?xml") || line.IsIn("<script>") )
 | 
        
           |  |  | 6936 | 					{
 | 
        
           |  |  | 6937 | 						isxml = true;
 | 
        
           |  |  | 6938 | 						break;
 | 
        
           |  |  | 6939 | 					}
 | 
        
           |  |  | 6940 | 					--readmaxlines;
 | 
        
           |  |  | 6941 | 					if ( readmaxlines <= 0 )
 | 
        
           |  |  | 6942 | 						break;
 | 
        
           |  |  | 6943 | 				} while (pckFile.IsOpened());
 | 
        
           |  |  | 6944 |   | 
        
           |  |  | 6945 | 				if ( pckFile.IsOpened() )
 | 
        
           |  |  | 6946 | 					pckFile.StopRead();
 | 
        
           |  |  | 6947 |   | 
        
           |  |  | 6948 | 				if ( isxml )
 | 
        
           |  |  | 6949 | 					pckFile.Rename(pckFile.ChangeFileExtension("xml"));
 | 
        
           |  |  | 6950 | 			}
 | 
        
           |  |  | 6951 |   | 
        
           |  |  | 6952 | 			return true;
 | 
        
           |  |  | 6953 | 		}
 | 
        
           |  |  | 6954 | 	}
 | 
        
           |  |  | 6955 |   | 
        
           |  |  | 6956 | 	return false;
 | 
        
           |  |  | 6957 | }
 | 
        
           |  |  | 6958 |   | 
        
           |  |  | 6959 | bool CPackages::PackFile(CFileIO *File, CyString filename)
 | 
        
           |  |  | 6960 | {
 | 
        
           |  |  | 6961 | 	filename = filename.FindReplace("\\", "/");
 | 
        
           |  |  | 6962 | 	if ( m_iGame == GAME_X3 )
 | 
        
           |  |  | 6963 | 	{
 | 
        
           |  |  | 6964 | 		CCatFile catFile;
 | 
        
           |  |  | 6965 | 		int error = catFile.Open(m_sCurrentDir + "/mods/PluginManager.cat", this->GetAddonDir(), CATREAD_CATDECRYPT, true);
 | 
        
           |  |  | 6966 | 		if ( error == CATERR_NONE || error == CATERR_CREATED )
 | 
        
           |  |  | 6967 | 		{
 | 
        
           |  |  | 6968 | 			// it it wrote ok, remove the old ones
 | 
        
           |  |  | 6969 | 			if ( !catFile.AppendFile(File->GetFullFilename(), filename, true, true) )
 | 
        
           |  |  | 6970 | 				return false;
 | 
        
           |  |  | 6971 | 			return true;
 | 
        
           |  |  | 6972 | 		}
 | 
        
           |  |  | 6973 | 	}
 | 
        
           |  |  | 6974 | 	else
 | 
        
           |  |  | 6975 | 	{
 | 
        
           |  |  | 6976 | 		// compress the file
 | 
        
           |  |  | 6977 | 		size_t fileSize;
 | 
        
           |  |  | 6978 | 		char *fileData = CFileIO(File->GetFullFilename()).ReadToData(&fileSize);
 | 
        
           |  |  | 6979 |   | 
        
           |  |  | 6980 | 		if ( fileData && fileSize)
 | 
        
           |  |  | 6981 | 		{
 | 
        
           |  |  | 6982 | 			size_t newFileSize;
 | 
        
           |  |  | 6983 | 			unsigned char *pckData = PCKData((unsigned char *)fileData, fileSize, &newFileSize, true);
 | 
        
           |  |  | 6984 | 			if ( pckData )
 | 
        
           |  |  | 6985 | 			{
 | 
        
           |  |  | 6986 | //				if ( !this->GetAddonDir().Empty() && CCatFile::IsAddonDir(filename) )
 | 
        
           |  |  | 6987 | //					filename = this->GetAddonDir() + "/" + filename;
 | 
        
           |  |  | 6988 | 				CFileIO pckFile(m_sCurrentDir + "/" + filename);
 | 
        
           |  |  | 6989 | 				if ( !CDirIO(pckFile.GetDir()).Exists() )
 | 
        
           |  |  | 6990 | 					CDirIO(pckFile.GetDir()).Create();
 | 
        
           |  |  | 6991 | 				pckFile.WriteData((char *)pckData, newFileSize);
 | 
        
           |  |  | 6992 | 				this->AddCreatedFile(pckFile.GetFullFilename());
 | 
        
           |  |  | 6993 | 				return true;
 | 
        
           |  |  | 6994 | 			}
 | 
        
           |  |  | 6995 | 		}
 | 
        
           |  |  | 6996 | 	}
 | 
        
           |  |  | 6997 |   | 
        
           |  |  | 6998 | 	return false;
 | 
        
           |  |  | 6999 | }
 | 
        
           |  |  | 7000 |   | 
        
           |  |  | 7001 | CyStringList *CPackages::CreateCockpits()
 | 
        
           |  |  | 7002 | {
 | 
        
           |  |  | 7003 | 	// first check we have any ships
 | 
        
           |  |  | 7004 | 	if ( m_lGameShips.empty() || !this->CountPackages(TYPE_XSP, true) )
 | 
        
           |  |  | 7005 | 		return NULL;
 | 
        
           |  |  | 7006 |   | 
        
           |  |  | 7007 | 	CyStringList *cockpitList = new CyStringList;
 | 
        
           |  |  | 7008 |   | 
        
           |  |  | 7009 | 	// now extract the existing cockpits
 | 
        
           |  |  | 7010 | 	int fileType = 51;
 | 
        
           |  |  | 7011 | 	int e = ExtractGameFile("types/TCockpits.pck", m_sTempDir + "/TCockpits.txt");
 | 
        
           |  |  | 7012 | 	if ( e )
 | 
        
           |  |  | 7013 | 	{
 | 
        
           |  |  | 7014 | 		// read the dummies
 | 
        
           |  |  | 7015 | 		CFileIO File;
 | 
        
           |  |  | 7016 | 		if ( File.Open((e == -1) ? "TCockpits.txt" : m_sTempDir + "/TCockpits.txt") )
 | 
        
           |  |  | 7017 | 		{
 | 
        
           |  |  | 7018 | 			CyStringList *lines = File.ReadLinesStr();
 | 
        
           |  |  | 7019 | 			if ( lines )
 | 
        
           |  |  | 7020 | 			{
 | 
        
           |  |  | 7021 | 				int count = -1;
 | 
        
           |  |  | 7022 | 				for ( SStringList *str = lines->Head(); str; str = str->next )
 | 
        
           |  |  | 7023 | 				{
 | 
        
           |  |  | 7024 | 					CyString line(str->str);
 | 
        
           |  |  | 7025 | 					line.RemoveChar('\r');
 | 
        
           |  |  | 7026 | 					line.RemoveChar(9);
 | 
        
           |  |  | 7027 | 					line = line.RemoveFirstSpace();
 | 
        
           |  |  | 7028 | 					line = line.RemoveEndSpace();
 | 
        
           |  |  | 7029 | 					if ( line.Empty() )
 | 
        
           |  |  | 7030 | 						continue;
 | 
        
           |  |  | 7031 | 					if ( line[0] == '/' )
 | 
        
           |  |  | 7032 | 						continue;
 | 
        
           |  |  | 7033 |   | 
        
           |  |  | 7034 | 					if ( count == -1 )
 | 
        
           |  |  | 7035 | 					{
 | 
        
           |  |  | 7036 | 						fileType = line.GetToken(";", 1, 1).ToInt();
 | 
        
           |  |  | 7037 | 						count = line.GetToken(";", 2, 2).ToInt();
 | 
        
           |  |  | 7038 | 					}
 | 
        
           |  |  | 7039 | 					else
 | 
        
           |  |  | 7040 | 					{
 | 
        
           |  |  | 7041 | 						while ( !line.Empty() )
 | 
        
           |  |  | 7042 | 						{
 | 
        
           |  |  | 7043 | 							CyString data = line.GetToken(";", 1, 19);
 | 
        
           |  |  | 7044 | 							cockpitList->PushBack(data + ";");
 | 
        
           |  |  | 7045 | 							line = line.DelToken(";", 1, 19);
 | 
        
           |  |  | 7046 |   | 
        
           |  |  | 7047 | 							--count;
 | 
        
           |  |  | 7048 | 							if ( count < 1 )
 | 
        
           |  |  | 7049 | 								break;
 | 
        
           |  |  | 7050 | 						}
 | 
        
           |  |  | 7051 | 					}
 | 
        
           |  |  | 7052 | 				}
 | 
        
           |  |  | 7053 |   | 
        
           |  |  | 7054 | 				delete lines;
 | 
        
           |  |  | 7055 | 			}
 | 
        
           |  |  | 7056 |   | 
        
           |  |  | 7057 | 			File.Remove();
 | 
        
           |  |  | 7058 | 		}
 | 
        
           |  |  | 7059 |   | 
        
           |  |  | 7060 | 		// now add the new ones
 | 
        
           |  |  | 7061 | 		for ( CListNode<SGameShip> *node = m_lGameShips.Front(); node; node = node->next() )
 | 
        
           |  |  | 7062 | 		{
 | 
        
           |  |  | 7063 | 			SGameShip *s = node->Data();
 | 
        
           |  |  | 7064 | 			if ( s->iType != WARETYPE_ADDED || !s->pPackage )
 | 
        
           |  |  | 7065 | 				continue;
 | 
        
           |  |  | 7066 |   | 
        
           |  |  | 7067 | 			if ( !s->pPackage->AnyCockpits() )
 | 
        
           |  |  | 7068 | 				continue;
 | 
        
           |  |  | 7069 |   | 
        
           |  |  | 7070 | 			bool found = false;
 | 
        
           |  |  | 7071 | 			for ( CListNode<SCockpit> *cn = s->pPackage->GetCockpits()->Front(); cn; cn = cn->next() )
 | 
        
           |  |  | 7072 | 			{
 | 
        
           |  |  | 7073 | 				bool foundEntry = false;
 | 
        
           |  |  | 7074 | 				CyString cockpitStr = cn->Data()->sCockpit;
 | 
        
           |  |  | 7075 | 				// search for matching game entry
 | 
        
           |  |  | 7076 | 				for ( CListNode<SWeaponMask> *wm = cn->Data()->lWeaponMask.Front(); wm; wm = wm->next() )
 | 
        
           |  |  | 7077 | 				{
 | 
        
           |  |  | 7078 | 					if ( wm->Data()->iGame == (m_iGame - 1) )
 | 
        
           |  |  | 7079 | 					{
 | 
        
           |  |  | 7080 | 						if ( wm->Data()->iMask != -1 )
 | 
        
           |  |  | 7081 | 							cockpitStr = cockpitStr.RepToken(";", 9, CyString::Number(wm->Data()->iMask));
 | 
        
           |  |  | 7082 | 						foundEntry = true;
 | 
        
           |  |  | 7083 | 						break;
 | 
        
           |  |  | 7084 | 					}
 | 
        
           |  |  | 7085 | 				}
 | 
        
           |  |  | 7086 | 				for ( SStringList *str = cockpitList->Head(); str; str = str->next )
 | 
        
           |  |  | 7087 | 				{
 | 
        
           |  |  | 7088 | 					if ( str->str.GetToken(";", 19, 19).Compare(cn->Data()->sCockpit.GetToken(";", 19, 19)) )
 | 
        
           |  |  | 7089 | 					{
 | 
        
           |  |  | 7090 | 						// only replace existing entry if we have sepeperate weapon masks set
 | 
        
           |  |  | 7091 | 						if ( foundEntry )
 | 
        
           |  |  | 7092 | 							str->str = cockpitStr;
 | 
        
           |  |  | 7093 | 						found = true;
 | 
        
           |  |  | 7094 | 						break;
 | 
        
           |  |  | 7095 | 					}
 | 
        
           |  |  | 7096 | 				}
 | 
        
           |  |  | 7097 |   | 
        
           |  |  | 7098 | 				if ( !found )
 | 
        
           |  |  | 7099 | 					cockpitList->PushBack(cockpitStr);
 | 
        
           |  |  | 7100 | 			}
 | 
        
           |  |  | 7101 | 		}
 | 
        
           |  |  | 7102 |   | 
        
           |  |  | 7103 | 		// finally, write the file
 | 
        
           |  |  | 7104 | 		cockpitList->PushFront(CyString::Number(fileType) + ";" + CyString::Number(cockpitList->Count()) + ";", "");
 | 
        
           |  |  | 7105 | 		cockpitList->PushFront(CyString("// TCockpits file, created by SPK Libraries V") + CyString::CreateFromFloat(GetLibraryVersion(), 2), "");
 | 
        
           |  |  | 7106 |   | 
        
           |  |  | 7107 | 		CFileIO WriteFile(m_sTempDir + "/TCockpits.txt");
 | 
        
           |  |  | 7108 | 		if ( WriteFile.WriteFile(cockpitList) )
 | 
        
           |  |  | 7109 | 		{
 | 
        
           |  |  | 7110 | 			this->PackFile(&WriteFile, "types\\TCockpits.pck");
 | 
        
           |  |  | 7111 | 			WriteFile.Remove();
 | 
        
           |  |  | 7112 | 		}
 | 
        
           |  |  | 7113 |   | 
        
           |  |  | 7114 | 		// remove those entrys
 | 
        
           |  |  | 7115 | 		cockpitList->PopFront();
 | 
        
           |  |  | 7116 | 		cockpitList->PopFront();
 | 
        
           |  |  | 7117 | 	}
 | 
        
           |  |  | 7118 |   | 
        
           |  |  | 7119 | 	return cockpitList;
 | 
        
           |  |  | 7120 | }
 | 
        
           |  |  | 7121 |   | 
        
           |  |  | 7122 | CBaseFile *CPackages::FindScriptByAuthor(CyString author, CBaseFile *prev)
 | 
        
           |  |  | 7123 | {
 | 
        
           |  |  | 7124 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 7125 | 	{
 | 
        
           |  |  | 7126 | 		CBaseFile *p = node->Data();
 | 
        
           |  |  | 7127 | 		if ( prev )
 | 
        
           |  |  | 7128 | 		{
 | 
        
           |  |  | 7129 | 			if ( p == prev )
 | 
        
           |  |  | 7130 | 				prev = NULL;
 | 
        
           |  |  | 7131 | 			continue;
 | 
        
           |  |  | 7132 | 		}
 | 
        
           |  |  | 7133 | 		if ( p->GetAuthor().Compare(author) )
 | 
        
           |  |  | 7134 | 			return p;
 | 
        
           |  |  | 7135 | 	}
 | 
        
           |  |  | 7136 |   | 
        
           |  |  | 7137 | 	return NULL;
 | 
        
           |  |  | 7138 | }
 | 
        
           |  |  | 7139 |   | 
        
           |  |  | 7140 | CBaseFile *CPackages::LoadPackagerScript(CyString filename, int compression, CyString (*askFunc)(CyString), CyStringList *malformedLines, CyStringList *unknownCommands, CyStringList *variables)
 | 
        
           |  |  | 7141 | {
 | 
        
           |  |  | 7142 | 	// check the file exists
 | 
        
           |  |  | 7143 | 	if ( !CFileIO(filename).Exists() )
 | 
        
           |  |  | 7144 | 		return NULL;
 | 
        
           |  |  | 7145 |   | 
        
           |  |  | 7146 | 	// read all the lines
 | 
        
           |  |  | 7147 | 	CFileIO File(filename);
 | 
        
           |  |  | 7148 | 	std::vector<CyString> *lines = File.ReadLines();
 | 
        
           |  |  | 7149 |   | 
        
           |  |  | 7150 | 	if ( !lines )
 | 
        
           |  |  | 7151 | 		return NULL;
 | 
        
           |  |  | 7152 |   | 
        
           |  |  | 7153 | 	CBaseFile *package = NULL;
 | 
        
           |  |  | 7154 |   | 
        
           |  |  | 7155 | 	// filter out blank lines and comments
 | 
        
           |  |  | 7156 | 	CyStringList fileData;
 | 
        
           |  |  | 7157 | 	for ( int i = 0; i < (int)lines->size(); i++ )
 | 
        
           |  |  | 7158 | 	{
 | 
        
           |  |  | 7159 | 		CyString line(lines->at(i));
 | 
        
           |  |  | 7160 |   | 
        
           |  |  | 7161 | 		// dont include empty lines (whitespace)
 | 
        
           |  |  | 7162 | 		if ( line.Empty() )
 | 
        
           |  |  | 7163 | 			continue;
 | 
        
           |  |  | 7164 |   | 
        
           |  |  | 7165 | 		// filter out any spaces, tabs in front
 | 
        
           |  |  | 7166 | 		line.RemoveChar('\t');
 | 
        
           |  |  | 7167 | 		line.RemoveChar('\r');
 | 
        
           |  |  | 7168 | 		CyString linenospace = line;
 | 
        
           |  |  | 7169 | 		linenospace.RemoveFirstSpace();
 | 
        
           |  |  | 7170 | 		if ( linenospace.Empty() )
 | 
        
           |  |  | 7171 | 			continue;
 | 
        
           |  |  | 7172 |   | 
        
           |  |  | 7173 | 		// check for any comments
 | 
        
           |  |  | 7174 | 		if ( linenospace.Left(2) == "//" )
 | 
        
           |  |  | 7175 | 			continue;
 | 
        
           |  |  | 7176 | 		if ( linenospace[0] == '#' )
 | 
        
           |  |  | 7177 | 			continue;
 | 
        
           |  |  | 7178 |   | 
        
           |  |  | 7179 | 		// all commands start with a keyword followed by a colon, if one doesn't exist, it cant be a valid line
 | 
        
           |  |  | 7180 | 		if ( !line.IsIn(':') )
 | 
        
           |  |  | 7181 | 		{
 | 
        
           |  |  | 7182 | 			// there are some exeptions, and these are one word entrys only
 | 
        
           |  |  | 7183 | 			line.RemoveEndSpace();
 | 
        
           |  |  | 7184 | 			if ( line.IsIn(" ") )
 | 
        
           |  |  | 7185 | 			{
 | 
        
           |  |  | 7186 | 				if ( malformedLines )
 | 
        
           |  |  | 7187 | 					malformedLines->PushBack(line, CyString::Number(i));
 | 
        
           |  |  | 7188 | 				continue;
 | 
        
           |  |  | 7189 | 			}
 | 
        
           |  |  | 7190 | 		}
 | 
        
           |  |  | 7191 |   | 
        
           |  |  | 7192 | 		// check for the type line
 | 
        
           |  |  | 7193 | 		if ( !package && line.GetToken(":", 1, 1).Compare("FileType") )
 | 
        
           |  |  | 7194 | 		{
 | 
        
           |  |  | 7195 | 			CyString sFileType = line.GetToken(":", 2).RemoveFirstSpace();
 | 
        
           |  |  | 7196 | 			if ( sFileType.Compare("Ship") )
 | 
        
           |  |  | 7197 | 				package = new CXspFile();
 | 
        
           |  |  | 7198 | 			else if ( sFileType.Compare("Script") )
 | 
        
           |  |  | 7199 | 				package = new CSpkFile();
 | 
        
           |  |  | 7200 | 			else if ( sFileType.Compare("Base") )
 | 
        
           |  |  | 7201 | 				package = new CBaseFile();
 | 
        
           |  |  | 7202 | 		}
 | 
        
           |  |  | 7203 |   | 
        
           |  |  | 7204 | 		fileData.PushBack(line, CyString::Number(i));
 | 
        
           |  |  | 7205 | 	}
 | 
        
           |  |  | 7206 |   | 
        
           |  |  | 7207 | 	delete lines;
 | 
        
           |  |  | 7208 |   | 
        
           |  |  | 7209 | 	// assume its a script if no type is set (all old versions are scripts)
 | 
        
           |  |  | 7210 | 	if ( !package )
 | 
        
           |  |  | 7211 | 		package = new CSpkFile();
 | 
        
           |  |  | 7212 |   | 
        
           |  |  | 7213 | 	if ( compression != -1 )
 | 
        
           |  |  | 7214 | 		package->SetDataCompression(compression);
 | 
        
           |  |  | 7215 |   | 
        
           |  |  | 7216 | 	CyString ftpaddr;
 | 
        
           |  |  | 7217 | 	CyString ftpuser;
 | 
        
           |  |  | 7218 | 	CyString ftppass;
 | 
        
           |  |  | 7219 | 	CyString ftpdir;
 | 
        
           |  |  | 7220 | 	// now lets read the rest of the day
 | 
        
           |  |  | 7221 | 	CyStringList listVaribles;
 | 
        
           |  |  | 7222 | 	for ( SStringList *strNode = fileData.Head(); strNode; strNode = strNode->next )
 | 
        
           |  |  | 7223 | 	{
 | 
        
           |  |  | 7224 | 		CyString first = strNode->str.GetToken(":", 1, 1);
 | 
        
           |  |  | 7225 | 		CyString rest = strNode->str.GetToken(":", 2).RemoveFirstSpace();
 | 
        
           |  |  | 7226 |   | 
        
           |  |  | 7227 | 		if ( first.Compare("Varible") || first.Compare("Variable") )
 | 
        
           |  |  | 7228 | 			listVaribles.PushBack(rest.GetToken(" ", 1, 1), rest.GetToken(" ", 2), true);
 | 
        
           |  |  | 7229 | 		else
 | 
        
           |  |  | 7230 | 		{
 | 
        
           |  |  | 7231 | 			// replace variables
 | 
        
           |  |  | 7232 | 			if ( rest.IsIn("$") )
 | 
        
           |  |  | 7233 | 			{
 | 
        
           |  |  | 7234 | 				for ( SStringList *strVar = listVaribles.Head(); strVar; strVar = strVar->next )
 | 
        
           |  |  | 7235 | 				{
 | 
        
           |  |  | 7236 | 					if ( rest.IsIn(strVar->str) )
 | 
        
           |  |  | 7237 | 						rest.FindReplace(strVar->str, strVar->data);
 | 
        
           |  |  | 7238 | 				}
 | 
        
           |  |  | 7239 |   | 
        
           |  |  | 7240 | 				if ( variables )
 | 
        
           |  |  | 7241 | 				{
 | 
        
           |  |  | 7242 | 					for ( SStringList *strVar = variables->Head(); strVar; strVar = strVar->next )
 | 
        
           |  |  | 7243 | 					{
 | 
        
           |  |  | 7244 | 						if ( rest.IsIn(strVar->str) )
 | 
        
           |  |  | 7245 | 							rest.FindReplace(strVar->str, strVar->data);
 | 
        
           |  |  | 7246 | 					}
 | 
        
           |  |  | 7247 | 				}
 | 
        
           |  |  | 7248 | 			}
 | 
        
           |  |  | 7249 |   | 
        
           |  |  | 7250 | 			//check for the built in varibles
 | 
        
           |  |  | 7251 | 			if ( rest.IsIn("$ASK") )
 | 
        
           |  |  | 7252 | 			{
 | 
        
           |  |  | 7253 | 				CyString replace = "$ASK";
 | 
        
           |  |  | 7254 | 				CyString result;
 | 
        
           |  |  | 7255 |   | 
        
           |  |  | 7256 | 				if ( askFunc )
 | 
        
           |  |  | 7257 | 					result = askFunc(first);
 | 
        
           |  |  | 7258 |   | 
        
           |  |  | 7259 | 				if ( rest.IsIn("$ASK(") )
 | 
        
           |  |  | 7260 | 				{
 | 
        
           |  |  | 7261 | 					replace = rest.GetToken("$ASK(", 2).GetToken(")", 1, 1);
 | 
        
           |  |  | 7262 | 					if ( result.Empty() )
 | 
        
           |  |  | 7263 | 						result = replace;
 | 
        
           |  |  | 7264 | 					replace = CyString("$ASK(") + replace + ")";
 | 
        
           |  |  | 7265 | 				}
 | 
        
           |  |  | 7266 |   | 
        
           |  |  | 7267 |   | 
        
           |  |  | 7268 | 				if ( !result.Empty() )
 | 
        
           |  |  | 7269 | 					rest.FindReplace(replace, result);
 | 
        
           |  |  | 7270 | 			}
 | 
        
           |  |  | 7271 | 			// todays date
 | 
        
           |  |  | 7272 | 			if ( rest.IsIn("$DATE") )
 | 
        
           |  |  | 7273 | 			{
 | 
        
           |  |  | 7274 | 				time_t now;
 | 
        
           |  |  | 7275 | 				time(&now);
 | 
        
           |  |  | 7276 | 				struct tm *timeinfo = localtime(&now);
 | 
        
           |  |  | 7277 | 				CyString result = CyString::Number(timeinfo->tm_mday) + "." + CyString::Number(timeinfo->tm_mon + 1) + "." + CyString::Number(timeinfo->tm_year + 1900);
 | 
        
           |  |  | 7278 | 				if ( !result.Empty() )
 | 
        
           |  |  | 7279 | 					rest.FindReplace("$DATE", result);
 | 
        
           |  |  | 7280 | 			}
 | 
        
           |  |  | 7281 | 			// mydocuments
 | 
        
           |  |  | 7282 | 			if ( rest.IsIn("$MYDOCUMENTS") )
 | 
        
           |  |  | 7283 | 			{
 | 
        
           |  |  | 7284 | 				if ( !m_sMyDoc.Empty() )
 | 
        
           |  |  | 7285 | 					rest.FindReplace("$MYDOCUMENTS", m_sMyDoc);
 | 
        
           |  |  | 7286 | 			}
 | 
        
           |  |  | 7287 |   | 
        
           |  |  | 7288 | 			// current path
 | 
        
           |  |  | 7289 | 			if ( rest.IsIn("$PATH") )
 | 
        
           |  |  | 7290 | 			{
 | 
        
           |  |  | 7291 | 				CyString currentDir = CFileIO(filename).GetDir();
 | 
        
           |  |  | 7292 | 				if ( !currentDir.Empty() )
 | 
        
           |  |  | 7293 | 					rest.FindReplace("$PATH", currentDir);
 | 
        
           |  |  | 7294 | 			}
 | 
        
           |  |  | 7295 |   | 
        
           |  |  | 7296 | 			// now parse the rest of the values
 | 
        
           |  |  | 7297 | 			if ( first.Compare("FtpUpload") )
 | 
        
           |  |  | 7298 | 				ftpaddr = rest.GetToken(" ", 1, 1) + ":" + rest.GetToken(" ", 2, 2);
 | 
        
           |  |  | 7299 | 			else if ( first.Compare("FtpUser") )
 | 
        
           |  |  | 7300 | 				ftpuser = rest;
 | 
        
           |  |  | 7301 | 			else if ( first.Compare("FtpPass") )
 | 
        
           |  |  | 7302 | 				ftppass = rest;
 | 
        
           |  |  | 7303 | 			else if ( first.Compare("FtpDir") )
 | 
        
           |  |  | 7304 | 				ftpdir = rest;
 | 
        
           | 14 | cycrow | 7305 | 			else if ( !package->LoadPackageData(first.ToString(), rest.ToString()) )
 | 
        
           | 1 | cycrow | 7306 | 			{
 | 
        
           |  |  | 7307 | 				if ( unknownCommands )
 | 
        
           |  |  | 7308 | 					unknownCommands->PushBack(first, rest);
 | 
        
           |  |  | 7309 | 			}
 | 
        
           |  |  | 7310 | 		}
 | 
        
           |  |  | 7311 | 	}
 | 
        
           |  |  | 7312 |   | 
        
           |  |  | 7313 | 	if ( package->GetFilename().Empty() )
 | 
        
           |  |  | 7314 | 		package->LoadPackageData("AutoSave", "$AUTOSAVE");
 | 
        
           |  |  | 7315 |   | 
        
           |  |  | 7316 | 	if ( !ftpaddr.Empty() )
 | 
        
           |  |  | 7317 | 	{
 | 
        
           |  |  | 7318 | 		if ( !ftpuser.Empty() )
 | 
        
           |  |  | 7319 | 		{
 | 
        
           |  |  | 7320 | 			if ( !ftppass.Empty() )
 | 
        
           |  |  | 7321 | 				ftpaddr = ftpuser + ":" + ftppass + "@" + ftpaddr;
 | 
        
           |  |  | 7322 | 			else
 | 
        
           |  |  | 7323 | 				ftpaddr = ftpuser + "@" + ftpaddr;
 | 
        
           |  |  | 7324 | 		}
 | 
        
           |  |  | 7325 |   | 
        
           |  |  | 7326 | 		if ( !ftpdir.Empty() )
 | 
        
           |  |  | 7327 | 			ftpaddr += ftpdir;
 | 
        
           |  |  | 7328 |   | 
        
           |  |  | 7329 | 		package->SetFtpAddr(ftpaddr);
 | 
        
           |  |  | 7330 | 	}
 | 
        
           |  |  | 7331 |   | 
        
           |  |  | 7332 | 	return package;
 | 
        
           |  |  | 7333 | }
 | 
        
           |  |  | 7334 |   | 
        
           |  |  | 7335 | CyString CPackages::GetLanguageName()
 | 
        
           |  |  | 7336 | {
 | 
        
           |  |  | 7337 | 	return CPackages::ConvertLanguage(m_iLanguage);
 | 
        
           |  |  | 7338 | }
 | 
        
           |  |  | 7339 |   | 
        
           |  |  | 7340 | CyString CPackages::ConvertLanguage(int lang)
 | 
        
           |  |  | 7341 | {
 | 
        
           |  |  | 7342 | 	switch ( lang )
 | 
        
           |  |  | 7343 | 	{
 | 
        
           |  |  | 7344 | 		case 44:
 | 
        
           |  |  | 7345 | 			return "English";
 | 
        
           |  |  | 7346 | 		case 49:
 | 
        
           |  |  | 7347 | 			return "German";
 | 
        
           |  |  | 7348 | 		case 7:
 | 
        
           |  |  | 7349 | 			return "Russian";
 | 
        
           |  |  | 7350 | 		case 33:
 | 
        
           |  |  | 7351 | 			return "French";
 | 
        
           |  |  | 7352 | 		case 30:
 | 
        
           |  |  | 7353 | 			return "Greek";
 | 
        
           |  |  | 7354 | 		case 31:
 | 
        
           |  |  | 7355 | 			return "Dutch";
 | 
        
           |  |  | 7356 | 		case 32:
 | 
        
           |  |  | 7357 | 			return "Belgian";
 | 
        
           |  |  | 7358 | 		case 34:
 | 
        
           |  |  | 7359 | 			return "Spanish";
 | 
        
           |  |  | 7360 | 		case 36:
 | 
        
           |  |  | 7361 | 			return "Hungarian";
 | 
        
           |  |  | 7362 | 		case 39:
 | 
        
           |  |  | 7363 | 			return "Italian";
 | 
        
           |  |  | 7364 | 		case 40:
 | 
        
           |  |  | 7365 | 			return "Romanian";
 | 
        
           |  |  | 7366 | 		case 41:
 | 
        
           |  |  | 7367 | 			return "Swiss";
 | 
        
           |  |  | 7368 | 		case 42:
 | 
        
           |  |  | 7369 | 			return "Czech";
 | 
        
           |  |  | 7370 | 		case 43:
 | 
        
           |  |  | 7371 | 			return "Austrian";
 | 
        
           |  |  | 7372 | 		case 45:
 | 
        
           |  |  | 7373 | 			return "Danish";
 | 
        
           |  |  | 7374 | 		case 46:
 | 
        
           |  |  | 7375 | 			return "Swedish";
 | 
        
           |  |  | 7376 | 		case 47:
 | 
        
           |  |  | 7377 | 			return "Norweigen";
 | 
        
           |  |  | 7378 | 		case 48:
 | 
        
           |  |  | 7379 | 			return "Polish";
 | 
        
           |  |  | 7380 | 	}
 | 
        
           |  |  | 7381 |   | 
        
           |  |  | 7382 | 	return CyString::Number(lang);
 | 
        
           |  |  | 7383 | }
 | 
        
           |  |  | 7384 |   | 
        
           |  |  | 7385 | bool CPackages::CheckAccessRights(CyString dir)
 | 
        
           |  |  | 7386 | {
 | 
        
           |  |  | 7387 | 	if ( dir.Empty() )
 | 
        
           |  |  | 7388 | 		dir = m_sCurrentDir;
 | 
        
           |  |  | 7389 |   | 
        
           |  |  | 7390 | 	// write a file, then read the contents
 | 
        
           |  |  | 7391 | 	CFileIO File(dir + "/accessrightscheck.dat");
 | 
        
           |  |  | 7392 |   | 
        
           |  |  | 7393 | 	// check if file exists and remove it
 | 
        
           |  |  | 7394 | 	if ( File.Exists() )
 | 
        
           |  |  | 7395 | 	{
 | 
        
           |  |  | 7396 | 		// if we cant remove it, we dont have enough rights
 | 
        
           |  |  | 7397 | 		if ( !File.Remove() )
 | 
        
           |  |  | 7398 | 			return false;
 | 
        
           |  |  | 7399 |   | 
        
           |  |  | 7400 | 		// if its still there, we dont have enough rights
 | 
        
           |  |  | 7401 | 		if ( File.Exists() )
 | 
        
           |  |  | 7402 | 			return false;
 | 
        
           |  |  | 7403 | 	}
 | 
        
           |  |  | 7404 |   | 
        
           |  |  | 7405 | 	// now create the file
 | 
        
           |  |  | 7406 | 	if ( !File.WriteString("testing access rights") )
 | 
        
           |  |  | 7407 | 		return false;
 | 
        
           |  |  | 7408 |   | 
        
           |  |  | 7409 | 	// now check it exists
 | 
        
           |  |  | 7410 | 	if ( !File.Exists() )
 | 
        
           |  |  | 7411 | 		return false;
 | 
        
           |  |  | 7412 |   | 
        
           |  |  | 7413 | 	// now read the file for the correct contents
 | 
        
           |  |  | 7414 | 	CyStringList *lines = File.ReadLinesStr();
 | 
        
           |  |  | 7415 | 	if ( !lines )
 | 
        
           |  |  | 7416 | 		return false;
 | 
        
           |  |  | 7417 |   | 
        
           |  |  | 7418 | 	// check that one of the lines is correct
 | 
        
           |  |  | 7419 | 	for ( SStringList *s = lines->Head(); s; s = s->next )
 | 
        
           |  |  | 7420 | 	{
 | 
        
           |  |  | 7421 | 		if ( s->str == "testing access rights" )
 | 
        
           |  |  | 7422 | 		{
 | 
        
           |  |  | 7423 | 			delete lines;
 | 
        
           |  |  | 7424 | 			return true;
 | 
        
           |  |  | 7425 | 		}
 | 
        
           |  |  | 7426 | 	}
 | 
        
           |  |  | 7427 |   | 
        
           |  |  | 7428 | 	delete lines;
 | 
        
           |  |  | 7429 |   | 
        
           |  |  | 7430 | 	return false;
 | 
        
           |  |  | 7431 | }
 | 
        
           |  |  | 7432 |   | 
        
           |  |  | 7433 | bool CPackages::LoadShipData(CyString file, CyStringList *list)
 | 
        
           |  |  | 7434 | {
 | 
        
           |  |  | 7435 | 	CFileIO File;
 | 
        
           |  |  | 7436 | 	bool deleteFile = false;
 | 
        
           |  |  | 7437 |   | 
        
           |  |  | 7438 | 	// load from cat file
 | 
        
           |  |  | 7439 | 	if ( CFileIO(file).CheckFileExtension("cat") )
 | 
        
           |  |  | 7440 | 	{
 | 
        
           |  |  | 7441 | 		CCatFile cat;
 | 
        
           |  |  | 7442 | 		if ( cat.Open(file, this->GetAddonDir(), CATREAD_CATDECRYPT, false) != CATERR_NONE )
 | 
        
           |  |  | 7443 | 			return false;
 | 
        
           |  |  | 7444 |   | 
        
           |  |  | 7445 | 		if ( !cat.ExtractFile("types\\TShips.pck", m_sTempDir + "/tships.txt") )
 | 
        
           |  |  | 7446 | 			return false;
 | 
        
           |  |  | 7447 |   | 
        
           |  |  | 7448 | 		File.Open(m_sTempDir + "/tships.txt");
 | 
        
           |  |  | 7449 | 		deleteFile = true;
 | 
        
           |  |  | 7450 | 	}
 | 
        
           |  |  | 7451 | 	// otherwise its a normal file
 | 
        
           |  |  | 7452 | 	else if ( CFileIO(file).CheckFileExtension("pck") )
 | 
        
           |  |  | 7453 | 	{
 | 
        
           |  |  | 7454 | 		C_File f(file);
 | 
        
           |  |  | 7455 | 		if ( !f.ReadFromFile() )
 | 
        
           |  |  | 7456 | 			return false;
 | 
        
           |  |  | 7457 | 		f.UnPCKFile();
 | 
        
           |  |  | 7458 |   | 
        
           |  |  | 7459 | 		f.SetFilename(m_sTempDir + "/tships.txt");
 | 
        
           |  |  | 7460 | 		if ( !f.WriteFilePointer() )
 | 
        
           |  |  | 7461 | 			return false;
 | 
        
           |  |  | 7462 |   | 
        
           |  |  | 7463 | 		File.Open(m_sTempDir + "/tships.txt");
 | 
        
           |  |  | 7464 | 		deleteFile = true;
 | 
        
           |  |  | 7465 | 	}
 | 
        
           |  |  | 7466 | 	else
 | 
        
           |  |  | 7467 | 		File.Open(file);
 | 
        
           |  |  | 7468 |   | 
        
           |  |  | 7469 | 	if ( !File.Exists() )
 | 
        
           |  |  | 7470 | 		return false;
 | 
        
           |  |  | 7471 |   | 
        
           |  |  | 7472 | 	bool ret = false;
 | 
        
           |  |  | 7473 | 	CyStringList *lines = File.ReadLinesStr();
 | 
        
           |  |  | 7474 | 	if ( lines )
 | 
        
           |  |  | 7475 | 	{
 | 
        
           |  |  | 7476 | 		bool readFirst = false;
 | 
        
           |  |  | 7477 | 		for ( SStringList *str = lines->Head(); str; str = str->next )
 | 
        
           |  |  | 7478 | 		{
 | 
        
           |  |  | 7479 | 			if ( str->str.Empty() )
 | 
        
           |  |  | 7480 | 				continue;
 | 
        
           |  |  | 7481 | 			str->str.RemoveChar('\r');
 | 
        
           |  |  | 7482 | 			str->str.RemoveChar(9);
 | 
        
           |  |  | 7483 | 			str->str.RemoveFirstSpace();
 | 
        
           |  |  | 7484 | 			if ( str->str.Empty() )
 | 
        
           |  |  | 7485 | 				continue;
 | 
        
           |  |  | 7486 | 			if ( str->str[0] == '/' || str->str[0] == '#' )
 | 
        
           |  |  | 7487 | 				continue;
 | 
        
           |  |  | 7488 |   | 
        
           |  |  | 7489 | 			if ( !readFirst )
 | 
        
           |  |  | 7490 | 				readFirst = true;
 | 
        
           |  |  | 7491 | 			else
 | 
        
           |  |  | 7492 | 			{
 | 
        
           |  |  | 7493 | 				CyString t = str->str.GetToken(";", -2);
 | 
        
           |  |  | 7494 | 				while ( t.Right(1) == ";" )
 | 
        
           |  |  | 7495 | 					t.Truncate((int)t.Length() - 1);
 | 
        
           |  |  | 7496 | 				list->PushBack(t, str->str);
 | 
        
           |  |  | 7497 | 			}
 | 
        
           |  |  | 7498 | 		}
 | 
        
           |  |  | 7499 |   | 
        
           |  |  | 7500 | 		delete lines;
 | 
        
           |  |  | 7501 | 		ret = true;
 | 
        
           |  |  | 7502 | 	}
 | 
        
           |  |  | 7503 |   | 
        
           |  |  | 7504 | 	if ( deleteFile )
 | 
        
           |  |  | 7505 | 		File.Remove();
 | 
        
           |  |  | 7506 |   | 
        
           |  |  | 7507 | 	return ret;
 | 
        
           |  |  | 7508 | }
 | 
        
           |  |  | 7509 |   | 
        
           |  |  | 7510 | CyString CPackages::ReadShipData(CyString file, CyString id)
 | 
        
           |  |  | 7511 | {
 | 
        
           |  |  | 7512 | 	CyStringList *list = this->LoadShipData(file);
 | 
        
           |  |  | 7513 | 	if ( !list )
 | 
        
           |  |  | 7514 | 		return NullString;
 | 
        
           |  |  | 7515 |   | 
        
           |  |  | 7516 | 	CShipData data;
 | 
        
           |  |  | 7517 | 	for ( SStringList *str = list->Head(); str; str = str->next )
 | 
        
           |  |  | 7518 | 	{
 | 
        
           |  |  | 7519 | 		if ( str->str.Compare(id) )
 | 
        
           |  |  | 7520 | 		{
 | 
        
           |  |  | 7521 | 			delete list;
 | 
        
           |  |  | 7522 | 			return str->data;
 | 
        
           |  |  | 7523 | 		}
 | 
        
           |  |  | 7524 | 	}
 | 
        
           |  |  | 7525 |   | 
        
           |  |  | 7526 | 	delete list;
 | 
        
           |  |  | 7527 | 	return NullString;
 | 
        
           |  |  | 7528 | }
 | 
        
           |  |  | 7529 |   | 
        
           |  |  | 7530 | CyStringList *CPackages::LoadShipData(CyString file)
 | 
        
           |  |  | 7531 | {
 | 
        
           |  |  | 7532 | 	CyStringList *list = new CyStringList;
 | 
        
           |  |  | 7533 | 	if ( this->LoadShipData(file, list) )
 | 
        
           |  |  | 7534 | 		return list;
 | 
        
           |  |  | 7535 |   | 
        
           |  |  | 7536 | 	delete list;
 | 
        
           |  |  | 7537 | 	return NULL;
 | 
        
           |  |  | 7538 | }
 | 
        
           |  |  | 7539 |   | 
        
           |  |  | 7540 | bool CPackages::ReadTextPage(CyString file, CyStringList *list, bool search, int page)
 | 
        
           |  |  | 7541 | {
 | 
        
           |  |  | 7542 | 	CFileIO File;
 | 
        
           |  |  | 7543 | 	bool deleteFile = false;
 | 
        
           |  |  | 7544 |   | 
        
           |  |  | 7545 | 	// read all text files from mod
 | 
        
           |  |  | 7546 | 	if ( CFileIO(file).CheckFileExtension("cat") )
 | 
        
           |  |  | 7547 | 	{
 | 
        
           |  |  | 7548 | 		bool done = false;
 | 
        
           |  |  | 7549 |   | 
        
           |  |  | 7550 | 		CCatFile cat;
 | 
        
           |  |  | 7551 | 		if ( cat.Open(file, this->GetAddonDir(), CATREAD_CATDECRYPT, false) != CATERR_NONE )
 | 
        
           |  |  | 7552 | 			return false;
 | 
        
           |  |  | 7553 |   | 
        
           |  |  | 7554 | 		// extract 1 at a time
 | 
        
           |  |  | 7555 | 		for ( int i = 0; i < cat.GetNumFiles(); i++ )
 | 
        
           |  |  | 7556 | 		{
 | 
        
           |  |  | 7557 | 			SInCatFile *f = cat.GetFile(i);
 | 
        
           |  |  | 7558 | 			CyString sF = f->sFile;
 | 
        
           |  |  | 7559 | 			// is a text file
 | 
        
           |  |  | 7560 | 			sF = sF.FindReplace("\\", "/");
 | 
        
           |  |  | 7561 | 			if ( !sF.GetToken("/", 1, 1).Compare("t") )
 | 
        
           |  |  | 7562 | 				continue;
 | 
        
           |  |  | 7563 |   | 
        
           |  |  | 7564 | 			CyString baseFile = CFileIO(sF).GetBaseName();
 | 
        
           |  |  | 7565 | 			// check language
 | 
        
           |  |  | 7566 | 			int lang = 0;
 | 
        
           |  |  | 7567 | 			if ( baseFile.FindPos("-L") != -1 ) // new language file
 | 
        
           |  |  | 7568 | 				lang = baseFile.Right(3).ToInt();
 | 
        
           |  |  | 7569 | 			else
 | 
        
           |  |  | 7570 | 			{
 | 
        
           |  |  | 7571 | 				baseFile.Truncate((int)baseFile.Length() - 4);
 | 
        
           |  |  | 7572 | 				lang = baseFile.ToInt();
 | 
        
           |  |  | 7573 | 			}
 | 
        
           |  |  | 7574 |   | 
        
           |  |  | 7575 | 			if ( lang != m_iLanguage )
 | 
        
           |  |  | 7576 | 				continue;
 | 
        
           |  |  | 7577 |   | 
        
           |  |  | 7578 | 			// now extract and parse
 | 
        
           |  |  | 7579 | 			if ( cat.ExtractFile(f->sFile, m_sTempDir + "/" + CFileIO(f->sFile).GetBaseName() + ".xml") )
 | 
        
           |  |  | 7580 | 			{
 | 
        
           |  |  | 7581 | 				if ( this->ReadTextPage(m_sTempDir + "/" + CFileIO(f->sFile).GetBaseName() + ".xml", list, search, page) )
 | 
        
           |  |  | 7582 | 					done = true;
 | 
        
           |  |  | 7583 | 			}
 | 
        
           |  |  | 7584 | 		}
 | 
        
           |  |  | 7585 |   | 
        
           |  |  | 7586 | 		return done;
 | 
        
           |  |  | 7587 | 	}
 | 
        
           |  |  | 7588 | 	// otherwise its a normal file
 | 
        
           |  |  | 7589 | 	else if ( CFileIO(file).CheckFileExtension("pck") )
 | 
        
           |  |  | 7590 | 	{
 | 
        
           |  |  | 7591 | 		C_File f(file);
 | 
        
           |  |  | 7592 | 		if ( !f.ReadFromFile() )
 | 
        
           |  |  | 7593 | 			return false;
 | 
        
           |  |  | 7594 | 		f.UnPCKFile();
 | 
        
           |  |  | 7595 |   | 
        
           |  |  | 7596 | 		f.SetFilename(m_sTempDir + "/textfile.xml");
 | 
        
           |  |  | 7597 | 		if ( !f.WriteFilePointer() )
 | 
        
           |  |  | 7598 | 			return false;
 | 
        
           |  |  | 7599 |   | 
        
           |  |  | 7600 | 		File.Open(m_sTempDir + "/textfile.xml");
 | 
        
           |  |  | 7601 | 		deleteFile = true;
 | 
        
           |  |  | 7602 | 	}
 | 
        
           |  |  | 7603 | 	else
 | 
        
           |  |  | 7604 | 		File.Open(file);
 | 
        
           |  |  | 7605 |   | 
        
           |  |  | 7606 | 	if ( !File.Exists() )
 | 
        
           |  |  | 7607 | 		return false;
 | 
        
           |  |  | 7608 |   | 
        
           |  |  | 7609 | 	// open and read file
 | 
        
           |  |  | 7610 | 	CyStringList *lines = File.ReadLinesStr();
 | 
        
           |  |  | 7611 | 	if ( !lines )
 | 
        
           |  |  | 7612 | 		return false;
 | 
        
           |  |  | 7613 |   | 
        
           |  |  | 7614 | 	bool inPage = false;
 | 
        
           |  |  | 7615 | 	for ( SStringList *str = lines->Head(); str; str = str->next )
 | 
        
           |  |  | 7616 | 	{
 | 
        
           |  |  | 7617 | 		// search for page
 | 
        
           |  |  | 7618 | 		if ( !inPage )
 | 
        
           |  |  | 7619 | 		{
 | 
        
           |  |  | 7620 | 			if ( str->str.FindPos("<page") > -1 )
 | 
        
           |  |  | 7621 | 			{
 | 
        
           |  |  | 7622 | 				// find the page id
 | 
        
           |  |  | 7623 | 				int pos = str->str.FindPos("\"");
 | 
        
           |  |  | 7624 | 				if ( pos > -1 )
 | 
        
           |  |  | 7625 | 				{
 | 
        
           |  |  | 7626 | 					int endpos = str->str.FindPos("\"", pos + 1);
 | 
        
           |  |  | 7627 | 					if ( endpos > -1 )
 | 
        
           |  |  | 7628 | 					{
 | 
        
           |  |  | 7629 | 						CyString p = str->str.Mid(pos + 2, endpos - pos - 1);
 | 
        
           |  |  | 7630 | 						if ( p.Length() > 4 )
 | 
        
           |  |  | 7631 | 							p = p.Right(4);
 | 
        
           |  |  | 7632 | 						int checkPage = p.ToInt();
 | 
        
           |  |  | 7633 | 						if ( checkPage == page )
 | 
        
           |  |  | 7634 | 							inPage = true;
 | 
        
           |  |  | 7635 | 					}
 | 
        
           |  |  | 7636 | 				}
 | 
        
           |  |  | 7637 | 			}
 | 
        
           |  |  | 7638 |   | 
        
           |  |  | 7639 | 		}
 | 
        
           |  |  | 7640 | 		// add each id
 | 
        
           |  |  | 7641 | 		else
 | 
        
           |  |  | 7642 | 		{
 | 
        
           |  |  | 7643 | 			if ( str->str.FindPos("</page") > -1 )
 | 
        
           |  |  | 7644 | 				break;
 | 
        
           |  |  | 7645 |   | 
        
           |  |  | 7646 | 			if ( str->str.FindPos("<t id") > -1 )
 | 
        
           |  |  | 7647 | 			{
 | 
        
           |  |  | 7648 | 				int pos = str->str.FindPos("\"");
 | 
        
           |  |  | 7649 | 				if ( pos > -1 )
 | 
        
           |  |  | 7650 | 				{
 | 
        
           |  |  | 7651 | 					int endpos = str->str.FindPos("\"", pos + 1);
 | 
        
           |  |  | 7652 | 					if ( endpos > -1 )
 | 
        
           |  |  | 7653 | 					{
 | 
        
           |  |  | 7654 | 						int id = str->str.Mid(pos + 2, endpos - pos - 1).ToInt();
 | 
        
           |  |  | 7655 | 						pos = str->str.FindPos(">", endpos);
 | 
        
           |  |  | 7656 | 						if ( pos > -1 )
 | 
        
           |  |  | 7657 | 						{
 | 
        
           |  |  | 7658 | 							++pos;
 | 
        
           |  |  | 7659 | 							endpos = str->str.FindPos("</", pos);
 | 
        
           |  |  | 7660 | 							if ( endpos > -1 )
 | 
        
           |  |  | 7661 | 							{
 | 
        
           |  |  | 7662 | 								CyString text = str->str.Mid(pos + 1, endpos - pos);
 | 
        
           |  |  | 7663 | 								while ( text.FindPos('(') != -1 && text.FindPos(')') != -1 )
 | 
        
           |  |  | 7664 | 								{
 | 
        
           |  |  | 7665 | 									int s = text.FindPos('(');
 | 
        
           |  |  | 7666 | 									text = text.Erase(s, text.FindPos(')') - s + 1);
 | 
        
           |  |  | 7667 | 								}
 | 
        
           |  |  | 7668 | 								list->PushBack(CyString::Number(id), text, search);
 | 
        
           |  |  | 7669 | 							}
 | 
        
           |  |  | 7670 | 						}
 | 
        
           |  |  | 7671 | 					}
 | 
        
           |  |  | 7672 | 				}
 | 
        
           |  |  | 7673 | 			}
 | 
        
           |  |  | 7674 | 		}
 | 
        
           |  |  | 7675 | 	}
 | 
        
           |  |  | 7676 |   | 
        
           |  |  | 7677 | 	delete lines;
 | 
        
           |  |  | 7678 |   | 
        
           |  |  | 7679 | 	return true;
 | 
        
           |  |  | 7680 | }
 | 
        
           |  |  | 7681 |   | 
        
           |  |  | 7682 | CyStringList *CPackages::ReadTextPage(CyString file, bool search, int page)
 | 
        
           |  |  | 7683 | {
 | 
        
           |  |  | 7684 | 	CyStringList *list = new CyStringList;
 | 
        
           |  |  | 7685 | 	if ( this->ReadTextPage(file, list, search, page) )
 | 
        
           |  |  | 7686 | 		return list;
 | 
        
           |  |  | 7687 |   | 
        
           |  |  | 7688 | 	delete list;
 | 
        
           |  |  | 7689 | 	return NULL;
 | 
        
           |  |  | 7690 | }
 | 
        
           |  |  | 7691 |   | 
        
           |  |  | 7692 | int CPackages::AdjustFileType(CyString file, int filetype)
 | 
        
           |  |  | 7693 | {
 | 
        
           |  |  | 7694 | 	CFileIO File(file);
 | 
        
           |  |  | 7695 | 	CyString dir = File.GetDirIO().TopDir();
 | 
        
           |  |  | 7696 | 	CyString basename = File.GetBaseName();
 | 
        
           |  |  | 7697 |   | 
        
           |  |  | 7698 | 	// mod files
 | 
        
           |  |  | 7699 | 	if ( File.CheckFileExtension("cat") || File.CheckFileExtension("dat") )
 | 
        
           |  |  | 7700 | 		return FILETYPE_MOD;
 | 
        
           |  |  | 7701 | 	// check for text files
 | 
        
           |  |  | 7702 | 	if ( File.GetFilename().IsIn("-L") && File.GetFilename().Left(4).ToInt() )
 | 
        
           |  |  | 7703 | 		return FILETYPE_TEXT;
 | 
        
           |  |  | 7704 | 	if ( basename.Length() <= 4 && basename.IsNumber() && (File.CheckFileExtension("xml") || File.CheckFileExtension("pck")) )
 | 
        
           |  |  | 7705 | 		return FILETYPE_TEXT;
 | 
        
           |  |  | 7706 | 	// X2/X3 text file
 | 
        
           |  |  | 7707 | 	if ( basename.Length() >= 5 && basename.Length() <= 8 && File.GetBaseName().ToInt() )
 | 
        
           |  |  | 7708 | 		return FILETYPE_TEXT;
 | 
        
           |  |  | 7709 | 	if ( filetype == FILETYPE_TEXT ) // should no longer be anything text
 | 
        
           |  |  | 7710 | 		return FILETYPE_SCRIPT;
 | 
        
           |  |  | 7711 | 	if ( File.CheckFileExtension("wav") || File.CheckFileExtension("mp3") )
 | 
        
           |  |  | 7712 | 		return FILETYPE_SOUND;
 | 
        
           |  |  | 7713 | 	return filetype;
 | 
        
           |  |  | 7714 | }
 | 
        
           |  |  | 7715 |   | 
        
           |  |  | 7716 | void CPackages::RemoveFailedFiles()
 | 
        
           |  |  | 7717 | {
 | 
        
           |  |  | 7718 | 	for ( SStringList *str = m_lNonRemovedFiles.Head(); str; str = str->next )
 | 
        
           |  |  | 7719 | 	{
 | 
        
           |  |  | 7720 | 		if ( CFileIO(str->str).Remove() )
 | 
        
           |  |  | 7721 | 			str->remove = true;
 | 
        
           |  |  | 7722 | 	}
 | 
        
           |  |  | 7723 |   | 
        
           |  |  | 7724 | 	m_lNonRemovedFiles.RemoveMarked();
 | 
        
           |  |  | 7725 | }
 | 
        
           |  |  | 7726 |   | 
        
           |  |  | 7727 | CXspFile *CPackages::ExtractShip(CyString catfile, CyString id, CProgressInfo *progress)
 | 
        
           |  |  | 7728 | {
 | 
        
           |  |  | 7729 | 	CCatFile cat;
 | 
        
           |  |  | 7730 | 	if ( cat.Open(catfile, this->GetAddonDir(), CATREAD_CATDECRYPT, false) != CATERR_NONE )
 | 
        
           |  |  | 7731 | 		return NULL;
 | 
        
           |  |  | 7732 |   | 
        
           |  |  | 7733 | 	CXspFile *newShip = new CXspFile;
 | 
        
           |  |  | 7734 | 	if ( !newShip->ExtractShip(&cat, id, progress) )
 | 
        
           |  |  | 7735 | 	{
 | 
        
           |  |  | 7736 | 		delete newShip;
 | 
        
           |  |  | 7737 | 		return NULL;
 | 
        
           |  |  | 7738 | 	}
 | 
        
           |  |  | 7739 |   | 
        
           |  |  | 7740 | 	return newShip;
 | 
        
           |  |  | 7741 | }
 | 
        
           |  |  | 7742 |   | 
        
           |  |  | 7743 | CyStringList *CPackages::GetMergedFiles(CCatFile *cat1, CCatFile *cat2)
 | 
        
           |  |  | 7744 | {
 | 
        
           |  |  | 7745 | 	CyStringList *list = new CyStringList;
 | 
        
           |  |  | 7746 |   | 
        
           |  |  | 7747 | 	// first add all files from the "primary" mod
 | 
        
           |  |  | 7748 | 	for ( SInCatFile *f = cat1->GetFiles()->First(); f; f = cat1->GetFiles()->Next() )
 | 
        
           |  |  | 7749 | 		list->PushBack(f->sFile.findreplace("\\", "/"), "1");
 | 
        
           |  |  | 7750 |   | 
        
           |  |  | 7751 | 	// now add the ones from the secondary
 | 
        
           |  |  | 7752 | 	for ( SInCatFile *f = cat2->GetFiles()->First(); f; f = cat2->GetFiles()->Next() )
 | 
        
           |  |  | 7753 | 	{
 | 
        
           |  |  | 7754 | 		CyString sFile = f->sFile.findreplace("\\", "/");
 | 
        
           |  |  | 7755 | 		// if its found on the 2nd list, dont add, just adjust the type
 | 
        
           |  |  | 7756 | 		SStringList *found = list->FindString(sFile);
 | 
        
           |  |  | 7757 | 		if ( found )
 | 
        
           |  |  | 7758 | 			found->data = "-1"; // found in both
 | 
        
           |  |  | 7759 | 		else
 | 
        
           |  |  | 7760 | 			list->PushBack(sFile, "2");
 | 
        
           |  |  | 7761 | 	}
 | 
        
           |  |  | 7762 |   | 
        
           |  |  | 7763 | 	return list;
 | 
        
           |  |  | 7764 | }
 | 
        
           |  |  | 7765 |   | 
        
           |  |  | 7766 | bool CPackages::CanWeMerge(CyString file)
 | 
        
           |  |  | 7767 | {
 | 
        
           |  |  | 7768 | 	return CModDiff::CanBeDiffed(file);
 | 
        
           |  |  | 7769 | }
 | 
        
           |  |  | 7770 |   | 
        
           |  |  | 7771 | bool CPackages::NeedToMerge(CyString file)
 | 
        
           |  |  | 7772 | {
 | 
        
           |  |  | 7773 | 	CyString firstDir = file.GetToken("/", 1, 1);
 | 
        
           |  |  | 7774 | 	if ( firstDir.Compare("t") )
 | 
        
           |  |  | 7775 | 		return true;
 | 
        
           |  |  | 7776 | 	if ( firstDir.Compare("types") )
 | 
        
           |  |  | 7777 | 		return true;
 | 
        
           |  |  | 7778 | 	if ( firstDir.Compare("maps") )
 | 
        
           |  |  | 7779 | 		return true;
 | 
        
           |  |  | 7780 |   | 
        
           |  |  | 7781 | 	return false;
 | 
        
           |  |  | 7782 | }
 | 
        
           |  |  | 7783 |   | 
        
           |  |  | 7784 | bool CPackages::MergeMods(CCatFile *mod1, CCatFile *mod2, CyString outFile, CyStringList *cantMerge)
 | 
        
           |  |  | 7785 | {
 | 
        
           |  |  | 7786 | 	CyStringList *list = this->GetMergedFiles(mod1, mod2);
 | 
        
           |  |  | 7787 | 	if ( !list )
 | 
        
           |  |  | 7788 | 		return false;
 | 
        
           |  |  | 7789 |   | 
        
           |  |  | 7790 | 	CCatFile newCat;
 | 
        
           |  |  | 7791 | 	if ( newCat.Open(outFile, this->GetAddonDir()) != CATERR_CREATED )
 | 
        
           |  |  | 7792 | 		return false;
 | 
        
           |  |  | 7793 |   | 
        
           |  |  | 7794 | 	// add all the files to the new mod first
 | 
        
           |  |  | 7795 | 	CyStringList conflicts;
 | 
        
           |  |  | 7796 | 	for ( SStringList *str = list->Head(); str; str = str->next )
 | 
        
           |  |  | 7797 | 	{
 | 
        
           |  |  | 7798 | 		int status = str->data.ToInt();
 | 
        
           |  |  | 7799 | 		if ( status == 1 )
 | 
        
           |  |  | 7800 | 		{
 | 
        
           |  |  | 7801 | 			if ( !newCat.WriteFromCat(mod1, str->str) )
 | 
        
           |  |  | 7802 | 			{
 | 
        
           |  |  | 7803 | 				if ( cantMerge )
 | 
        
           |  |  | 7804 | 					cantMerge->PushBack(str->str, "1");
 | 
        
           |  |  | 7805 | 			}
 | 
        
           |  |  | 7806 | 		}
 | 
        
           |  |  | 7807 | 		else if ( status == 2 )
 | 
        
           |  |  | 7808 | 		{
 | 
        
           |  |  | 7809 | 			if ( !newCat.WriteFromCat(mod2, str->str) )
 | 
        
           |  |  | 7810 | 			{
 | 
        
           |  |  | 7811 | 				if ( cantMerge )
 | 
        
           |  |  | 7812 | 					cantMerge->PushBack(str->str, "2");
 | 
        
           |  |  | 7813 | 			}
 | 
        
           |  |  | 7814 | 		}
 | 
        
           |  |  | 7815 | 		else if ( status == -1 )
 | 
        
           |  |  | 7816 | 		{
 | 
        
           |  |  | 7817 | 			if ( this->NeedToMerge(str->str) )
 | 
        
           |  |  | 7818 | 			{
 | 
        
           |  |  | 7819 | 				if ( this->CanWeMerge(str->str) )
 | 
        
           |  |  | 7820 | 					conflicts.PushBack(str->str);
 | 
        
           |  |  | 7821 | 				else if ( cantMerge )
 | 
        
           |  |  | 7822 | 					cantMerge->PushBack(str->str, "-1");
 | 
        
           |  |  | 7823 | 			}
 | 
        
           |  |  | 7824 | 			else
 | 
        
           |  |  | 7825 | 			{
 | 
        
           |  |  | 7826 | 				if ( !newCat.WriteFromCat(mod1, str->str) )
 | 
        
           |  |  | 7827 | 				{
 | 
        
           |  |  | 7828 | 					if ( cantMerge )
 | 
        
           |  |  | 7829 | 						cantMerge->PushBack(str->str, "1");
 | 
        
           |  |  | 7830 | 				}
 | 
        
           |  |  | 7831 | 			}
 | 
        
           |  |  | 7832 | 		}
 | 
        
           |  |  | 7833 | 	}
 | 
        
           |  |  | 7834 |   | 
        
           |  |  | 7835 | 	delete list;
 | 
        
           |  |  | 7836 |   | 
        
           |  |  | 7837 | 	/* 
 | 
        
           |  |  | 7838 | 		Merging Files
 | 
        
           |  |  | 7839 |   | 
        
           |  |  | 7840 | 		* Text Files: Join all text entries into a single file (excluding page 17)
 | 
        
           |  |  | 7841 | 		* Weapons: TBullets and TLaser (grab matching entrys from text files and adjust ids)
 | 
        
           |  |  | 7842 | 	*/
 | 
        
           |  |  | 7843 | 	// new merge the conflicting files
 | 
        
           |  |  | 7844 | 	// first the text files
 | 
        
           |  |  | 7845 | //	CyStringList *text = this->MergeTextFiles(conflicts, mod1, mod2);
 | 
        
           |  |  | 7846 | //	delete text;
 | 
        
           |  |  | 7847 |   | 
        
           |  |  | 7848 | 	// write the cat file when we're done
 | 
        
           |  |  | 7849 | 	if ( !newCat.WriteCatFile() )
 | 
        
           |  |  | 7850 | 		return false;
 | 
        
           |  |  | 7851 |   | 
        
           |  |  | 7852 | 	return true;
 | 
        
           |  |  | 7853 | }
 | 
        
           |  |  | 7854 |   | 
        
           |  |  | 7855 | /**
 | 
        
           |  |  | 7856 |  * Gets the file list from a mod that might have compatability problems
 | 
        
           |  |  | 7857 |  *
 | 
        
           |  |  | 7858 |  * This includes all types and text files
 | 
        
           |  |  | 7859 |  *
 | 
        
           |  |  | 7860 |  * Returns true if it finds any files
 | 
        
           |  |  | 7861 |  */
 | 
        
           |  |  | 7862 | bool CPackages::GetModCompatabilityList(C_File *file, CyStringList *list)
 | 
        
           |  |  | 7863 | {
 | 
        
           |  |  | 7864 | 	// not a valid file
 | 
        
           |  |  | 7865 | 	if ( !file ) return false;
 | 
        
           |  |  | 7866 | 	if ( file->GetFileType() != FILETYPE_MOD ) return false;
 | 
        
           |  |  | 7867 | 	if ( !file->GetFileExt().Compare("cat") ) return false;
 | 
        
           |  |  | 7868 |   | 
        
           |  |  | 7869 | 	// we need to read the file list for the mod
 | 
        
           |  |  | 7870 | 	CCatFile cat;
 | 
        
           |  |  | 7871 | 	if ( cat.Open(file->GetFilePointer(), this->GetAddonDir(), CATREAD_JUSTCONTENTS, false) == CATERR_NONE )
 | 
        
           |  |  | 7872 | 	{
 | 
        
           |  |  | 7873 | 		for ( int i = 0; i < cat.GetNumFiles(); i++ )
 | 
        
           |  |  | 7874 | 		{
 | 
        
           |  |  | 7875 | 			SInCatFile *f = cat.GetFile(i);
 | 
        
           |  |  | 7876 | 			CyString filename = f->sFile;
 | 
        
           |  |  | 7877 | 			filename = filename.FindReplace("\\", "/");
 | 
        
           |  |  | 7878 | 			if ( filename.Left(2).Compare("t/") || filename.Left(6).Compare("types/") )
 | 
        
           |  |  | 7879 | 			{
 | 
        
           |  |  | 7880 | 				if ( list )
 | 
        
           |  |  | 7881 | 					list->PushBack(filename, CyString(f->lSize));
 | 
        
           |  |  | 7882 | 				else
 | 
        
           |  |  | 7883 | 					return true;
 | 
        
           |  |  | 7884 | 			}
 | 
        
           |  |  | 7885 | 		}
 | 
        
           |  |  | 7886 | 	}
 | 
        
           |  |  | 7887 |   | 
        
           |  |  | 7888 | 	if ( list && !list->Empty() )
 | 
        
           |  |  | 7889 | 		return true;
 | 
        
           |  |  | 7890 |   | 
        
           |  |  | 7891 | 	return false;
 | 
        
           |  |  | 7892 | }
 | 
        
           |  |  | 7893 |   | 
        
           |  |  | 7894 | /**
 | 
        
           |  |  | 7895 |  * Gets the files that are not compatable with each other
 | 
        
           |  |  | 7896 |  *
 | 
        
           |  |  | 7897 |  * Returns true if theres any files that are not compatable
 | 
        
           |  |  | 7898 |  *
 | 
        
           |  |  | 7899 |  * If list is specified, fills up with all files that were found
 | 
        
           |  |  | 7900 |  */
 | 
        
           |  |  | 7901 | bool CPackages::CheckCompatabilityBetweenModFiles(C_File *from, C_File *to, CyStringList *list)
 | 
        
           |  |  | 7902 | {
 | 
        
           |  |  | 7903 | 	// not a valid file
 | 
        
           |  |  | 7904 | 	if ( !from || !to ) return false;
 | 
        
           |  |  | 7905 | 	if ( from->GetFileType() != FILETYPE_MOD ) return false;
 | 
        
           |  |  | 7906 | 	if ( to->GetFileType() != FILETYPE_MOD ) return false;
 | 
        
           |  |  | 7907 | 	if ( !from->GetFileExt().Compare("cat") ) return false;
 | 
        
           |  |  | 7908 | 	if ( !to->GetFileExt().Compare("cat") ) return false;
 | 
        
           |  |  | 7909 |   | 
        
           |  |  | 7910 | 	// get file lists from each file
 | 
        
           |  |  | 7911 | 	CyStringList fromList;
 | 
        
           |  |  | 7912 | 	if ( GetModCompatabilityList(from, &fromList) )
 | 
        
           |  |  | 7913 | 	{
 | 
        
           |  |  | 7914 | 		CyStringList toList;
 | 
        
           |  |  | 7915 | 		if ( GetModCompatabilityList(to, &toList) )
 | 
        
           |  |  | 7916 | 		{
 | 
        
           |  |  | 7917 | 			// both have files we need to check, compare them
 | 
        
           |  |  | 7918 | 			for ( SStringList *str = fromList.Head(); str; str = str->next )
 | 
        
           |  |  | 7919 | 			{
 | 
        
           |  |  | 7920 | 				CyString fromFile = str->str;
 | 
        
           |  |  | 7921 | 				fromFile = fromFile.FindReplace("\\", "/");
 | 
        
           |  |  | 7922 | 				fromFile = fromFile.FindReplace("//", "/");
 | 
        
           |  |  | 7923 | 				for ( SStringList *toStr = toList.Head(); toStr; toStr = toStr->next )
 | 
        
           |  |  | 7924 | 				{
 | 
        
           |  |  | 7925 | 					CyString toFile = toStr->str;
 | 
        
           |  |  | 7926 | 					toFile = toFile.FindReplace("\\", "/");
 | 
        
           |  |  | 7927 | 					toFile = toFile.FindReplace("//", "/");
 | 
        
           |  |  | 7928 | 					if ( fromFile.Compare(toFile) )
 | 
        
           |  |  | 7929 | 					{
 | 
        
           |  |  | 7930 | 						if ( list )
 | 
        
           |  |  | 7931 | 							list->PushBack(from->GetFilename() + "::" + str->str, to->GetFilename() + "::" + toStr->str);
 | 
        
           |  |  | 7932 | 						else
 | 
        
           |  |  | 7933 | 							return true;
 | 
        
           |  |  | 7934 | 					}
 | 
        
           |  |  | 7935 | 				}
 | 
        
           |  |  | 7936 | 			}
 | 
        
           |  |  | 7937 | 		}
 | 
        
           |  |  | 7938 | 	}
 | 
        
           |  |  | 7939 |   | 
        
           |  |  | 7940 | 	if ( list && !list->Empty() )
 | 
        
           |  |  | 7941 | 		return true;
 | 
        
           |  |  | 7942 |   | 
        
           |  |  | 7943 | 	return false;
 | 
        
           |  |  | 7944 | }
 | 
        
           |  |  | 7945 |   | 
        
           |  |  | 7946 | bool CPackages::CheckCompatabilityBetweenMods(CBaseFile *from, CBaseFile *to, CyStringList *list)
 | 
        
           |  |  | 7947 | {
 | 
        
           |  |  | 7948 | 	if ( !from || !to ) return false;
 | 
        
           |  |  | 7949 | 	if ( !from->IsEnabled() || !to->IsEnabled() ) return false;
 | 
        
           |  |  | 7950 | 	if ( !from->AnyFileType(FILETYPE_MOD) ) return false;
 | 
        
           |  |  | 7951 | 	if ( !to->AnyFileType(FILETYPE_MOD) ) return false;
 | 
        
           |  |  | 7952 |   | 
        
           |  |  | 7953 | 	if ( from == to ) return false; // cant have incompatabilities to itself
 | 
        
           |  |  | 7954 |   | 
        
           |  |  | 7955 | 	int count = 0;
 | 
        
           |  |  | 7956 | 	for ( C_File *f = from->GetFirstFile(FILETYPE_MOD); f; f = from->GetNextFile(f) )
 | 
        
           |  |  | 7957 | 	{
 | 
        
           |  |  | 7958 | 		if ( !f->IsFakePatch() ) continue;
 | 
        
           |  |  | 7959 | 		if ( f->GetFileExt().Compare("dat") ) continue;
 | 
        
           |  |  | 7960 |   | 
        
           |  |  | 7961 | 		for ( C_File *compareFile = to->GetFirstFile(FILETYPE_MOD); compareFile; compareFile = to->GetNextFile(compareFile) )
 | 
        
           |  |  | 7962 | 		{
 | 
        
           |  |  | 7963 | 			if ( compareFile == f ) continue; // same file we're checking against
 | 
        
           |  |  | 7964 | 			if ( !compareFile->IsFakePatch() ) continue;
 | 
        
           |  |  | 7965 | 			if ( compareFile->GetFileExt().Compare("dat") ) continue;
 | 
        
           |  |  | 7966 |   | 
        
           |  |  | 7967 | 			// now we have to files to compare
 | 
        
           |  |  | 7968 | 			if ( CheckCompatabilityBetweenModFiles(f, compareFile, list) )
 | 
        
           |  |  | 7969 | 				++count;
 | 
        
           |  |  | 7970 | 		}
 | 
        
           |  |  | 7971 | 	}
 | 
        
           |  |  | 7972 |   | 
        
           |  |  | 7973 | 	if ( count )
 | 
        
           |  |  | 7974 | 		return true;
 | 
        
           |  |  | 7975 |   | 
        
           |  |  | 7976 | 	return false;
 | 
        
           |  |  | 7977 | }
 | 
        
           |  |  | 7978 |   | 
        
           |  |  | 7979 | int CPackages::CheckCompatabilityAgainstPackages(CBaseFile *newFile, CyStringList *list, CLinkList<CBaseFile> *packages)
 | 
        
           |  |  | 7980 | {
 | 
        
           |  |  | 7981 | 	if ( !newFile->IsEnabled() ) return 0;
 | 
        
           |  |  | 7982 | 	if ( !newFile->AnyFileType(FILETYPE_MOD) ) return 0;
 | 
        
           |  |  | 7983 |   | 
        
           |  |  | 7984 | 	// we need to extract all mod files
 | 
        
           |  |  | 7985 | 	for ( CListNode<C_File> *fNode = newFile->GetFileList()->Front(); fNode; fNode = fNode->next() )
 | 
        
           |  |  | 7986 | 	{
 | 
        
           |  |  | 7987 | 		C_File *f = fNode->Data();
 | 
        
           |  |  | 7988 | 		if ( f->GetFileType() != FILETYPE_MOD ) continue;
 | 
        
           |  |  | 7989 | 		if ( !f->IsFakePatch() ) continue;
 | 
        
           |  |  | 7990 | 		if ( !f->CheckFileExt("cat") ) continue;
 | 
        
           |  |  | 7991 |   | 
        
           |  |  | 7992 | 		if ( newFile->ExtractFile(f, m_sTempDir) )
 | 
        
           |  |  | 7993 | 			f->SetFullDir(m_sTempDir);
 | 
        
           |  |  | 7994 | 	}
 | 
        
           |  |  | 7995 |   | 
        
           |  |  | 7996 | 	// compare mod files against all installed packages
 | 
        
           |  |  | 7997 | 	int count = 0;
 | 
        
           |  |  | 7998 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 7999 | 	{
 | 
        
           |  |  | 8000 | 		if ( !node->Data() ) continue;
 | 
        
           |  |  | 8001 | 		CBaseFile *p = node->Data();
 | 
        
           |  |  | 8002 | 		if ( !p->IsEnabled() ) continue;
 | 
        
           |  |  | 8003 | 		if ( !p->AnyFileType(FILETYPE_MOD) ) continue;
 | 
        
           |  |  | 8004 |   | 
        
           |  |  | 8005 | 		if ( this->IsSamePackage(p, newFile) ) continue; // dont include self
 | 
        
           |  |  | 8006 |   | 
        
           |  |  | 8007 | 		if ( CheckCompatabilityBetweenMods(newFile, p, list) )
 | 
        
           |  |  | 8008 | 		{
 | 
        
           |  |  | 8009 | 			++count;
 | 
        
           |  |  | 8010 | 			if ( packages && !packages->FindData(p) )
 | 
        
           |  |  | 8011 | 				packages->push_back(p);
 | 
        
           |  |  | 8012 | 		}
 | 
        
           |  |  | 8013 | 	}
 | 
        
           |  |  | 8014 |   | 
        
           |  |  | 8015 | 	for ( CListNode<C_File> *fNode = newFile->GetFileList()->Front(); fNode; fNode = fNode->next() )
 | 
        
           |  |  | 8016 | 	{
 | 
        
           |  |  | 8017 | 		C_File *f = fNode->Data();
 | 
        
           |  |  | 8018 | 		CFileIO(f->GetFilePointer()).Remove();
 | 
        
           |  |  | 8019 | 		f->SetFullDir("");
 | 
        
           |  |  | 8020 | 	}
 | 
        
           |  |  | 8021 |   | 
        
           |  |  | 8022 | 	return count;
 | 
        
           |  |  | 8023 | }
 | 
        
           |  |  | 8024 |   | 
        
           |  |  | 8025 | bool CPackages::IsSamePackage(CBaseFile *p1, CBaseFile *p2)
 | 
        
           |  |  | 8026 | {
 | 
        
           |  |  | 8027 | 	if ( !p1 || !p2 ) return false;
 | 
        
           |  |  | 8028 | 	if ( p1 == p2 ) return true;
 | 
        
           |  |  | 8029 |   | 
        
           |  |  | 8030 | 	if ( p1->GetName().Compare(p2->GetName()) && p1->GetAuthor().Compare(p2->GetAuthor()) )
 | 
        
           |  |  | 8031 | 		return true;
 | 
        
           |  |  | 8032 | 	return false;
 | 
        
           |  |  | 8033 | }
 | 
        
           |  |  | 8034 |   | 
        
           |  |  | 8035 | void CPackages::ApplyFakePatchOrder(CyStringList *list)
 | 
        
           |  |  | 8036 | {
 | 
        
           |  |  | 8037 | 	if ( !list ) return;
 | 
        
           |  |  | 8038 | 	m_lFakePatchOrder.Clear();
 | 
        
           |  |  | 8039 | 	for ( SStringList *str = list->Head(); str; str = str->next )
 | 
        
           |  |  | 8040 | 		m_lFakePatchOrder.PushBack(str->str, str->data);
 | 
        
           |  |  | 8041 | }
 | 
        
           |  |  | 8042 |   | 
        
           |  |  | 8043 | SAvailablePackage *CPackages::CreateAvailablePackageData(CBaseFile *package)
 | 
        
           |  |  | 8044 | {
 | 
        
           |  |  | 8045 | 	if ( !package ) return NULL;
 | 
        
           |  |  | 8046 |   | 
        
           |  |  | 8047 | 	SAvailablePackage *p = new SAvailablePackage;
 | 
        
           |  |  | 8048 |   | 
        
           |  |  | 8049 | 	for ( CListNode<SGameCompat> *node = package->GetGameCompatabilityList()->Front(); node; node = node->next() ) {
 | 
        
           |  |  | 8050 | 		SGameCompat *gc = new SGameCompat;
 | 
        
           |  |  | 8051 | 		gc->iGame = node->Data()->iGame;
 | 
        
           |  |  | 8052 | 		gc->iVersion = node->Data()->iVersion;
 | 
        
           |  |  | 8053 | 		gc->sVersion = node->Data()->sVersion;
 | 
        
           |  |  | 8054 | 		p->lGames.push_back(gc);
 | 
        
           |  |  | 8055 | 	}
 | 
        
           |  |  | 8056 | 	p->bSigned = package->IsSigned();
 | 
        
           |  |  | 8057 | 	p->iChanging = package->GetGameChanging();
 | 
        
           |  |  | 8058 | 	p->iEase = package->GetEaseOfUse();
 | 
        
           |  |  | 8059 | 	p->iPluginType = package->GetPluginType();
 | 
        
           |  |  | 8060 | 	p->iRec = package->GetRecommended();
 | 
        
           |  |  | 8061 | 	p->iScriptType = -1;
 | 
        
           |  |  | 8062 | 	if ( package->GetType() == TYPE_XSP )
 | 
        
           |  |  | 8063 | 		p->iType = PACKAGETYPE_SHIP;
 | 
        
           |  |  | 8064 | 	else if ( package->IsMod() )
 | 
        
           |  |  | 8065 | 		p->iType = PACKAGETYPE_MOD;
 | 
        
           |  |  | 8066 | 	else 
 | 
        
           |  |  | 8067 | 	{
 | 
        
           |  |  | 8068 | 		p->iType = ((CSpkFile *)package)->GetPackageType();
 | 
        
           |  |  | 8069 | 		p->iScriptType = ((CSpkFile *)package)->GetScriptType();
 | 
        
           |  |  | 8070 | 	}
 | 
        
           |  |  | 8071 | 	p->sAuthor = package->GetAuthor();
 | 
        
           |  |  | 8072 | 	p->sDesc = package->GetDescription().findreplace("\n", "::newline::");
 | 
        
           |  |  | 8073 | 	p->sName = package->GetName();
 | 
        
           |  |  | 8074 | 	p->sUpdated = package->GetCreationDate();
 | 
        
           |  |  | 8075 | 	p->sVersion = package->GetVersion();
 | 
        
           |  |  | 8076 | 	p->sFilename = CFileIO(package->GetFilename()).GetFilename();
 | 
        
           |  |  | 8077 |   | 
        
           |  |  | 8078 | 	return p;
 | 
        
           |  |  | 8079 | }
 | 
        
           |  |  | 8080 |   | 
        
           |  |  | 8081 | CyString CPackages::FormatAvailablePackageData(CBaseFile *package)
 | 
        
           |  |  | 8082 | {
 | 
        
           |  |  | 8083 | 	SAvailablePackage *p = CPackages::CreateAvailablePackageData(package);
 | 
        
           |  |  | 8084 | 	CyString ret = CPackages::FormatAvailablePackageData(p);
 | 
        
           |  |  | 8085 | 	delete p;
 | 
        
           |  |  | 8086 | 	return ret;
 | 
        
           |  |  | 8087 | }
 | 
        
           |  |  | 8088 |   | 
        
           |  |  | 8089 | CyString CPackages::FormatAvailablePackageData(SAvailablePackage *package)
 | 
        
           |  |  | 8090 | {
 | 
        
           |  |  | 8091 | 	CyString ret = (long)package->iType;
 | 
        
           |  |  | 8092 |   | 
        
           |  |  | 8093 | 	CyString gameCompat;
 | 
        
           |  |  | 8094 | 	for ( CListNode<SGameCompat> *node = package->lGames.Front(); node; node = node->next() ) {
 | 
        
           |  |  | 8095 | 		if ( !gameCompat.Empty() )
 | 
        
           |  |  | 8096 | 			gameCompat += "!";
 | 
        
           |  |  | 8097 | 		gameCompat += CyString::Number(node->Data()->iGame);
 | 
        
           |  |  | 8098 | 	}
 | 
        
           |  |  | 8099 |   | 
        
           |  |  | 8100 | 	if ( gameCompat.Empty() )
 | 
        
           |  |  | 8101 | 		gameCompat = "0";
 | 
        
           |  |  | 8102 |   | 
        
           |  |  | 8103 | 	ret.AddToken("::", gameCompat);
 | 
        
           |  |  | 8104 | 	ret.AddToken("::", package->sName);
 | 
        
           |  |  | 8105 | 	ret.AddToken("::", package->sAuthor);
 | 
        
           |  |  | 8106 | 	ret.AddToken("::", package->sVersion);
 | 
        
           |  |  | 8107 | 	ret.AddToken("::", package->sUpdated);
 | 
        
           |  |  | 8108 | 	ret.AddToken("::", package->sFilename);
 | 
        
           |  |  | 8109 | 	ret.AddToken("::", CyString::Number(package->iEase));
 | 
        
           |  |  | 8110 | 	ret.AddToken("::", CyString::Number(package->iChanging));
 | 
        
           |  |  | 8111 | 	ret.AddToken("::", CyString::Number(package->iRec));
 | 
        
           |  |  | 8112 | 	ret.AddToken("::", CyString::Number(package->iPluginType));
 | 
        
           |  |  | 8113 | 	ret.AddToken("::", CyString::Number(package->iScriptType));
 | 
        
           |  |  | 8114 | 	ret.AddToken("::", (package->bSigned) ? "1" : "0");
 | 
        
           |  |  | 8115 | 	ret.AddToken("::", package->sDesc);
 | 
        
           |  |  | 8116 |   | 
        
           |  |  | 8117 | 	return ret;
 | 
        
           |  |  | 8118 | }
 | 
        
           |  |  | 8119 |   | 
        
           |  |  | 8120 | void CPackages::ParseAvailablePackage(CyString str, CyString webaddress)
 | 
        
           |  |  | 8121 | {
 | 
        
           |  |  | 8122 | 	// first check game
 | 
        
           |  |  | 8123 | 	int game = str.GetToken("::", 2, 2).ToInt();
 | 
        
           |  |  | 8124 | 	if ( game && m_iGame && m_iGame != game )
 | 
        
           |  |  | 8125 | 		return;
 | 
        
           |  |  | 8126 |   | 
        
           |  |  | 8127 | 	int num = 0;
 | 
        
           |  |  | 8128 | 	CyString *tok = str.SplitToken("::", &num);
 | 
        
           |  |  | 8129 | 	if ( !num || !tok ) return;
 | 
        
           |  |  | 8130 | 	if ( num < 7 ) { CLEANSPLIT(tok, num); return; }
 | 
        
           |  |  | 8131 |   | 
        
           |  |  | 8132 | 	SAvailablePackage *p = new SAvailablePackage;
 | 
        
           |  |  | 8133 | 	p->iType = tok[0].ToInt();
 | 
        
           |  |  | 8134 | 	p->bSigned = false;
 | 
        
           |  |  | 8135 |   | 
        
           |  |  | 8136 | 	CyString gameCompat = tok[1];
 | 
        
           |  |  | 8137 | 	if ( gameCompat.IsIn("!") ) {
 | 
        
           |  |  | 8138 | 		int maxSplit = 0;
 | 
        
           |  |  | 8139 | 		CyString *games = gameCompat.SplitToken("!", &maxSplit);
 | 
        
           |  |  | 8140 | 		if ( games && maxSplit ) {
 | 
        
           |  |  | 8141 | 			for ( int i = 0; i < maxSplit; i++ ) {
 | 
        
           |  |  | 8142 | 				SGameCompat *gc = new SGameCompat;
 | 
        
           |  |  | 8143 | 				gc->iVersion = 0;
 | 
        
           |  |  | 8144 | 				gc->iGame = games[i].ToInt();
 | 
        
           |  |  | 8145 | 				p->lGames.push_back(gc);
 | 
        
           |  |  | 8146 | 			}
 | 
        
           |  |  | 8147 | 		}
 | 
        
           |  |  | 8148 | 		CLEANSPLIT(games, maxSplit);
 | 
        
           |  |  | 8149 | 	}
 | 
        
           |  |  | 8150 | 	else {
 | 
        
           |  |  | 8151 | 		SGameCompat *gc = new SGameCompat;
 | 
        
           |  |  | 8152 | 		gc->iVersion = 0;
 | 
        
           |  |  | 8153 | 		gc->iGame = gameCompat.ToInt();
 | 
        
           |  |  | 8154 | 		p->lGames.push_back(gc);
 | 
        
           |  |  | 8155 | 	}
 | 
        
           |  |  | 8156 | 	p->sName = tok[2];
 | 
        
           |  |  | 8157 | 	p->sAuthor = tok[3];
 | 
        
           |  |  | 8158 | 	p->sVersion = tok[4];
 | 
        
           |  |  | 8159 | 	p->sUpdated = tok[5];
 | 
        
           |  |  | 8160 | 	p->sFilename = tok[6];
 | 
        
           |  |  | 8161 |   | 
        
           |  |  | 8162 | 	if ( !webaddress.Empty() )
 | 
        
           |  |  | 8163 | 		p->sFilename = webaddress + "/" + p->sFilename;
 | 
        
           |  |  | 8164 |   | 
        
           |  |  | 8165 | 	p->iChanging = p->iEase = p->iPluginType = p->iRec = p->iScriptType = -1;
 | 
        
           |  |  | 8166 |   | 
        
           |  |  | 8167 | 	if ( num >= 12 )
 | 
        
           |  |  | 8168 | 	{
 | 
        
           |  |  | 8169 | 		p->iEase = tok[7].ToInt();
 | 
        
           |  |  | 8170 | 		p->iChanging = tok[8].ToInt();
 | 
        
           |  |  | 8171 | 		p->iRec = tok[9].ToInt();
 | 
        
           |  |  | 8172 | 		p->iPluginType = tok[10].ToInt();
 | 
        
           |  |  | 8173 | 		p->iScriptType = tok[11].ToInt();
 | 
        
           |  |  | 8174 | 		if ( num > 12 ) {
 | 
        
           |  |  | 8175 | 			if ( num > 13 ) {
 | 
        
           |  |  | 8176 | 				p->sDesc = str.GetToken("::", 14); 
 | 
        
           |  |  | 8177 | 				p->bSigned = str.GetToken("::", 13).ToBool();
 | 
        
           |  |  | 8178 | 			}
 | 
        
           |  |  | 8179 | 			else
 | 
        
           |  |  | 8180 | 				p->sDesc = str.GetToken("::", 13); 
 | 
        
           |  |  | 8181 | 		}
 | 
        
           |  |  | 8182 | 	}
 | 
        
           |  |  | 8183 | 	else if ( num > 7 )
 | 
        
           |  |  | 8184 | 		p->sDesc = str.GetToken("::", 8); 
 | 
        
           |  |  | 8185 |   | 
        
           |  |  | 8186 | 	if ( !p->sDesc.Empty() )
 | 
        
           |  |  | 8187 | 		p->sDesc.FindReplace("::newline::", "\\n");
 | 
        
           |  |  | 8188 |   | 
        
           |  |  | 8189 | 	AddAvailablePackage(p);
 | 
        
           |  |  | 8190 |   | 
        
           |  |  | 8191 | 	CLEANSPLIT(tok, num);
 | 
        
           |  |  | 8192 | }
 | 
        
           |  |  | 8193 |   | 
        
           |  |  | 8194 | SAvailablePackage *CPackages::FindAvailablePackage(CyString &filename)
 | 
        
           |  |  | 8195 | {
 | 
        
           |  |  | 8196 | 	for ( CListNode<SAvailablePackage> *node = m_lAvailablePackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 8197 | 	{
 | 
        
           |  |  | 8198 | 		if ( node->Data()->sFilename.Compare(filename) )
 | 
        
           |  |  | 8199 | 			return node->Data();
 | 
        
           |  |  | 8200 | 	}
 | 
        
           |  |  | 8201 | 	return NULL;
 | 
        
           |  |  | 8202 | }
 | 
        
           |  |  | 8203 |   | 
        
           |  |  | 8204 | bool CPackages::AddAvailablePackage(SAvailablePackage *package)	
 | 
        
           |  |  | 8205 | { 
 | 
        
           |  |  | 8206 | 	if ( !package->lGames.empty() ) {
 | 
        
           |  |  | 8207 | 		bool found = false;
 | 
        
           |  |  | 8208 | 		for ( CListNode<SGameCompat> *node = package->lGames.Front(); node; node = node->next() ) {
 | 
        
           |  |  | 8209 | 			if ( !node->Data()->iGame || node->Data()->iGame == m_iGame ) {
 | 
        
           |  |  | 8210 | 				found = true;
 | 
        
           |  |  | 8211 | 				break;
 | 
        
           |  |  | 8212 | 			}
 | 
        
           |  |  | 8213 | 		}
 | 
        
           |  |  | 8214 |   | 
        
           |  |  | 8215 | 		if ( !found )
 | 
        
           |  |  | 8216 | 			return false;
 | 
        
           |  |  | 8217 | 	}
 | 
        
           |  |  | 8218 |   | 
        
           |  |  | 8219 | 	SAvailablePackage *p = FindAvailablePackage(package->sFilename);
 | 
        
           |  |  | 8220 | 	if ( p )
 | 
        
           |  |  | 8221 | 		m_lAvailablePackages.remove(p);
 | 
        
           |  |  | 8222 | 	m_lAvailablePackages.push_back(package); 
 | 
        
           |  |  | 8223 |   | 
        
           |  |  | 8224 | 	return true;
 | 
        
           |  |  | 8225 | }
 | 
        
           |  |  | 8226 |   | 
        
           |  |  | 8227 | bool CPackages::AnyAvailablePackages(int type)
 | 
        
           |  |  | 8228 | {
 | 
        
           |  |  | 8229 | 	if ( type == -1 ) return !m_lAvailablePackages.empty();
 | 
        
           |  |  | 8230 |   | 
        
           |  |  | 8231 | 	for ( CListNode<SAvailablePackage> *node = m_lAvailablePackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 8232 | 	{
 | 
        
           |  |  | 8233 | 		if ( node->Data()->iType == type )
 | 
        
           |  |  | 8234 | 			return true;
 | 
        
           |  |  | 8235 | 	}
 | 
        
           |  |  | 8236 |   | 
        
           |  |  | 8237 | 	return false;
 | 
        
           |  |  | 8238 | }
 | 
        
           |  |  | 8239 |   | 
        
           |  |  | 8240 | int CPackages::FindAllServers(CyStringList *list)
 | 
        
           |  |  | 8241 | {
 | 
        
           |  |  | 8242 | 	for ( CListNode<CBaseFile> *node = m_lPackages.Front(); node; node = node->next() )
 | 
        
           |  |  | 8243 | 	{
 | 
        
           |  |  | 8244 | 		if ( !node->Data()->GetWebAddress().Empty() )
 | 
        
           |  |  | 8245 | 			list->PushBack(node->Data()->GetWebAddress(), true);
 | 
        
           |  |  | 8246 | 		if ( node->Data()->AnyWebMirrors() )
 | 
        
           |  |  | 8247 | 		{
 | 
        
           |  |  | 8248 | 			for ( SStringList *str = node->Data()->GetWebMirrors()->Head(); str; str = str->next )
 | 
        
           |  |  | 8249 | 				list->PushBack(str->str, true);
 | 
        
           |  |  | 8250 | 		}
 | 
        
           |  |  | 8251 | 	}
 | 
        
           |  |  | 8252 |   | 
        
           |  |  | 8253 | 	return list->Count();
 | 
        
           |  |  | 8254 | }
 | 
        
           |  |  | 8255 |   | 
        
           |  |  | 8256 | void CPackages::ReadArchiveData(CyString filename, CBaseFile *archive)
 | 
        
           |  |  | 8257 | {
 | 
        
           |  |  | 8258 | 	size_t size;
 | 
        
           |  |  | 8259 | 	char *data = CFileIO(filename).ReadToData(&size);
 | 
        
           |  |  | 8260 | 	if ( size && data )
 | 
        
           |  |  | 8261 | 		ReadArchiveData(data, size, archive);
 | 
        
           |  |  | 8262 | }
 | 
        
           |  |  | 8263 |   | 
        
           |  |  | 8264 | void CPackages::ReadArchiveData(const char *buf, size_t len, CBaseFile *archive)
 | 
        
           |  |  | 8265 | {
 | 
        
           |  |  | 8266 | 	CyString data(buf);
 | 
        
           |  |  | 8267 | 	int max;
 | 
        
           |  |  | 8268 | 	CyString *str = data.SplitToken("\n", &max);
 | 
        
           |  |  | 8269 | 	if ( str && max )
 | 
        
           |  |  | 8270 | 	{
 | 
        
           |  |  | 8271 | 		for ( int i = 0; i < max; i++ )
 | 
        
           |  |  | 8272 | 		{
 | 
        
           |  |  | 8273 | 			CyString line = str[i];
 | 
        
           |  |  | 8274 | 			if ( line.Empty() )
 | 
        
           |  |  | 8275 | 				continue;
 | 
        
           |  |  | 8276 |   | 
        
           |  |  | 8277 | 			// filter out any spaces, tabs in front
 | 
        
           |  |  | 8278 | 			line.RemoveChar('\t');
 | 
        
           |  |  | 8279 | 			line.RemoveChar('\r');
 | 
        
           |  |  | 8280 | 			CyString linenospace = line;
 | 
        
           |  |  | 8281 | 			linenospace.RemoveFirstSpace();
 | 
        
           |  |  | 8282 | 			if ( linenospace.Empty() )
 | 
        
           |  |  | 8283 | 				continue;
 | 
        
           |  |  | 8284 |   | 
        
           |  |  | 8285 | 			// check for any comments
 | 
        
           |  |  | 8286 | 			if ( linenospace.Left(2) == "//" )
 | 
        
           |  |  | 8287 | 				continue;
 | 
        
           |  |  | 8288 | 			if ( linenospace[0] == '#' )
 | 
        
           |  |  | 8289 | 				continue;
 | 
        
           |  |  | 8290 |   | 
        
           |  |  | 8291 | 			// all commands start with a keyword followed by a colon, if one doesn't exist, it cant be a valid line
 | 
        
           |  |  | 8292 | 			if ( !line.IsIn(':') )
 | 
        
           |  |  | 8293 | 				continue;
 | 
        
           |  |  | 8294 |   | 
        
           |  |  | 8295 | 			CyString first = line.GetToken(":", 1, 1);
 | 
        
           |  |  | 8296 | 			CyString rest = line.GetToken(":", 2).RemoveFirstSpace();
 | 
        
           |  |  | 8297 |   | 
        
           |  |  | 8298 | 			CyString checkType = first;
 | 
        
           |  |  | 8299 | 			bool shared = false;
 | 
        
           |  |  | 8300 | 			if ( checkType.Left(6).Compare("Shared") )
 | 
        
           |  |  | 8301 | 			{
 | 
        
           |  |  | 8302 | 				checkType = first.Right(-6);
 | 
        
           |  |  | 8303 | 				shared = true;
 | 
        
           |  |  | 8304 | 			}
 | 
        
           |  |  | 8305 |   | 
        
           |  |  | 8306 | 			// now check type name
 | 
        
           |  |  | 8307 | 			int filetype = GetFileTypeFromString(checkType);
 | 
        
           |  |  | 8308 | 			if ( filetype == -1 )
 | 
        
           | 14 | cycrow | 8309 | 				archive->LoadPackageData(first.ToString(), rest.ToString());
 | 
        
           | 1 | cycrow | 8310 | 		}
 | 
        
           |  |  | 8311 | 	}
 | 
        
           |  |  | 8312 |   | 
        
           |  |  | 8313 | 	CLEANSPLIT(str, max)
 | 
        
           |  |  | 8314 | }
 | 
        
           |  |  | 8315 |   | 
        
           |  |  | 8316 | CBaseFile *CPackages::CreateFromArchive(CyString filename, bool toInstall )
 | 
        
           |  |  | 8317 | {
 | 
        
           |  |  | 8318 | 	// make sure we can open the zip file
 | 
        
           |  |  | 8319 | 	CBaseFile *archive = NULL;
 | 
        
           |  |  | 8320 | 	if ( CFileIO(filename).CheckFileExtension("rar") )
 | 
        
           |  |  | 8321 | 	{
 | 
        
           |  |  | 8322 | #ifdef _RAR
 | 
        
           |  |  | 8323 | 		HANDLE hArcData;
 | 
        
           |  |  | 8324 | 		int RHCode,PFCode;
 | 
        
           |  |  | 8325 | 		char CmtBuf[16384];
 | 
        
           |  |  | 8326 | 		struct RARHeaderDataEx HeaderData;
 | 
        
           |  |  | 8327 | 		struct RAROpenArchiveDataEx OpenArchiveData;
 | 
        
           |  |  | 8328 |   | 
        
           |  |  | 8329 | 		if ( toInstall )
 | 
        
           |  |  | 8330 | 		{
 | 
        
           |  |  | 8331 | 			memset(&OpenArchiveData,0,sizeof(OpenArchiveData));
 | 
        
           |  |  | 8332 | 			OpenArchiveData.ArcName=(char *)filename.c_str();
 | 
        
           |  |  | 8333 | 			OpenArchiveData.CmtBuf=CmtBuf;
 | 
        
           |  |  | 8334 | 			OpenArchiveData.CmtBufSize=sizeof(CmtBuf);
 | 
        
           |  |  | 8335 | 			OpenArchiveData.OpenMode=RAR_OM_LIST;
 | 
        
           |  |  | 8336 | 	//		OpenArchiveData.UserData=LIST;
 | 
        
           |  |  | 8337 | 			hArcData=RAROpenArchiveEx(&OpenArchiveData);
 | 
        
           |  |  | 8338 |   | 
        
           |  |  | 8339 | 			if (OpenArchiveData.OpenResult!=0)
 | 
        
           |  |  | 8340 | 				return NULL;
 | 
        
           |  |  | 8341 |   | 
        
           |  |  | 8342 | 			HeaderData.CmtBuf=NULL;
 | 
        
           |  |  | 8343 | 			memset(&OpenArchiveData.Reserved,0,sizeof(OpenArchiveData.Reserved));
 | 
        
           |  |  | 8344 |   | 
        
           |  |  | 8345 | 			while ((RHCode=RARReadHeaderEx(hArcData,&HeaderData))==0)
 | 
        
           |  |  | 8346 | 			{
 | 
        
           |  |  | 8347 | 				if ( CyString(HeaderData.FileName).Compare("pluginmanager.txt") )
 | 
        
           |  |  | 8348 | 				{
 | 
        
           |  |  | 8349 | 					toInstall = false;
 | 
        
           |  |  | 8350 | 					break;
 | 
        
           |  |  | 8351 | 				}
 | 
        
           |  |  | 8352 | 			}
 | 
        
           |  |  | 8353 | 			RARCloseArchive(hArcData);
 | 
        
           |  |  | 8354 | 		}
 | 
        
           |  |  | 8355 |   | 
        
           |  |  | 8356 | 		if ( toInstall )
 | 
        
           |  |  | 8357 | 			archive = new CArchiveFile(); // just installing an archive file
 | 
        
           |  |  | 8358 | 		else
 | 
        
           |  |  | 8359 | 			archive = new CSpkFile(); // converting to a spk file
 | 
        
           |  |  | 8360 |   | 
        
           |  |  | 8361 | 		memset(&OpenArchiveData,0,sizeof(OpenArchiveData));
 | 
        
           |  |  | 8362 | 		OpenArchiveData.ArcName=(char *)filename.c_str();
 | 
        
           |  |  | 8363 | 		OpenArchiveData.CmtBuf=CmtBuf;
 | 
        
           |  |  | 8364 | 		OpenArchiveData.CmtBufSize=sizeof(CmtBuf);
 | 
        
           |  |  | 8365 | 		OpenArchiveData.OpenMode=RAR_OM_EXTRACT;
 | 
        
           |  |  | 8366 | 		OpenArchiveData.UserData=EXTRACT;
 | 
        
           |  |  | 8367 | 		hArcData=RAROpenArchiveEx(&OpenArchiveData);
 | 
        
           |  |  | 8368 |   | 
        
           |  |  | 8369 | 		if (OpenArchiveData.OpenResult!=0)
 | 
        
           |  |  | 8370 | 			return NULL;
 | 
        
           |  |  | 8371 |   | 
        
           |  |  | 8372 | 		HeaderData.CmtBuf=NULL;
 | 
        
           |  |  | 8373 | 		memset(&OpenArchiveData.Reserved,0,sizeof(OpenArchiveData.Reserved));
 | 
        
           |  |  | 8374 |   | 
        
           |  |  | 8375 | 		bool error = false;
 | 
        
           |  |  | 8376 | 		CyString extractedFile = CDirIO(m_sTempDir).File("extracted.tst").findreplace("/", "\\").findreplace("\\\\", "\\");
 | 
        
           |  |  | 8377 | 		while ((RHCode=RARReadHeaderEx(hArcData,&HeaderData))==0)
 | 
        
           |  |  | 8378 | 		{
 | 
        
           |  |  | 8379 | 			CyString fileName = HeaderData.FileName;
 | 
        
           |  |  | 8380 |   | 
        
           |  |  | 8381 | 			if ( HeaderData.FileAttr == 16 )
 | 
        
           |  |  | 8382 | 				continue;
 | 
        
           |  |  | 8383 | 			wchar_t wText[200];
 | 
        
           |  |  | 8384 | 			::MultiByteToWideChar(CP_ACP, NULL, (char *)extractedFile.c_str(), -1, wText, extractedFile.Length() + 1);
 | 
        
           |  |  | 8385 | 			PFCode=RARProcessFileW(hArcData, RAR_EXTRACT, NULL, NULL);
 | 
        
           |  |  | 8386 | 			if (PFCode!=0)
 | 
        
           |  |  | 8387 | 			{
 | 
        
           |  |  | 8388 | 				error = true;
 | 
        
           |  |  | 8389 | 				break;
 | 
        
           |  |  | 8390 | 			}
 | 
        
           |  |  | 8391 |   | 
        
           |  |  | 8392 | 			CFileIO File(fileName);
 | 
        
           |  |  | 8393 | 			if ( File.Exists() )
 | 
        
           |  |  | 8394 | 			{
 | 
        
           |  |  | 8395 | 				if ( fileName.Compare("pluginmanager.txt") )
 | 
        
           |  |  | 8396 | 					this->ReadArchiveData(File.GetFullFilename(), archive);
 | 
        
           |  |  | 8397 | 				else
 | 
        
           |  |  | 8398 | 				{
 | 
        
           |  |  | 8399 | 					CyString extradir;
 | 
        
           |  |  | 8400 | 					int type = SPK::GetAutomaticFiletype(fileName, &extradir);
 | 
        
           |  |  | 8401 |   | 
        
           |  |  | 8402 | 					C_File *f = NULL;
 | 
        
           |  |  | 8403 | 					if ( type == -1 )
 | 
        
           |  |  | 8404 | 						f = archive->AddFile(CFileIO(fileName).GetFilename(), CFileIO(fileName).GetDir(), FILETYPE_EXTRA);
 | 
        
           |  |  | 8405 | 					else
 | 
        
           |  |  | 8406 | 						f = archive->AddFile(CFileIO(fileName).GetFilename(), extradir, type);
 | 
        
           |  |  | 8407 | 					f->ReadFromFile(File.GetFullFilename());
 | 
        
           |  |  | 8408 | 				}
 | 
        
           |  |  | 8409 |   | 
        
           |  |  | 8410 | 				File.Remove();
 | 
        
           |  |  | 8411 | 			}
 | 
        
           |  |  | 8412 | 		}
 | 
        
           |  |  | 8413 |   | 
        
           |  |  | 8414 | 		RARCloseArchive(hArcData);
 | 
        
           |  |  | 8415 |   | 
        
           |  |  | 8416 | 		if ( error )
 | 
        
           |  |  | 8417 | 		{
 | 
        
           |  |  | 8418 | 			delete archive;
 | 
        
           |  |  | 8419 | 			archive = NULL;
 | 
        
           |  |  | 8420 | 		}
 | 
        
           |  |  | 8421 | #endif
 | 
        
           |  |  | 8422 | 	}
 | 
        
           |  |  | 8423 | 	else if ( CFileIO(filename).CheckFileExtension("zip") )
 | 
        
           |  |  | 8424 | 	{
 | 
        
           |  |  | 8425 | 		TCHAR buf[5000];
 | 
        
           |  |  | 8426 | 		wsprintf(buf, L"%hs", filename.c_str());
 | 
        
           |  |  | 8427 | 		HZIP hz = OpenZip(buf, 0);
 | 
        
           |  |  | 8428 | 		if ( !hz ) 
 | 
        
           |  |  | 8429 | 			return NULL;
 | 
        
           |  |  | 8430 |   | 
        
           |  |  | 8431 | 		int index;
 | 
        
           |  |  | 8432 | 		// move the files from the zip to the package
 | 
        
           |  |  | 8433 | 		ZIPENTRY ze;
 | 
        
           |  |  | 8434 | 		if ( FindZipItem(hz, L"pluginmanager.txt", true, &index, &ze) == Z_OK )
 | 
        
           |  |  | 8435 | 			toInstall = false;
 | 
        
           |  |  | 8436 | 		CloseZip(hz);
 | 
        
           |  |  | 8437 |   | 
        
           |  |  | 8438 | 		hz = OpenZip(buf, 0);
 | 
        
           |  |  | 8439 | 		if ( !hz ) 
 | 
        
           |  |  | 8440 | 			return NULL;
 | 
        
           |  |  | 8441 |   | 
        
           |  |  | 8442 | 		// create the correct package
 | 
        
           |  |  | 8443 | 		if ( toInstall )
 | 
        
           |  |  | 8444 | 			archive = new CArchiveFile(); // just installing an archive file
 | 
        
           |  |  | 8445 | 		else
 | 
        
           |  |  | 8446 | 			archive = new CSpkFile(); // converting to a spk file
 | 
        
           |  |  | 8447 |   | 
        
           |  |  | 8448 | 		GetZipItem(hz, -1, &ze);
 | 
        
           |  |  | 8449 | 		int numitems = ze.index;
 | 
        
           |  |  | 8450 |   | 
        
           |  |  | 8451 | 		bool error = false;
 | 
        
           |  |  | 8452 | 		for ( int zi = 0; zi < numitems; zi++ )
 | 
        
           |  |  | 8453 | 		{
 | 
        
           |  |  | 8454 | 			ZIPENTRY ze;
 | 
        
           |  |  | 8455 | 			if ( GetZipItem(hz, zi, &ze) != Z_OK )
 | 
        
           |  |  | 8456 | 			{
 | 
        
           |  |  | 8457 | 				error = true;
 | 
        
           |  |  | 8458 | 				break;
 | 
        
           |  |  | 8459 | 			}
 | 
        
           |  |  | 8460 |   | 
        
           |  |  | 8461 | 			if ( ze.attr & FILE_ATTRIBUTE_DIRECTORY )
 | 
        
           |  |  | 8462 | 				continue; // dont do directories
 | 
        
           |  |  | 8463 |   | 
        
           |  |  | 8464 |   | 
        
           |  |  | 8465 | 			char *iBuf = new char[ze.unc_size];
 | 
        
           |  |  | 8466 | 			UnzipItem(hz, zi, iBuf, ze.unc_size);
 | 
        
           |  |  | 8467 |   | 
        
           |  |  | 8468 | 			CyString Name(ze.name);
 | 
        
           |  |  | 8469 |   | 
        
           |  |  | 8470 | 			// if its the data file, dont add it, but extract to get settings from
 | 
        
           |  |  | 8471 | 			if ( Name.Compare("pluginmanager.txt") )
 | 
        
           |  |  | 8472 | 			{
 | 
        
           |  |  | 8473 | 				this->ReadArchiveData(iBuf, ze.unc_size, archive);
 | 
        
           |  |  | 8474 | 				delete[] iBuf;
 | 
        
           |  |  | 8475 | 			}
 | 
        
           |  |  | 8476 | 			else
 | 
        
           |  |  | 8477 | 			{
 | 
        
           |  |  | 8478 | 				CyString extradir;
 | 
        
           |  |  | 8479 | 				int type = SPK::GetAutomaticFiletype(Name, &extradir);
 | 
        
           |  |  | 8480 |   | 
        
           |  |  | 8481 | 				C_File *f = NULL;
 | 
        
           |  |  | 8482 | 				if ( type == -1 )
 | 
        
           |  |  | 8483 | 					f = archive->AddFile(CFileIO(Name).GetFilename(), CFileIO(Name).GetDir(), FILETYPE_EXTRA);
 | 
        
           |  |  | 8484 | 				else
 | 
        
           |  |  | 8485 | 					f = archive->AddFile(CFileIO(Name).GetFilename(), extradir, type);
 | 
        
           |  |  | 8486 |   | 
        
           |  |  | 8487 | 				if ( f )
 | 
        
           |  |  | 8488 | 					f->SetData((const unsigned char *)iBuf, ze.unc_size);
 | 
        
           |  |  | 8489 | 				else
 | 
        
           |  |  | 8490 | 					delete[] iBuf;
 | 
        
           |  |  | 8491 | 			}
 | 
        
           |  |  | 8492 | 		}
 | 
        
           |  |  | 8493 |   | 
        
           |  |  | 8494 | 		CloseZip(hz);
 | 
        
           |  |  | 8495 |   | 
        
           |  |  | 8496 | 		if ( error )
 | 
        
           |  |  | 8497 | 		{
 | 
        
           |  |  | 8498 | 			delete archive;
 | 
        
           |  |  | 8499 | 			archive = NULL;
 | 
        
           |  |  | 8500 | 		}
 | 
        
           |  |  | 8501 | 	}
 | 
        
           |  |  | 8502 |   | 
        
           |  |  | 8503 | 	if ( archive )
 | 
        
           |  |  | 8504 | 	{
 | 
        
           |  |  | 8505 | 		archive->SetFilename(CFileIO(filename).ChangeFileExtension("spk"));
 | 
        
           |  |  | 8506 | 		if ( toInstall )
 | 
        
           |  |  | 8507 | 			archive->SetName(CFileIO(filename).GetFilename());
 | 
        
           |  |  | 8508 | 		else
 | 
        
           |  |  | 8509 | 			archive->SetName(CFileIO(filename).GetBaseName());
 | 
        
           |  |  | 8510 | 	}
 | 
        
           |  |  | 8511 |   | 
        
           |  |  | 8512 | 	return archive;
 | 
        
           |  |  | 8513 | }
 | 
        
           |  |  | 8514 |   | 
        
           |  |  | 8515 | CyString CPackages::CreateFromPackagerScript(CyString filename)
 | 
        
           |  |  | 8516 | {
 | 
        
           |  |  | 8517 | 	CyString curDir = CFileIO(filename).GetDir();
 | 
        
           |  |  | 8518 | 	CyStringList variables;
 | 
        
           |  |  | 8519 | 	variables.PushBack("$PATH", curDir);
 | 
        
           |  |  | 8520 | 	CPackages p;
 | 
        
           |  |  | 8521 | 	CBaseFile *package = p.LoadPackagerScript(filename, NULL, NULL, NULL, &variables);
 | 
        
           |  |  | 8522 |   | 
        
           |  |  | 8523 | 	if ( !package )
 | 
        
           |  |  | 8524 | 		return NullString;
 | 
        
           |  |  | 8525 |   | 
        
           |  |  | 8526 | 	CyString saveto = package->GetFilename();
 | 
        
           |  |  | 8527 | 	saveto = saveto.FindReplace("$DEFAULTDIR", curDir + "/");
 | 
        
           |  |  | 8528 | 	saveto = saveto.FindReplace("$PATH", curDir);
 | 
        
           |  |  | 8529 | 	saveto = saveto.FindReplace("\\", "/");
 | 
        
           |  |  | 8530 | 	saveto = saveto.FindReplace("//", "/");
 | 
        
           |  |  | 8531 | 	if ( !saveto.Right(4).Compare(".spk") && package->GetType() != TYPE_XSP )
 | 
        
           |  |  | 8532 | 		saveto += ".spk";
 | 
        
           |  |  | 8533 | 	else if ( !saveto.Right(4).Compare(".xsp") && package->GetType() == TYPE_XSP )
 | 
        
           |  |  | 8534 | 		saveto += ".xsp";
 | 
        
           |  |  | 8535 |   | 
        
           |  |  | 8536 | 	// write script
 | 
        
           |  |  | 8537 | 	if ( package->WriteFile(saveto) )
 | 
        
           |  |  | 8538 | 	{
 | 
        
           |  |  | 8539 | 		if ( package->AutoGenerateUpdateFile() )
 | 
        
           |  |  | 8540 | 			package->CreateUpdateFile(CFileIO(saveto).GetDir());
 | 
        
           |  |  | 8541 | 		return saveto;
 | 
        
           |  |  | 8542 | 	}
 | 
        
           |  |  | 8543 |   | 
        
           |  |  | 8544 | 	return NullString;
 | 
        
           |  |  | 8545 | }
 | 
        
           |  |  | 8546 |   | 
        
           |  |  | 8547 | int CPackages::GeneratePackageUpdateData(CyString dir, bool includeSingle)
 | 
        
           |  |  | 8548 | {
 | 
        
           |  |  | 8549 | 	CyStringList filedata;
 | 
        
           |  |  | 8550 |   | 
        
           |  |  | 8551 | 	CPackages packages;
 | 
        
           |  |  | 8552 |   | 
        
           |  |  | 8553 | 	CDirIO Dir(dir);
 | 
        
           |  |  | 8554 | 	for ( int i = 0; i < 2; i++ )
 | 
        
           |  |  | 8555 | 	{
 | 
        
           |  |  | 8556 | 		CyString pattern;
 | 
        
           |  |  | 8557 | 		if ( i == 0 ) pattern = "*.spk";
 | 
        
           |  |  | 8558 | 		else if ( i == 1 ) pattern = ".xsp";
 | 
        
           |  |  | 8559 | 		else break;
 | 
        
           |  |  | 8560 |   | 
        
           |  |  | 8561 | 		CyStringList *files = Dir.DirList("", pattern);
 | 
        
           |  |  | 8562 | 		if ( files )
 | 
        
           |  |  | 8563 | 		{
 | 
        
           |  |  | 8564 | 			for ( SStringList *node = files->Head(); node; node = node->next )
 | 
        
           |  |  | 8565 | 			{
 | 
        
           |  |  | 8566 | 				int error = 0;
 | 
        
           |  |  | 8567 | 				CBaseFile *p = packages.OpenPackage(Dir.File(node->str), &error, 0, SPKREAD_NODATA);
 | 
        
           |  |  | 8568 | 				if ( !p )
 | 
        
           |  |  | 8569 | 					continue;
 | 
        
           |  |  | 8570 |   | 
        
           |  |  | 8571 | 				if ( includeSingle )
 | 
        
           |  |  | 8572 | 					p->CreateUpdateFile(dir);
 | 
        
           |  |  | 8573 | 				filedata.PushBack(CPackages::FormatAvailablePackageData(p));
 | 
        
           |  |  | 8574 | 				delete p;
 | 
        
           |  |  | 8575 | 			}
 | 
        
           |  |  | 8576 | 			delete files;
 | 
        
           |  |  | 8577 | 		}
 | 
        
           |  |  | 8578 | 	}
 | 
        
           |  |  | 8579 |   | 
        
           |  |  | 8580 | 	if ( !filedata.Empty() )
 | 
        
           |  |  | 8581 | 	{
 | 
        
           |  |  | 8582 | 		CFileIO File(dir + "/xpackagedata.dat");
 | 
        
           |  |  | 8583 | 		if ( File.WriteFile(&filedata) )
 | 
        
           |  |  | 8584 | 			return filedata.Count();
 | 
        
           |  |  | 8585 | 	}
 | 
        
           |  |  | 8586 |   | 
        
           |  |  | 8587 | 	return 0;
 | 
        
           |  |  | 8588 | }
 | 
        
           |  |  | 8589 |   | 
        
           |  |  | 8590 | int CPackages::VerifyInstalledFiles(CyStringList *missingFiles, bool getPackages)
 | 
        
           |  |  | 8591 | {
 | 
        
           |  |  | 8592 | 	int count = 0;
 | 
        
           |  |  | 8593 | 	for ( CListNode<C_File> *fn = m_lFiles.Front(); fn; fn = fn->next() )
 | 
        
           |  |  | 8594 | 	{
 | 
        
           |  |  | 8595 | 		C_File *f = fn->Data();
 | 
        
           |  |  | 8596 | 		bool exists = false;
 | 
        
           |  |  | 8597 | 		if ( f->GetFilePointer().IsIn("::") ) {
 | 
        
           |  |  | 8598 | 			CyString modFile = f->GetFilePointer().GetToken("::", 1, 1);
 | 
        
           |  |  | 8599 | 			CyString file = f->GetFilePointer().GetToken("::", 2, 2);
 | 
        
           |  |  | 8600 |   | 
        
           |  |  | 8601 | 			if ( CFileIO(modFile).Exists() ) {
 | 
        
           |  |  | 8602 | 				CCatFile catFile;
 | 
        
           |  |  | 8603 | 				if ( catFile.Open(modFile, "", CATREAD_CATDECRYPT, false) == CATERR_NONE ) {
 | 
        
           |  |  | 8604 | 					if ( catFile.FindData(file) )
 | 
        
           |  |  | 8605 | 						exists = true;
 | 
        
           |  |  | 8606 | 				}
 | 
        
           |  |  | 8607 | 			}
 | 
        
           |  |  | 8608 | 		}
 | 
        
           |  |  | 8609 | 		else {
 | 
        
           |  |  | 8610 | 			exists = CFileIO(f->GetFilePointer()).Exists();
 | 
        
           |  |  | 8611 | 		}
 | 
        
           |  |  | 8612 |   | 
        
           |  |  | 8613 | 		if ( !exists )
 | 
        
           |  |  | 8614 | 		{
 | 
        
           |  |  | 8615 | 			++count;
 | 
        
           |  |  | 8616 | 			if ( missingFiles )
 | 
        
           |  |  | 8617 | 			{
 | 
        
           |  |  | 8618 | 				CyString packages;
 | 
        
           |  |  | 8619 | 				if ( getPackages )
 | 
        
           |  |  | 8620 | 				{
 | 
        
           |  |  | 8621 | 					for ( CListNode<CBaseFile> *p = m_lPackages.Front(); p; p = p->next() )
 | 
        
           |  |  | 8622 | 					{
 | 
        
           |  |  | 8623 | 						CBaseFile *package = p->Data();
 | 
        
           |  |  | 8624 | 						if ( package->IsFileAdded(f) )
 | 
        
           |  |  | 8625 | 						{
 | 
        
           |  |  | 8626 | 							if ( !packages.Empty() )
 | 
        
           |  |  | 8627 | 								packages += "\n";
 | 
        
           |  |  | 8628 | 							packages += package->GetFullPackageName(m_iLanguage);
 | 
        
           |  |  | 8629 | 						}
 | 
        
           |  |  | 8630 | 					}
 | 
        
           |  |  | 8631 | 				}
 | 
        
           |  |  | 8632 | 				CyString filename = f->GetFilePointer();
 | 
        
           |  |  | 8633 | 				filename = filename.Remove(m_sCurrentDir);
 | 
        
           |  |  | 8634 | 				missingFiles->PushBack(filename, packages, false);
 | 
        
           |  |  | 8635 | 			}
 | 
        
           |  |  | 8636 | 		}
 | 
        
           |  |  | 8637 | 	}
 | 
        
           |  |  | 8638 | 	return count;
 | 
        
           |  |  | 8639 | }
 |