Botan 3.3.0
Crypto and TLS for C&
bzip2.cpp
Go to the documentation of this file.
1/*
2* Bzip2 Compressor
3* (C) 2001 Peter J Jones
4* 2001-2007,2014 Jack Lloyd
5* 2006 Matt Johnston
6*
7* Botan is released under the Simplified BSD License (see license.txt)
8*/
9
10#include <botan/bzip2.h>
11
12#include <botan/exceptn.h>
13#include <botan/internal/compress_utils.h>
14
15#define BZ_NO_STDIO
16#include <bzlib.h>
17
18namespace Botan {
19
20namespace {
21
22class Bzip2_Stream : public Zlib_Style_Stream<bz_stream, char, unsigned int> {
23 public:
24 Bzip2_Stream() {
25 streamp()->opaque = alloc();
26 streamp()->bzalloc = Compression_Alloc_Info::malloc<int>;
27 streamp()->bzfree = Compression_Alloc_Info::free;
28 }
29
30 uint32_t run_flag() const override { return BZ_RUN; }
31
32 uint32_t flush_flag() const override { return BZ_FLUSH; }
33
34 uint32_t finish_flag() const override { return BZ_FINISH; }
35};
36
37class Bzip2_Compression_Stream final : public Bzip2_Stream {
38 public:
39 explicit Bzip2_Compression_Stream(size_t block_size) {
40 /*
41 * Defaults to 900k blocks as the computation cost of
42 * compression is not overly affected by the size, though
43 * more memory is required.
44 */
45 if(block_size == 0 || block_size >= 9) {
46 block_size = 9;
47 }
48
49 int rc = BZ2_bzCompressInit(streamp(), static_cast<unsigned int>(block_size), 0, 0);
50
51 if(rc != BZ_OK) {
52 throw Compression_Error("BZ2_bzCompressInit", ErrorType::Bzip2Error, rc);
53 }
54 }
55
56 Bzip2_Compression_Stream(const Bzip2_Compression_Stream& other) = delete;
57 Bzip2_Compression_Stream(Bzip2_Compression_Stream&& other) = delete;
58 Bzip2_Compression_Stream& operator=(const Bzip2_Compression_Stream& other) = delete;
59 Bzip2_Compression_Stream& operator=(Bzip2_Compression_Stream&& other) = delete;
60
61 ~Bzip2_Compression_Stream() override { BZ2_bzCompressEnd(streamp()); }
62
63 bool run(uint32_t flags) override {
64 int rc = BZ2_bzCompress(streamp(), flags);
65
66 if(rc < 0) {
67 throw Compression_Error("BZ2_bzCompress", ErrorType::Bzip2Error, rc);
68 }
69
70 return (rc == BZ_STREAM_END);
71 }
72};
73
74class Bzip2_Decompression_Stream final : public Bzip2_Stream {
75 public:
76 Bzip2_Decompression_Stream() {
77 int rc = BZ2_bzDecompressInit(streamp(), 0, 0);
78
79 if(rc != BZ_OK) {
80 throw Compression_Error("BZ2_bzDecompressInit", ErrorType::Bzip2Error, rc);
81 }
82 }
83
84 Bzip2_Decompression_Stream(const Bzip2_Decompression_Stream& other) = delete;
85 Bzip2_Decompression_Stream(Bzip2_Decompression_Stream&& other) = delete;
86 Bzip2_Decompression_Stream& operator=(const Bzip2_Decompression_Stream& other) = delete;
87 Bzip2_Decompression_Stream& operator=(Bzip2_Decompression_Stream&& other) = delete;
88
89 ~Bzip2_Decompression_Stream() override { BZ2_bzDecompressEnd(streamp()); }
90
91 bool run(uint32_t) override {
92 int rc = BZ2_bzDecompress(streamp());
93
94 if(rc != BZ_OK && rc != BZ_STREAM_END) {
95 throw Compression_Error("BZ2_bzDecompress", ErrorType::Bzip2Error, rc);
96 }
97
98 return (rc == BZ_STREAM_END);
99 }
100};
101
102} // namespace
103
104std::unique_ptr<Compression_Stream> Bzip2_Compression::make_stream(size_t comp_level) const {
105 return std::make_unique<Bzip2_Compression_Stream>(comp_level);
106}
107
108std::unique_ptr<Compression_Stream> Bzip2_Decompression::make_stream() const {
109 return std::make_unique<Bzip2_Decompression_Stream>();
110}
111
112} // namespace Botan
static void free(void *self, void *ptr)
int(* final)(unsigned char *, CTX *)