summaryrefslogtreecommitdiff
path: root/klm/util/read_compressed.cc
diff options
context:
space:
mode:
authorPaul Baltescu <pauldb89@gmail.com>2013-02-21 14:13:55 +0000
committerPaul Baltescu <pauldb89@gmail.com>2013-02-21 14:13:55 +0000
commitbca26d953a774b8efca12f30407390b3f5eef9d0 (patch)
treefe922de5c89b1844f677d550dcc24e87edd67a55 /klm/util/read_compressed.cc
parent54a1c0e2bde259e3acc9c0a8ec8da3c7704e80ca (diff)
parent95c364f2cb002241c4a62bedb1c5ef6f1e9a7f22 (diff)
Merge branch 'master' of https://github.com/pauldb89/cdec
Diffstat (limited to 'klm/util/read_compressed.cc')
-rw-r--r--klm/util/read_compressed.cc30
1 files changed, 28 insertions, 2 deletions
diff --git a/klm/util/read_compressed.cc b/klm/util/read_compressed.cc
index 4ec94c4e..b81549e4 100644
--- a/klm/util/read_compressed.cc
+++ b/klm/util/read_compressed.cc
@@ -320,6 +320,23 @@ class XZip : public ReadBase {
};
#endif // HAVE_XZLIB
+class IStreamReader : public ReadBase {
+ public:
+ explicit IStreamReader(std::istream &stream) : stream_(stream) {}
+
+ std::size_t Read(void *to, std::size_t amount, ReadCompressed &thunk) {
+ if (!stream_.read(static_cast<char*>(to), amount)) {
+ UTIL_THROW_IF(!stream_.eof(), ErrnoException, "istream error");
+ amount = stream_.gcount();
+ }
+ ReadCount(thunk) += amount;
+ return amount;
+ }
+
+ private:
+ std::istream &stream_;
+};
+
enum MagicResult {
UNKNOWN, GZIP, BZIP, XZIP
};
@@ -329,7 +346,7 @@ MagicResult DetectMagic(const void *from_void) {
if (header[0] == 0x1f && header[1] == 0x8b) {
return GZIP;
}
- if (header[0] == 'B' && header[1] == 'Z') {
+ if (header[0] == 'B' && header[1] == 'Z' && header[2] == 'h') {
return BZIP;
}
const uint8_t xzmagic[6] = { 0xFD, '7', 'z', 'X', 'Z', 0x00 };
@@ -370,7 +387,7 @@ ReadBase *ReadFactory(int fd, uint64_t &raw_amount) {
break;
}
try {
- AdvanceOrThrow(fd, -ReadCompressed::kMagicSize);
+ SeekOrThrow(fd, 0);
} catch (const util::ErrnoException &e) {
return new UncompressedWithHeader(hold.release(), header, ReadCompressed::kMagicSize);
}
@@ -387,6 +404,10 @@ ReadCompressed::ReadCompressed(int fd) {
Reset(fd);
}
+ReadCompressed::ReadCompressed(std::istream &in) {
+ Reset(in);
+}
+
ReadCompressed::ReadCompressed() {}
ReadCompressed::~ReadCompressed() {}
@@ -396,6 +417,11 @@ void ReadCompressed::Reset(int fd) {
internal_.reset(ReadFactory(fd, raw_amount_));
}
+void ReadCompressed::Reset(std::istream &in) {
+ internal_.reset();
+ internal_.reset(new IStreamReader(in));
+}
+
std::size_t ReadCompressed::Read(void *to, std::size_t amount) {
return internal_->Read(to, amount, *this);
}