avcodec/proresenc_anatoliy: Use fdct from DSPContext instead of direct call.
[ffmpeg.git] / libavcodec / proresenc_anatoliy.c
1 /*
2  * Apple ProRes encoder
3  *
4  * Copyright (c) 2011 Anatoliy Wasserman
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 /**
24  * @file
25  * Apple ProRes encoder (Anatoliy Wasserman version)
26  * Known FOURCCs: 'apch' (HQ), 'apcn' (SD), 'apcs' (LT), 'acpo' (Proxy)
27  */
28
29 #include "avcodec.h"
30 #include "dct.h"
31 #include "internal.h"
32 #include "put_bits.h"
33 #include "bytestream.h"
34 #include "dsputil.h"
35
36 #define DEFAULT_SLICE_MB_WIDTH 8
37
38 #define FF_PROFILE_PRORES_PROXY     0
39 #define FF_PROFILE_PRORES_LT        1
40 #define FF_PROFILE_PRORES_STANDARD  2
41 #define FF_PROFILE_PRORES_HQ        3
42
43 static const AVProfile profiles[] = {
44     { FF_PROFILE_PRORES_PROXY,    "apco"},
45     { FF_PROFILE_PRORES_LT,       "apcs"},
46     { FF_PROFILE_PRORES_STANDARD, "apcn"},
47     { FF_PROFILE_PRORES_HQ,       "apch"},
48     { FF_PROFILE_UNKNOWN }
49 };
50
51 static const int qp_start_table[4] = { 4, 1, 1, 1 };
52 static const int qp_end_table[4]   = { 8, 9, 6, 6 };
53 static const int bitrate_table[5]  = { 1000, 2100, 3500, 5400 };
54
55 static const uint8_t progressive_scan[64] = {
56      0,  1,  8,  9,  2,  3, 10, 11,
57     16, 17, 24, 25, 18, 19, 26, 27,
58      4,  5, 12, 20, 13,  6,  7, 14,
59     21, 28, 29, 22, 15, 23, 30, 31,
60     32, 33, 40, 48, 41, 34, 35, 42,
61     49, 56, 57, 50, 43, 36, 37, 44,
62     51, 58, 59, 52, 45, 38, 39, 46,
63     53, 60, 61, 54, 47, 55, 62, 63
64 };
65
66 static const uint8_t QMAT_LUMA[4][64] = {
67     {
68          4,  7,  9, 11, 13, 14, 15, 63,
69          7,  7, 11, 12, 14, 15, 63, 63,
70          9, 11, 13, 14, 15, 63, 63, 63,
71         11, 11, 13, 14, 63, 63, 63, 63,
72         11, 13, 14, 63, 63, 63, 63, 63,
73         13, 14, 63, 63, 63, 63, 63, 63,
74         13, 63, 63, 63, 63, 63, 63, 63,
75         63, 63, 63, 63, 63, 63, 63, 63
76     }, {
77          4,  5,  6,  7,  9, 11, 13, 15,
78          5,  5,  7,  8, 11, 13, 15, 17,
79          6,  7,  9, 11, 13, 15, 15, 17,
80          7,  7,  9, 11, 13, 15, 17, 19,
81          7,  9, 11, 13, 14, 16, 19, 23,
82          9, 11, 13, 14, 16, 19, 23, 29,
83          9, 11, 13, 15, 17, 21, 28, 35,
84         11, 13, 16, 17, 21, 28, 35, 41
85     }, {
86          4,  4,  5,  5,  6,  7,  7,  9,
87          4,  4,  5,  6,  7,  7,  9,  9,
88          5,  5,  6,  7,  7,  9,  9, 10,
89          5,  5,  6,  7,  7,  9,  9, 10,
90          5,  6,  7,  7,  8,  9, 10, 12,
91          6,  7,  7,  8,  9, 10, 12, 15,
92          6,  7,  7,  9, 10, 11, 14, 17,
93          7,  7,  9, 10, 11, 14, 17, 21
94     }, {
95          4,  4,  4,  4,  4,  4,  4,  4,
96          4,  4,  4,  4,  4,  4,  4,  4,
97          4,  4,  4,  4,  4,  4,  4,  4,
98          4,  4,  4,  4,  4,  4,  4,  5,
99          4,  4,  4,  4,  4,  4,  5,  5,
100          4,  4,  4,  4,  4,  5,  5,  6,
101          4,  4,  4,  4,  5,  5,  6,  7,
102          4,  4,  4,  4,  5,  6,  7,  7
103     }
104 };
105
106 static const uint8_t QMAT_CHROMA[4][64] = {
107     {
108          4,  7,  9, 11, 13, 14, 63, 63,
109          7,  7, 11, 12, 14, 63, 63, 63,
110          9, 11, 13, 14, 63, 63, 63, 63,
111         11, 11, 13, 14, 63, 63, 63, 63,
112         11, 13, 14, 63, 63, 63, 63, 63,
113         13, 14, 63, 63, 63, 63, 63, 63,
114         13, 63, 63, 63, 63, 63, 63, 63,
115         63, 63, 63, 63, 63, 63, 63, 63
116     }, {
117          4,  5,  6,  7,  9, 11, 13, 15,
118          5,  5,  7,  8, 11, 13, 15, 17,
119          6,  7,  9, 11, 13, 15, 15, 17,
120          7,  7,  9, 11, 13, 15, 17, 19,
121          7,  9, 11, 13, 14, 16, 19, 23,
122          9, 11, 13, 14, 16, 19, 23, 29,
123          9, 11, 13, 15, 17, 21, 28, 35,
124         11, 13, 16, 17, 21, 28, 35, 41
125     }, {
126          4,  4,  5,  5,  6,  7,  7,  9,
127          4,  4,  5,  6,  7,  7,  9,  9,
128          5,  5,  6,  7,  7,  9,  9, 10,
129          5,  5,  6,  7,  7,  9,  9, 10,
130          5,  6,  7,  7,  8,  9, 10, 12,
131          6,  7,  7,  8,  9, 10, 12, 15,
132          6,  7,  7,  9, 10, 11, 14, 17,
133          7,  7,  9, 10, 11, 14, 17, 21
134     }, {
135          4,  4,  4,  4,  4,  4,  4,  4,
136          4,  4,  4,  4,  4,  4,  4,  4,
137          4,  4,  4,  4,  4,  4,  4,  4,
138          4,  4,  4,  4,  4,  4,  4,  5,
139          4,  4,  4,  4,  4,  4,  5,  5,
140          4,  4,  4,  4,  4,  5,  5,  6,
141          4,  4,  4,  4,  5,  5,  6,  7,
142          4,  4,  4,  4,  5,  6,  7,  7
143     }
144 };
145
146
147 typedef struct {
148     DSPContext dsp;
149     uint8_t* fill_y;
150     uint8_t* fill_u;
151     uint8_t* fill_v;
152
153     int qmat_luma[16][64];
154     int qmat_chroma[16][64];
155 } ProresContext;
156
157 static void encode_codeword(PutBitContext *pb, int val, int codebook)
158 {
159     unsigned int rice_order, exp_order, switch_bits, first_exp, exp, zeros,
160             mask;
161
162     /* number of bits to switch between rice and exp golomb */
163     switch_bits = codebook & 3;
164     rice_order  = codebook >> 5;
165     exp_order   = (codebook >> 2) & 7;
166
167     first_exp = ((switch_bits + 1) << rice_order);
168
169     if (val >= first_exp) { /* exp golomb */
170         val -= first_exp;
171         val += (1 << exp_order);
172         exp = av_log2(val);
173         zeros = exp - exp_order + switch_bits + 1;
174         put_bits(pb, zeros, 0);
175         put_bits(pb, exp + 1, val);
176     } else if (rice_order) {
177         mask = (1 << rice_order) - 1;
178         put_bits(pb, (val >> rice_order), 0);
179         put_bits(pb, 1, 1);
180         put_bits(pb, rice_order, val & mask);
181     } else {
182         put_bits(pb, val, 0);
183         put_bits(pb, 1, 1);
184     }
185 }
186
187 #define QSCALE(qmat,ind,val) ((val) / ((qmat)[ind]))
188 #define TO_GOLOMB(val) (((val) << 1) ^ ((val) >> 31))
189 #define DIFF_SIGN(val, sign) (((val) >> 31) ^ (sign))
190 #define IS_NEGATIVE(val) ((((val) >> 31) ^ -1) + 1)
191 #define TO_GOLOMB2(val,sign) ((val)==0 ? 0 : ((val) << 1) + (sign))
192
193 static av_always_inline int get_level(int val)
194 {
195     int sign = (val >> 31);
196     return (val ^ sign) - sign;
197 }
198
199 #define FIRST_DC_CB 0xB8
200
201 static const uint8_t dc_codebook[7] = { 0x04, 0x28, 0x28, 0x4D, 0x4D, 0x70, 0x70};
202
203 static void encode_dc_coeffs(PutBitContext *pb, int16_t *in,
204         int blocks_per_slice, int *qmat)
205 {
206     int prev_dc, code;
207     int i, sign, idx;
208     int new_dc, delta, diff_sign, new_code;
209
210     prev_dc = QSCALE(qmat, 0, in[0] - 16384);
211     code = TO_GOLOMB(prev_dc);
212     encode_codeword(pb, code, FIRST_DC_CB);
213
214     code = 5; sign = 0; idx = 64;
215     for (i = 1; i < blocks_per_slice; i++, idx += 64) {
216         new_dc    = QSCALE(qmat, 0, in[idx] - 16384);
217         delta     = new_dc - prev_dc;
218         diff_sign = DIFF_SIGN(delta, sign);
219         new_code  = TO_GOLOMB2(get_level(delta), diff_sign);
220
221         encode_codeword(pb, new_code, dc_codebook[FFMIN(code, 6)]);
222
223         code      = new_code;
224         sign      = delta >> 31;
225         prev_dc   = new_dc;
226     }
227 }
228
229 static const uint8_t run_to_cb[16] = { 0x06, 0x06, 0x05, 0x05, 0x04, 0x29,
230         0x29, 0x29, 0x29, 0x28, 0x28, 0x28, 0x28, 0x28, 0x28, 0x4C };
231 static const uint8_t lev_to_cb[10] = { 0x04, 0x0A, 0x05, 0x06, 0x04, 0x28,
232         0x28, 0x28, 0x28, 0x4C };
233
234 static void encode_ac_coeffs(AVCodecContext *avctx, PutBitContext *pb,
235         int16_t *in, int blocks_per_slice, int *qmat)
236 {
237     int prev_run = 4;
238     int prev_level = 2;
239
240     int run = 0, level, code, i, j;
241     for (i = 1; i < 64; i++) {
242         int indp = progressive_scan[i];
243         for (j = 0; j < blocks_per_slice; j++) {
244             int val = QSCALE(qmat, indp, in[(j << 6) + indp]);
245             if (val) {
246                 encode_codeword(pb, run, run_to_cb[FFMIN(prev_run, 15)]);
247
248                 prev_run   = run;
249                 run        = 0;
250                 level      = get_level(val);
251                 code       = level - 1;
252
253                 encode_codeword(pb, code, lev_to_cb[FFMIN(prev_level, 9)]);
254
255                 prev_level = level;
256
257                 put_bits(pb, 1, IS_NEGATIVE(val));
258             } else {
259                 ++run;
260             }
261         }
262     }
263 }
264
265 static void get(uint8_t *pixels, int stride, int16_t* block)
266 {
267     int16_t *p = (int16_t*)pixels;
268     int i, j;
269
270     stride >>= 1;
271     for (i = 0; i < 8; i++) {
272         for (j = 0; j < 8; j++) {
273             block[j] = p[j];
274         }
275         p += stride;
276         block += 8;
277     }
278 }
279
280 static void fdct_get(DSPContext *dsp, uint8_t *pixels, int stride, int16_t* block)
281 {
282     get(pixels, stride, block);
283     dsp->fdct(block);
284 }
285
286 static int encode_slice_plane(AVCodecContext *avctx, int mb_count,
287         uint8_t *src, int src_stride, uint8_t *buf, unsigned buf_size,
288         int *qmat, int chroma)
289 {
290     ProresContext* ctx = avctx->priv_data;
291     DSPContext *dsp = &ctx->dsp;
292     DECLARE_ALIGNED(16, int16_t, blocks)[DEFAULT_SLICE_MB_WIDTH << 8], *block;
293     int i, blocks_per_slice;
294     PutBitContext pb;
295
296     block = blocks;
297     for (i = 0; i < mb_count; i++) {
298         fdct_get(dsp, src,                  src_stride, block + (0 << 6));
299         fdct_get(dsp, src + 8 * src_stride, src_stride, block + ((2 - chroma) << 6));
300         if (!chroma) {
301             fdct_get(dsp, src + 16,                  src_stride, block + (1 << 6));
302             fdct_get(dsp, src + 16 + 8 * src_stride, src_stride, block + (3 << 6));
303         }
304
305         block += (256 >> chroma);
306         src   += (32  >> chroma);
307     }
308
309     blocks_per_slice = mb_count << (2 - chroma);
310     init_put_bits(&pb, buf, buf_size << 3);
311
312     encode_dc_coeffs(&pb, blocks, blocks_per_slice, qmat);
313     encode_ac_coeffs(avctx, &pb, blocks, blocks_per_slice, qmat);
314
315     flush_put_bits(&pb);
316     return put_bits_ptr(&pb) - pb.buf;
317 }
318
319 static av_always_inline unsigned encode_slice_data(AVCodecContext *avctx,
320         uint8_t *dest_y, uint8_t *dest_u, uint8_t *dest_v, int luma_stride,
321         int chroma_stride, unsigned mb_count, uint8_t *buf, unsigned data_size,
322         unsigned* y_data_size, unsigned* u_data_size, unsigned* v_data_size,
323         int qp)
324 {
325     ProresContext* ctx = avctx->priv_data;
326
327     *y_data_size = encode_slice_plane(avctx, mb_count, dest_y, luma_stride,
328             buf, data_size, ctx->qmat_luma[qp - 1], 0);
329
330     if (!(avctx->flags & CODEC_FLAG_GRAY)) {
331         *u_data_size = encode_slice_plane(avctx, mb_count, dest_u,
332                 chroma_stride, buf + *y_data_size, data_size - *y_data_size,
333                 ctx->qmat_chroma[qp - 1], 1);
334
335         *v_data_size = encode_slice_plane(avctx, mb_count, dest_v,
336                 chroma_stride, buf + *y_data_size + *u_data_size,
337                 data_size - *y_data_size - *u_data_size,
338                 ctx->qmat_chroma[qp - 1], 1);
339     }
340
341     return *y_data_size + *u_data_size + *v_data_size;
342 }
343
344 static void subimage_with_fill(uint16_t *src, unsigned x, unsigned y,
345         unsigned stride, unsigned width, unsigned height, uint16_t *dst,
346         unsigned dst_width, unsigned dst_height)
347 {
348
349     int box_width = FFMIN(width - x, dst_width);
350     int box_height = FFMIN(height - y, dst_height);
351     int i, j, src_stride = stride >> 1;
352     uint16_t last_pix, *last_line;
353
354     src += y * src_stride + x;
355     for (i = 0; i < box_height; ++i) {
356         for (j = 0; j < box_width; ++j) {
357             dst[j] = src[j];
358         }
359         last_pix = dst[j - 1];
360         for (; j < dst_width; j++)
361             dst[j] = last_pix;
362         src += src_stride;
363         dst += dst_width;
364     }
365     last_line = dst - dst_width;
366     for (; i < dst_height; i++) {
367         for (j = 0; j < dst_width; ++j) {
368             dst[j] = last_line[j];
369         }
370         dst += dst_width;
371     }
372 }
373
374 static int encode_slice(AVCodecContext *avctx, const AVFrame *pic, int mb_x,
375         int mb_y, unsigned mb_count, uint8_t *buf, unsigned data_size,
376         int unsafe, int *qp)
377 {
378     int luma_stride, chroma_stride;
379     int hdr_size = 6, slice_size;
380     uint8_t *dest_y, *dest_u, *dest_v;
381     unsigned y_data_size = 0, u_data_size = 0, v_data_size = 0;
382     ProresContext* ctx = avctx->priv_data;
383     int tgt_bits   = (mb_count * bitrate_table[avctx->profile]) >> 2;
384     int low_bytes  = (tgt_bits - (tgt_bits >> 3)) >> 3; // 12% bitrate fluctuation
385     int high_bytes = (tgt_bits + (tgt_bits >> 3)) >> 3;
386
387     luma_stride   = pic->linesize[0];
388     chroma_stride = pic->linesize[1];
389
390     dest_y = pic->data[0] + (mb_y << 4) * luma_stride   + (mb_x << 5);
391     dest_u = pic->data[1] + (mb_y << 4) * chroma_stride + (mb_x << 4);
392     dest_v = pic->data[2] + (mb_y << 4) * chroma_stride + (mb_x << 4);
393
394     if (unsafe) {
395
396         subimage_with_fill((uint16_t *) pic->data[0], mb_x << 4, mb_y << 4,
397                 luma_stride, avctx->width, avctx->height,
398                 (uint16_t *) ctx->fill_y, mb_count << 4, 16);
399         subimage_with_fill((uint16_t *) pic->data[1], mb_x << 3, mb_y << 4,
400                 chroma_stride, avctx->width >> 1, avctx->height,
401                 (uint16_t *) ctx->fill_u, mb_count << 3, 16);
402         subimage_with_fill((uint16_t *) pic->data[2], mb_x << 3, mb_y << 4,
403                 chroma_stride, avctx->width >> 1, avctx->height,
404                 (uint16_t *) ctx->fill_v, mb_count << 3, 16);
405
406         encode_slice_data(avctx, ctx->fill_y, ctx->fill_u, ctx->fill_v,
407                 mb_count << 5, mb_count << 4, mb_count, buf + hdr_size,
408                 data_size - hdr_size, &y_data_size, &u_data_size, &v_data_size,
409                 *qp);
410     } else {
411         slice_size = encode_slice_data(avctx, dest_y, dest_u, dest_v,
412                 luma_stride, chroma_stride, mb_count, buf + hdr_size,
413                 data_size - hdr_size, &y_data_size, &u_data_size, &v_data_size,
414                 *qp);
415
416         if (slice_size > high_bytes && *qp < qp_end_table[avctx->profile]) {
417             do {
418                 *qp += 1;
419                 slice_size = encode_slice_data(avctx, dest_y, dest_u, dest_v,
420                         luma_stride, chroma_stride, mb_count, buf + hdr_size,
421                         data_size - hdr_size, &y_data_size, &u_data_size,
422                         &v_data_size, *qp);
423             } while (slice_size > high_bytes && *qp < qp_end_table[avctx->profile]);
424         } else if (slice_size < low_bytes && *qp
425                 > qp_start_table[avctx->profile]) {
426             do {
427                 *qp -= 1;
428                 slice_size = encode_slice_data(avctx, dest_y, dest_u, dest_v,
429                         luma_stride, chroma_stride, mb_count, buf + hdr_size,
430                         data_size - hdr_size, &y_data_size, &u_data_size,
431                         &v_data_size, *qp);
432             } while (slice_size < low_bytes && *qp > qp_start_table[avctx->profile]);
433         }
434     }
435
436     buf[0] = hdr_size << 3;
437     buf[1] = *qp;
438     AV_WB16(buf + 2, y_data_size);
439     AV_WB16(buf + 4, u_data_size);
440
441     return hdr_size + y_data_size + u_data_size + v_data_size;
442 }
443
444 static int prores_encode_picture(AVCodecContext *avctx, const AVFrame *pic,
445         uint8_t *buf, const int buf_size)
446 {
447     int mb_width = (avctx->width + 15) >> 4;
448     int mb_height = (avctx->height + 15) >> 4;
449     int hdr_size, sl_size, i;
450     int mb_y, sl_data_size, qp;
451     int unsafe_bot, unsafe_right;
452     uint8_t *sl_data, *sl_data_sizes;
453     int slice_per_line = 0, rem = mb_width;
454
455     for (i = av_log2(DEFAULT_SLICE_MB_WIDTH); i >= 0; --i) {
456         slice_per_line += rem >> i;
457         rem &= (1 << i) - 1;
458     }
459
460     qp = qp_start_table[avctx->profile];
461     hdr_size = 8; sl_data_size = buf_size - hdr_size;
462     sl_data_sizes = buf + hdr_size;
463     sl_data = sl_data_sizes + (slice_per_line * mb_height * 2);
464     for (mb_y = 0; mb_y < mb_height; mb_y++) {
465         int mb_x = 0;
466         int slice_mb_count = DEFAULT_SLICE_MB_WIDTH;
467         while (mb_x < mb_width) {
468             while (mb_width - mb_x < slice_mb_count)
469                 slice_mb_count >>= 1;
470
471             unsafe_bot = (avctx->height & 0xf) && (mb_y == mb_height - 1);
472             unsafe_right = (avctx->width & 0xf) && (mb_x + slice_mb_count == mb_width);
473
474             sl_size = encode_slice(avctx, pic, mb_x, mb_y, slice_mb_count,
475                     sl_data, sl_data_size, unsafe_bot || unsafe_right, &qp);
476
477             bytestream_put_be16(&sl_data_sizes, sl_size);
478             sl_data           += sl_size;
479             sl_data_size      -= sl_size;
480             mb_x              += slice_mb_count;
481         }
482     }
483
484     buf[0] = hdr_size << 3;
485     AV_WB32(buf + 1, sl_data - buf);
486     AV_WB16(buf + 5, slice_per_line * mb_height);
487     buf[7] = av_log2(DEFAULT_SLICE_MB_WIDTH) << 4;
488
489     return sl_data - buf;
490 }
491
492 static int prores_encode_frame(AVCodecContext *avctx, AVPacket *pkt,
493                                const AVFrame *pict, int *got_packet)
494 {
495     int header_size = 148;
496     uint8_t *buf;
497     int pic_size, ret;
498     int frame_size = FFALIGN(avctx->width, 16) * FFALIGN(avctx->height, 16)*16 + 500 + FF_MIN_BUFFER_SIZE; //FIXME choose tighter limit
499
500
501     if ((ret = ff_alloc_packet2(avctx, pkt, frame_size + FF_MIN_BUFFER_SIZE)) < 0)
502         return ret;
503
504     buf = pkt->data;
505     pic_size = prores_encode_picture(avctx, pict, buf + header_size + 8,
506             pkt->size - header_size - 8);
507
508     bytestream_put_be32(&buf, pic_size + 8 + header_size);
509     bytestream_put_buffer(&buf, "icpf", 4);
510
511     bytestream_put_be16(&buf, header_size);
512     bytestream_put_be16(&buf, 0);
513     bytestream_put_buffer(&buf, "fmpg", 4);
514     bytestream_put_be16(&buf, avctx->width);
515     bytestream_put_be16(&buf, avctx->height);
516     *buf++ = 0x83; // {10}(422){00}{00}(frame){11}
517     *buf++ = 0;
518     *buf++ = 2;
519     *buf++ = 2;
520     *buf++ = 6;
521     *buf++ = 32;
522     *buf++ = 0;
523     *buf++ = 3;
524
525     bytestream_put_buffer(&buf, QMAT_LUMA[avctx->profile],   64);
526     bytestream_put_buffer(&buf, QMAT_CHROMA[avctx->profile], 64);
527
528     pkt->flags |= AV_PKT_FLAG_KEY;
529     pkt->size = pic_size + 8 + header_size;
530     *got_packet = 1;
531
532     return 0;
533 }
534
535 static void scale_mat(const uint8_t* src, int* dst, int scale)
536 {
537     int i;
538     for (i = 0; i < 64; i++)
539         dst[i] = src[i] * scale;
540 }
541
542 static av_cold int prores_encode_init(AVCodecContext *avctx)
543 {
544     int i;
545     ProresContext* ctx = avctx->priv_data;
546
547     if (avctx->pix_fmt != AV_PIX_FMT_YUV422P10) {
548         av_log(avctx, AV_LOG_ERROR, "need YUV422P10\n");
549         return -1;
550     }
551     avctx->bits_per_raw_sample = 10;
552
553     if (avctx->width & 0x1) {
554         av_log(avctx, AV_LOG_ERROR,
555                 "frame width needs to be multiple of 2\n");
556         return -1;
557     }
558
559     if ((avctx->height & 0xf) || (avctx->width & 0xf)) {
560         ctx->fill_y = av_malloc(4 * (DEFAULT_SLICE_MB_WIDTH << 8));
561         if (!ctx->fill_y)
562             return AVERROR(ENOMEM);
563         ctx->fill_u = ctx->fill_y + (DEFAULT_SLICE_MB_WIDTH << 9);
564         ctx->fill_v = ctx->fill_u + (DEFAULT_SLICE_MB_WIDTH << 8);
565     }
566
567     if (avctx->profile == FF_PROFILE_UNKNOWN) {
568         avctx->profile = FF_PROFILE_PRORES_STANDARD;
569         av_log(avctx, AV_LOG_INFO,
570                 "encoding with ProRes standard (apcn) profile\n");
571
572     } else if (avctx->profile < FF_PROFILE_PRORES_PROXY
573             || avctx->profile > FF_PROFILE_PRORES_HQ) {
574         av_log(
575                 avctx,
576                 AV_LOG_ERROR,
577                 "unknown profile %d, use [0 - apco, 1 - apcs, 2 - apcn (default), 3 - apch]\n",
578                 avctx->profile);
579         return -1;
580     }
581
582     ff_dsputil_init(&ctx->dsp, avctx);
583
584     avctx->codec_tag = AV_RL32((const uint8_t*)profiles[avctx->profile].name);
585
586     for (i = 1; i <= 16; i++) {
587         scale_mat(QMAT_LUMA[avctx->profile]  , ctx->qmat_luma[i - 1]  , i);
588         scale_mat(QMAT_CHROMA[avctx->profile], ctx->qmat_chroma[i - 1], i);
589     }
590
591     avctx->coded_frame = av_frame_alloc();
592     avctx->coded_frame->key_frame = 1;
593     avctx->coded_frame->pict_type = AV_PICTURE_TYPE_I;
594
595     return 0;
596 }
597
598 static av_cold int prores_encode_close(AVCodecContext *avctx)
599 {
600     ProresContext* ctx = avctx->priv_data;
601     av_freep(&avctx->coded_frame);
602     av_freep(&ctx->fill_y);
603
604     return 0;
605 }
606
607 AVCodec ff_prores_aw_encoder = {
608     .name           = "prores_aw",
609     .long_name      = NULL_IF_CONFIG_SMALL("Apple ProRes"),
610     .type           = AVMEDIA_TYPE_VIDEO,
611     .id             = AV_CODEC_ID_PRORES,
612     .priv_data_size = sizeof(ProresContext),
613     .init           = prores_encode_init,
614     .close          = prores_encode_close,
615     .encode2        = prores_encode_frame,
616     .pix_fmts       = (const enum AVPixelFormat[]){AV_PIX_FMT_YUV422P10, AV_PIX_FMT_NONE},
617     .capabilities   = CODEC_CAP_FRAME_THREADS | CODEC_CAP_INTRA_ONLY,
618     .profiles       = profiles
619 };
620
621 AVCodec ff_prores_encoder = {
622     .name           = "prores",
623     .long_name      = NULL_IF_CONFIG_SMALL("Apple ProRes"),
624     .type           = AVMEDIA_TYPE_VIDEO,
625     .id             = AV_CODEC_ID_PRORES,
626     .priv_data_size = sizeof(ProresContext),
627     .init           = prores_encode_init,
628     .close          = prores_encode_close,
629     .encode2        = prores_encode_frame,
630     .pix_fmts       = (const enum AVPixelFormat[]){AV_PIX_FMT_YUV422P10, AV_PIX_FMT_NONE},
631     .capabilities   = CODEC_CAP_FRAME_THREADS | CODEC_CAP_INTRA_ONLY,
632     .profiles       = profiles
633 };