// ******************************************************************************************** void HuffmanEncoder::StoreTree(BitStream& bit_stream, HuffmanEncoder& tree) { static uchar* mem_buf = NULL; static uint32 mem_size; tree.StoreTree(mem_buf, mem_size); my_assert(mem_size > 0); my_assert(mem_buf); bit_stream.FlushPartialWordBuffer(); bit_stream.PutWord(mem_size); bit_stream.PutBytes(mem_buf, mem_size); delete [] mem_buf; }
// ******************************************************************************************** void Block::Process(BitStream &bit_stream, LzMatcher &lz_matcher, std::vector<Field> &fields, uint32 /*n_fields*/, uint32 fastq_flags, uchar *sym_code, HuffmanEncoder::Code *sym_huf_codes, uchar *qua_code, HuffmanEncoder::Code **qua_huf_codes, uint32 /*max_run_len*/, HuffmanEncoder::Code **run_huf_codes, uint32 n_qualities, uint32 _global_max_sequence_length, uint32 max_quality_length, uint32 block_no, uint32 _quality_stats_mode) { global_max_sequence_length = _global_max_sequence_length; #if (D_RESERVE_BYTES_PER_BLOCK) { uchar bytes[Block::RESERVED_BYTES]; std::fill(bytes, bytes+Block::RESERVED_BYTES, INVALID_BYTE); bit_stream.PutBytes(bytes, Block::RESERVED_BYTES); } #endif if ((fastq_flags & FLAG_PLUS_ONLY) == 0) { for (uint32 i = 0; i < rec_count; ++i) { bit_stream.PutBit(records[i].plus_len == 1); } } uint32 quality_len_bits = BitStream::BitLength(max_quality_length); if ((fastq_flags & FLAG_VARIABLE_LENGTH) != 0) { for (uint32 i = 0; i < rec_count; ++i) { bit_stream.PutBits(records[i].quality_len, quality_len_bits); } } if ((fastq_flags & FLAG_LINE_BREAKS) != 0) { uint32 max_line_break_len = 0; for (uint32 i = 0; i < rec_count; ++i) { if (records[i].sequence_breaks) { for (uint32 j = 0; j < records[i].sequence_breaks->size(); ++j) { if ((*records[i].sequence_breaks)[j] > (int32) max_line_break_len) { max_line_break_len = (*records[i].sequence_breaks)[j]; } } } if (records[i].quality_breaks) { for (uint32 j = 0; j < records[i].quality_breaks->size(); ++j) { if ((*records[i].quality_breaks)[j] > (int32) max_line_break_len) { max_line_break_len = (*records[i].quality_breaks)[j]; } } } } uint32 line_breaks_bits = BitStream::BitLength(max_line_break_len); bit_stream.PutBits(line_breaks_bits, 5); for (uint32 i = 0; i < rec_count; ++i) { if (records[i].sequence_breaks) { for (uint32 j = 0; j < records[i].sequence_breaks->size(); ++j) { bit_stream.PutBits((*records[i].sequence_breaks)[j], line_breaks_bits); } } bit_stream.PutBits(0, line_breaks_bits); if (records[i].quality_breaks) { for (uint32 j = 0; j < records[i].quality_breaks->size(); ++j) { bit_stream.PutBits((*records[i].quality_breaks)[j], line_breaks_bits); } } bit_stream.PutBits(0, line_breaks_bits); } } bit_stream.FlushPartialWordBuffer(); bool is_num_field_constant = (fastq_flags & FLAG_CONST_NUM_FIELDS) != 0; StoreTitle(bit_stream, fields, block_no, is_num_field_constant); if (_quality_stats_mode == QUALITY_RLE) { StoreQualityRLE(bit_stream, qua_code, qua_huf_codes, run_huf_codes, n_qualities); } else { bool use_trunc_hash = _quality_stats_mode == QUALITY_PLAIN_TRUNC; StoreQualityPlain(bit_stream, qua_code, qua_huf_codes, n_qualities, use_trunc_hash); } bool try_lz = (fastq_flags & FLAG_TRY_LZ) != 0; if ((fastq_flags & FLAG_DNA_PLAIN) != 0) { StoreDNAPlain(bit_stream, lz_matcher, sym_code, try_lz); } else { StoreDNAHuf(bit_stream, lz_matcher, sym_code, sym_huf_codes, try_lz); } #if (D_COMPUTE_RECORDS_CRC_PER_BLOCK) uint32 hash = ComputeRecordsCrc32(); bit_stream.PutWord(hash); #endif }