1 /*
2 * Scalable Video Technology for AV1 encoder library plugin
3 *
4 * Copyright (c) 2018 Intel Corporation
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 this program; if not, write to the Free Software
20 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
21 */
22
23 #include <stdint.h>
24 #include <EbSvtAv1ErrorCodes.h>
25 #include <EbSvtAv1Enc.h>
26
33
39
44 }EOS_STATUS;
45
48
51
55
57
59
61
62 // User options.
69
71
75
76 static const struct {
81 { EB_ErrorNone, 0, "success" },
82 { EB_ErrorInsufficientResources,
AVERROR(ENOMEM),
"insufficient resources" },
83 { EB_ErrorUndefined,
AVERROR(EINVAL),
"undefined error" },
84 { EB_ErrorInvalidComponent,
AVERROR(EINVAL),
"invalid component" },
85 { EB_ErrorBadParameter,
AVERROR(EINVAL),
"bad parameter" },
86 { EB_ErrorDestroyThreadFailed,
AVERROR_EXTERNAL,
"failed to destroy thread" },
87 { EB_ErrorSemaphoreUnresponsive,
AVERROR_EXTERNAL,
"semaphore unresponsive" },
88 { EB_ErrorDestroySemaphoreFailed,
AVERROR_EXTERNAL,
"failed to destroy semaphore"},
92 { EB_NoErrorEmptyQueue,
AVERROR(EAGAIN),
"empty queue" },
93 };
94
96 {
98
104 }
105 }
106 *
desc =
"unknown error";
108 }
109
111 const char *error_string)
112 {
115
117
119 }
120
122 {
123 const int pack_mode_10bit =
124 (
config->encoder_bit_depth > 8) && (
config->compressed_ten_bit_format == 0) ? 1 : 0;
125 const size_t luma_size_8bit =
126 config->source_width *
config->source_height * (1 << pack_mode_10bit);
127 const size_t luma_size_10bit =
128 (
config->encoder_bit_depth > 8 && pack_mode_10bit == 0) ? luma_size_8bit : 0;
129
130 EbSvtIOFormat *in_data;
131
132 svt_enc->
raw_size = (luma_size_8bit + luma_size_10bit) * 3 / 2;
133
134 // allocate buffer for in and out
138
140 if (!svt_enc->
in_buf->p_buffer)
142
144
145 return 0;
146
147 }
148
151 {
154
155 param->source_width = avctx->
width;
156 param->source_height = avctx->
height;
157
159 param->encoder_bit_depth =
desc->comp[0].depth;
160
161 if (
desc->log2_chroma_w == 1 &&
desc->log2_chroma_h == 1)
162 param->encoder_color_format = EB_YUV420;
163 else if (
desc->log2_chroma_w == 1 &&
desc->log2_chroma_h == 0)
164 param->encoder_color_format = EB_YUV422;
165 else if (!
desc->log2_chroma_w && !
desc->log2_chroma_h)
166 param->encoder_color_format = EB_YUV444;
167 else {
170 }
171
173 param->profile = avctx->
profile;
174
176 param->level = avctx->
level;
177
178 if ((param->encoder_color_format == EB_YUV422 || param->encoder_bit_depth > 10)
182 }
else if (param->encoder_color_format == EB_YUV444 && param->profile !=
FF_PROFILE_AV1_HIGH) {
185 }
186
187 // Update param from options
189 param->enc_mode = svt_enc->
enc_mode;
190 param->tier = svt_enc->
tier;
191 param->rate_control_mode = svt_enc->
rc_mode;
192 param->scene_change_detection = svt_enc->
scd;
193 param->qp = svt_enc->
qp;
194
195 param->target_bit_rate = avctx->
bit_rate;
196
198 param->intra_period_length = avctx->
gop_size - 1;
199
203 } else {
206 }
207
208 param->enable_tpl_la = !!param->rate_control_mode;
209 if (param->rate_control_mode) {
210 param->max_qp_allowed = avctx->
qmax;
211 param->min_qp_allowed = avctx->
qmin;
212 }
213
214 /* 2 = IDR, closed GOP, 1 = CRA, open GOP */
216
218 param->look_ahead_distance = svt_enc->
la_depth;
219
222
223 return 0;
224 }
225
227 EbBufferHeaderType *header_ptr)
228 {
229 EbSvtIOFormat *in_data = (EbSvtIOFormat *)header_ptr->p_buffer;
230 ptrdiff_t linesizes[4];
232 int bytes_shift = param->encoder_bit_depth > 8 ? 1 : 0;
234
235 for (
int i = 0;
i < 4;
i++)
236 linesizes[
i] =
frame->linesize[
i];
237
239 linesizes);
242
244 for (
int i = 0;
i < 4;
i++) {
248 }
249
250 in_data->luma =
frame->data[0];
251 in_data->cb =
frame->data[1];
252 in_data->cr =
frame->data[2];
253
257
259
260 return 0;
261 }
262
264 {
266 EbErrorType svt_ret;
268
270
272 if (svt_ret != EB_ErrorNone) {
273 return svt_print_error(avctx, svt_ret,
"Error initializing encoder handle");
274 }
275
280 }
281
283 if (svt_ret != EB_ErrorNone) {
284 return svt_print_error(avctx, svt_ret,
"Error setting encoder parameters");
285 }
286
287 svt_ret = svt_av1_enc_init(svt_enc->
svt_handle);
288 if (svt_ret != EB_ErrorNone) {
290 }
291
293 EbBufferHeaderType *headerPtr =
NULL;
294
295 svt_ret = svt_av1_enc_stream_header(svt_enc->
svt_handle, &headerPtr);
296 if (svt_ret != EB_ErrorNone) {
297 return svt_print_error(avctx, svt_ret,
"Error building stream header");
298 }
299
304 "Cannot allocate AV1 header of size %d.\n", avctx->
extradata_size);
306 }
307
309
310 svt_ret = svt_av1_enc_stream_header_release(headerPtr);
311 if (svt_ret != EB_ErrorNone) {
313 }
314 }
315
319
321 }
322
324 {
326 EbBufferHeaderType *headerPtr = svt_enc->
in_buf;
328
330 EbBufferHeaderType headerPtrLast;
331
333 return 0;
334
335 headerPtrLast.n_alloc_len = 0;
336 headerPtrLast.n_filled_len = 0;
337 headerPtrLast.n_tick_count = 0;
338 headerPtrLast.p_app_private =
NULL;
339 headerPtrLast.p_buffer =
NULL;
340 headerPtrLast.flags = EB_BUFFERFLAG_EOS;
341
342 svt_av1_enc_send_picture(svt_enc->
svt_handle, &headerPtrLast);
344 return 0;
345 }
346
350
351 headerPtr->flags = 0;
352 headerPtr->p_app_private =
NULL;
353 headerPtr->pts =
frame->pts;
354
355 svt_av1_enc_send_picture(svt_enc->
svt_handle, headerPtr);
356
357 return 0;
358 }
359
361 {
363 const int max_frames = 8;
364 int max_tu_size;
365
366 if (filled_len > svt_enc->
raw_size * max_frames) {
369 }
370
376
378 }
380
382 }
383
385 {
387 EbBufferHeaderType *headerPtr;
389 EbErrorType svt_ret;
391 int ret = 0, pict_type;
392
395
401
406
408 if (svt_ret == EB_NoErrorEmptyQueue)
410
414 svt_av1_enc_release_out_buffer(&headerPtr);
416 }
419
420 memcpy(
pkt->
data, headerPtr->p_buffer, headerPtr->n_filled_len);
422
423 pkt->
size = headerPtr->n_filled_len;
424 pkt->
pts = headerPtr->pts;
425 pkt->
dts = headerPtr->dts;
426
427 switch (headerPtr->pic_type) {
428 case EB_AV1_KEY_PICTURE:
430 // fall-through
431 case EB_AV1_INTRA_ONLY_PICTURE:
433 break;
434 case EB_AV1_INVALID_PICTURE:
436 break;
437 default:
439 break;
440 }
441
442 if (headerPtr->pic_type == EB_AV1_NON_REF_PICTURE)
444
445 if (headerPtr->flags & EB_BUFFERFLAG_EOS)
447
449
450 svt_av1_enc_release_out_buffer(&headerPtr);
451
452 return 0;
453 }
454
456 {
458
461 svt_av1_enc_deinit_handle(svt_enc->
svt_handle);
462 }
466 }
467
470
471 return 0;
472 }
473
474 #define OFFSET(x) offsetof(SvtContext, x)
475 #define VE AV_OPT_FLAG_VIDEO_PARAM | AV_OPT_FLAG_ENCODING_PARAM
477 {
"hielevel",
"Hierarchical prediction levels setting",
OFFSET(hierarchical_level),
481
482 {
"la_depth",
"Look ahead distance [0, 120]",
OFFSET(la_depth),
484
485 { "preset", "Encoding preset [0, 8]",
487
488 {
"tier",
"Set operating point tier",
OFFSET(tier),
492
494
495 #define LEVEL(name, value) name, NULL, 0, AV_OPT_TYPE_CONST, \
496 { .i64 = value }, 0, 0, VE, "avctx.level"
497 {
LEVEL(
"2.0", 20) },
498 {
LEVEL(
"2.1", 21) },
499 {
LEVEL(
"2.2", 22) },
500 {
LEVEL(
"2.3", 23) },
501 {
LEVEL(
"3.0", 30) },
502 {
LEVEL(
"3.1", 31) },
503 {
LEVEL(
"3.2", 32) },
504 {
LEVEL(
"3.3", 33) },
505 {
LEVEL(
"4.0", 40) },
506 {
LEVEL(
"4.1", 41) },
507 {
LEVEL(
"4.2", 42) },
508 {
LEVEL(
"4.3", 43) },
509 {
LEVEL(
"5.0", 50) },
510 {
LEVEL(
"5.1", 51) },
511 {
LEVEL(
"5.2", 52) },
512 {
LEVEL(
"5.3", 53) },
513 {
LEVEL(
"6.0", 60) },
514 {
LEVEL(
"6.1", 61) },
515 {
LEVEL(
"6.2", 62) },
516 {
LEVEL(
"6.3", 63) },
517 {
LEVEL(
"7.0", 70) },
518 {
LEVEL(
"7.1", 71) },
519 {
LEVEL(
"7.2", 72) },
520 {
LEVEL(
"7.3", 73) },
521 #undef LEVEL
522
525 {
"cqp",
"Constant quantizer", 0,
AV_OPT_TYPE_CONST, { .i64 = 0 }, INT_MIN, INT_MAX,
VE,
"rc" },
526 {
"vbr",
"Variable Bit Rate, use a target bitrate for the entire stream", 0,
AV_OPT_TYPE_CONST, { .i64 = 1 }, INT_MIN, INT_MAX,
VE,
"rc" },
527 {
"cvbr",
"Constrained Variable Bit Rate, use a target bitrate for each GOP", 0,
AV_OPT_TYPE_CONST,{ .i64 = 2 }, INT_MIN, INT_MAX,
VE,
"rc" },
528
529 {
"qp",
"Quantizer to use with cqp rate control mode",
OFFSET(qp),
531
532 {
"sc_detection",
"Scene change detection",
OFFSET(scd),
534
535 {
"tile_columns",
"Log2 of number of tile columns to use",
OFFSET(tile_columns),
AV_OPT_TYPE_INT, {.i64 = 0}, 0, 4,
VE},
537
539 };
540
546 };
547
549 { "b", "7M" },
550 { "flags", "+cgop" },
551 { "g", "-1" },
552 { "qmin", "0" },
553 { "qmax", "63" },
555 };
556
571 .priv_class = &class,
573 .wrapper_name = "libsvtav1",
574 };