FFmpeg coverage


Directory: ../../../ffmpeg/
File: src/libavcodec/aic.c
Date: 2023-01-27 00:32:08
Exec Total Coverage
Lines: 167 192 87.0%
Functions: 9 9 100.0%
Branches: 93 114 81.6%

Line Branch Exec Source
1 /*
2 * Apple Intermediate Codec decoder
3 *
4 * Copyright (c) 2013 Konstantin Shishkov
5 *
6 * This file is part of FFmpeg.
7 *
8 * FFmpeg is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU Lesser General Public
10 * License as published by the Free Software Foundation; either
11 * version 2.1 of the License, or (at your option) any later version.
12 *
13 * FFmpeg is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 * Lesser General Public License for more details.
17 *
18 * You should have received a copy of the GNU Lesser General Public
19 * License along with FFmpeg; if not, write to the Free Software
20 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
21 */
22
23 #include <inttypes.h>
24
25 #include "libavutil/mem_internal.h"
26
27 #include "avcodec.h"
28 #include "bytestream.h"
29 #include "codec_internal.h"
30 #include "get_bits.h"
31 #include "golomb.h"
32 #include "idctdsp.h"
33 #include "thread.h"
34 #include "unary.h"
35
36 #define AIC_HDR_SIZE 24
37 #define AIC_BAND_COEFFS (64 + 32 + 192 + 96)
38
39 enum AICBands {
40 COEFF_LUMA = 0,
41 COEFF_CHROMA,
42 COEFF_LUMA_EXT,
43 COEFF_CHROMA_EXT,
44 NUM_BANDS
45 };
46
47 static const uint8_t aic_num_band_coeffs[NUM_BANDS] = { 64, 32, 192, 96 };
48
49 static const uint16_t aic_band_off[NUM_BANDS] = { 0, 64, 96, 288 };
50
51 static const uint8_t aic_quant_matrix[64] = {
52 8, 16, 19, 22, 22, 26, 26, 27,
53 16, 16, 22, 22, 26, 27, 27, 29,
54 19, 22, 26, 26, 27, 29, 29, 35,
55 22, 24, 27, 27, 29, 32, 34, 38,
56 26, 27, 29, 29, 32, 35, 38, 46,
57 27, 29, 34, 34, 35, 40, 46, 56,
58 29, 34, 34, 37, 40, 48, 56, 69,
59 34, 37, 38, 40, 48, 58, 69, 83,
60 };
61
62 static const uint8_t aic_y_scan[64] = {
63 0, 4, 1, 2, 5, 8, 12, 9,
64 6, 3, 7, 10, 13, 14, 11, 15,
65 47, 43, 46, 45, 42, 39, 35, 38,
66 41, 44, 40, 37, 34, 33, 36, 32,
67 16, 20, 17, 18, 21, 24, 28, 25,
68 22, 19, 23, 26, 29, 30, 27, 31,
69 63, 59, 62, 61, 58, 55, 51, 54,
70 57, 60, 56, 53, 50, 49, 52, 48,
71 };
72
73 static const uint8_t aic_y_ext_scan[192] = {
74 64, 72, 65, 66, 73, 80, 88, 81,
75 74, 67, 75, 82, 89, 90, 83, 91,
76 0, 4, 1, 2, 5, 8, 12, 9,
77 6, 3, 7, 10, 13, 14, 11, 15,
78 16, 20, 17, 18, 21, 24, 28, 25,
79 22, 19, 23, 26, 29, 30, 27, 31,
80 155, 147, 154, 153, 146, 139, 131, 138,
81 145, 152, 144, 137, 130, 129, 136, 128,
82 47, 43, 46, 45, 42, 39, 35, 38,
83 41, 44, 40, 37, 34, 33, 36, 32,
84 63, 59, 62, 61, 58, 55, 51, 54,
85 57, 60, 56, 53, 50, 49, 52, 48,
86 96, 104, 97, 98, 105, 112, 120, 113,
87 106, 99, 107, 114, 121, 122, 115, 123,
88 68, 76, 69, 70, 77, 84, 92, 85,
89 78, 71, 79, 86, 93, 94, 87, 95,
90 100, 108, 101, 102, 109, 116, 124, 117,
91 110, 103, 111, 118, 125, 126, 119, 127,
92 187, 179, 186, 185, 178, 171, 163, 170,
93 177, 184, 176, 169, 162, 161, 168, 160,
94 159, 151, 158, 157, 150, 143, 135, 142,
95 149, 156, 148, 141, 134, 133, 140, 132,
96 191, 183, 190, 189, 182, 175, 167, 174,
97 181, 188, 180, 173, 166, 165, 172, 164,
98 };
99
100 static const uint8_t aic_c_scan[64] = {
101 0, 4, 1, 2, 5, 8, 12, 9,
102 6, 3, 7, 10, 13, 14, 11, 15,
103 31, 27, 30, 29, 26, 23, 19, 22,
104 25, 28, 24, 21, 18, 17, 20, 16,
105 32, 36, 33, 34, 37, 40, 44, 41,
106 38, 35, 39, 42, 45, 46, 43, 47,
107 63, 59, 62, 61, 58, 55, 51, 54,
108 57, 60, 56, 53, 50, 49, 52, 48,
109 };
110
111 static const uint8_t aic_c_ext_scan[192] = {
112 16, 24, 17, 18, 25, 32, 40, 33,
113 26, 19, 27, 34, 41, 42, 35, 43,
114 0, 4, 1, 2, 5, 8, 12, 9,
115 6, 3, 7, 10, 13, 14, 11, 15,
116 20, 28, 21, 22, 29, 36, 44, 37,
117 30, 23, 31, 38, 45, 46, 39, 47,
118 95, 87, 94, 93, 86, 79, 71, 78,
119 85, 92, 84, 77, 70, 69, 76, 68,
120 63, 59, 62, 61, 58, 55, 51, 54,
121 57, 60, 56, 53, 50, 49, 52, 48,
122 91, 83, 90, 89, 82, 75, 67, 74,
123 81, 88, 80, 73, 66, 65, 72, 64,
124 112, 120, 113, 114, 121, 128, 136, 129,
125 122, 115, 123, 130, 137, 138, 131, 139,
126 96, 100, 97, 98, 101, 104, 108, 105,
127 102, 99, 103, 106, 109, 110, 107, 111,
128 116, 124, 117, 118, 125, 132, 140, 133,
129 126, 119, 127, 134, 141, 142, 135, 143,
130 191, 183, 190, 189, 182, 175, 167, 174,
131 181, 188, 180, 173, 166, 165, 172, 164,
132 159, 155, 158, 157, 154, 151, 147, 150,
133 153, 156, 152, 149, 146, 145, 148, 144,
134 187, 179, 186, 185, 178, 171, 163, 170,
135 177, 184, 176, 169, 162, 161, 168, 160,
136 };
137
138 static const uint8_t * const aic_scan[NUM_BANDS] = {
139 aic_y_scan, aic_c_scan, aic_y_ext_scan, aic_c_ext_scan
140 };
141
142 typedef struct AICContext {
143 AVCodecContext *avctx;
144 AVFrame *frame;
145 IDCTDSPContext idsp;
146
147 int num_x_slices;
148 int slice_width;
149 int mb_width, mb_height;
150 int quant;
151 int interlaced;
152
153 int16_t *slice_data;
154 int16_t *data_ptr[NUM_BANDS];
155
156 DECLARE_ALIGNED(16, int16_t, block)[64];
157 DECLARE_ALIGNED(16, uint8_t, quant_matrix)[64];
158 } AICContext;
159
160 72 static int aic_decode_header(AICContext *ctx, const uint8_t *src, int size)
161 {
162 uint32_t frame_size;
163 int width, height;
164
165
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 72 times.
72 if (src[0] != 1) {
166 av_log(ctx->avctx, AV_LOG_ERROR, "Invalid version %d\n", src[0]);
167 return AVERROR_INVALIDDATA;
168 }
169
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 72 times.
72 if (src[1] != AIC_HDR_SIZE - 2) {
170 av_log(ctx->avctx, AV_LOG_ERROR, "Invalid header size %d\n", src[1]);
171 return AVERROR_INVALIDDATA;
172 }
173 72 frame_size = AV_RB32(src + 2);
174 72 width = AV_RB16(src + 6);
175 72 height = AV_RB16(src + 8);
176
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 72 times.
72 if (frame_size > size) {
177 av_log(ctx->avctx, AV_LOG_ERROR, "Frame size should be %"PRIu32" got %d\n",
178 frame_size, size);
179 return AVERROR_INVALIDDATA;
180 }
181
2/4
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 72 times.
72 if (width != ctx->avctx->width || height != ctx->avctx->height) {
182 av_log(ctx->avctx, AV_LOG_ERROR,
183 "Picture dimension changed: old: %d x %d, new: %d x %d\n",
184 ctx->avctx->width, ctx->avctx->height, width, height);
185 return AVERROR_INVALIDDATA;
186 }
187 72 ctx->quant = src[15];
188 72 ctx->interlaced = ((src[16] >> 4) == 3);
189
190 72 return 0;
191 }
192
193 #define GET_CODE(val, type, add_bits) \
194 do { \
195 if (type) \
196 val = get_ue_golomb(gb); \
197 else \
198 val = get_unary(gb, 1, 31); \
199 if (add_bits) \
200 val = (val << add_bits) + get_bits(gb, add_bits); \
201 } while (0)
202
203 15888 static int aic_decode_coeffs(GetBitContext *gb, int16_t *dst,
204 int band, int slice_width, int force_chroma)
205 {
206 int has_skips, coeff_type, coeff_bits, skip_type, skip_bits;
207 15888 const int num_coeffs = aic_num_band_coeffs[band];
208 15888 const uint8_t *scan = aic_scan[band | force_chroma];
209 int mb, idx;
210 unsigned val;
211
212
1/2
✗ Branch 1 not taken.
✓ Branch 2 taken 15888 times.
15888 if (get_bits_left(gb) < 5)
213 return AVERROR_INVALIDDATA;
214
215 15888 has_skips = get_bits1(gb);
216 15888 coeff_type = get_bits1(gb);
217 15888 coeff_bits = get_bits(gb, 3);
218
219
2/2
✓ Branch 0 taken 13996 times.
✓ Branch 1 taken 1892 times.
15888 if (has_skips) {
220 13996 skip_type = get_bits1(gb);
221 13996 skip_bits = get_bits(gb, 3);
222
223
2/2
✓ Branch 0 taken 423437 times.
✓ Branch 1 taken 13996 times.
437433 for (mb = 0; mb < slice_width; mb++) {
224 423437 idx = -1;
225 do {
226
3/4
✓ Branch 0 taken 5032630 times.
✗ Branch 1 not taken.
✓ Branch 4 taken 323504 times.
✓ Branch 5 taken 4709126 times.
5032630 GET_CODE(val, skip_type, skip_bits);
227
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 5032630 times.
5032630 if (val >= 0x10000)
228 return AVERROR_INVALIDDATA;
229 5032630 idx += val + 1;
230
2/2
✓ Branch 0 taken 252068 times.
✓ Branch 1 taken 4780562 times.
5032630 if (idx >= num_coeffs)
231 252068 break;
232
4/4
✓ Branch 0 taken 4639461 times.
✓ Branch 1 taken 141101 times.
✓ Branch 4 taken 4639461 times.
✓ Branch 5 taken 141101 times.
4780562 GET_CODE(val, coeff_type, coeff_bits);
233 4780562 val++;
234
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 4780562 times.
4780562 if (val >= 0x10000)
235 return AVERROR_INVALIDDATA;
236 4780562 dst[scan[idx]] = val;
237
2/2
✓ Branch 0 taken 4609193 times.
✓ Branch 1 taken 171369 times.
4780562 } while (idx < num_coeffs - 1);
238 423437 dst += num_coeffs;
239 }
240 } else {
241
2/2
✓ Branch 0 taken 56851 times.
✓ Branch 1 taken 1892 times.
58743 for (mb = 0; mb < slice_width; mb++) {
242
2/2
✓ Branch 0 taken 10519744 times.
✓ Branch 1 taken 56851 times.
10576595 for (idx = 0; idx < num_coeffs; idx++) {
243
3/4
✓ Branch 0 taken 10519744 times.
✗ Branch 1 not taken.
✓ Branch 4 taken 180544 times.
✓ Branch 5 taken 10339200 times.
10519744 GET_CODE(val, coeff_type, coeff_bits);
244
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 10519744 times.
10519744 if (val >= 0x10000)
245 return AVERROR_INVALIDDATA;
246 10519744 dst[scan[idx]] = val;
247 }
248 56851 dst += num_coeffs;
249 }
250 }
251 15888 return 0;
252 }
253
254 353232 static void recombine_block(int16_t *dst, const uint8_t *scan,
255 int16_t **base, int16_t **ext)
256 {
257 int i, j;
258
259
2/2
✓ Branch 0 taken 1412928 times.
✓ Branch 1 taken 353232 times.
1766160 for (i = 0; i < 4; i++) {
260
2/2
✓ Branch 0 taken 5651712 times.
✓ Branch 1 taken 1412928 times.
7064640 for (j = 0; j < 4; j++)
261 5651712 dst[scan[i * 8 + j]] = (*base)[j];
262
2/2
✓ Branch 0 taken 5651712 times.
✓ Branch 1 taken 1412928 times.
7064640 for (j = 0; j < 4; j++)
263 5651712 dst[scan[i * 8 + j + 4]] = (*ext)[j];
264 1412928 *base += 4;
265 1412928 *ext += 4;
266 }
267
2/2
✓ Branch 0 taken 1412928 times.
✓ Branch 1 taken 353232 times.
1766160 for (; i < 8; i++) {
268
2/2
✓ Branch 0 taken 11303424 times.
✓ Branch 1 taken 1412928 times.
12716352 for (j = 0; j < 8; j++)
269 11303424 dst[scan[i * 8 + j]] = (*ext)[j];
270 1412928 *ext += 8;
271 }
272 353232 }
273
274 367200 static void recombine_block_il(int16_t *dst, const uint8_t *scan,
275 int16_t **base, int16_t **ext,
276 int block_no)
277 {
278 int i, j;
279
280
2/2
✓ Branch 0 taken 183600 times.
✓ Branch 1 taken 183600 times.
367200 if (block_no < 2) {
281
2/2
✓ Branch 0 taken 1468800 times.
✓ Branch 1 taken 183600 times.
1652400 for (i = 0; i < 8; i++) {
282
2/2
✓ Branch 0 taken 5875200 times.
✓ Branch 1 taken 1468800 times.
7344000 for (j = 0; j < 4; j++)
283 5875200 dst[scan[i * 8 + j]] = (*base)[j];
284
2/2
✓ Branch 0 taken 5875200 times.
✓ Branch 1 taken 1468800 times.
7344000 for (j = 0; j < 4; j++)
285 5875200 dst[scan[i * 8 + j + 4]] = (*ext)[j];
286 1468800 *base += 4;
287 1468800 *ext += 4;
288 }
289 } else {
290
2/2
✓ Branch 0 taken 11750400 times.
✓ Branch 1 taken 183600 times.
11934000 for (i = 0; i < 64; i++)
291 11750400 dst[scan[i]] = (*ext)[i];
292 183600 *ext += 64;
293 }
294 367200 }
295
296 720432 static void unquant_block(int16_t *block, int q, uint8_t *quant_matrix)
297 {
298 int i;
299
300
2/2
✓ Branch 0 taken 46107648 times.
✓ Branch 1 taken 720432 times.
46828080 for (i = 0; i < 64; i++) {
301 46107648 int val = (uint16_t)block[i];
302 46107648 int sign = val & 1;
303
304 46107648 block[i] = (((val >> 1) ^ -sign) * q * quant_matrix[i] >> 4)
305 46107648 + sign;
306 }
307 720432 }
308
309 3972 static int aic_decode_slice(AICContext *ctx, int mb_x, int mb_y,
310 const uint8_t *src, int src_size)
311 {
312 GetBitContext gb;
313 int ret, i, mb, blk;
314 3972 int slice_width = FFMIN(ctx->slice_width, ctx->mb_width - mb_x);
315
4/4
✓ Branch 0 taken 3870 times.
✓ Branch 1 taken 102 times.
✓ Branch 2 taken 102 times.
✓ Branch 3 taken 3768 times.
3972 int last_row = mb_y && mb_y == ctx->mb_height - 1;
316 int y_pos, c_pos;
317 uint8_t *Y, *C[2];
318 uint8_t *dst;
319 3972 int16_t *base_y = ctx->data_ptr[COEFF_LUMA];
320 3972 int16_t *base_c = ctx->data_ptr[COEFF_CHROMA];
321 3972 int16_t *ext_y = ctx->data_ptr[COEFF_LUMA_EXT];
322 3972 int16_t *ext_c = ctx->data_ptr[COEFF_CHROMA_EXT];
323 3972 const int ystride = ctx->frame->linesize[0];
324
325
2/2
✓ Branch 0 taken 102 times.
✓ Branch 1 taken 3870 times.
3972 if (last_row) {
326 102 y_pos = (ctx->avctx->height - 16);
327 102 c_pos = ((ctx->avctx->height+1)/2 - 8);
328 } else {
329 3870 y_pos = mb_y * 16;
330 3870 c_pos = mb_y * 8;
331 }
332
333 3972 Y = ctx->frame->data[0] + mb_x * 16 + y_pos * ystride;
334
2/2
✓ Branch 0 taken 7944 times.
✓ Branch 1 taken 3972 times.
11916 for (i = 0; i < 2; i++)
335 7944 C[i] = ctx->frame->data[i + 1] + mb_x * 8
336 7944 + c_pos * ctx->frame->linesize[i + 1];
337 3972 init_get_bits(&gb, src, src_size * 8);
338
339 3972 memset(ctx->slice_data, 0,
340 sizeof(*ctx->slice_data) * slice_width * AIC_BAND_COEFFS);
341
2/2
✓ Branch 0 taken 15888 times.
✓ Branch 1 taken 3972 times.
19860 for (i = 0; i < NUM_BANDS; i++)
342
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 15888 times.
15888 if ((ret = aic_decode_coeffs(&gb, ctx->data_ptr[i],
343 i, slice_width,
344 15888 !ctx->interlaced)) < 0)
345 return ret;
346
347
2/2
✓ Branch 0 taken 120072 times.
✓ Branch 1 taken 3972 times.
124044 for (mb = 0; mb < slice_width; mb++) {
348
2/2
✓ Branch 0 taken 480288 times.
✓ Branch 1 taken 120072 times.
600360 for (blk = 0; blk < 4; blk++) {
349
2/2
✓ Branch 0 taken 113088 times.
✓ Branch 1 taken 367200 times.
480288 if (!ctx->interlaced)
350 113088 recombine_block(ctx->block, ctx->idsp.idct_permutation,
351 &base_y, &ext_y);
352 else
353 367200 recombine_block_il(ctx->block, ctx->idsp.idct_permutation,
354 &base_y, &ext_y, blk);
355 480288 unquant_block(ctx->block, ctx->quant, ctx->quant_matrix);
356 480288 ctx->idsp.idct(ctx->block);
357
358
2/2
✓ Branch 0 taken 113088 times.
✓ Branch 1 taken 367200 times.
480288 if (!ctx->interlaced) {
359 113088 dst = Y + (blk >> 1) * 8 * ystride + (blk & 1) * 8;
360 113088 ctx->idsp.put_signed_pixels_clamped(ctx->block, dst, ystride);
361 } else {
362 367200 dst = Y + (blk & 1) * 8 + (blk >> 1) * ystride;
363 367200 ctx->idsp.put_signed_pixels_clamped(ctx->block, dst,
364 367200 ystride * 2);
365 }
366 }
367 120072 Y += 16;
368
369
2/2
✓ Branch 0 taken 240144 times.
✓ Branch 1 taken 120072 times.
360216 for (blk = 0; blk < 2; blk++) {
370 240144 recombine_block(ctx->block, ctx->idsp.idct_permutation,
371 &base_c, &ext_c);
372 240144 unquant_block(ctx->block, ctx->quant, ctx->quant_matrix);
373 240144 ctx->idsp.idct(ctx->block);
374 240144 ctx->idsp.put_signed_pixels_clamped(ctx->block, C[blk],
375 240144 ctx->frame->linesize[blk + 1]);
376 240144 C[blk] += 8;
377 }
378 }
379
380 3972 return 0;
381 }
382
383 72 static int aic_decode_frame(AVCodecContext *avctx, AVFrame *frame,
384 int *got_frame, AVPacket *avpkt)
385 {
386 72 AICContext *ctx = avctx->priv_data;
387 72 const uint8_t *buf = avpkt->data;
388 72 int buf_size = avpkt->size;
389 GetByteContext gb;
390 uint32_t off;
391 int x, y, ret;
392 int slice_size;
393
394 72 ctx->frame = frame;
395 72 ctx->frame->pict_type = AV_PICTURE_TYPE_I;
396 72 ctx->frame->key_frame = 1;
397
398 72 off = FFALIGN(AIC_HDR_SIZE + ctx->num_x_slices * ctx->mb_height * 2, 4);
399
400
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 72 times.
72 if (buf_size < off) {
401 av_log(avctx, AV_LOG_ERROR, "Too small frame\n");
402 return AVERROR_INVALIDDATA;
403 }
404
405 72 ret = aic_decode_header(ctx, buf, buf_size);
406
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 72 times.
72 if (ret < 0) {
407 av_log(avctx, AV_LOG_ERROR, "Invalid header\n");
408 return ret;
409 }
410
411
1/2
✗ Branch 1 not taken.
✓ Branch 2 taken 72 times.
72 if ((ret = ff_thread_get_buffer(avctx, ctx->frame, 0)) < 0)
412 return ret;
413
414 72 bytestream2_init(&gb, buf + AIC_HDR_SIZE,
415 72 ctx->num_x_slices * ctx->mb_height * 2);
416
417
2/2
✓ Branch 0 taken 1932 times.
✓ Branch 1 taken 72 times.
2004 for (y = 0; y < ctx->mb_height; y++) {
418
2/2
✓ Branch 0 taken 3972 times.
✓ Branch 1 taken 1932 times.
5904 for (x = 0; x < ctx->mb_width; x += ctx->slice_width) {
419 3972 slice_size = bytestream2_get_le16(&gb) * 4;
420
2/4
✓ Branch 0 taken 3972 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 3972 times.
3972 if (slice_size + off > buf_size || !slice_size) {
421 av_log(avctx, AV_LOG_ERROR,
422 "Incorrect slice size %d at %d.%d\n", slice_size, x, y);
423 return AVERROR_INVALIDDATA;
424 }
425
426 3972 ret = aic_decode_slice(ctx, x, y, buf + off, slice_size);
427
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 3972 times.
3972 if (ret < 0) {
428 av_log(avctx, AV_LOG_ERROR,
429 "Error decoding slice at %d.%d\n", x, y);
430 return ret;
431 }
432
433 3972 off += slice_size;
434 }
435 }
436
437 72 *got_frame = 1;
438
439 72 return avpkt->size;
440 }
441
442 4 static av_cold int aic_decode_init(AVCodecContext *avctx)
443 {
444 4 AICContext *ctx = avctx->priv_data;
445 int i;
446
447 4 ctx->avctx = avctx;
448
449 4 avctx->pix_fmt = AV_PIX_FMT_YUV420P;
450
451 4 ff_idctdsp_init(&ctx->idsp, avctx);
452
453
2/2
✓ Branch 0 taken 256 times.
✓ Branch 1 taken 4 times.
260 for (i = 0; i < 64; i++)
454 256 ctx->quant_matrix[ctx->idsp.idct_permutation[i]] = aic_quant_matrix[i];
455
456 4 ctx->mb_width = FFALIGN(avctx->width, 16) >> 4;
457 4 ctx->mb_height = FFALIGN(avctx->height, 16) >> 4;
458
459 4 ctx->num_x_slices = (ctx->mb_width + 15) >> 4;
460 4 ctx->slice_width = 16;
461
1/2
✓ Branch 0 taken 8 times.
✗ Branch 1 not taken.
8 for (i = 1; i < ctx->mb_width; i++) {
462
3/4
✓ Branch 0 taken 8 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 4 times.
✓ Branch 3 taken 4 times.
8 if (!(ctx->mb_width % i) && (ctx->mb_width / i <= 32)) {
463 4 ctx->slice_width = ctx->mb_width / i;
464 4 ctx->num_x_slices = i;
465 4 break;
466 }
467 }
468
469 4 ctx->slice_data = av_malloc_array(ctx->slice_width, AIC_BAND_COEFFS
470 * sizeof(*ctx->slice_data));
471
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 4 times.
4 if (!ctx->slice_data) {
472 av_log(avctx, AV_LOG_ERROR, "Error allocating slice buffer\n");
473
474 return AVERROR(ENOMEM);
475 }
476
477
2/2
✓ Branch 0 taken 16 times.
✓ Branch 1 taken 4 times.
20 for (i = 0; i < NUM_BANDS; i++)
478 16 ctx->data_ptr[i] = ctx->slice_data + ctx->slice_width
479 16 * aic_band_off[i];
480
481 4 return 0;
482 }
483
484 4 static av_cold int aic_decode_close(AVCodecContext *avctx)
485 {
486 4 AICContext *ctx = avctx->priv_data;
487
488 4 av_freep(&ctx->slice_data);
489
490 4 return 0;
491 }
492
493 const FFCodec ff_aic_decoder = {
494 .p.name = "aic",
495 CODEC_LONG_NAME("Apple Intermediate Codec"),
496 .p.type = AVMEDIA_TYPE_VIDEO,
497 .p.id = AV_CODEC_ID_AIC,
498 .priv_data_size = sizeof(AICContext),
499 .init = aic_decode_init,
500 .close = aic_decode_close,
501 FF_CODEC_DECODE_CB(aic_decode_frame),
502 .p.capabilities = AV_CODEC_CAP_DR1 | AV_CODEC_CAP_FRAME_THREADS,
503 };
504