]> git.mxchange.org Git - quix0rs-blobwars.git/blob - src/CPak.cpp
Use time_t to store time data.
[quix0rs-blobwars.git] / src / CPak.cpp
1 /*
2 Copyright (C) 2004-2011 Parallel Realities
3 Copyright (C) 2011-2015 Perpendicular Dimensions
4
5 This program is free software; you can redistribute it and/or
6 modify it under the terms of the GNU General Public License
7 as published by the Free Software Foundation; either version 2
8 of the License, or (at your option) any later version.
9
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
13
14 See the GNU General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with this program; if not, write to the Free Software
18 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
19
20 */
21
22 #include "headers.h"
23
24 Pak::Pak()
25 {
26         input = NULL;
27         fd = NULL;
28         
29         numberOfFiles = 0;
30         listPos = 0;
31         currentFile = NULL;
32
33         pakFilename[0] = 0;
34         filename[0] = 0;
35 }
36
37 Pak::~Pak()
38 {
39         delete[] input;
40         delete[] fd;
41 }
42
43 void Pak::showPakErrorAndExit()
44 {
45         printf("\nFatal Error: The Blob Wars PAK file was either not found or was not accessable.\n");
46         printf("(If you compiled from source did you forget to run make install?)\n");
47         printf("The path to the file was expected to be,\n\n");
48         printf(PAKFULLPATH"\n\n");
49         printf("Please try running the game again. If problems persist either reinstall the game or check,\n\n");
50         printf("http://www.parallelrealities.co.uk/blobWars.php\n\n");
51         printf("for updates.\n\n");
52         exit(1);
53 }
54
55 void Pak::setPakFile(const char *pakFilename)
56 {
57         #if USEPAK
58         strlcpy(this->pakFilename, pakFilename, sizeof this->pakFilename);
59         
60         debug(("Pak : Filename set to %s\n", pakFilename));
61
62         FILE *pak = fopen(pakFilename, "rb");
63
64         if (!pak)
65         {
66                 return showPakErrorAndExit();
67         }
68
69         fseek(pak, (-sizeof(Uint32)) * 2, SEEK_END);
70         if (fread(&listPos, sizeof(Uint32), 1, pak) != 1)
71         {
72                 fclose(pak);
73                 return showPakErrorAndExit();
74         }
75         if (fread(&numberOfFiles, sizeof(Uint32), 1, pak) != 1)
76         {
77                 fclose(pak);
78                 return showPakErrorAndExit();
79         }
80         
81         debug(("Pak : File list resides at %d\n", (int)listPos));
82         debug(("Pak : Number of files are %d\n", (int)numberOfFiles));
83         
84         fd = new FileData[numberOfFiles];
85         
86         fseek(pak, listPos, SEEK_SET);
87         
88         int result = 0;
89         
90         for (unsigned int i = 0 ; i < numberOfFiles ; i++)
91         {
92                 result = fread(&fd[i], sizeof(FileData), 1, pak);
93                 
94                 if (!result)
95                 {
96                         fclose(pak);
97                         return showPakErrorAndExit();
98                 }
99                 
100                 debug(("Read FileData #%d / %d : %s\n", (i + 1), numberOfFiles, fd[i].filename));
101         }
102         
103         fclose(pak);
104
105         #else
106         (void)pakFilename;
107         #endif
108 }
109
110 bool Pak::unpack(const char *filename, unsigned char **buffer)
111 {
112         debug(("Pak : Unpacking %s...\n", filename));
113         
114         currentFile = NULL;
115         
116         for (unsigned int i = 0 ; i < numberOfFiles ; i++)
117         {
118                 if (strcmp(filename, fd[i].filename) == 0)
119                 {
120                         currentFile = &fd[i];
121                         break;
122                 }
123         }
124         
125         if (currentFile == NULL)
126         {
127                 return false;
128         }
129         
130         FILE *pak = fopen(pakFilename, "rb");
131         if (!pak)
132         {
133                 showPakErrorAndExit();
134         }
135         
136         fseek(pak, currentFile->location, SEEK_SET);
137
138         delete[] input;
139         input = NULL;
140         
141         input = new unsigned char[(int)(currentFile->cSize * 1.01) + 12];
142         *buffer = new unsigned char[currentFile->fSize + 1];
143
144         if (fread(input, 1, currentFile->cSize, pak) != currentFile->cSize)
145         {
146                 fclose(pak);
147                 return showPakErrorAndExit(), false;
148         }
149         
150         uLongf fSize = (uLongf)currentFile->fSize;
151         
152         uncompress(*buffer, &fSize, input, currentFile->cSize);
153         (*buffer)[currentFile->fSize] = 0;
154
155         fclose(pak);
156         
157         delete[] input;
158         input = NULL;
159         
160         debug(("Pak : Unpack %s...Done\n", filename));
161
162         return true;
163 }
164
165 bool Pak::fileExists(const char *filename)
166 {
167         for (unsigned int i = 0 ; i < numberOfFiles ; i++)
168         {
169                 if (strcmp(fd[i].filename, filename) == 0)
170                 {
171                         return true;
172                 }
173         }
174         
175         return false;
176 }
177
178 unsigned int Pak::getUncompressedSize() const
179 {
180         return (unsigned int)currentFile->fSize;
181 }