Skip to content
This repository
tree: 9ef4c036b7
Fetching contributors…

Octocat-spinner-32-eaf2f5

Cannot retrieve contributors at this time

file 85 lines (75 sloc) 3.069 kb
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84
/************************************************************************/
/* */
/* This file is part of VDrift. */
/* */
/* VDrift is free software: you can redistribute it and/or modify */
/* it under the terms of the GNU General Public License as published by */
/* the Free Software Foundation, either version 3 of the License, or */
/* (at your option) any later version. */
/* */
/* VDrift is distributed in the hope that it will be useful, */
/* but WITHOUT ANY WARRANTY; without even the implied warranty of */
/* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the */
/* GNU General Public License for more details. */
/* */
/* You should have received a copy of the GNU General Public License */
/* along with VDrift. If not, see <http://www.gnu.org/licenses/>. */
/* */
/************************************************************************/

#include <archive.h>
#include <archive_entry.h>
#include <fstream>
#include "archiveutils.h"
#include "pathmanager.h"

#define BUFFSIZE 10240

bool Decompress(const std::string & file, const std::string & output_path, std::ostream & info_output, std::ostream & error_output)
{
// Ensure the output path exists.
PATHMANAGER::MakeDir(output_path);

struct archive * a = archive_read_new();
archive_read_support_compression_all(a);
archive_read_support_format_all(a);
if (archive_read_open_filename(a, file.c_str(), BUFFSIZE) != ARCHIVE_OK)
{
error_output << "Unable to open " << file << std::endl;
return false;
}

char buff[BUFFSIZE];
struct archive_entry *entry;
while (archive_read_next_header(a, &entry) == ARCHIVE_OK)
{
std::string filename = archive_entry_pathname(entry);
std::string fullpath = output_path + "/" + filename;

if (archive_entry_filetype(entry) == AE_IFDIR)
PATHMANAGER::MakeDir(fullpath);
else
{
std::fstream f(fullpath.c_str(), std::ios_base::out | std::ios_base::binary | std::ios_base::trunc);
if (!f)
{
error_output << "Unable to open file for write (permissions issue?): " << fullpath << std::endl;
return false;
}

int size = -1;
while (size != 0)
{
size = archive_read_data(a, buff, BUFFSIZE);
if (size < 0)
{
error_output << "Encountered corrupt file: " << filename << std::endl;
return false;
}
else if (size != 0)
f.write(buff, size);
}
}

archive_read_data_skip(a);
}
if (archive_read_finish(a) != ARCHIVE_OK)
{
error_output << "Unable to finish read of " << file << std::endl;
return false;
}

info_output << "Successfully decompressed " << file << std::endl;
return true;
}
Something went wrong with that request. Please try again.