Imported Upstream version 0.9.0
[platform/upstream/libjxl.git] / lib / jpegli / bit_writer.cc
1 // Copyright (c) the JPEG XL Project Authors. All rights reserved.
2 //
3 // Use of this source code is governed by a BSD-style
4 // license that can be found in the LICENSE file.
5
6 #include "lib/jpegli/bit_writer.h"
7
8 #include "lib/jpegli/encode_internal.h"
9
10 namespace jpegli {
11
12 void JpegBitWriterInit(j_compress_ptr cinfo) {
13   jpeg_comp_master* m = cinfo->master;
14   JpegBitWriter* bw = &m->bw;
15   size_t buffer_size = m->blocks_per_iMCU_row * (DCTSIZE2 * 16 + 8) + (1 << 16);
16   bw->cinfo = cinfo;
17   bw->data = Allocate<uint8_t>(cinfo, buffer_size, JPOOL_IMAGE);
18   bw->len = buffer_size;
19   bw->pos = 0;
20   bw->output_pos = 0;
21   bw->put_buffer = 0;
22   bw->free_bits = 64;
23   bw->healthy = true;
24 }
25
26 bool EmptyBitWriterBuffer(JpegBitWriter* bw) {
27   while (bw->output_pos < bw->pos) {
28     j_compress_ptr cinfo = bw->cinfo;
29     if (cinfo->dest->free_in_buffer == 0 &&
30         !(*cinfo->dest->empty_output_buffer)(cinfo)) {
31       return false;
32     }
33     size_t buflen = bw->pos - bw->output_pos;
34     size_t copylen = std::min<size_t>(cinfo->dest->free_in_buffer, buflen);
35     memcpy(cinfo->dest->next_output_byte, bw->data + bw->output_pos, copylen);
36     bw->output_pos += copylen;
37     cinfo->dest->free_in_buffer -= copylen;
38     cinfo->dest->next_output_byte += copylen;
39   }
40   bw->output_pos = bw->pos = 0;
41   return true;
42 }
43
44 void JumpToByteBoundary(JpegBitWriter* bw) {
45   size_t n_bits = bw->free_bits & 7u;
46   if (n_bits > 0) {
47     WriteBits(bw, n_bits, (1u << n_bits) - 1);
48   }
49   bw->put_buffer <<= bw->free_bits;
50   while (bw->free_bits <= 56) {
51     int c = (bw->put_buffer >> 56) & 0xFF;
52     EmitByte(bw, c);
53     bw->put_buffer <<= 8;
54     bw->free_bits += 8;
55   }
56   bw->put_buffer = 0;
57   bw->free_bits = 64;
58 }
59
60 }  // namespace jpegli