AlcapDAQ  1
Functions | Variables
comp_compress.cpp File Reference
#include <stdio.h>
#include "midas.h"
#include "mucap_compress.h"
#include "mucap_structures.h"

Go to the source code of this file.

Functions

void comp_optimize ()
 
void comp_load ()
 
static int sign_extend (int in, int bits)
 
int encode_cmp_bits (comp_word *input, int input_size, io_buffer *output)
 
int encode_cmp_times (comp_word *input, int input_size, io_buffer *output)
 
int cmp_compress (comp_word *input, int input_size, unsigned char *output, int userParam)
 
void decode_cmp_times (io_buffer *input, comp_word *output)
 
void decode_cmp_bits (io_buffer *input, comp_word *output, int output_size)
 
int cmp_expand (unsigned char *input, int input_size, comp_word *output, int userParam)
 

Variables

huffman_table cmp_bits_huffman [2]
 
huffman_table cmp_channel_huffman
 
BOOL should_compress_comp = TRUE
 

Function Documentation

int cmp_compress ( comp_word input,
int  input_size,
unsigned char *  output,
int  userParam 
)

Definition at line 133 of file comp_compress.cpp.

References encode_cmp_bits(), encode_cmp_times(), rle_bits_setup(), and start_output_buffer().

Referenced by compress_event().

134 {
135  //
136  // Encode compressor data, which are in the following format:
137  // | B | A | FPGA number (6 bits) | Time (24 bits) |
138  // ... followed by one or two 32-bit masks indicating which
139  // channels
140  // within the group have fired.
141  //
142 
143  input_size /= sizeof(comp_word);
144 
145  rle_bits_setup();
146 
147  io_buffer output_buffer;
148 
149  // store size of input data
150  int *uncompressed_size_p = (int *) output;
151  *uncompressed_size_p = input_size;
152  output += sizeof(int);
153 
154  // reserve space for the size of the compressed times
155  int *compressed_time_size_p = (int *) output;
156  output += sizeof(int);
157 
158  // compress times
159  start_output_buffer(&output_buffer, output);
160  int compressed_time_size =
161  encode_cmp_times(input, input_size, &output_buffer);
162  output += compressed_time_size;
163 
164  // store size of compressed times
165  *compressed_time_size_p = compressed_time_size;
166 
167  // reserve space for the size of the compressed bit patterns
168  int *compressed_bits_size_p = (int *) output;
169  output += sizeof(int);
170 
171  // compress bit patterns
172  start_output_buffer(&output_buffer, output);
173  int compressed_bits_size =
174  encode_cmp_bits(input, input_size, &output_buffer);
175  output += compressed_time_size;
176 
177  // store size of compressed bit patterns
178  *compressed_bits_size_p = compressed_bits_size;
179 
180  return compressed_time_size + compressed_bits_size + 3 * sizeof(int);
181 }
int cmp_expand ( unsigned char *  input,
int  input_size,
comp_word output,
int  userParam 
)

Definition at line 243 of file comp_compress.cpp.

References decode_cmp_bits(), decode_cmp_times(), rle_bits_setup(), and start_input_buffer().

Referenced by expand_event().

244 {
245  //
246  // Uncompress the data produced by cmp_compress().
247  //
248 
249  rle_bits_setup();
250 
251  // Get uncompressed data size
252  int *uncompressed_size_p = (int *) input;
253  int uncompressed_size = *uncompressed_size_p;
254  input += sizeof(int);
255  input_size -= sizeof(int);
256 
257  // Get size of compressed time data
258  int *compressed_time_size_p = (int *) input;
259  int compressed_time_size = *compressed_time_size_p;
260  input += sizeof(int);
261  input_size -= sizeof(int);
262 
263  // Uncompress times
264  io_buffer input_buffer;
265  start_input_buffer(&input_buffer, input);
266  decode_cmp_times(&input_buffer, output);
267  input += compressed_time_size;
268  input_size -= compressed_time_size;
269 
270  // Get size of compressed bit patterns
271  int *compressed_bits_size_p = (int *) input;
272  int compressed_bits_size = *compressed_bits_size_p;
273  input += sizeof(int);
274  input_size -= sizeof(int);
275 
276  // Uncompress bit patterns
277  start_input_buffer(&input_buffer, input);
278  decode_cmp_bits(&input_buffer, output, uncompressed_size);
279 
280  return uncompressed_size * sizeof(comp_word);
281 }
void comp_load ( )

