1 /*
2  *  compression/DecompressorGZIP.cpp
3  *
4  *  Copyright 2009 Peter Barth
5  *
6  *  This file is part of Milkytracker.
7  *
8  *  Milkytracker is free software: you can redistribute it and/or modify
9  *  it under the terms of the GNU General Public License as published by
10  *  the Free Software Foundation, either version 3 of the License, or
11  *  (at your option) any later version.
12  *
13  *  Milkytracker is distributed in the hope that it will be useful,
14  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
15  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16  *  GNU General Public License for more details.
17  *
18  *  You should have received a copy of the GNU General Public License
19  *  along with Milkytracker.  If not, see <http://www.gnu.org/licenses/>.
20  *
21  */
22 
23 /*
24  *  DecompressorGZIP.cpp
25  *  milkytracker_universal
26  *
27  *  Created by Peter Barth on 22.06.08.
28  *
29  */
30 
31 #include "DecompressorGZIP.h"
32 #include "XMFile.h"
33 #include "LittleEndian.h"
34 #include "zlib.h"
35 
36 // -- GZIP --------------------------------------------------------------------
DecompressorGZIP(const PPSystemString & fileName)37 DecompressorGZIP::DecompressorGZIP(const PPSystemString& fileName) :
38 	DecompressorBase(fileName)
39 {
40 }
41 
identify(XMFile & f)42 bool DecompressorGZIP::identify(XMFile& f)
43 {
44 	f.seek(0);
45 	mp_dword id = f.readDword();
46 
47 	// GZIP ID
48 	return (id == 0x08088B1F);
49 }
50 
getDescriptors(Hints hint) const51 const PPSimpleVector<Descriptor>& DecompressorGZIP::getDescriptors(Hints hint) const
52 {
53 	descriptors.clear();
54 	descriptors.add(new Descriptor("gz", "GZIP Archive"));
55 	return descriptors;
56 }
57 
decompress(const PPSystemString & outFileName,Hints hint)58 bool DecompressorGZIP::decompress(const PPSystemString& outFileName, Hints hint)
59 {
60 	gzFile gz_input_file = NULL;
61 	int len = 0;
62 	pp_uint8 *buf;
63 
64 	if ((gz_input_file = gzopen (fileName.getStrBuffer(), "r")) == NULL)
65 		return false;
66 
67 	if ((buf = new pp_uint8[0x10000]) == NULL)
68 		return false;
69 
70 	XMFile fOut(outFileName, true);
71 
72 	while (true)
73 	{
74 		len = gzread (gz_input_file, buf, 0x10000);
75 
76 		if (len < 0)
77 		{
78 			delete[] buf;
79 			return false;
80 		}
81 
82 		if (len == 0) break;
83 
84 		fOut.write(buf, 1, len);
85 	}
86 
87 	if (gzclose (gz_input_file) != Z_OK)
88 	{
89 		delete[] buf;
90 		return false;
91 	}
92 
93 	delete[] buf;
94 
95 	return true;
96 }
97 
clone()98 DecompressorBase* DecompressorGZIP::clone()
99 {
100 	return new DecompressorGZIP(fileName);
101 }
102 
103 static Decompressor::RegisterDecompressor<DecompressorGZIP> registerDecompressor;
104