CMS 3D CMS Logo

LHEXMLStringProduct.cc
Go to the documentation of this file.
1 #include <iostream>
2 #include <algorithm>
3 #include <lzma.h>
4 
6 
8 
9 using namespace edm;
10 using namespace std;
11 
12 
14 {
15 }
16 
17 LHEXMLStringProduct::LHEXMLStringProduct(const string& onelheoutput) :
18  content_()
19 {
20  content_.push_back(onelheoutput);
21 }
22 
23 
25 {
26 }
27 
28 void LHEXMLStringProduct::fillCompressedContent(std::istream &input, unsigned int initialSize) {
29  //create blob with desired size
30  compressedContent_.emplace_back(initialSize);
31  std::vector<uint8_t> &output = compressedContent_.back();
32 
33  //read buffer
34  constexpr unsigned int bufsize = 4096;
35  char inbuf[bufsize];
36 
37  const unsigned int threshsize = 32*1024*1024;
38 
39  //initialize lzma
40  uint32_t preset = 9;
41  lzma_stream strm = LZMA_STREAM_INIT;
42  lzma_ret ret = lzma_easy_encoder(&strm, preset, LZMA_CHECK_CRC64);
43 
44  lzma_action action = LZMA_RUN;
45 
46  strm.next_in = reinterpret_cast<uint8_t*>(&inbuf[0]);
47  strm.avail_in = 0;
48  strm.next_out = output.data();
49  strm.avail_out = output.size();
50 
51  unsigned int compressedSize = 0;
52 
53  while (ret==LZMA_OK) {
54  //read input to buffer if necessary
55  if (strm.avail_in == 0 && !input.eof()) {
56  input.read(inbuf, bufsize);
57  strm.next_in = reinterpret_cast<uint8_t*>(&inbuf[0]);
58  strm.avail_in = input.gcount();
59  if (input.eof()) {
60  //signal to lzma that there is no more input
61  action = LZMA_FINISH;
62  }
63  }
64 
65  //actual compression
66  ret = lzma_code(&strm, action);
67 
68  //update compressed size
69  compressedSize = output.size() - strm.avail_out;
70 
71  //if output blob is full and compression is still going, allocate more memory
72  if (strm.avail_out == 0 && ret==LZMA_OK) {
73  unsigned int oldsize = output.size();
74  if (oldsize<threshsize) {
75  output.resize(2*oldsize);
76  }
77  else {
78  output.resize(oldsize + threshsize);
79  }
80  strm.next_out = &output[oldsize];
81  strm.avail_out = output.size() - oldsize;
82  }
83 
84  }
85 
86  lzma_end(&strm);
87 
88  if (ret!=LZMA_STREAM_END) {
89  throw cms::Exception("CompressionError")
90  << "There was a failure in LZMA compression in LHEXMLStringProduct.";
91  }
92 
93  //trim output blob
94  output.resize(compressedSize);
95 
96 }
97 
98 void LHEXMLStringProduct::writeCompressedContent(std::ostream &output, unsigned int i) const {
99 
100  //initialize lzma
101  lzma_stream strm = LZMA_STREAM_INIT;
102  lzma_ret ret = lzma_stream_decoder(&strm, UINT64_MAX, LZMA_CONCATENATED);
103  //all output available from the start, so start "close out" immediately
104  lzma_action action = LZMA_FINISH;
105 
106  //write buffer
107  constexpr unsigned int bufsize = 4096;
108  char outbuf[bufsize];
109 
110  const std::vector<uint8_t> &input = compressedContent_[i];
111 
112  strm.next_in = input.data();
113  strm.avail_in = input.size();
114  strm.next_out = reinterpret_cast<uint8_t*>(&outbuf[0]);
115  strm.avail_out = bufsize;
116 
117  while (ret==LZMA_OK) {
118 
119  ret = lzma_code(&strm, action);
120 
121  //write to stream
122  output.write(outbuf,bufsize-strm.avail_out);
123 
124  //output buffer full, recycle
125  if (strm.avail_out==0 && ret==LZMA_OK) {
126  strm.next_out = reinterpret_cast<uint8_t*>(&outbuf[0]);
127  strm.avail_out = bufsize;
128  }
129  }
130 
131  lzma_end(&strm);
132 
133  if (ret!=LZMA_STREAM_END) {
134  throw cms::Exception("DecompressionError")
135  << "There was a failure in LZMA decompression in LHEXMLStringProduct.";
136  }
137 
138 }
139 
140 
141 
143 {
144  content_.insert(content_.end(), other.getStrings().begin(), other.getStrings().end());
145  compressedContent_.insert(compressedContent_.end(), other.getCompressed().begin(), other.getCompressed().end());
146  return true;
147 }
148 
int i
Definition: DBlmapReader.cc:9
const std::vector< std::string > & getStrings() const
#define constexpr
static std::string const input
Definition: EdmProvDump.cc:44
const std::vector< std::vector< uint8_t > > & getCompressed() const
HLT enums.
void writeCompressedContent(std::ostream &output, unsigned int i) const
bool mergeProduct(LHEXMLStringProduct const &other)
void fillCompressedContent(std::istream &input, unsigned int initialSize=4 *1024 *1024)