Definition at line 29 of file comp_compress.cpp.

References hDB, huffman_init_default(), load_huffman(), should_compress_comp, size, and TRUE.

Referenced by compress_load_all().

30 {
34 
35  load_huffman("/Compression/Lossless/COMP/Huffman/Channel", &cmp_channel_huffman);
36  load_huffman("/Compression/Lossless/COMP/Huffman/Bits 0", &cmp_bits_huffman[0]);
37  load_huffman("/Compression/Lossless/COMP/Huffman/Bits 1", &cmp_bits_huffman[1]);
38 
39  int size = sizeof(BOOL);
40  db_get_value(hDB, 0, "/Compression/Lossless/COMP/Enabled", &should_compress_comp,
41  &size, TID_BOOL, TRUE);
42 }
void comp_optimize ( )

Definition at line 18 of file comp_compress.cpp.

References huffman_optimize_tree(), and save_huffman().

Referenced by compress_optimize_all().

19 {
23 
24  save_huffman("/Compression/Lossless/COMP/Huffman/Channel", &cmp_channel_huffman);
25  save_huffman("/Compression/Lossless/COMP/Huffman/Bits 0", &cmp_bits_huffman[0]);
26  save_huffman("/Compression/Lossless/COMP/Huffman/Bits 1", &cmp_bits_huffman[1]);
27 }
void decode_cmp_bits ( io_buffer input,
comp_word output,
int  output_size 
)

Definition at line 225 of file comp_compress.cpp.

References comp_word::a, comp_word::b, comp_word::bytes, i, comp_word::r1, rle_get(), and s.

Referenced by cmp_expand().

226 {
227  int num_bit_words = 0;
228 
229  rle_state s = { 1, 0, {128, 128}, 0, cmp_bits_huffman };
230 
231  for (int i = 0; i < output_size; i++) {
232  if (num_bit_words == 0) {
233  num_bit_words = output[i].r1.a + output[i].r1.b;
234  } else {
235  for (int j = 0; j < 4; j++) {
236  output[i].bytes[j] = rle_get(input, &s);
237  }
238  num_bit_words--;
239  }
240  }
241 }
void decode_cmp_times ( io_buffer input,
comp_word output 
)

Definition at line 183 of file comp_compress.cpp.

References comp_word::a, comp_word::b, channel, comp_word::fpga, huffman_get_symbol(), i, io_buffer_get(), io_buffer::num_codes, comp_word::r1, sign_extend(), and comp_word::time.

Referenced by cmp_expand().

184 {
185  //
186  // Reverse the encoding performed by encode_times.
187  //
188 
189  int num_words_in = input->num_codes;
190  int output_size = 0;
191  int prev_time = 0;
192 
193  for (int i = 0; i < num_words_in; i++) {
194 
196  output[output_size].r1.fpga = channel & 0x3f;
197  output[output_size].r1.a = (channel >> 6) & 1;
198  output[output_size].r1.b = (channel >> 7) & 1;
199 
200  int time_length_flag1 = io_buffer_get(input, 1);
201  int time_diff;
202  if (time_length_flag1 == 0) {
203  time_diff = io_buffer_get(input, 4);
204  time_diff = sign_extend(time_diff, 4);
205  } else {
206  int time_length_flag2 = io_buffer_get(input, 1);
207  if (time_length_flag2 == 0) {
208  time_diff = io_buffer_get(input, 10);
209  time_diff = sign_extend(time_diff, 10);
210  } else {
211  time_diff = io_buffer_get(input, 24);
212  time_diff = sign_extend(time_diff, 24);
213  }
214  }
215 
216  output[output_size].r1.time = (prev_time + time_diff) & 0xffffff;
217  prev_time = output[output_size].r1.time;
218 
219  int num_bit_words =
220  output[output_size].r1.a + output[output_size].r1.b;
221  output_size += 1 + num_bit_words;
222  }
223 }
int encode_cmp_bits ( comp_word input,
int  input_size,
io_buffer output 
)

