Coverage Report

Created: 2025-06-22 08:04

/src/libjxl/lib/jxl/enc_progressive_split.cc
Line
Count
Source (jump to first uncovered line)
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/jxl/enc_progressive_split.h"
7
8
#include <string.h>
9
10
#include <algorithm>
11
#include <memory>
12
13
#include "lib/jxl/ac_strategy.h"
14
#include "lib/jxl/common.h"  // kMaxNumPasses
15
#include "lib/jxl/image.h"
16
17
namespace jxl {
18
19
template <typename T>
20
void ProgressiveSplitter::SplitACCoefficients(
21
    const T* JXL_RESTRICT block, const AcStrategy& acs, size_t bx, size_t by,
22
0
    T* JXL_RESTRICT output[kMaxNumPasses]) {
23
0
  size_t size = acs.covered_blocks_x() * acs.covered_blocks_y() * kDCTBlockSize;
24
0
  auto shift_right_round0 = [&](T v, int shift) {
25
0
    T one_if_negative = static_cast<uint32_t>(v) >> 31;
26
0
    T add = (one_if_negative << shift) - one_if_negative;
27
0
    return (v + add) >> shift;
28
0
  };
Unexecuted instantiation: jxl::ProgressiveSplitter::SplitACCoefficients<int>(int const*, jxl::AcStrategy const&, unsigned long, unsigned long, int* restrict*)::{lambda(int, int)#1}::operator()(int, int) const
Unexecuted instantiation: jxl::ProgressiveSplitter::SplitACCoefficients<short>(short const*, jxl::AcStrategy const&, unsigned long, unsigned long, short* restrict*)::{lambda(short, int)#1}::operator()(short, int) const
29
  // Early quit for the simple case of only one pass.
30
0
  if (mode_.num_passes == 1) {
31
0
    memcpy(output[0], block, sizeof(T) * size);
32
0
    return;
33
0
  }
34
0
  size_t ncoeffs_all_done_from_earlier_passes = 1;
35
36
0
  int previous_pass_shift = 0;
37
0
  for (size_t num_pass = 0; num_pass < mode_.num_passes; num_pass++) {  // pass
38
    // Zero out output block.
39
0
    memset(output[num_pass], 0, size * sizeof(T));
40
0
    const int pass_shift = mode_.passes[num_pass].shift;
41
0
    size_t frame_ncoeffs = mode_.passes[num_pass].num_coefficients;
42
0
    size_t xsize = acs.covered_blocks_x();
43
0
    size_t ysize = acs.covered_blocks_y();
44
0
    CoefficientLayout(&ysize, &xsize);
45
0
    for (size_t y = 0; y < ysize * frame_ncoeffs; y++) {    // superblk-y
46
0
      for (size_t x = 0; x < xsize * frame_ncoeffs; x++) {  // superblk-x
47
0
        size_t pos = y * xsize * kBlockDim + x;
48
0
        if (x < xsize * ncoeffs_all_done_from_earlier_passes &&
49
0
            y < ysize * ncoeffs_all_done_from_earlier_passes) {
50
          // This coefficient was already included in an earlier pass,
51
          // which included a genuinely smaller set of coefficients.
52
0
          continue;
53
0
        }
54
0
        T v = block[pos];
55
        // Previous pass discarded some bits: do not encode them again.
56
0
        if (previous_pass_shift != 0) {
57
0
          T previous_v = shift_right_round0(v, previous_pass_shift) *
58
0
                         (1 << previous_pass_shift);
59
0
          v -= previous_v;
60
0
        }
61
0
        output[num_pass][pos] = shift_right_round0(v, pass_shift);
62
0
      }  // superblk-x
63
0
    }    // superblk-y
64
    // We just finished a pass.
65
    // Hence, we are now guaranteed to have included all coeffs up to
66
    // frame_ncoeffs in every block, unless the current pass is shifted.
67
0
    if (mode_.passes[num_pass].shift == 0) {
68
0
      ncoeffs_all_done_from_earlier_passes = frame_ncoeffs;
69
0
    }
70
0
    previous_pass_shift = mode_.passes[num_pass].shift;
71
0
  }  // num_pass
72
0
}
Unexecuted instantiation: void jxl::ProgressiveSplitter::SplitACCoefficients<int>(int const*, jxl::AcStrategy const&, unsigned long, unsigned long, int* restrict*)
Unexecuted instantiation: void jxl::ProgressiveSplitter::SplitACCoefficients<short>(short const*, jxl::AcStrategy const&, unsigned long, unsigned long, short* restrict*)
73
74
template void ProgressiveSplitter::SplitACCoefficients<int32_t>(
75
    const int32_t* JXL_RESTRICT, const AcStrategy&, size_t, size_t,
76
    int32_t* JXL_RESTRICT[kMaxNumPasses]);
77
78
template void ProgressiveSplitter::SplitACCoefficients<int16_t>(
79
    const int16_t* JXL_RESTRICT, const AcStrategy&, size_t, size_t,
80
    int16_t* JXL_RESTRICT[kMaxNumPasses]);
81
82
}  // namespace jxl