| Line | Branch | Exec | Source |
|---|---|---|---|
| 1 | /* | ||
| 2 | * Copyright (C) 2016 Open Broadcast Systems Ltd. | ||
| 3 | * Author 2016 Rostislav Pehlivanov <atomnuker@gmail.com> | ||
| 4 | * | ||
| 5 | * This file is part of FFmpeg. | ||
| 6 | * | ||
| 7 | * FFmpeg is free software; you can redistribute it and/or | ||
| 8 | * modify it under the terms of the GNU Lesser General Public | ||
| 9 | * License as published by the Free Software Foundation; either | ||
| 10 | * version 2.1 of the License, or (at your option) any later version. | ||
| 11 | * | ||
| 12 | * FFmpeg is distributed in the hope that it will be useful, | ||
| 13 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
| 14 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
| 15 | * Lesser General Public License for more details. | ||
| 16 | * | ||
| 17 | * You should have received a copy of the GNU Lesser General Public | ||
| 18 | * License along with FFmpeg; if not, write to the Free Software | ||
| 19 | * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
| 20 | */ | ||
| 21 | |||
| 22 | #include "libavutil/mem.h" | ||
| 23 | #include "libavutil/pixdesc.h" | ||
| 24 | #include "libavutil/opt.h" | ||
| 25 | #include "libavutil/thread.h" | ||
| 26 | #include "libavutil/version.h" | ||
| 27 | #include "codec_internal.h" | ||
| 28 | #include "dirac.h" | ||
| 29 | #include "encode.h" | ||
| 30 | #include "put_bits.h" | ||
| 31 | #include "version.h" | ||
| 32 | |||
| 33 | #include "vc2enc_dwt.h" | ||
| 34 | #include "diractab.h" | ||
| 35 | |||
| 36 | /* The limited size resolution of each slice forces us to do this */ | ||
| 37 | #define SSIZE_ROUND(b) (FFALIGN((b), s->size_scaler) + 4 + s->prefix_bytes) | ||
| 38 | |||
| 39 | /* Decides the cutoff point in # of slices to distribute the leftover bytes */ | ||
| 40 | #define SLICE_REDIST_TOTAL 150 | ||
| 41 | |||
| 42 | typedef struct VC2BaseVideoFormat { | ||
| 43 | enum AVPixelFormat pix_fmt; | ||
| 44 | AVRational time_base; | ||
| 45 | int width, height; | ||
| 46 | uint8_t interlaced, level; | ||
| 47 | char name[13]; | ||
| 48 | } VC2BaseVideoFormat; | ||
| 49 | |||
| 50 | static const VC2BaseVideoFormat base_video_fmts[] = { | ||
| 51 | { 0 }, /* Custom format, here just to make indexing equal to base_vf */ | ||
| 52 | { AV_PIX_FMT_YUV420P, { 1001, 15000 }, 176, 120, 0, 1, "QSIF525" }, | ||
| 53 | { AV_PIX_FMT_YUV420P, { 2, 25 }, 176, 144, 0, 1, "QCIF" }, | ||
| 54 | { AV_PIX_FMT_YUV420P, { 1001, 15000 }, 352, 240, 0, 1, "SIF525" }, | ||
| 55 | { AV_PIX_FMT_YUV420P, { 2, 25 }, 352, 288, 0, 1, "CIF" }, | ||
| 56 | { AV_PIX_FMT_YUV420P, { 1001, 15000 }, 704, 480, 0, 1, "4SIF525" }, | ||
| 57 | { AV_PIX_FMT_YUV420P, { 2, 25 }, 704, 576, 0, 1, "4CIF" }, | ||
| 58 | |||
| 59 | { AV_PIX_FMT_YUV422P10, { 1001, 30000 }, 720, 480, 1, 2, "SD480I-60" }, | ||
| 60 | { AV_PIX_FMT_YUV422P10, { 1, 25 }, 720, 576, 1, 2, "SD576I-50" }, | ||
| 61 | |||
| 62 | { AV_PIX_FMT_YUV422P10, { 1001, 60000 }, 1280, 720, 0, 3, "HD720P-60" }, | ||
| 63 | { AV_PIX_FMT_YUV422P10, { 1, 50 }, 1280, 720, 0, 3, "HD720P-50" }, | ||
| 64 | { AV_PIX_FMT_YUV422P10, { 1001, 30000 }, 1920, 1080, 1, 3, "HD1080I-60" }, | ||
| 65 | { AV_PIX_FMT_YUV422P10, { 1, 25 }, 1920, 1080, 1, 3, "HD1080I-50" }, | ||
| 66 | { AV_PIX_FMT_YUV422P10, { 1001, 60000 }, 1920, 1080, 0, 3, "HD1080P-60" }, | ||
| 67 | { AV_PIX_FMT_YUV422P10, { 1, 50 }, 1920, 1080, 0, 3, "HD1080P-50" }, | ||
| 68 | |||
| 69 | { AV_PIX_FMT_YUV444P12, { 1, 24 }, 2048, 1080, 0, 4, "DC2K" }, | ||
| 70 | { AV_PIX_FMT_YUV444P12, { 1, 24 }, 4096, 2160, 0, 5, "DC4K" }, | ||
| 71 | |||
| 72 | { AV_PIX_FMT_YUV422P10, { 1001, 60000 }, 3840, 2160, 0, 6, "UHDTV 4K-60" }, | ||
| 73 | { AV_PIX_FMT_YUV422P10, { 1, 50 }, 3840, 2160, 0, 6, "UHDTV 4K-50" }, | ||
| 74 | |||
| 75 | { AV_PIX_FMT_YUV422P10, { 1001, 60000 }, 7680, 4320, 0, 7, "UHDTV 8K-60" }, | ||
| 76 | { AV_PIX_FMT_YUV422P10, { 1, 50 }, 7680, 4320, 0, 7, "UHDTV 8K-50" }, | ||
| 77 | |||
| 78 | { AV_PIX_FMT_YUV422P10, { 1001, 24000 }, 1920, 1080, 0, 3, "HD1080P-24" }, | ||
| 79 | { AV_PIX_FMT_YUV422P10, { 1001, 30000 }, 720, 486, 1, 2, "SD Pro486" }, | ||
| 80 | }; | ||
| 81 | static const int base_video_fmts_len = FF_ARRAY_ELEMS(base_video_fmts); | ||
| 82 | |||
| 83 | enum VC2_QM { | ||
| 84 | VC2_QM_DEF = 0, | ||
| 85 | VC2_QM_COL, | ||
| 86 | VC2_QM_FLAT, | ||
| 87 | |||
| 88 | VC2_QM_NB | ||
| 89 | }; | ||
| 90 | |||
| 91 | typedef struct SubBand { | ||
| 92 | dwtcoef *buf; | ||
| 93 | ptrdiff_t stride; | ||
| 94 | int width; | ||
| 95 | int height; | ||
| 96 | } SubBand; | ||
| 97 | |||
| 98 | typedef struct Plane { | ||
| 99 | SubBand band[MAX_DWT_LEVELS][4]; | ||
| 100 | dwtcoef *coef_buf; | ||
| 101 | int width; | ||
| 102 | int height; | ||
| 103 | int dwt_width; | ||
| 104 | int dwt_height; | ||
| 105 | ptrdiff_t coef_stride; | ||
| 106 | } Plane; | ||
| 107 | |||
| 108 | typedef struct SliceArgs { | ||
| 109 | const struct VC2EncContext *ctx; | ||
| 110 | union { | ||
| 111 | int cache[DIRAC_MAX_QUANT_INDEX]; | ||
| 112 | uint8_t *buf; | ||
| 113 | }; | ||
| 114 | int x; | ||
| 115 | int y; | ||
| 116 | int quant_idx; | ||
| 117 | int bits_ceil; | ||
| 118 | int bits_floor; | ||
| 119 | int bytes; | ||
| 120 | } SliceArgs; | ||
| 121 | |||
| 122 | typedef struct TransformArgs { | ||
| 123 | const struct VC2EncContext *ctx; | ||
| 124 | Plane *plane; | ||
| 125 | const void *idata; | ||
| 126 | ptrdiff_t istride; | ||
| 127 | int field; | ||
| 128 | VC2TransformContext t; | ||
| 129 | } TransformArgs; | ||
| 130 | |||
| 131 | typedef struct VC2EncContext { | ||
| 132 | AVClass *av_class; | ||
| 133 | PutBitContext pb; | ||
| 134 | Plane plane[3]; | ||
| 135 | AVCodecContext *avctx; | ||
| 136 | DiracVersionInfo ver; | ||
| 137 | |||
| 138 | SliceArgs *slice_args; | ||
| 139 | TransformArgs transform_args[3]; | ||
| 140 | |||
| 141 | /* For conversion from unsigned pixel values to signed */ | ||
| 142 | int diff_offset; | ||
| 143 | int bpp; | ||
| 144 | int bpp_idx; | ||
| 145 | |||
| 146 | /* Picture number */ | ||
| 147 | uint32_t picture_number; | ||
| 148 | |||
| 149 | /* Base video format */ | ||
| 150 | int base_vf; | ||
| 151 | int level; | ||
| 152 | int profile; | ||
| 153 | |||
| 154 | /* Quantization matrix */ | ||
| 155 | uint8_t quant[MAX_DWT_LEVELS][4]; | ||
| 156 | int custom_quant_matrix; | ||
| 157 | |||
| 158 | /* Division LUT */ | ||
| 159 | uint32_t qmagic_lut[116][2]; | ||
| 160 | |||
| 161 | int num_x; /* #slices horizontally */ | ||
| 162 | int num_y; /* #slices vertically */ | ||
| 163 | int prefix_bytes; | ||
| 164 | int size_scaler; | ||
| 165 | int chroma_x_shift; | ||
| 166 | int chroma_y_shift; | ||
| 167 | |||
| 168 | /* Rate control stuff */ | ||
| 169 | int frame_max_bytes; | ||
| 170 | int slice_max_bytes; | ||
| 171 | int slice_min_bytes; | ||
| 172 | int q_ceil; | ||
| 173 | int q_avg; | ||
| 174 | |||
| 175 | /* Options */ | ||
| 176 | double tolerance; | ||
| 177 | int wavelet_idx; | ||
| 178 | int wavelet_depth; | ||
| 179 | int strict_compliance; | ||
| 180 | int slice_height; | ||
| 181 | int slice_width; | ||
| 182 | int interlaced; | ||
| 183 | enum VC2_QM quant_matrix; | ||
| 184 | |||
| 185 | /* Parse code state */ | ||
| 186 | uint32_t next_parse_offset; | ||
| 187 | enum DiracParseCodes last_parse_code; | ||
| 188 | } VC2EncContext; | ||
| 189 | |||
| 190 | /// x_k x_{k-1} ... x_0 -> 0 x_k 0 x_{k - 1} ... 0 x_0 | ||
| 191 | static uint16_t interleaved_ue_golomb_tab[256]; | ||
| 192 | /// 1 x_{k-1} ... x_0 -> 0 0 0 x_{k - 1} ... 0 x_0 | ||
| 193 | static uint16_t top_interleaved_ue_golomb_tab[256]; | ||
| 194 | /// 1 x_{k-1} ... x_0 -> 2 * k | ||
| 195 | static uint8_t golomb_len_tab[256]; | ||
| 196 | /// quant -> av_log2(ff_dirac_qscale_tab[quant]) + 32 | ||
| 197 | static uint8_t qscale_len_tab[FF_ARRAY_ELEMS(ff_dirac_qscale_tab)]; | ||
| 198 | |||
| 199 | 33 | static av_cold void vc2_init_static_data(void) | |
| 200 | { | ||
| 201 | 33 | interleaved_ue_golomb_tab[1] = 1; | |
| 202 |
2/2✓ Branch 0 taken 8382 times.
✓ Branch 1 taken 33 times.
|
8415 | for (unsigned i = 2; i < 256; ++i) { |
| 203 | 8382 | golomb_len_tab[i] = golomb_len_tab[i >> 1] + 2; | |
| 204 | 8382 | interleaved_ue_golomb_tab[i] = (interleaved_ue_golomb_tab[i >> 1] << 2) | (i & 1); | |
| 205 | 8382 | top_interleaved_ue_golomb_tab[i] = interleaved_ue_golomb_tab[i] ^ (1 << golomb_len_tab[i]); | |
| 206 | } | ||
| 207 |
2/2✓ Branch 0 taken 3828 times.
✓ Branch 1 taken 33 times.
|
3861 | for (size_t i = 0; i < FF_ARRAY_ELEMS(qscale_len_tab); ++i) |
| 208 | 3828 | qscale_len_tab[i] = av_log2(ff_dirac_qscale_tab[i]) + 32; | |
| 209 | 33 | } | |
| 210 | |||
| 211 | 35739495 | static av_always_inline void put_vc2_ue_uint_inline(PutBitContext *pb, uint32_t val) | |
| 212 | { | ||
| 213 | 35739495 | uint64_t pbits = 1; | |
| 214 | 35739495 | int bits = 1; | |
| 215 | |||
| 216 | 35739495 | ++val; | |
| 217 | |||
| 218 |
2/2✓ Branch 0 taken 3267506 times.
✓ Branch 1 taken 35739495 times.
|
39007001 | while (val >> 8) { |
| 219 | 3267506 | pbits |= (uint64_t)interleaved_ue_golomb_tab[val & 0xff] << bits; | |
| 220 | 3267506 | val >>= 8; | |
| 221 | 3267506 | bits += 16; | |
| 222 | } | ||
| 223 | 35739495 | pbits |= (uint64_t)top_interleaved_ue_golomb_tab[val] << bits; | |
| 224 | 35739495 | bits += golomb_len_tab[val]; | |
| 225 | |||
| 226 | 35739495 | put_bits63(pb, bits, pbits); | |
| 227 | 35739495 | } | |
| 228 | |||
| 229 | 4455 | static av_noinline void put_vc2_ue_uint(PutBitContext *pb, uint32_t val) | |
| 230 | { | ||
| 231 | 4455 | put_vc2_ue_uint_inline(pb, val); | |
| 232 | 4455 | } | |
| 233 | |||
| 234 | 35735040 | static av_always_inline int count_vc2_ue_uint(uint32_t val) | |
| 235 | { | ||
| 236 | 35735040 | return 2 * av_log2(val + 1) + 1; | |
| 237 | } | ||
| 238 | |||
| 239 | /* VC-2 10.4 - parse_info() */ | ||
| 240 | 660 | static void encode_parse_info(VC2EncContext *s, enum DiracParseCodes pcode) | |
| 241 | { | ||
| 242 | uint32_t cur_pos, dist; | ||
| 243 | |||
| 244 | 660 | align_put_bits(&s->pb); | |
| 245 | |||
| 246 | 660 | cur_pos = put_bytes_count(&s->pb, 0); | |
| 247 | |||
| 248 | /* Magic string */ | ||
| 249 | 660 | ff_put_string(&s->pb, "BBCD", 0); | |
| 250 | |||
| 251 | /* Parse code */ | ||
| 252 | 660 | put_bits(&s->pb, 8, pcode); | |
| 253 | |||
| 254 | /* Next parse offset */ | ||
| 255 | 660 | dist = cur_pos - s->next_parse_offset; | |
| 256 | 660 | AV_WB32(s->pb.buf + s->next_parse_offset + 5, dist); | |
| 257 | 660 | s->next_parse_offset = cur_pos; | |
| 258 |
2/2✓ Branch 0 taken 165 times.
✓ Branch 1 taken 495 times.
|
660 | put_bits32(&s->pb, pcode == DIRAC_PCODE_END_SEQ ? 13 : 0); |
| 259 | |||
| 260 | /* Last parse offset */ | ||
| 261 |
1/2✓ Branch 0 taken 660 times.
✗ Branch 1 not taken.
|
660 | put_bits32(&s->pb, s->last_parse_code == DIRAC_PCODE_END_SEQ ? 13 : dist); |
| 262 | |||
| 263 | 660 | s->last_parse_code = pcode; | |
| 264 | 660 | } | |
| 265 | |||
| 266 | /* VC-2 11.1 - parse_parameters() | ||
| 267 | * The level dictates what the decoder should expect in terms of resolution | ||
| 268 | * and allows it to quickly reject whatever it can't support. Remember, | ||
| 269 | * this codec kinda targets cheapo FPGAs without much memory. Unfortunately | ||
| 270 | * it also limits us greatly in our choice of formats, hence the flag to disable | ||
| 271 | * strict_compliance */ | ||
| 272 | 165 | static void encode_parse_params(VC2EncContext *s) | |
| 273 | { | ||
| 274 | 165 | put_vc2_ue_uint(&s->pb, s->ver.major); /* VC-2 demands this to be 2 */ | |
| 275 | 165 | put_vc2_ue_uint(&s->pb, s->ver.minor); /* ^^ and this to be 0 */ | |
| 276 | 165 | put_vc2_ue_uint(&s->pb, s->profile); /* 3 to signal HQ profile */ | |
| 277 | 165 | put_vc2_ue_uint(&s->pb, s->level); /* 3 - 1080/720, 6 - 4K */ | |
| 278 | 165 | } | |
| 279 | |||
| 280 | /* VC-2 11.3 - frame_size() */ | ||
| 281 | 165 | static void encode_frame_size(VC2EncContext *s) | |
| 282 | { | ||
| 283 | 165 | put_bits(&s->pb, 1, !s->strict_compliance); | |
| 284 |
1/2✓ Branch 0 taken 165 times.
✗ Branch 1 not taken.
|
165 | if (!s->strict_compliance) { |
| 285 | 165 | AVCodecContext *avctx = s->avctx; | |
| 286 | 165 | put_vc2_ue_uint(&s->pb, avctx->width); | |
| 287 | 165 | put_vc2_ue_uint(&s->pb, avctx->height); | |
| 288 | } | ||
| 289 | 165 | } | |
| 290 | |||
| 291 | /* VC-2 11.3.3 - color_diff_sampling_format() */ | ||
| 292 | 165 | static void encode_sample_fmt(VC2EncContext *s) | |
| 293 | { | ||
| 294 | 165 | put_bits(&s->pb, 1, !s->strict_compliance); | |
| 295 |
1/2✓ Branch 0 taken 165 times.
✗ Branch 1 not taken.
|
165 | if (!s->strict_compliance) { |
| 296 | int idx; | ||
| 297 |
4/4✓ Branch 0 taken 120 times.
✓ Branch 1 taken 45 times.
✓ Branch 2 taken 75 times.
✓ Branch 3 taken 45 times.
|
165 | if (s->chroma_x_shift == 1 && s->chroma_y_shift == 0) |
| 298 | 75 | idx = 1; /* 422 */ | |
| 299 |
3/4✓ Branch 0 taken 45 times.
✓ Branch 1 taken 45 times.
✓ Branch 2 taken 45 times.
✗ Branch 3 not taken.
|
90 | else if (s->chroma_x_shift == 1 && s->chroma_y_shift == 1) |
| 300 | 45 | idx = 2; /* 420 */ | |
| 301 | else | ||
| 302 | 45 | idx = 0; /* 444 */ | |
| 303 | 165 | put_vc2_ue_uint(&s->pb, idx); | |
| 304 | } | ||
| 305 | 165 | } | |
| 306 | |||
| 307 | /* VC-2 11.3.4 - scan_format() */ | ||
| 308 | 165 | static void encode_scan_format(VC2EncContext *s) | |
| 309 | { | ||
| 310 | 165 | put_bits(&s->pb, 1, !s->strict_compliance); | |
| 311 |
1/2✓ Branch 0 taken 165 times.
✗ Branch 1 not taken.
|
165 | if (!s->strict_compliance) |
| 312 | 165 | put_vc2_ue_uint(&s->pb, s->interlaced); | |
| 313 | 165 | } | |
| 314 | |||
| 315 | /* VC-2 11.3.5 - frame_rate() */ | ||
| 316 | 165 | static void encode_frame_rate(VC2EncContext *s) | |
| 317 | { | ||
| 318 | 165 | put_bits(&s->pb, 1, !s->strict_compliance); | |
| 319 |
1/2✓ Branch 0 taken 165 times.
✗ Branch 1 not taken.
|
165 | if (!s->strict_compliance) { |
| 320 | 165 | AVCodecContext *avctx = s->avctx; | |
| 321 | 165 | put_vc2_ue_uint(&s->pb, 0); | |
| 322 | 165 | put_vc2_ue_uint(&s->pb, avctx->time_base.den); | |
| 323 | 165 | put_vc2_ue_uint(&s->pb, avctx->time_base.num); | |
| 324 | } | ||
| 325 | 165 | } | |
| 326 | |||
| 327 | /* VC-2 11.3.6 - aspect_ratio() */ | ||
| 328 | 165 | static void encode_aspect_ratio(VC2EncContext *s) | |
| 329 | { | ||
| 330 | 165 | put_bits(&s->pb, 1, !s->strict_compliance); | |
| 331 |
1/2✓ Branch 0 taken 165 times.
✗ Branch 1 not taken.
|
165 | if (!s->strict_compliance) { |
| 332 | 165 | AVCodecContext *avctx = s->avctx; | |
| 333 | 165 | put_vc2_ue_uint(&s->pb, 0); | |
| 334 | 165 | put_vc2_ue_uint(&s->pb, avctx->sample_aspect_ratio.num); | |
| 335 | 165 | put_vc2_ue_uint(&s->pb, avctx->sample_aspect_ratio.den); | |
| 336 | } | ||
| 337 | 165 | } | |
| 338 | |||
| 339 | /* VC-2 11.3.7 - clean_area() */ | ||
| 340 | 165 | static void encode_clean_area(VC2EncContext *s) | |
| 341 | { | ||
| 342 | 165 | put_bits(&s->pb, 1, 0); | |
| 343 | 165 | } | |
| 344 | |||
| 345 | /* VC-2 11.3.8 - signal_range() */ | ||
| 346 | 165 | static void encode_signal_range(VC2EncContext *s) | |
| 347 | { | ||
| 348 | 165 | put_bits(&s->pb, 1, !s->strict_compliance); | |
| 349 |
1/2✓ Branch 0 taken 165 times.
✗ Branch 1 not taken.
|
165 | if (!s->strict_compliance) |
| 350 | 165 | put_vc2_ue_uint(&s->pb, s->bpp_idx); | |
| 351 | 165 | } | |
| 352 | |||
| 353 | /* VC-2 11.3.9 - color_spec() */ | ||
| 354 | 165 | static void encode_color_spec(VC2EncContext *s) | |
| 355 | { | ||
| 356 | 165 | AVCodecContext *avctx = s->avctx; | |
| 357 | 165 | put_bits(&s->pb, 1, !s->strict_compliance); | |
| 358 |
1/2✓ Branch 0 taken 165 times.
✗ Branch 1 not taken.
|
165 | if (!s->strict_compliance) { |
| 359 | int val; | ||
| 360 | 165 | put_vc2_ue_uint(&s->pb, 0); | |
| 361 | |||
| 362 | /* primaries */ | ||
| 363 | 165 | put_bits(&s->pb, 1, 1); | |
| 364 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 165 times.
|
165 | if (avctx->color_primaries == AVCOL_PRI_BT470BG) |
| 365 | ✗ | val = 2; | |
| 366 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 165 times.
|
165 | else if (avctx->color_primaries == AVCOL_PRI_SMPTE170M) |
| 367 | ✗ | val = 1; | |
| 368 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 165 times.
|
165 | else if (avctx->color_primaries == AVCOL_PRI_SMPTE240M) |
| 369 | ✗ | val = 1; | |
| 370 | else | ||
| 371 | 165 | val = 0; | |
| 372 | 165 | put_vc2_ue_uint(&s->pb, val); | |
| 373 | |||
| 374 | /* color matrix */ | ||
| 375 | 165 | put_bits(&s->pb, 1, 1); | |
| 376 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 165 times.
|
165 | if (avctx->colorspace == AVCOL_SPC_RGB) |
| 377 | ✗ | val = 3; | |
| 378 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 165 times.
|
165 | else if (avctx->colorspace == AVCOL_SPC_YCOCG) |
| 379 | ✗ | val = 2; | |
| 380 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 165 times.
|
165 | else if (avctx->colorspace == AVCOL_SPC_BT470BG) |
| 381 | ✗ | val = 1; | |
| 382 | else | ||
| 383 | 165 | val = 0; | |
| 384 | 165 | put_vc2_ue_uint(&s->pb, val); | |
| 385 | |||
| 386 | /* transfer function */ | ||
| 387 | 165 | put_bits(&s->pb, 1, 1); | |
| 388 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 165 times.
|
165 | if (avctx->color_trc == AVCOL_TRC_LINEAR) |
| 389 | ✗ | val = 2; | |
| 390 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 165 times.
|
165 | else if (avctx->color_trc == AVCOL_TRC_BT1361_ECG) |
| 391 | ✗ | val = 1; | |
| 392 | else | ||
| 393 | 165 | val = 0; | |
| 394 | 165 | put_vc2_ue_uint(&s->pb, val); | |
| 395 | } | ||
| 396 | 165 | } | |
| 397 | |||
| 398 | /* VC-2 11.3 - source_parameters() */ | ||
| 399 | 165 | static void encode_source_params(VC2EncContext *s) | |
| 400 | { | ||
| 401 | 165 | encode_frame_size(s); | |
| 402 | 165 | encode_sample_fmt(s); | |
| 403 | 165 | encode_scan_format(s); | |
| 404 | 165 | encode_frame_rate(s); | |
| 405 | 165 | encode_aspect_ratio(s); | |
| 406 | 165 | encode_clean_area(s); | |
| 407 | 165 | encode_signal_range(s); | |
| 408 | 165 | encode_color_spec(s); | |
| 409 | 165 | } | |
| 410 | |||
| 411 | /* VC-2 11 - sequence_header() */ | ||
| 412 | 165 | static void encode_seq_header(VC2EncContext *s) | |
| 413 | { | ||
| 414 | 165 | align_put_bits(&s->pb); | |
| 415 | 165 | encode_parse_params(s); | |
| 416 | 165 | put_vc2_ue_uint(&s->pb, s->base_vf); | |
| 417 | 165 | encode_source_params(s); | |
| 418 | 165 | put_vc2_ue_uint(&s->pb, s->interlaced); /* Frames or fields coding */ | |
| 419 | 165 | } | |
| 420 | |||
| 421 | /* VC-2 12.1 - picture_header() */ | ||
| 422 | 165 | static void encode_picture_header(VC2EncContext *s) | |
| 423 | { | ||
| 424 | 165 | align_put_bits(&s->pb); | |
| 425 | 165 | put_bits32(&s->pb, s->picture_number++); | |
| 426 | 165 | } | |
| 427 | |||
| 428 | /* VC-2 12.3.4.1 - slice_parameters() */ | ||
| 429 | 165 | static void encode_slice_params(VC2EncContext *s) | |
| 430 | { | ||
| 431 | 165 | put_vc2_ue_uint(&s->pb, s->num_x); | |
| 432 | 165 | put_vc2_ue_uint(&s->pb, s->num_y); | |
| 433 | 165 | put_vc2_ue_uint(&s->pb, s->prefix_bytes); | |
| 434 | 165 | put_vc2_ue_uint(&s->pb, s->size_scaler); | |
| 435 | 165 | } | |
| 436 | |||
| 437 | /* 1st idx = LL, second - vertical, third - horizontal, fourth - total */ | ||
| 438 | static const uint8_t vc2_qm_col_tab[][4] = { | ||
| 439 | {20, 9, 15, 4}, | ||
| 440 | { 0, 6, 6, 4}, | ||
| 441 | { 0, 3, 3, 5}, | ||
| 442 | { 0, 3, 5, 1}, | ||
| 443 | { 0, 11, 10, 11} | ||
| 444 | }; | ||
| 445 | |||
| 446 | static const uint8_t vc2_qm_flat_tab[][4] = { | ||
| 447 | { 0, 0, 0, 0}, | ||
| 448 | { 0, 0, 0, 0}, | ||
| 449 | { 0, 0, 0, 0}, | ||
| 450 | { 0, 0, 0, 0}, | ||
| 451 | { 0, 0, 0, 0} | ||
| 452 | }; | ||
| 453 | |||
| 454 | 165 | static void init_quant_matrix(VC2EncContext *s) | |
| 455 | { | ||
| 456 | int level, orientation; | ||
| 457 | |||
| 458 |
2/4✓ Branch 0 taken 165 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 165 times.
✗ Branch 3 not taken.
|
165 | if (s->wavelet_depth <= 4 && s->quant_matrix == VC2_QM_DEF) { |
| 459 | 165 | s->custom_quant_matrix = 0; | |
| 460 |
2/2✓ Branch 0 taken 660 times.
✓ Branch 1 taken 165 times.
|
825 | for (level = 0; level < s->wavelet_depth; level++) { |
| 461 | 660 | s->quant[level][0] = ff_dirac_default_qmat[s->wavelet_idx][level][0]; | |
| 462 | 660 | s->quant[level][1] = ff_dirac_default_qmat[s->wavelet_idx][level][1]; | |
| 463 | 660 | s->quant[level][2] = ff_dirac_default_qmat[s->wavelet_idx][level][2]; | |
| 464 | 660 | s->quant[level][3] = ff_dirac_default_qmat[s->wavelet_idx][level][3]; | |
| 465 | } | ||
| 466 | 165 | return; | |
| 467 | } | ||
| 468 | |||
| 469 | ✗ | s->custom_quant_matrix = 1; | |
| 470 | |||
| 471 | ✗ | if (s->quant_matrix == VC2_QM_DEF) { | |
| 472 | ✗ | for (level = 0; level < s->wavelet_depth; level++) { | |
| 473 | ✗ | for (orientation = 0; orientation < 4; orientation++) { | |
| 474 | ✗ | if (level <= 3) | |
| 475 | ✗ | s->quant[level][orientation] = ff_dirac_default_qmat[s->wavelet_idx][level][orientation]; | |
| 476 | else | ||
| 477 | ✗ | s->quant[level][orientation] = vc2_qm_col_tab[level][orientation]; | |
| 478 | } | ||
| 479 | } | ||
| 480 | ✗ | } else if (s->quant_matrix == VC2_QM_COL) { | |
| 481 | ✗ | for (level = 0; level < s->wavelet_depth; level++) { | |
| 482 | ✗ | for (orientation = 0; orientation < 4; orientation++) { | |
| 483 | ✗ | s->quant[level][orientation] = vc2_qm_col_tab[level][orientation]; | |
| 484 | } | ||
| 485 | } | ||
| 486 | } else { | ||
| 487 | ✗ | for (level = 0; level < s->wavelet_depth; level++) { | |
| 488 | ✗ | for (orientation = 0; orientation < 4; orientation++) { | |
| 489 | ✗ | s->quant[level][orientation] = vc2_qm_flat_tab[level][orientation]; | |
| 490 | } | ||
| 491 | } | ||
| 492 | } | ||
| 493 | } | ||
| 494 | |||
| 495 | /* VC-2 12.3.4.2 - quant_matrix() */ | ||
| 496 | 165 | static void encode_quant_matrix(VC2EncContext *s) | |
| 497 | { | ||
| 498 | int level; | ||
| 499 | 165 | put_bits(&s->pb, 1, s->custom_quant_matrix); | |
| 500 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 165 times.
|
165 | if (s->custom_quant_matrix) { |
| 501 | ✗ | put_vc2_ue_uint(&s->pb, s->quant[0][0]); | |
| 502 | ✗ | for (level = 0; level < s->wavelet_depth; level++) { | |
| 503 | ✗ | put_vc2_ue_uint(&s->pb, s->quant[level][1]); | |
| 504 | ✗ | put_vc2_ue_uint(&s->pb, s->quant[level][2]); | |
| 505 | ✗ | put_vc2_ue_uint(&s->pb, s->quant[level][3]); | |
| 506 | } | ||
| 507 | } | ||
| 508 | 165 | } | |
| 509 | |||
| 510 | /* VC-2 12.3 - transform_parameters() */ | ||
| 511 | 165 | static void encode_transform_params(VC2EncContext *s) | |
| 512 | { | ||
| 513 | 165 | put_vc2_ue_uint(&s->pb, s->wavelet_idx); | |
| 514 | 165 | put_vc2_ue_uint(&s->pb, s->wavelet_depth); | |
| 515 | |||
| 516 | 165 | encode_slice_params(s); | |
| 517 | 165 | encode_quant_matrix(s); | |
| 518 | 165 | } | |
| 519 | |||
| 520 | /* VC-2 12.2 - wavelet_transform() */ | ||
| 521 | 165 | static void encode_wavelet_transform(VC2EncContext *s) | |
| 522 | { | ||
| 523 | 165 | encode_transform_params(s); | |
| 524 | 165 | align_put_bits(&s->pb); | |
| 525 | 165 | } | |
| 526 | |||
| 527 | /* VC-2 12 - picture_parse() */ | ||
| 528 | 165 | static void encode_picture_start(VC2EncContext *s) | |
| 529 | { | ||
| 530 | 165 | align_put_bits(&s->pb); | |
| 531 | 165 | encode_picture_header(s); | |
| 532 | 165 | align_put_bits(&s->pb); | |
| 533 | 165 | encode_wavelet_transform(s); | |
| 534 | 165 | } | |
| 535 | |||
| 536 | #define QUANT(c, mul, add, shift) (((mul) * (c) + (add)) >> (shift)) | ||
| 537 | |||
| 538 | /* VC-2 13.5.5.2 - slice_band() */ | ||
| 539 | 1274130 | static void encode_subband(const VC2EncContext *s, PutBitContext *pb, | |
| 540 | int sx, int sy, const SubBand *b, int quant) | ||
| 541 | { | ||
| 542 | int x, y; | ||
| 543 | |||
| 544 | 1274130 | const int left = b->width * (sx+0) / s->num_x; | |
| 545 | 1274130 | const int right = b->width * (sx+1) / s->num_x; | |
| 546 | 1274130 | const int top = b->height * (sy+0) / s->num_y; | |
| 547 | 1274130 | const int bottom = b->height * (sy+1) / s->num_y; | |
| 548 | |||
| 549 | 1274130 | dwtcoef *coeff = b->buf + top * b->stride; | |
| 550 | 1274130 | const uint64_t q_m = ((uint64_t)(s->qmagic_lut[quant][0])) << 2; | |
| 551 | 1274130 | const uint64_t q_a = s->qmagic_lut[quant][1]; | |
| 552 | 1274130 | const int q_s = qscale_len_tab[quant]; | |
| 553 | |||
| 554 |
2/2✓ Branch 0 taken 4098600 times.
✓ Branch 1 taken 1274130 times.
|
5372730 | for (y = top; y < bottom; y++) { |
| 555 |
2/2✓ Branch 0 taken 35735040 times.
✓ Branch 1 taken 4098600 times.
|
39833640 | for (x = left; x < right; x++) { |
| 556 |
2/2✓ Branch 0 taken 19457858 times.
✓ Branch 1 taken 16277182 times.
|
35735040 | uint32_t c_abs = QUANT(FFABS(coeff[x]), q_m, q_a, q_s); |
| 557 | 35735040 | put_vc2_ue_uint_inline(pb, c_abs); | |
| 558 |
2/2✓ Branch 0 taken 32314611 times.
✓ Branch 1 taken 3420429 times.
|
35735040 | if (c_abs) |
| 559 | 32314611 | put_bits(pb, 1, coeff[x] < 0); | |
| 560 | } | ||
| 561 | 4098600 | coeff += b->stride; | |
| 562 | } | ||
| 563 | 1274130 | } | |
| 564 | |||
| 565 | 130680 | static int count_hq_slice(SliceArgs *slice, int quant_idx) | |
| 566 | { | ||
| 567 | int x, y; | ||
| 568 | uint8_t quants[MAX_DWT_LEVELS][4]; | ||
| 569 | 130680 | int bits = 0, p, level, orientation; | |
| 570 | 130680 | const VC2EncContext *s = slice->ctx; | |
| 571 | |||
| 572 |
2/2✓ Branch 0 taken 98010 times.
✓ Branch 1 taken 32670 times.
|
130680 | if (slice->cache[quant_idx]) |
| 573 | 98010 | return slice->cache[quant_idx]; | |
| 574 | |||
| 575 | 32670 | bits += 8*s->prefix_bytes; | |
| 576 | 32670 | bits += 8; /* quant_idx */ | |
| 577 | |||
| 578 |
2/2✓ Branch 0 taken 130680 times.
✓ Branch 1 taken 32670 times.
|
163350 | for (level = 0; level < s->wavelet_depth; level++) |
| 579 |
2/2✓ Branch 0 taken 424710 times.
✓ Branch 1 taken 130680 times.
|
555390 | for (orientation = !!level; orientation < 4; orientation++) |
| 580 | 424710 | quants[level][orientation] = FFMAX(quant_idx - s->quant[level][orientation], 0); | |
| 581 | |||
| 582 |
2/2✓ Branch 0 taken 98010 times.
✓ Branch 1 taken 32670 times.
|
130680 | for (p = 0; p < 3; p++) { |
| 583 | int bytes_start, bytes_len, pad_s, pad_c; | ||
| 584 | 98010 | bytes_start = bits >> 3; | |
| 585 | 98010 | bits += 8; | |
| 586 |
2/2✓ Branch 0 taken 392040 times.
✓ Branch 1 taken 98010 times.
|
490050 | for (level = 0; level < s->wavelet_depth; level++) { |
| 587 |
2/2✓ Branch 0 taken 1274130 times.
✓ Branch 1 taken 392040 times.
|
1666170 | for (orientation = !!level; orientation < 4; orientation++) { |
| 588 | 1274130 | const SubBand *b = &s->plane[p].band[level][orientation]; | |
| 589 | |||
| 590 | 1274130 | const int q_idx = quants[level][orientation]; | |
| 591 | 1274130 | const uint64_t q_m = ((uint64_t)s->qmagic_lut[q_idx][0]) << 2; | |
| 592 | 1274130 | const uint64_t q_a = s->qmagic_lut[q_idx][1]; | |
| 593 | 1274130 | const int q_s = qscale_len_tab[q_idx]; | |
| 594 | |||
| 595 | 1274130 | const int left = b->width * slice->x / s->num_x; | |
| 596 | 1274130 | const int right = b->width *(slice->x+1) / s->num_x; | |
| 597 | 1274130 | const int top = b->height * slice->y / s->num_y; | |
| 598 | 1274130 | const int bottom = b->height *(slice->y+1) / s->num_y; | |
| 599 | |||
| 600 | 1274130 | dwtcoef *buf = b->buf + top * b->stride; | |
| 601 | |||
| 602 |
2/2✓ Branch 0 taken 4098600 times.
✓ Branch 1 taken 1274130 times.
|
5372730 | for (y = top; y < bottom; y++) { |
| 603 |
2/2✓ Branch 0 taken 35735040 times.
✓ Branch 1 taken 4098600 times.
|
39833640 | for (x = left; x < right; x++) { |
| 604 |
2/2✓ Branch 0 taken 19457858 times.
✓ Branch 1 taken 16277182 times.
|
35735040 | uint32_t c_abs = QUANT(FFABS(buf[x]), q_m, q_a, q_s); |
| 605 | 35735040 | bits += count_vc2_ue_uint(c_abs); | |
| 606 | 35735040 | bits += !!c_abs; | |
| 607 | } | ||
| 608 | 4098600 | buf += b->stride; | |
| 609 | } | ||
| 610 | } | ||
| 611 | } | ||
| 612 | 98010 | bits += FFALIGN(bits, 8) - bits; | |
| 613 | 98010 | bytes_len = (bits >> 3) - bytes_start - 1; | |
| 614 | 98010 | pad_s = FFALIGN(bytes_len, s->size_scaler)/s->size_scaler; | |
| 615 | 98010 | pad_c = (pad_s*s->size_scaler) - bytes_len; | |
| 616 | 98010 | bits += pad_c*8; | |
| 617 | } | ||
| 618 | |||
| 619 | 32670 | slice->cache[quant_idx] = bits; | |
| 620 | |||
| 621 | 32670 | return bits; | |
| 622 | } | ||
| 623 | |||
| 624 | /* Approaches the best possible quantizer asymptotically, its kinda exhaustive | ||
| 625 | * but we have a LUT to get the coefficient size in bits. Guaranteed to never | ||
| 626 | * overshoot, which is apparently very important when streaming */ | ||
| 627 | 32670 | static int rate_control(AVCodecContext *avctx, void *arg) | |
| 628 | { | ||
| 629 | 32670 | SliceArgs *slice_dat = arg; | |
| 630 | 32670 | const VC2EncContext *s = slice_dat->ctx; | |
| 631 | 32670 | const int top = slice_dat->bits_ceil; | |
| 632 | 32670 | const int bottom = slice_dat->bits_floor; | |
| 633 | 32670 | int quant_buf[2] = {-1, -1}; | |
| 634 | 32670 | int quant = slice_dat->quant_idx, step = 1; | |
| 635 | 32670 | int bits_last, bits = count_hq_slice(slice_dat, quant); | |
| 636 |
2/4✗ Branch 0 not taken.
✓ Branch 1 taken 98010 times.
✓ Branch 2 taken 98010 times.
✗ Branch 3 not taken.
|
98010 | while ((bits > top) || (bits < bottom)) { |
| 637 |
1/2✓ Branch 0 taken 98010 times.
✗ Branch 1 not taken.
|
98010 | const int signed_step = bits > top ? +step : -step; |
| 638 | 98010 | quant = av_clip(quant + signed_step, 0, s->q_ceil-1); | |
| 639 | 98010 | bits = count_hq_slice(slice_dat, quant); | |
| 640 |
2/2✓ Branch 0 taken 32670 times.
✓ Branch 1 taken 65340 times.
|
98010 | if (quant_buf[1] == quant) { |
| 641 | 32670 | quant = FFMAX(quant_buf[0], quant); | |
| 642 |
1/2✓ Branch 0 taken 32670 times.
✗ Branch 1 not taken.
|
32670 | bits = quant == quant_buf[0] ? bits_last : bits; |
| 643 | 32670 | break; | |
| 644 | } | ||
| 645 | 65340 | step = av_clip(step/2, 1, (s->q_ceil-1)/2); | |
| 646 | 65340 | quant_buf[1] = quant_buf[0]; | |
| 647 | 65340 | quant_buf[0] = quant; | |
| 648 | 65340 | bits_last = bits; | |
| 649 | } | ||
| 650 | 32670 | slice_dat->quant_idx = av_clip(quant, 0, s->q_ceil-1); | |
| 651 | 32670 | slice_dat->bytes = SSIZE_ROUND(bits >> 3); | |
| 652 | 32670 | return 0; | |
| 653 | } | ||
| 654 | |||
| 655 | 165 | static int calc_slice_sizes(VC2EncContext *s) | |
| 656 | { | ||
| 657 | 165 | int i, j, slice_x, slice_y, bytes_left = 0; | |
| 658 | 165 | int bytes_top[SLICE_REDIST_TOTAL] = {0}; | |
| 659 | 165 | int64_t total_bytes_needed = 0; | |
| 660 | 165 | int slice_redist_range = FFMIN(SLICE_REDIST_TOTAL, s->num_x*s->num_y); | |
| 661 | 165 | SliceArgs *enc_args = s->slice_args; | |
| 662 | 165 | SliceArgs *top_loc[SLICE_REDIST_TOTAL] = {NULL}; | |
| 663 | |||
| 664 | 165 | init_quant_matrix(s); | |
| 665 | |||
| 666 |
2/2✓ Branch 0 taken 2970 times.
✓ Branch 1 taken 165 times.
|
3135 | for (slice_y = 0; slice_y < s->num_y; slice_y++) { |
| 667 |
2/2✓ Branch 0 taken 32670 times.
✓ Branch 1 taken 2970 times.
|
35640 | for (slice_x = 0; slice_x < s->num_x; slice_x++) { |
| 668 | 32670 | SliceArgs *args = &enc_args[s->num_x*slice_y + slice_x]; | |
| 669 | 32670 | args->ctx = s; | |
| 670 | 32670 | args->x = slice_x; | |
| 671 | 32670 | args->y = slice_y; | |
| 672 | 32670 | args->bits_ceil = s->slice_max_bytes << 3; | |
| 673 | 32670 | args->bits_floor = s->slice_min_bytes << 3; | |
| 674 | 32670 | memset(args->cache, 0, s->q_ceil*sizeof(*args->cache)); | |
| 675 | } | ||
| 676 | } | ||
| 677 | |||
| 678 | /* First pass - determine baseline slice sizes w.r.t. max_slice_size */ | ||
| 679 | 165 | s->avctx->execute(s->avctx, rate_control, enc_args, NULL, s->num_x*s->num_y, | |
| 680 | sizeof(SliceArgs)); | ||
| 681 | |||
| 682 |
2/2✓ Branch 0 taken 32670 times.
✓ Branch 1 taken 165 times.
|
32835 | for (i = 0; i < s->num_x*s->num_y; i++) { |
| 683 | 32670 | SliceArgs *args = &enc_args[i]; | |
| 684 | 32670 | bytes_left += args->bytes; | |
| 685 |
1/2✓ Branch 0 taken 1155403 times.
✗ Branch 1 not taken.
|
1155403 | for (j = 0; j < slice_redist_range; j++) { |
| 686 |
2/2✓ Branch 0 taken 32670 times.
✓ Branch 1 taken 1122733 times.
|
1155403 | if (args->bytes > bytes_top[j]) { |
| 687 | 32670 | bytes_top[j] = args->bytes; | |
| 688 | 32670 | top_loc[j] = args; | |
| 689 | 32670 | break; | |
| 690 | } | ||
| 691 | } | ||
| 692 | } | ||
| 693 | |||
| 694 | 165 | bytes_left = s->frame_max_bytes - bytes_left; | |
| 695 | |||
| 696 | /* Second pass - distribute leftover bytes */ | ||
| 697 |
1/2✓ Branch 0 taken 165 times.
✗ Branch 1 not taken.
|
165 | while (bytes_left > 0) { |
| 698 | 165 | int distributed = 0; | |
| 699 |
1/2✓ Branch 0 taken 165 times.
✗ Branch 1 not taken.
|
165 | for (i = 0; i < slice_redist_range; i++) { |
| 700 | SliceArgs *args; | ||
| 701 | int bits, bytes, diff, prev_bytes, new_idx; | ||
| 702 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 165 times.
|
165 | if (bytes_left <= 0) |
| 703 | ✗ | break; | |
| 704 |
2/4✓ Branch 0 taken 165 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 165 times.
|
165 | if (!top_loc[i] || !top_loc[i]->quant_idx) |
| 705 | break; | ||
| 706 | ✗ | args = top_loc[i]; | |
| 707 | ✗ | prev_bytes = args->bytes; | |
| 708 | ✗ | new_idx = FFMAX(args->quant_idx - 1, 0); | |
| 709 | ✗ | bits = count_hq_slice(args, new_idx); | |
| 710 | ✗ | bytes = SSIZE_ROUND(bits >> 3); | |
| 711 | ✗ | diff = bytes - prev_bytes; | |
| 712 | ✗ | if ((bytes_left - diff) > 0) { | |
| 713 | ✗ | args->quant_idx = new_idx; | |
| 714 | ✗ | args->bytes = bytes; | |
| 715 | ✗ | bytes_left -= diff; | |
| 716 | ✗ | distributed++; | |
| 717 | } | ||
| 718 | } | ||
| 719 |
1/2✓ Branch 0 taken 165 times.
✗ Branch 1 not taken.
|
165 | if (!distributed) |
| 720 | 165 | break; | |
| 721 | } | ||
| 722 | |||
| 723 |
2/2✓ Branch 0 taken 32670 times.
✓ Branch 1 taken 165 times.
|
32835 | for (i = 0; i < s->num_x*s->num_y; i++) { |
| 724 | 32670 | SliceArgs *args = &enc_args[i]; | |
| 725 | 32670 | total_bytes_needed += args->bytes; | |
| 726 | 32670 | s->q_avg = (s->q_avg + args->quant_idx)/2; | |
| 727 | } | ||
| 728 | |||
| 729 | 165 | return total_bytes_needed; | |
| 730 | } | ||
| 731 | |||
| 732 | /* VC-2 13.5.3 - hq_slice */ | ||
| 733 | 32670 | static int encode_hq_slice(AVCodecContext *avctx, void *arg) | |
| 734 | { | ||
| 735 | 32670 | const SliceArgs *slice_dat = arg; | |
| 736 | 32670 | const VC2EncContext *s = slice_dat->ctx; | |
| 737 | 32670 | PutBitContext pb0, *const pb = &pb0; | |
| 738 | 32670 | const int slice_x = slice_dat->x; | |
| 739 | 32670 | const int slice_y = slice_dat->y; | |
| 740 | 32670 | const int quant_idx = slice_dat->quant_idx; | |
| 741 | 32670 | const int slice_bytes_max = slice_dat->bytes; | |
| 742 | uint8_t quants[MAX_DWT_LEVELS][4]; | ||
| 743 | int p, level, orientation; | ||
| 744 | |||
| 745 | /* The reference decoder ignores it, and its typical length is 0 */ | ||
| 746 | 32670 | memset(slice_dat->buf, 0, s->prefix_bytes); | |
| 747 | |||
| 748 | 32670 | init_put_bits(pb, slice_dat->buf + s->prefix_bytes, slice_dat->bytes - s->prefix_bytes); | |
| 749 | |||
| 750 | 32670 | put_bits(pb, 8, quant_idx); | |
| 751 | |||
| 752 | /* Slice quantization (slice_quantizers() in the specs) */ | ||
| 753 |
2/2✓ Branch 0 taken 130680 times.
✓ Branch 1 taken 32670 times.
|
163350 | for (level = 0; level < s->wavelet_depth; level++) |
| 754 |
2/2✓ Branch 0 taken 424710 times.
✓ Branch 1 taken 130680 times.
|
555390 | for (orientation = !!level; orientation < 4; orientation++) |
| 755 | 424710 | quants[level][orientation] = FFMAX(quant_idx - s->quant[level][orientation], 0); | |
| 756 | |||
| 757 | /* Luma + 2 Chroma planes */ | ||
| 758 |
2/2✓ Branch 0 taken 98010 times.
✓ Branch 1 taken 32670 times.
|
130680 | for (p = 0; p < 3; p++) { |
| 759 | int bytes_start, bytes_len, pad_s, pad_c; | ||
| 760 | 98010 | bytes_start = put_bytes_count(pb, 0); | |
| 761 | 98010 | put_bits(pb, 8, 0); | |
| 762 |
2/2✓ Branch 0 taken 392040 times.
✓ Branch 1 taken 98010 times.
|
490050 | for (level = 0; level < s->wavelet_depth; level++) { |
| 763 |
2/2✓ Branch 0 taken 1274130 times.
✓ Branch 1 taken 392040 times.
|
1666170 | for (orientation = !!level; orientation < 4; orientation++) { |
| 764 | 1274130 | encode_subband(s, pb, slice_x, slice_y, | |
| 765 | &s->plane[p].band[level][orientation], | ||
| 766 | 1274130 | quants[level][orientation]); | |
| 767 | } | ||
| 768 | } | ||
| 769 | 98010 | flush_put_bits(pb); | |
| 770 | 98010 | bytes_len = put_bytes_output(pb) - bytes_start - 1; | |
| 771 |
2/2✓ Branch 0 taken 32670 times.
✓ Branch 1 taken 65340 times.
|
98010 | if (p == 2) { |
| 772 | 32670 | int len_diff = slice_bytes_max - put_bytes_output(pb); | |
| 773 | 32670 | pad_s = FFALIGN((bytes_len + len_diff), s->size_scaler)/s->size_scaler; | |
| 774 | 32670 | pad_c = (pad_s*s->size_scaler) - bytes_len; | |
| 775 | } else { | ||
| 776 | 65340 | pad_s = FFALIGN(bytes_len, s->size_scaler)/s->size_scaler; | |
| 777 | 65340 | pad_c = (pad_s*s->size_scaler) - bytes_len; | |
| 778 | } | ||
| 779 | 98010 | pb->buf[bytes_start] = pad_s; | |
| 780 | /* vc2-reference uses that padding that decodes to '0' coeffs */ | ||
| 781 | 98010 | memset(put_bits_ptr(pb), 0xFF, pad_c); | |
| 782 | 98010 | skip_put_bytes(pb, pad_c); | |
| 783 | } | ||
| 784 | |||
| 785 | 32670 | return 0; | |
| 786 | } | ||
| 787 | |||
| 788 | /* VC-2 13.5.1 - low_delay_transform_data() */ | ||
| 789 | 165 | static int encode_slices(VC2EncContext *s) | |
| 790 | { | ||
| 791 | uint8_t *buf; | ||
| 792 | 165 | int slice_x, slice_y, skip = 0; | |
| 793 | 165 | SliceArgs *enc_args = s->slice_args; | |
| 794 | |||
| 795 | 165 | flush_put_bits(&s->pb); | |
| 796 | 165 | buf = put_bits_ptr(&s->pb); | |
| 797 | |||
| 798 |
2/2✓ Branch 0 taken 2970 times.
✓ Branch 1 taken 165 times.
|
3135 | for (slice_y = 0; slice_y < s->num_y; slice_y++) { |
| 799 |
2/2✓ Branch 0 taken 32670 times.
✓ Branch 1 taken 2970 times.
|
35640 | for (slice_x = 0; slice_x < s->num_x; slice_x++) { |
| 800 | 32670 | SliceArgs *args = &enc_args[s->num_x*slice_y + slice_x]; | |
| 801 | 32670 | args->buf = buf + skip; | |
| 802 | 32670 | skip += args->bytes; | |
| 803 | } | ||
| 804 | } | ||
| 805 | |||
| 806 | 165 | s->avctx->execute(s->avctx, encode_hq_slice, enc_args, NULL, s->num_x*s->num_y, | |
| 807 | sizeof(SliceArgs)); | ||
| 808 | |||
| 809 | 165 | skip_put_bytes(&s->pb, skip); | |
| 810 | |||
| 811 | 165 | return 0; | |
| 812 | } | ||
| 813 | |||
| 814 | /* | ||
| 815 | * Transform basics for a 3 level transform | ||
| 816 | * |---------------------------------------------------------------------| | ||
| 817 | * | LL-0 | HL-0 | | | | ||
| 818 | * |--------|-------| HL-1 | | | ||
| 819 | * | LH-0 | HH-0 | | | | ||
| 820 | * |----------------|-----------------| HL-2 | | ||
| 821 | * | | | | | ||
| 822 | * | LH-1 | HH-1 | | | ||
| 823 | * | | | | | ||
| 824 | * |----------------------------------|----------------------------------| | ||
| 825 | * | | | | ||
| 826 | * | | | | ||
| 827 | * | | | | ||
| 828 | * | LH-2 | HH-2 | | ||
| 829 | * | | | | ||
| 830 | * | | | | ||
| 831 | * | | | | ||
| 832 | * |---------------------------------------------------------------------| | ||
| 833 | * | ||
| 834 | * DWT transforms are generally applied by splitting the image in two vertically | ||
| 835 | * and applying a low pass transform on the left part and a corresponding high | ||
| 836 | * pass transform on the right hand side. This is known as the horizontal filter | ||
| 837 | * stage. | ||
| 838 | * After that, the same operation is performed except the image is divided | ||
| 839 | * horizontally, with the high pass on the lower and the low pass on the higher | ||
| 840 | * side. | ||
| 841 | * Therefore, you're left with 4 subdivisions - known as low-low, low-high, | ||
| 842 | * high-low and high-high. They're referred to as orientations in the decoder | ||
| 843 | * and encoder. | ||
| 844 | * | ||
| 845 | * The LL (low-low) area contains the original image downsampled by the amount | ||
| 846 | * of levels. The rest of the areas can be thought as the details needed | ||
| 847 | * to restore the image perfectly to its original size. | ||
| 848 | */ | ||
| 849 | 495 | static int dwt_plane(AVCodecContext *avctx, void *arg) | |
| 850 | { | ||
| 851 | 495 | TransformArgs *transform_dat = arg; | |
| 852 | 495 | const VC2EncContext *s = transform_dat->ctx; | |
| 853 | 495 | const void *frame_data = transform_dat->idata; | |
| 854 | 495 | const ptrdiff_t linesize = transform_dat->istride; | |
| 855 | 495 | const int field = transform_dat->field; | |
| 856 | 495 | const Plane *p = transform_dat->plane; | |
| 857 | 495 | VC2TransformContext *t = &transform_dat->t; | |
| 858 | 495 | dwtcoef *buf = p->coef_buf; | |
| 859 | 495 | const int idx = s->wavelet_idx; | |
| 860 | 495 | const int skip = 1 + s->interlaced; | |
| 861 | |||
| 862 | int x, y, level, offset; | ||
| 863 | 495 | ptrdiff_t pix_stride = linesize >> (s->bpp - 1); | |
| 864 | |||
| 865 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 495 times.
|
495 | if (field == 1) { |
| 866 | ✗ | offset = 0; | |
| 867 | ✗ | pix_stride <<= 1; | |
| 868 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 495 times.
|
495 | } else if (field == 2) { |
| 869 | ✗ | offset = pix_stride; | |
| 870 | ✗ | pix_stride <<= 1; | |
| 871 | } else { | ||
| 872 | 495 | offset = 0; | |
| 873 | } | ||
| 874 | |||
| 875 |
2/2✓ Branch 0 taken 135 times.
✓ Branch 1 taken 360 times.
|
495 | if (s->bpp == 1) { |
| 876 | 135 | const uint8_t *pix = (const uint8_t *)frame_data + offset; | |
| 877 |
2/2✓ Branch 0 taken 34560 times.
✓ Branch 1 taken 135 times.
|
34695 | for (y = 0; y < p->height*skip; y+=skip) { |
| 878 |
2/2✓ Branch 0 taken 9884160 times.
✓ Branch 1 taken 34560 times.
|
9918720 | for (x = 0; x < p->width; x++) { |
| 879 | 9884160 | buf[x] = pix[x] - s->diff_offset; | |
| 880 | } | ||
| 881 | 34560 | memset(&buf[x], 0, (p->coef_stride - p->width)*sizeof(dwtcoef)); | |
| 882 | 34560 | buf += p->coef_stride; | |
| 883 | 34560 | pix += pix_stride; | |
| 884 | } | ||
| 885 | } else { | ||
| 886 | 360 | const uint16_t *pix = (const uint16_t *)frame_data + offset; | |
| 887 |
2/2✓ Branch 0 taken 95040 times.
✓ Branch 1 taken 360 times.
|
95400 | for (y = 0; y < p->height*skip; y+=skip) { |
| 888 |
2/2✓ Branch 0 taken 25850880 times.
✓ Branch 1 taken 95040 times.
|
25945920 | for (x = 0; x < p->width; x++) { |
| 889 | 25850880 | buf[x] = pix[x] - s->diff_offset; | |
| 890 | } | ||
| 891 | 95040 | memset(&buf[x], 0, (p->coef_stride - p->width)*sizeof(dwtcoef)); | |
| 892 | 95040 | buf += p->coef_stride; | |
| 893 | 95040 | pix += pix_stride; | |
| 894 | } | ||
| 895 | } | ||
| 896 | |||
| 897 | 495 | memset(buf, 0, p->coef_stride * (p->dwt_height - p->height) * sizeof(dwtcoef)); | |
| 898 | |||
| 899 |
2/2✓ Branch 0 taken 1980 times.
✓ Branch 1 taken 495 times.
|
2475 | for (level = s->wavelet_depth-1; level >= 0; level--) { |
| 900 | 1980 | const SubBand *b = &p->band[level][0]; | |
| 901 | 1980 | t->vc2_subband_dwt[idx](t, p->coef_buf, p->coef_stride, | |
| 902 | 1980 | b->width, b->height); | |
| 903 | } | ||
| 904 | |||
| 905 | 495 | return 0; | |
| 906 | } | ||
| 907 | |||
| 908 | 165 | static int encode_frame(VC2EncContext *s, AVPacket *avpkt, const AVFrame *frame, | |
| 909 | const char *aux_data, const int header_size, int field) | ||
| 910 | { | ||
| 911 | int i, ret; | ||
| 912 | int64_t max_frame_bytes; | ||
| 913 | |||
| 914 | /* Threaded DWT transform */ | ||
| 915 |
2/2✓ Branch 0 taken 495 times.
✓ Branch 1 taken 165 times.
|
660 | for (i = 0; i < 3; i++) { |
| 916 | 495 | s->transform_args[i].ctx = s; | |
| 917 | 495 | s->transform_args[i].field = field; | |
| 918 | 495 | s->transform_args[i].plane = &s->plane[i]; | |
| 919 | 495 | s->transform_args[i].idata = frame->data[i]; | |
| 920 | 495 | s->transform_args[i].istride = frame->linesize[i]; | |
| 921 | } | ||
| 922 | 165 | s->avctx->execute(s->avctx, dwt_plane, s->transform_args, NULL, 3, | |
| 923 | sizeof(TransformArgs)); | ||
| 924 | |||
| 925 | /* Calculate per-slice quantizers and sizes */ | ||
| 926 | 165 | max_frame_bytes = header_size + calc_slice_sizes(s); | |
| 927 | |||
| 928 |
1/2✓ Branch 0 taken 165 times.
✗ Branch 1 not taken.
|
165 | if (field < 2) { |
| 929 | 165 | ret = ff_get_encode_buffer(s->avctx, avpkt, | |
| 930 | 165 | max_frame_bytes << s->interlaced, 0); | |
| 931 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 165 times.
|
165 | if (ret < 0) |
| 932 | ✗ | return ret; | |
| 933 | 165 | init_put_bits(&s->pb, avpkt->data, avpkt->size); | |
| 934 | } | ||
| 935 | |||
| 936 | /* Sequence header */ | ||
| 937 | 165 | encode_parse_info(s, DIRAC_PCODE_SEQ_HEADER); | |
| 938 | 165 | encode_seq_header(s); | |
| 939 | |||
| 940 | /* Encoder version */ | ||
| 941 |
1/2✓ Branch 0 taken 165 times.
✗ Branch 1 not taken.
|
165 | if (aux_data) { |
| 942 | 165 | encode_parse_info(s, DIRAC_PCODE_AUX); | |
| 943 | 165 | ff_put_string(&s->pb, aux_data, 1); | |
| 944 | } | ||
| 945 | |||
| 946 | /* Picture header */ | ||
| 947 | 165 | encode_parse_info(s, DIRAC_PCODE_PICTURE_HQ); | |
| 948 | 165 | encode_picture_start(s); | |
| 949 | |||
| 950 | /* Encode slices */ | ||
| 951 | 165 | encode_slices(s); | |
| 952 | |||
| 953 | /* End sequence */ | ||
| 954 | 165 | encode_parse_info(s, DIRAC_PCODE_END_SEQ); | |
| 955 | |||
| 956 | 165 | return 0; | |
| 957 | } | ||
| 958 | |||
| 959 | 165 | static av_cold int vc2_encode_frame(AVCodecContext *avctx, AVPacket *avpkt, | |
| 960 | const AVFrame *frame, int *got_packet) | ||
| 961 | { | ||
| 962 | 165 | int ret = 0; | |
| 963 | 165 | int slice_ceil, sig_size = 256; | |
| 964 | 165 | VC2EncContext *s = avctx->priv_data; | |
| 965 | 165 | const int bitexact = avctx->flags & AV_CODEC_FLAG_BITEXACT; | |
| 966 |
1/2✓ Branch 0 taken 165 times.
✗ Branch 1 not taken.
|
165 | const char *aux_data = bitexact ? "Lavc" : LIBAVCODEC_IDENT; |
| 967 |
1/2✓ Branch 0 taken 165 times.
✗ Branch 1 not taken.
|
165 | const int aux_data_size = bitexact ? sizeof("Lavc") : sizeof(LIBAVCODEC_IDENT); |
| 968 | 165 | const int header_size = 100 + aux_data_size; | |
| 969 | 165 | int64_t r_bitrate = avctx->bit_rate >> (s->interlaced); | |
| 970 | |||
| 971 | 165 | s->avctx = avctx; | |
| 972 | 165 | s->size_scaler = 2; | |
| 973 | 165 | s->prefix_bytes = 0; | |
| 974 | 165 | s->last_parse_code = 0; | |
| 975 | 165 | s->next_parse_offset = 0; | |
| 976 | |||
| 977 | /* Rate control */ | ||
| 978 | 165 | s->frame_max_bytes = (av_rescale(r_bitrate, s->avctx->time_base.num, | |
| 979 | 165 | s->avctx->time_base.den) >> 3) - header_size; | |
| 980 | 165 | s->slice_max_bytes = slice_ceil = av_rescale(s->frame_max_bytes, 1, s->num_x*s->num_y); | |
| 981 | |||
| 982 | /* Find an appropriate size scaler */ | ||
| 983 |
2/2✓ Branch 0 taken 990 times.
✓ Branch 1 taken 165 times.
|
1155 | while (sig_size > 255) { |
| 984 | 990 | int r_size = SSIZE_ROUND(s->slice_max_bytes); | |
| 985 |
2/2✓ Branch 0 taken 825 times.
✓ Branch 1 taken 165 times.
|
990 | if (r_size > slice_ceil) { |
| 986 | 825 | s->slice_max_bytes -= r_size - slice_ceil; | |
| 987 | 825 | r_size = SSIZE_ROUND(s->slice_max_bytes); | |
| 988 | } | ||
| 989 | 990 | sig_size = r_size/s->size_scaler; /* Signalled slize size */ | |
| 990 | 990 | s->size_scaler <<= 1; | |
| 991 | } | ||
| 992 | |||
| 993 | 165 | s->slice_min_bytes = s->slice_max_bytes - s->slice_max_bytes*(s->tolerance/100.0f); | |
| 994 |
2/4✓ Branch 0 taken 165 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 165 times.
|
165 | if (s->slice_min_bytes < 0 || s->slice_max_bytes > INT_MAX >> 3) |
| 995 | ✗ | return AVERROR(EINVAL); | |
| 996 | |||
| 997 | 165 | ret = encode_frame(s, avpkt, frame, aux_data, header_size, s->interlaced); | |
| 998 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 165 times.
|
165 | if (ret) |
| 999 | ✗ | return ret; | |
| 1000 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 165 times.
|
165 | if (s->interlaced) { |
| 1001 | ✗ | ret = encode_frame(s, avpkt, frame, aux_data, header_size, 2); | |
| 1002 | ✗ | if (ret) | |
| 1003 | ✗ | return ret; | |
| 1004 | } | ||
| 1005 | |||
| 1006 | 165 | flush_put_bits(&s->pb); | |
| 1007 | 165 | av_shrink_packet(avpkt, put_bytes_output(&s->pb)); | |
| 1008 | |||
| 1009 | 165 | *got_packet = 1; | |
| 1010 | |||
| 1011 | 165 | return 0; | |
| 1012 | } | ||
| 1013 | |||
| 1014 | 33 | static av_cold int vc2_encode_end(AVCodecContext *avctx) | |
| 1015 | { | ||
| 1016 | int i; | ||
| 1017 | 33 | VC2EncContext *s = avctx->priv_data; | |
| 1018 | |||
| 1019 | 33 | av_log(avctx, AV_LOG_INFO, "Qavg: %i\n", s->q_avg); | |
| 1020 | |||
| 1021 |
2/2✓ Branch 0 taken 99 times.
✓ Branch 1 taken 33 times.
|
132 | for (i = 0; i < 3; i++) { |
| 1022 | 99 | ff_vc2enc_free_transforms(&s->transform_args[i].t); | |
| 1023 | 99 | av_freep(&s->plane[i].coef_buf); | |
| 1024 | } | ||
| 1025 | |||
| 1026 | 33 | av_freep(&s->slice_args); | |
| 1027 | |||
| 1028 | 33 | return 0; | |
| 1029 | } | ||
| 1030 | |||
| 1031 | 33 | static av_cold int vc2_encode_init(AVCodecContext *avctx) | |
| 1032 | { | ||
| 1033 | static AVOnce init_static_once = AV_ONCE_INIT; | ||
| 1034 | Plane *p; | ||
| 1035 | SubBand *b; | ||
| 1036 | int i, level, o, shift; | ||
| 1037 | const AVPixFmtDescriptor *pixdesc; | ||
| 1038 | int depth; | ||
| 1039 | 33 | VC2EncContext *s = avctx->priv_data; | |
| 1040 | |||
| 1041 | 33 | s->picture_number = 0; | |
| 1042 | |||
| 1043 | /* Total allowed quantization range */ | ||
| 1044 | 33 | s->q_ceil = DIRAC_MAX_QUANT_INDEX; | |
| 1045 | |||
| 1046 | 33 | s->ver.major = 2; | |
| 1047 | 33 | s->ver.minor = 0; | |
| 1048 | 33 | s->profile = 3; | |
| 1049 | 33 | s->level = 3; | |
| 1050 | |||
| 1051 | 33 | s->base_vf = -1; | |
| 1052 | 33 | s->strict_compliance = 1; | |
| 1053 | |||
| 1054 | 33 | s->q_avg = 0; | |
| 1055 | 33 | s->slice_max_bytes = 0; | |
| 1056 | 33 | s->slice_min_bytes = 0; | |
| 1057 | |||
| 1058 | /* Mark unknown as progressive */ | ||
| 1059 |
1/2✓ Branch 0 taken 33 times.
✗ Branch 1 not taken.
|
66 | s->interlaced = !((avctx->field_order == AV_FIELD_UNKNOWN) || |
| 1060 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 33 times.
|
33 | (avctx->field_order == AV_FIELD_PROGRESSIVE)); |
| 1061 | |||
| 1062 |
2/2✓ Branch 0 taken 759 times.
✓ Branch 1 taken 33 times.
|
792 | for (i = 0; i < base_video_fmts_len; i++) { |
| 1063 | 759 | const VC2BaseVideoFormat *fmt = &base_video_fmts[i]; | |
| 1064 |
2/2✓ Branch 0 taken 606 times.
✓ Branch 1 taken 153 times.
|
759 | if (avctx->pix_fmt != fmt->pix_fmt) |
| 1065 | 606 | continue; | |
| 1066 |
2/2✓ Branch 0 taken 93 times.
✓ Branch 1 taken 60 times.
|
153 | if (avctx->time_base.num != fmt->time_base.num) |
| 1067 | 93 | continue; | |
| 1068 |
2/2✓ Branch 0 taken 42 times.
✓ Branch 1 taken 18 times.
|
60 | if (avctx->time_base.den != fmt->time_base.den) |
| 1069 | 42 | continue; | |
| 1070 |
1/2✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
|
18 | if (avctx->width != fmt->width) |
| 1071 | 18 | continue; | |
| 1072 | ✗ | if (avctx->height != fmt->height) | |
| 1073 | ✗ | continue; | |
| 1074 | ✗ | if (s->interlaced != fmt->interlaced) | |
| 1075 | ✗ | continue; | |
| 1076 | ✗ | s->base_vf = i; | |
| 1077 | ✗ | s->level = base_video_fmts[i].level; | |
| 1078 | ✗ | break; | |
| 1079 | } | ||
| 1080 | |||
| 1081 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 33 times.
|
33 | if (s->interlaced) |
| 1082 | ✗ | av_log(avctx, AV_LOG_WARNING, "Interlacing enabled!\n"); | |
| 1083 | |||
| 1084 |
1/2✓ Branch 0 taken 33 times.
✗ Branch 1 not taken.
|
33 | if ((s->slice_width & (s->slice_width - 1)) || |
| 1085 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 33 times.
|
33 | (s->slice_height & (s->slice_height - 1))) { |
| 1086 | ✗ | av_log(avctx, AV_LOG_ERROR, "Slice size is not a power of two!\n"); | |
| 1087 | ✗ | return AVERROR(EINVAL); | |
| 1088 | } | ||
| 1089 | |||
| 1090 |
1/2✓ Branch 0 taken 33 times.
✗ Branch 1 not taken.
|
33 | if ((s->slice_width > avctx->width) || |
| 1091 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 33 times.
|
33 | (s->slice_height > avctx->height)) { |
| 1092 | ✗ | av_log(avctx, AV_LOG_ERROR, "Slice size is bigger than the image!\n"); | |
| 1093 | ✗ | return AVERROR(EINVAL); | |
| 1094 | } | ||
| 1095 | |||
| 1096 |
1/2✓ Branch 0 taken 33 times.
✗ Branch 1 not taken.
|
33 | if (s->base_vf <= 0) { |
| 1097 |
1/2✓ Branch 0 taken 33 times.
✗ Branch 1 not taken.
|
33 | if (avctx->strict_std_compliance < FF_COMPLIANCE_STRICT) { |
| 1098 | 33 | s->strict_compliance = s->base_vf = 0; | |
| 1099 | 33 | av_log(avctx, AV_LOG_WARNING, "Format does not strictly comply with VC2 specs\n"); | |
| 1100 | } else { | ||
| 1101 | ✗ | av_log(avctx, AV_LOG_WARNING, "Given format does not strictly comply with " | |
| 1102 | "the specifications, decrease strictness to use it.\n"); | ||
| 1103 | ✗ | return AVERROR(EINVAL); | |
| 1104 | } | ||
| 1105 | } else { | ||
| 1106 | ✗ | av_log(avctx, AV_LOG_INFO, "Selected base video format = %i (%s)\n", | |
| 1107 | ✗ | s->base_vf, base_video_fmts[s->base_vf].name); | |
| 1108 | } | ||
| 1109 | |||
| 1110 | 33 | pixdesc = av_pix_fmt_desc_get(avctx->pix_fmt); | |
| 1111 | /* Chroma subsampling */ | ||
| 1112 | 33 | s->chroma_x_shift = pixdesc->log2_chroma_w; | |
| 1113 | 33 | s->chroma_y_shift = pixdesc->log2_chroma_h; | |
| 1114 | |||
| 1115 | /* Bit depth and color range index */ | ||
| 1116 | 33 | depth = pixdesc->comp[0].depth; | |
| 1117 |
3/4✓ Branch 0 taken 9 times.
✓ Branch 1 taken 24 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 9 times.
|
33 | if (depth == 8 && avctx->color_range == AVCOL_RANGE_JPEG) { |
| 1118 | ✗ | s->bpp = 1; | |
| 1119 | ✗ | s->bpp_idx = 1; | |
| 1120 | ✗ | s->diff_offset = 128; | |
| 1121 |
3/4✓ Branch 0 taken 9 times.
✓ Branch 1 taken 24 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 9 times.
|
33 | } else if (depth == 8 && (avctx->color_range == AVCOL_RANGE_MPEG || |
| 1122 | ✗ | avctx->color_range == AVCOL_RANGE_UNSPECIFIED)) { | |
| 1123 | 9 | s->bpp = 1; | |
| 1124 | 9 | s->bpp_idx = 2; | |
| 1125 | 9 | s->diff_offset = 128; | |
| 1126 |
2/2✓ Branch 0 taken 15 times.
✓ Branch 1 taken 9 times.
|
24 | } else if (depth == 10) { |
| 1127 | 15 | s->bpp = 2; | |
| 1128 | 15 | s->bpp_idx = 3; | |
| 1129 | 15 | s->diff_offset = 512; | |
| 1130 | } else { | ||
| 1131 | 9 | s->bpp = 2; | |
| 1132 | 9 | s->bpp_idx = 4; | |
| 1133 | 9 | s->diff_offset = 2048; | |
| 1134 | } | ||
| 1135 | |||
| 1136 | /* Planes initialization */ | ||
| 1137 |
2/2✓ Branch 0 taken 99 times.
✓ Branch 1 taken 33 times.
|
132 | for (i = 0; i < 3; i++) { |
| 1138 | int w, h; | ||
| 1139 | 99 | p = &s->plane[i]; | |
| 1140 |
2/2✓ Branch 0 taken 66 times.
✓ Branch 1 taken 33 times.
|
99 | p->width = avctx->width >> (i ? s->chroma_x_shift : 0); |
| 1141 |
2/2✓ Branch 0 taken 66 times.
✓ Branch 1 taken 33 times.
|
99 | p->height = avctx->height >> (i ? s->chroma_y_shift : 0); |
| 1142 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 99 times.
|
99 | if (s->interlaced) |
| 1143 | ✗ | p->height >>= 1; | |
| 1144 | 99 | p->dwt_width = w = FFALIGN(p->width, (1 << s->wavelet_depth)); | |
| 1145 | 99 | p->dwt_height = h = FFALIGN(p->height, (1 << s->wavelet_depth)); | |
| 1146 | 99 | p->coef_stride = FFALIGN(p->dwt_width, 32); | |
| 1147 | 99 | p->coef_buf = av_mallocz(p->coef_stride*p->dwt_height*sizeof(dwtcoef)); | |
| 1148 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 99 times.
|
99 | if (!p->coef_buf) |
| 1149 | ✗ | return AVERROR(ENOMEM); | |
| 1150 |
2/2✓ Branch 0 taken 396 times.
✓ Branch 1 taken 99 times.
|
495 | for (level = s->wavelet_depth-1; level >= 0; level--) { |
| 1151 | 396 | w = w >> 1; | |
| 1152 | 396 | h = h >> 1; | |
| 1153 |
2/2✓ Branch 0 taken 1584 times.
✓ Branch 1 taken 396 times.
|
1980 | for (o = 0; o < 4; o++) { |
| 1154 | 1584 | b = &p->band[level][o]; | |
| 1155 | 1584 | b->width = w; | |
| 1156 | 1584 | b->height = h; | |
| 1157 | 1584 | b->stride = p->coef_stride; | |
| 1158 | 1584 | shift = (o > 1)*b->height*b->stride + (o & 1)*b->width; | |
| 1159 | 1584 | b->buf = p->coef_buf + shift; | |
| 1160 | } | ||
| 1161 | } | ||
| 1162 | |||
| 1163 | /* DWT init */ | ||
| 1164 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 99 times.
|
99 | if (ff_vc2enc_init_transforms(&s->transform_args[i].t, |
| 1165 | 99 | s->plane[i].coef_stride, | |
| 1166 | s->plane[i].dwt_height, | ||
| 1167 | s->slice_width, s->slice_height)) | ||
| 1168 | ✗ | return AVERROR(ENOMEM); | |
| 1169 | } | ||
| 1170 | |||
| 1171 | /* Slices */ | ||
| 1172 | 33 | s->num_x = s->plane[0].dwt_width/s->slice_width; | |
| 1173 | 33 | s->num_y = s->plane[0].dwt_height/s->slice_height; | |
| 1174 | |||
| 1175 | 33 | s->slice_args = av_calloc(s->num_x*s->num_y, sizeof(SliceArgs)); | |
| 1176 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 33 times.
|
33 | if (!s->slice_args) |
| 1177 | ✗ | return AVERROR(ENOMEM); | |
| 1178 | |||
| 1179 |
2/2✓ Branch 0 taken 3828 times.
✓ Branch 1 taken 33 times.
|
3861 | for (i = 0; i < 116; i++) { |
| 1180 | 3828 | const uint64_t qf = ff_dirac_qscale_tab[i]; | |
| 1181 | 3828 | const uint32_t m = av_log2(qf); | |
| 1182 | 3828 | const uint32_t t = (1ULL << (m + 32)) / qf; | |
| 1183 | 3828 | const uint32_t r = (t*qf + qf) & UINT32_MAX; | |
| 1184 |
2/2✓ Branch 0 taken 957 times.
✓ Branch 1 taken 2871 times.
|
3828 | if (!(qf & (qf - 1))) { |
| 1185 | 957 | s->qmagic_lut[i][0] = 0xFFFFFFFF; | |
| 1186 | 957 | s->qmagic_lut[i][1] = 0xFFFFFFFF; | |
| 1187 |
2/2✓ Branch 0 taken 2145 times.
✓ Branch 1 taken 726 times.
|
2871 | } else if (r <= 1 << m) { |
| 1188 | 2145 | s->qmagic_lut[i][0] = t + 1; | |
| 1189 | 2145 | s->qmagic_lut[i][1] = 0; | |
| 1190 | } else { | ||
| 1191 | 726 | s->qmagic_lut[i][0] = t; | |
| 1192 | 726 | s->qmagic_lut[i][1] = t; | |
| 1193 | } | ||
| 1194 | } | ||
| 1195 | |||
| 1196 | 33 | ff_thread_once(&init_static_once, vc2_init_static_data); | |
| 1197 | |||
| 1198 | 33 | return 0; | |
| 1199 | } | ||
| 1200 | |||
| 1201 | #define VC2ENC_FLAGS (AV_OPT_FLAG_ENCODING_PARAM | AV_OPT_FLAG_VIDEO_PARAM) | ||
| 1202 | static const AVOption vc2enc_options[] = { | ||
| 1203 | {"tolerance", "Max undershoot in percent", offsetof(VC2EncContext, tolerance), AV_OPT_TYPE_DOUBLE, {.dbl = 5.0f}, 0.0f, 45.0f, VC2ENC_FLAGS, .unit = "tolerance"}, | ||
| 1204 | {"slice_width", "Slice width", offsetof(VC2EncContext, slice_width), AV_OPT_TYPE_INT, {.i64 = 32}, 32, 1024, VC2ENC_FLAGS, .unit = "slice_width"}, | ||
| 1205 | {"slice_height", "Slice height", offsetof(VC2EncContext, slice_height), AV_OPT_TYPE_INT, {.i64 = 16}, 8, 1024, VC2ENC_FLAGS, .unit = "slice_height"}, | ||
| 1206 | {"wavelet_depth", "Transform depth", offsetof(VC2EncContext, wavelet_depth), AV_OPT_TYPE_INT, {.i64 = 4}, 1, 5, VC2ENC_FLAGS, .unit = "wavelet_depth"}, | ||
| 1207 | {"wavelet_type", "Transform type", offsetof(VC2EncContext, wavelet_idx), AV_OPT_TYPE_INT, {.i64 = VC2_TRANSFORM_9_7}, 0, VC2_TRANSFORMS_NB, VC2ENC_FLAGS, .unit = "wavelet_idx"}, | ||
| 1208 | {"9_7", "Deslauriers-Dubuc (9,7)", 0, AV_OPT_TYPE_CONST, {.i64 = VC2_TRANSFORM_9_7}, INT_MIN, INT_MAX, VC2ENC_FLAGS, .unit = "wavelet_idx"}, | ||
| 1209 | {"5_3", "LeGall (5,3)", 0, AV_OPT_TYPE_CONST, {.i64 = VC2_TRANSFORM_5_3}, INT_MIN, INT_MAX, VC2ENC_FLAGS, .unit = "wavelet_idx"}, | ||
| 1210 | {"haar", "Haar (with shift)", 0, AV_OPT_TYPE_CONST, {.i64 = VC2_TRANSFORM_HAAR_S}, INT_MIN, INT_MAX, VC2ENC_FLAGS, .unit = "wavelet_idx"}, | ||
| 1211 | {"haar_noshift", "Haar (without shift)", 0, AV_OPT_TYPE_CONST, {.i64 = VC2_TRANSFORM_HAAR}, INT_MIN, INT_MAX, VC2ENC_FLAGS, .unit = "wavelet_idx"}, | ||
| 1212 | {"qm", "Custom quantization matrix", offsetof(VC2EncContext, quant_matrix), AV_OPT_TYPE_INT, {.i64 = VC2_QM_DEF}, 0, VC2_QM_NB, VC2ENC_FLAGS, .unit = "quant_matrix"}, | ||
| 1213 | {"default", "Default from the specifications", 0, AV_OPT_TYPE_CONST, {.i64 = VC2_QM_DEF}, INT_MIN, INT_MAX, VC2ENC_FLAGS, .unit = "quant_matrix"}, | ||
| 1214 | {"color", "Prevents low bitrate discoloration", 0, AV_OPT_TYPE_CONST, {.i64 = VC2_QM_COL}, INT_MIN, INT_MAX, VC2ENC_FLAGS, .unit = "quant_matrix"}, | ||
| 1215 | {"flat", "Optimize for PSNR", 0, AV_OPT_TYPE_CONST, {.i64 = VC2_QM_FLAT}, INT_MIN, INT_MAX, VC2ENC_FLAGS, .unit = "quant_matrix"}, | ||
| 1216 | {NULL} | ||
| 1217 | }; | ||
| 1218 | |||
| 1219 | static const AVClass vc2enc_class = { | ||
| 1220 | .class_name = "SMPTE VC-2 encoder", | ||
| 1221 | .category = AV_CLASS_CATEGORY_ENCODER, | ||
| 1222 | .option = vc2enc_options, | ||
| 1223 | .item_name = av_default_item_name, | ||
| 1224 | .version = LIBAVUTIL_VERSION_INT | ||
| 1225 | }; | ||
| 1226 | |||
| 1227 | static const FFCodecDefault vc2enc_defaults[] = { | ||
| 1228 | { "b", "600000000" }, | ||
| 1229 | { NULL }, | ||
| 1230 | }; | ||
| 1231 | |||
| 1232 | static const enum AVPixelFormat allowed_pix_fmts[] = { | ||
| 1233 | AV_PIX_FMT_YUV420P, AV_PIX_FMT_YUV422P, AV_PIX_FMT_YUV444P, | ||
| 1234 | AV_PIX_FMT_YUV420P10, AV_PIX_FMT_YUV422P10, AV_PIX_FMT_YUV444P10, | ||
| 1235 | AV_PIX_FMT_YUV420P12, AV_PIX_FMT_YUV422P12, AV_PIX_FMT_YUV444P12, | ||
| 1236 | AV_PIX_FMT_NONE | ||
| 1237 | }; | ||
| 1238 | |||
| 1239 | const FFCodec ff_vc2_encoder = { | ||
| 1240 | .p.name = "vc2", | ||
| 1241 | CODEC_LONG_NAME("SMPTE VC-2"), | ||
| 1242 | .p.type = AVMEDIA_TYPE_VIDEO, | ||
| 1243 | .p.id = AV_CODEC_ID_DIRAC, | ||
| 1244 | .p.capabilities = AV_CODEC_CAP_DR1 | AV_CODEC_CAP_SLICE_THREADS | | ||
| 1245 | AV_CODEC_CAP_ENCODER_REORDERED_OPAQUE, | ||
| 1246 | .caps_internal = FF_CODEC_CAP_INIT_CLEANUP, | ||
| 1247 | .priv_data_size = sizeof(VC2EncContext), | ||
| 1248 | .init = vc2_encode_init, | ||
| 1249 | .close = vc2_encode_end, | ||
| 1250 | FF_CODEC_ENCODE_CB(vc2_encode_frame), | ||
| 1251 | .p.priv_class = &vc2enc_class, | ||
| 1252 | .defaults = vc2enc_defaults, | ||
| 1253 | CODEC_PIXFMTS_ARRAY(allowed_pix_fmts), | ||
| 1254 | .color_ranges = AVCOL_RANGE_MPEG | AVCOL_RANGE_JPEG, | ||
| 1255 | }; | ||
| 1256 |