Definition at line 54 of file comp_compress.cpp.

References comp_word::a, comp_word::b, comp_word::bytes, flush_rle(), i, comp_word::r1, rle_put(), and s.

Referenced by cmp_compress().

55 {
56  //
57  // Run-length encode the bits in the compressor data. See the comment
58  // at the beginning of encode_bits for an explanation of this process.
59  //
60 
61  int num_bit_words = 0;
62  rle_state s = { 0, 0, {128, 128}, 0, cmp_bits_huffman };
63 
64  for (int i = 0; i < input_size; i++) {
65  // This word may be a header/time word:
66  if (num_bit_words == 0) {
67  num_bit_words = input[i].r1.a + input[i].r1.b;
68  } else {
69  for (int j = 0; j < 4; j++) {
70 
71  unsigned char b = input[i].bytes[j];
72  rle_put(b, &s, output);
73  }
74  num_bit_words--;
75  }
76  }
77 
78  return flush_rle(&s, output);
79 }
int encode_cmp_times ( comp_word input,
int  input_size,
io_buffer output 
)

Definition at line 81 of file comp_compress.cpp.

References comp_word::a, comp_word::b, channel, flush_output_buffer(), comp_word::fpga, huffman_put_symbol(), i, io_buffer_put(), printf(), comp_word::r1, and comp_word::time.

Referenced by cmp_compress().

82 {
83  //
84  // Encode the FPGA numbers and times in the compressor data.
85  //
86  // 1. The B and A bits, which indicate the meaning of the
87  // following words, are preserved.
88  // 2. The FPGA numbers are Huffman coded, since some values are
89  // probably more likely than others.
90  // 3. The times are encoded as successive differences, which are
91  // then stored on a variable scale.
92  //
93 
94  int num_bit_words = 0;
95  int prev_time = 0;
96 
97  for (int i = 0; i < input_size; i++) {
98  // This word may be a header/time word:
99  if (num_bit_words == 0) {
100  num_bit_words = input[i].r1.a + input[i].r1.b;
101 
102  if (num_bit_words != 1 && num_bit_words != 2) {
103  printf("Warning: corrupted compressor data.\n");
104  }
105 
106  int channel = input[i].r1.fpga | input[i].r1.a << 6 | input[i].r1.b << 7;
107  huffman_put_symbol(&cmp_channel_huffman, output, channel);
108 
109  int time_diff = input[i].r1.time - prev_time;
110 
111  if (time_diff < 8 && time_diff >= -8) {
112  io_buffer_put(output, 0, 1);
113  io_buffer_put(output, time_diff & 0xf, 4);
114  } else if (time_diff < 512 && time_diff >= -512) {
115  io_buffer_put(output, 2, 2);
116  io_buffer_put(output, time_diff & 0x3ff, 10);
117  } else {
118  io_buffer_put(output, 3, 2);
119  io_buffer_put(output, time_diff & 0xffffff, 24);
120  }
121 
122  prev_time = input[i].r1.time;
123  }
124 
125  else {
126  num_bit_words--;
127  }
128  }
129 
130  return flush_output_buffer(output);
131 }
static int sign_extend ( int  in,
int  bits 
)
static

Definition at line 44 of file comp_compress.cpp.

Referenced by decode_cmp_times().

45 {
46  int sign_bit = (1 << (bits-1));
47  if(in & sign_bit) {
48  return in | ~(sign_bit - 1);
49  } else {
50  return in;
51  }
52 }

Variable Documentation

huffman_table cmp_bits_huffman[2]

Definition at line 14 of file comp_compress.cpp.

huffman_table cmp_channel_huffman

Definition at line 15 of file comp_compress.cpp.

BOOL should_compress_comp = TRUE

Definition at line 16 of file comp_compress.cpp.

Referenced by comp_load(), and compress_event().