cbs.c (30227B)
1 /* 2 * This file is part of FFmpeg. 3 * 4 * FFmpeg is free software; you can redistribute it and/or 5 * modify it under the terms of the GNU Lesser General Public 6 * License as published by the Free Software Foundation; either 7 * version 2.1 of the License, or (at your option) any later version. 8 * 9 * FFmpeg is distributed in the hope that it will be useful, 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 12 * Lesser General Public License for more details. 13 * 14 * You should have received a copy of the GNU Lesser General Public 15 * License along with FFmpeg; if not, write to the Free Software 16 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA 17 */ 18 19 #include <string.h> 20 21 #include "config.h" 22 23 #include "libavutil/avassert.h" 24 #include "libavutil/buffer.h" 25 #include "libavutil/common.h" 26 #include "libavutil/mem.h" 27 #include "libavutil/opt.h" 28 29 #include "avcodec.h" 30 #include "cbs.h" 31 #include "cbs_internal.h" 32 #include "libavutil/refstruct.h" 33 34 35 static const CodedBitstreamType *const cbs_type_table[] = { 36 #if CONFIG_CBS_AV1 37 &ff_cbs_type_av1, 38 #endif 39 #if CONFIG_CBS_H264 40 &ff_cbs_type_h264, 41 #endif 42 #if CONFIG_CBS_H265 43 &ff_cbs_type_h265, 44 #endif 45 #if CONFIG_CBS_H266 46 &ff_cbs_type_h266, 47 #endif 48 #if CONFIG_CBS_JPEG 49 &ff_cbs_type_jpeg, 50 #endif 51 #if CONFIG_CBS_MPEG2 52 &ff_cbs_type_mpeg2, 53 #endif 54 #if CONFIG_CBS_VP8 55 &ff_cbs_type_vp8, 56 #endif 57 #if CONFIG_CBS_VP9 58 &ff_cbs_type_vp9, 59 #endif 60 }; 61 62 const enum AVCodecID ff_cbs_all_codec_ids[] = { 63 #if CONFIG_CBS_AV1 64 AV_CODEC_ID_AV1, 65 #endif 66 #if CONFIG_CBS_H264 67 AV_CODEC_ID_H264, 68 #endif 69 #if CONFIG_CBS_H265 70 AV_CODEC_ID_H265, 71 #endif 72 #if CONFIG_CBS_H266 73 AV_CODEC_ID_H266, 74 #endif 75 #if CONFIG_CBS_JPEG 76 AV_CODEC_ID_MJPEG, 77 #endif 78 #if CONFIG_CBS_MPEG2 79 AV_CODEC_ID_MPEG2VIDEO, 80 #endif 81 #if CONFIG_CBS_VP8 82 AV_CODEC_ID_VP8, 83 #endif 84 #if CONFIG_CBS_VP9 85 AV_CODEC_ID_VP9, 86 #endif 87 AV_CODEC_ID_NONE 88 }; 89 90 av_cold int ff_cbs_init(CodedBitstreamContext **ctx_ptr, 91 enum AVCodecID codec_id, void *log_ctx) 92 { 93 CodedBitstreamContext *ctx; 94 const CodedBitstreamType *type; 95 int i; 96 97 type = NULL; 98 for (i = 0; i < FF_ARRAY_ELEMS(cbs_type_table); i++) { 99 if (cbs_type_table[i]->codec_id == codec_id) { 100 type = cbs_type_table[i]; 101 break; 102 } 103 } 104 if (!type) 105 return AVERROR(EINVAL); 106 107 ctx = av_mallocz(sizeof(*ctx)); 108 if (!ctx) 109 return AVERROR(ENOMEM); 110 111 ctx->log_ctx = log_ctx; 112 ctx->codec = type; /* Must be before any error */ 113 114 if (type->priv_data_size) { 115 ctx->priv_data = av_mallocz(ctx->codec->priv_data_size); 116 if (!ctx->priv_data) { 117 av_freep(&ctx); 118 return AVERROR(ENOMEM); 119 } 120 if (type->priv_class) { 121 *(const AVClass **)ctx->priv_data = type->priv_class; 122 av_opt_set_defaults(ctx->priv_data); 123 } 124 } 125 126 ctx->decompose_unit_types = NULL; 127 128 ctx->trace_enable = 0; 129 ctx->trace_level = AV_LOG_TRACE; 130 ctx->trace_context = ctx; 131 132 *ctx_ptr = ctx; 133 return 0; 134 } 135 136 av_cold void ff_cbs_flush(CodedBitstreamContext *ctx) 137 { 138 if (ctx->codec->flush) 139 ctx->codec->flush(ctx); 140 } 141 142 av_cold void ff_cbs_close(CodedBitstreamContext **ctx_ptr) 143 { 144 CodedBitstreamContext *ctx = *ctx_ptr; 145 146 if (!ctx) 147 return; 148 149 if (ctx->codec->close) 150 ctx->codec->close(ctx); 151 152 av_freep(&ctx->write_buffer); 153 154 if (ctx->codec->priv_class && ctx->priv_data) 155 av_opt_free(ctx->priv_data); 156 157 av_freep(&ctx->priv_data); 158 av_freep(ctx_ptr); 159 } 160 161 static void cbs_unit_uninit(CodedBitstreamUnit *unit) 162 { 163 av_refstruct_unref(&unit->content_ref); 164 unit->content = NULL; 165 166 av_buffer_unref(&unit->data_ref); 167 unit->data = NULL; 168 unit->data_size = 0; 169 unit->data_bit_padding = 0; 170 } 171 172 void ff_cbs_fragment_reset(CodedBitstreamFragment *frag) 173 { 174 int i; 175 176 for (i = 0; i < frag->nb_units; i++) 177 cbs_unit_uninit(&frag->units[i]); 178 frag->nb_units = 0; 179 180 av_buffer_unref(&frag->data_ref); 181 frag->data = NULL; 182 frag->data_size = 0; 183 frag->data_bit_padding = 0; 184 } 185 186 av_cold void ff_cbs_fragment_free(CodedBitstreamFragment *frag) 187 { 188 ff_cbs_fragment_reset(frag); 189 190 av_freep(&frag->units); 191 frag->nb_units_allocated = 0; 192 } 193 194 static int cbs_read_fragment_content(CodedBitstreamContext *ctx, 195 CodedBitstreamFragment *frag) 196 { 197 int err, i, j; 198 199 for (i = 0; i < frag->nb_units; i++) { 200 CodedBitstreamUnit *unit = &frag->units[i]; 201 202 if (ctx->decompose_unit_types) { 203 for (j = 0; j < ctx->nb_decompose_unit_types; j++) { 204 if (ctx->decompose_unit_types[j] == unit->type) 205 break; 206 } 207 if (j >= ctx->nb_decompose_unit_types) 208 continue; 209 } 210 211 av_refstruct_unref(&unit->content_ref); 212 unit->content = NULL; 213 214 av_assert0(unit->data && unit->data_ref); 215 216 err = ctx->codec->read_unit(ctx, unit); 217 if (err == AVERROR(ENOSYS)) { 218 av_log(ctx->log_ctx, AV_LOG_VERBOSE, 219 "Decomposition unimplemented for unit %d " 220 "(type %"PRIu32").\n", i, unit->type); 221 } else if (err == AVERROR(EAGAIN)) { 222 av_log(ctx->log_ctx, AV_LOG_VERBOSE, 223 "Skipping decomposition of unit %d " 224 "(type %"PRIu32").\n", i, unit->type); 225 av_refstruct_unref(&unit->content_ref); 226 unit->content = NULL; 227 } else if (err < 0) { 228 av_log(ctx->log_ctx, AV_LOG_ERROR, "Failed to read unit %d " 229 "(type %"PRIu32").\n", i, unit->type); 230 return err; 231 } 232 } 233 234 return 0; 235 } 236 237 static int cbs_fill_fragment_data(CodedBitstreamFragment *frag, 238 const uint8_t *data, size_t size) 239 { 240 av_assert0(!frag->data && !frag->data_ref); 241 242 frag->data_ref = 243 av_buffer_alloc(size + AV_INPUT_BUFFER_PADDING_SIZE); 244 if (!frag->data_ref) 245 return AVERROR(ENOMEM); 246 247 frag->data = frag->data_ref->data; 248 frag->data_size = size; 249 250 memcpy(frag->data, data, size); 251 memset(frag->data + size, 0, 252 AV_INPUT_BUFFER_PADDING_SIZE); 253 254 return 0; 255 } 256 257 static int cbs_read_data(CodedBitstreamContext *ctx, 258 CodedBitstreamFragment *frag, 259 AVBufferRef *buf, 260 const uint8_t *data, size_t size, 261 int header) 262 { 263 int err; 264 265 if (buf) { 266 frag->data_ref = av_buffer_ref(buf); 267 if (!frag->data_ref) 268 return AVERROR(ENOMEM); 269 270 frag->data = (uint8_t *)data; 271 frag->data_size = size; 272 273 } else { 274 err = cbs_fill_fragment_data(frag, data, size); 275 if (err < 0) 276 return err; 277 } 278 279 err = ctx->codec->split_fragment(ctx, frag, header); 280 if (err < 0) 281 return err; 282 283 return cbs_read_fragment_content(ctx, frag); 284 } 285 286 int ff_cbs_read_extradata(CodedBitstreamContext *ctx, 287 CodedBitstreamFragment *frag, 288 const AVCodecParameters *par) 289 { 290 return cbs_read_data(ctx, frag, NULL, 291 par->extradata, 292 par->extradata_size, 1); 293 } 294 295 int ff_cbs_read_extradata_from_codec(CodedBitstreamContext *ctx, 296 CodedBitstreamFragment *frag, 297 const AVCodecContext *avctx) 298 { 299 return cbs_read_data(ctx, frag, NULL, 300 avctx->extradata, 301 avctx->extradata_size, 1); 302 } 303 304 int ff_cbs_read_packet(CodedBitstreamContext *ctx, 305 CodedBitstreamFragment *frag, 306 const AVPacket *pkt) 307 { 308 return cbs_read_data(ctx, frag, pkt->buf, 309 pkt->data, pkt->size, 0); 310 } 311 312 int ff_cbs_read_packet_side_data(CodedBitstreamContext *ctx, 313 CodedBitstreamFragment *frag, 314 const AVPacket *pkt) 315 { 316 size_t side_data_size; 317 const uint8_t *side_data = 318 av_packet_get_side_data(pkt, AV_PKT_DATA_NEW_EXTRADATA, 319 &side_data_size); 320 321 return cbs_read_data(ctx, frag, NULL, 322 side_data, side_data_size, 1); 323 } 324 325 int ff_cbs_read(CodedBitstreamContext *ctx, 326 CodedBitstreamFragment *frag, 327 const uint8_t *data, size_t size) 328 { 329 return cbs_read_data(ctx, frag, NULL, 330 data, size, 0); 331 } 332 333 /** 334 * Allocate a new internal data buffer of the given size in the unit. 335 * 336 * The data buffer will have input padding. 337 */ 338 static int cbs_alloc_unit_data(CodedBitstreamUnit *unit, 339 size_t size) 340 { 341 av_assert0(!unit->data && !unit->data_ref); 342 343 unit->data_ref = av_buffer_alloc(size + AV_INPUT_BUFFER_PADDING_SIZE); 344 if (!unit->data_ref) 345 return AVERROR(ENOMEM); 346 347 unit->data = unit->data_ref->data; 348 unit->data_size = size; 349 350 memset(unit->data + size, 0, AV_INPUT_BUFFER_PADDING_SIZE); 351 352 return 0; 353 } 354 355 static int cbs_write_unit_data(CodedBitstreamContext *ctx, 356 CodedBitstreamUnit *unit) 357 { 358 PutBitContext pbc; 359 int ret; 360 361 if (!ctx->write_buffer) { 362 // Initial write buffer size is 1MB. 363 ctx->write_buffer_size = 1024 * 1024; 364 365 reallocate_and_try_again: 366 ret = av_reallocp(&ctx->write_buffer, ctx->write_buffer_size); 367 if (ret < 0) { 368 av_log(ctx->log_ctx, AV_LOG_ERROR, "Unable to allocate a " 369 "sufficiently large write buffer (last attempt " 370 "%"SIZE_SPECIFIER" bytes).\n", ctx->write_buffer_size); 371 return ret; 372 } 373 } 374 375 init_put_bits(&pbc, ctx->write_buffer, ctx->write_buffer_size); 376 377 ret = ctx->codec->write_unit(ctx, unit, &pbc); 378 if (ret < 0) { 379 if (ret == AVERROR(ENOSPC)) { 380 // Overflow. 381 if (ctx->write_buffer_size == INT_MAX / 8) 382 return AVERROR(ENOMEM); 383 ctx->write_buffer_size = FFMIN(2 * ctx->write_buffer_size, INT_MAX / 8); 384 goto reallocate_and_try_again; 385 } 386 // Write failed for some other reason. 387 return ret; 388 } 389 390 // Overflow but we didn't notice. 391 av_assert0(put_bits_count(&pbc) <= 8 * ctx->write_buffer_size); 392 393 if (put_bits_count(&pbc) % 8) 394 unit->data_bit_padding = 8 - put_bits_count(&pbc) % 8; 395 else 396 unit->data_bit_padding = 0; 397 398 flush_put_bits(&pbc); 399 400 ret = cbs_alloc_unit_data(unit, put_bytes_output(&pbc)); 401 if (ret < 0) 402 return ret; 403 404 memcpy(unit->data, ctx->write_buffer, unit->data_size); 405 406 return 0; 407 } 408 409 int ff_cbs_write_fragment_data(CodedBitstreamContext *ctx, 410 CodedBitstreamFragment *frag) 411 { 412 int err, i; 413 414 for (i = 0; i < frag->nb_units; i++) { 415 CodedBitstreamUnit *unit = &frag->units[i]; 416 417 if (!unit->content) 418 continue; 419 420 av_buffer_unref(&unit->data_ref); 421 unit->data = NULL; 422 423 err = cbs_write_unit_data(ctx, unit); 424 if (err < 0) { 425 av_log(ctx->log_ctx, AV_LOG_ERROR, "Failed to write unit %d " 426 "(type %"PRIu32").\n", i, unit->type); 427 return err; 428 } 429 av_assert0(unit->data && unit->data_ref); 430 } 431 432 av_buffer_unref(&frag->data_ref); 433 frag->data = NULL; 434 435 err = ctx->codec->assemble_fragment(ctx, frag); 436 if (err < 0) { 437 av_log(ctx->log_ctx, AV_LOG_ERROR, "Failed to assemble fragment.\n"); 438 return err; 439 } 440 av_assert0(frag->data && frag->data_ref); 441 442 return 0; 443 } 444 445 int ff_cbs_write_extradata(CodedBitstreamContext *ctx, 446 AVCodecParameters *par, 447 CodedBitstreamFragment *frag) 448 { 449 int err; 450 451 err = ff_cbs_write_fragment_data(ctx, frag); 452 if (err < 0) 453 return err; 454 455 av_freep(&par->extradata); 456 par->extradata_size = 0; 457 458 if (!frag->data_size) 459 return 0; 460 461 par->extradata = av_malloc(frag->data_size + 462 AV_INPUT_BUFFER_PADDING_SIZE); 463 if (!par->extradata) 464 return AVERROR(ENOMEM); 465 466 memcpy(par->extradata, frag->data, frag->data_size); 467 memset(par->extradata + frag->data_size, 0, 468 AV_INPUT_BUFFER_PADDING_SIZE); 469 par->extradata_size = frag->data_size; 470 471 return 0; 472 } 473 474 int ff_cbs_write_packet(CodedBitstreamContext *ctx, 475 AVPacket *pkt, 476 CodedBitstreamFragment *frag) 477 { 478 AVBufferRef *buf; 479 int err; 480 481 err = ff_cbs_write_fragment_data(ctx, frag); 482 if (err < 0) 483 return err; 484 485 buf = av_buffer_ref(frag->data_ref); 486 if (!buf) 487 return AVERROR(ENOMEM); 488 489 av_buffer_unref(&pkt->buf); 490 491 pkt->buf = buf; 492 pkt->data = frag->data; 493 pkt->size = frag->data_size; 494 495 return 0; 496 } 497 498 499 void ff_cbs_trace_header(CodedBitstreamContext *ctx, 500 const char *name) 501 { 502 if (!ctx->trace_enable) 503 return; 504 505 av_log(ctx->log_ctx, ctx->trace_level, "%s\n", name); 506 } 507 508 void ff_cbs_trace_read_log(void *trace_context, 509 GetBitContext *gbc, int length, 510 const char *str, const int *subscripts, 511 int64_t value) 512 { 513 CodedBitstreamContext *ctx = trace_context; 514 char name[256]; 515 char bits[256]; 516 size_t name_len, bits_len; 517 int pad, subs, i, j, k, n; 518 int position; 519 520 av_assert0(value >= INT_MIN && value <= UINT32_MAX); 521 522 position = get_bits_count(gbc); 523 524 av_assert0(length < 256); 525 for (i = 0; i < length; i++) 526 bits[i] = get_bits1(gbc) ? '1' : '0'; 527 bits[length] = 0; 528 529 subs = subscripts ? subscripts[0] : 0; 530 n = 0; 531 for (i = j = 0; str[i];) { 532 if (str[i] == '[') { 533 if (n < subs) { 534 ++n; 535 k = snprintf(name + j, sizeof(name) - j, "[%d", subscripts[n]); 536 av_assert0(k > 0 && j + k < sizeof(name)); 537 j += k; 538 for (++i; str[i] && str[i] != ']'; i++); 539 av_assert0(str[i] == ']'); 540 } else { 541 while (str[i] && str[i] != ']') 542 name[j++] = str[i++]; 543 av_assert0(str[i] == ']'); 544 } 545 } else { 546 av_assert0(j + 1 < sizeof(name)); 547 name[j++] = str[i++]; 548 } 549 } 550 av_assert0(j + 1 < sizeof(name)); 551 name[j] = 0; 552 av_assert0(n == subs); 553 554 name_len = strlen(name); 555 bits_len = length; 556 557 if (name_len + bits_len > 60) 558 pad = bits_len + 2; 559 else 560 pad = 61 - name_len; 561 562 av_log(ctx->log_ctx, ctx->trace_level, "%-10d %s%*s = %"PRId64"\n", 563 position, name, pad, bits, value); 564 } 565 566 void ff_cbs_trace_write_log(void *trace_context, 567 PutBitContext *pbc, int length, 568 const char *str, const int *subscripts, 569 int64_t value) 570 { 571 CodedBitstreamContext *ctx = trace_context; 572 573 // Ensure that the syntax element is written to the output buffer, 574 // make a GetBitContext pointed at the start position, then call the 575 // read log function which can read the bits back to log them. 576 577 GetBitContext gbc; 578 int position; 579 580 if (length > 0) { 581 PutBitContext flush; 582 flush = *pbc; 583 flush_put_bits(&flush); 584 } 585 586 position = put_bits_count(pbc); 587 av_assert0(position >= length); 588 589 init_get_bits(&gbc, pbc->buf, position); 590 591 skip_bits_long(&gbc, position - length); 592 593 ff_cbs_trace_read_log(ctx, &gbc, length, str, subscripts, value); 594 } 595 596 static av_always_inline int cbs_read_unsigned(CodedBitstreamContext *ctx, 597 GetBitContext *gbc, 598 int width, const char *name, 599 const int *subscripts, 600 uint32_t *write_to, 601 uint32_t range_min, 602 uint32_t range_max) 603 { 604 uint32_t value; 605 606 CBS_TRACE_READ_START(); 607 608 av_assert0(width > 0 && width <= 32); 609 610 if (get_bits_left(gbc) < width) { 611 av_log(ctx->log_ctx, AV_LOG_ERROR, "Invalid value at " 612 "%s: bitstream ended.\n", name); 613 return AVERROR_INVALIDDATA; 614 } 615 616 value = get_bits_long(gbc, width); 617 618 CBS_TRACE_READ_END(); 619 620 if (value < range_min || value > range_max) { 621 av_log(ctx->log_ctx, AV_LOG_ERROR, "%s out of range: " 622 "%"PRIu32", but must be in [%"PRIu32",%"PRIu32"].\n", 623 name, value, range_min, range_max); 624 return AVERROR_INVALIDDATA; 625 } 626 627 *write_to = value; 628 return 0; 629 } 630 631 int ff_cbs_read_unsigned(CodedBitstreamContext *ctx, GetBitContext *gbc, 632 int width, const char *name, 633 const int *subscripts, uint32_t *write_to, 634 uint32_t range_min, uint32_t range_max) 635 { 636 return cbs_read_unsigned(ctx, gbc, width, name, subscripts, 637 write_to, range_min, range_max); 638 } 639 640 int ff_cbs_read_simple_unsigned(CodedBitstreamContext *ctx, GetBitContext *gbc, 641 int width, const char *name, uint32_t *write_to) 642 { 643 return cbs_read_unsigned(ctx, gbc, width, name, NULL, 644 write_to, 0, UINT32_MAX); 645 } 646 647 int ff_cbs_write_unsigned(CodedBitstreamContext *ctx, PutBitContext *pbc, 648 int width, const char *name, 649 const int *subscripts, uint32_t value, 650 uint32_t range_min, uint32_t range_max) 651 { 652 CBS_TRACE_WRITE_START(); 653 654 av_assert0(width > 0 && width <= 32); 655 656 if (value < range_min || value > range_max) { 657 av_log(ctx->log_ctx, AV_LOG_ERROR, "%s out of range: " 658 "%"PRIu32", but must be in [%"PRIu32",%"PRIu32"].\n", 659 name, value, range_min, range_max); 660 return AVERROR_INVALIDDATA; 661 } 662 663 if (put_bits_left(pbc) < width) 664 return AVERROR(ENOSPC); 665 666 if (width < 32) 667 put_bits(pbc, width, value); 668 else 669 put_bits32(pbc, value); 670 671 CBS_TRACE_WRITE_END(); 672 673 return 0; 674 } 675 676 int ff_cbs_write_simple_unsigned(CodedBitstreamContext *ctx, PutBitContext *pbc, 677 int width, const char *name, uint32_t value) 678 { 679 return ff_cbs_write_unsigned(ctx, pbc, width, name, NULL, 680 value, 0, MAX_UINT_BITS(width)); 681 } 682 683 int ff_cbs_read_signed(CodedBitstreamContext *ctx, GetBitContext *gbc, 684 int width, const char *name, 685 const int *subscripts, int32_t *write_to, 686 int32_t range_min, int32_t range_max) 687 { 688 int32_t value; 689 690 CBS_TRACE_READ_START(); 691 692 av_assert0(width > 0 && width <= 32); 693 694 if (get_bits_left(gbc) < width) { 695 av_log(ctx->log_ctx, AV_LOG_ERROR, "Invalid value at " 696 "%s: bitstream ended.\n", name); 697 return AVERROR_INVALIDDATA; 698 } 699 700 value = get_sbits_long(gbc, width); 701 702 CBS_TRACE_READ_END(); 703 704 if (value < range_min || value > range_max) { 705 av_log(ctx->log_ctx, AV_LOG_ERROR, "%s out of range: " 706 "%"PRId32", but must be in [%"PRId32",%"PRId32"].\n", 707 name, value, range_min, range_max); 708 return AVERROR_INVALIDDATA; 709 } 710 711 *write_to = value; 712 return 0; 713 } 714 715 int ff_cbs_write_signed(CodedBitstreamContext *ctx, PutBitContext *pbc, 716 int width, const char *name, 717 const int *subscripts, int32_t value, 718 int32_t range_min, int32_t range_max) 719 { 720 CBS_TRACE_WRITE_START(); 721 722 av_assert0(width > 0 && width <= 32); 723 724 if (value < range_min || value > range_max) { 725 av_log(ctx->log_ctx, AV_LOG_ERROR, "%s out of range: " 726 "%"PRId32", but must be in [%"PRId32",%"PRId32"].\n", 727 name, value, range_min, range_max); 728 return AVERROR_INVALIDDATA; 729 } 730 731 if (put_bits_left(pbc) < width) 732 return AVERROR(ENOSPC); 733 734 if (width < 32) 735 put_sbits(pbc, width, value); 736 else 737 put_bits32(pbc, value); 738 739 CBS_TRACE_WRITE_END(); 740 741 return 0; 742 } 743 744 745 static int cbs_insert_unit(CodedBitstreamFragment *frag, 746 int position) 747 { 748 CodedBitstreamUnit *units; 749 750 if (frag->nb_units < frag->nb_units_allocated) { 751 units = frag->units; 752 753 if (position < frag->nb_units) 754 memmove(units + position + 1, units + position, 755 (frag->nb_units - position) * sizeof(*units)); 756 } else { 757 units = av_malloc_array(frag->nb_units*2 + 1, sizeof(*units)); 758 if (!units) 759 return AVERROR(ENOMEM); 760 761 frag->nb_units_allocated = 2*frag->nb_units_allocated + 1; 762 763 if (position > 0) 764 memcpy(units, frag->units, position * sizeof(*units)); 765 766 if (position < frag->nb_units) 767 memcpy(units + position + 1, frag->units + position, 768 (frag->nb_units - position) * sizeof(*units)); 769 } 770 771 memset(units + position, 0, sizeof(*units)); 772 773 if (units != frag->units) { 774 av_free(frag->units); 775 frag->units = units; 776 } 777 778 ++frag->nb_units; 779 780 return 0; 781 } 782 783 int ff_cbs_insert_unit_content(CodedBitstreamFragment *frag, 784 int position, 785 CodedBitstreamUnitType type, 786 void *content, 787 void *content_ref) 788 { 789 CodedBitstreamUnit *unit; 790 int err; 791 792 if (position == -1) 793 position = frag->nb_units; 794 av_assert0(position >= 0 && position <= frag->nb_units); 795 796 err = cbs_insert_unit(frag, position); 797 if (err < 0) 798 return err; 799 800 if (content_ref) { 801 // Create our own reference out of the user-supplied one. 802 content_ref = av_refstruct_ref(content_ref); 803 } 804 805 unit = &frag->units[position]; 806 unit->type = type; 807 unit->content = content; 808 unit->content_ref = content_ref; 809 810 return 0; 811 } 812 813 static int cbs_insert_unit_data(CodedBitstreamFragment *frag, 814 CodedBitstreamUnitType type, 815 uint8_t *data, size_t data_size, 816 AVBufferRef *data_buf, 817 int position) 818 { 819 CodedBitstreamUnit *unit; 820 AVBufferRef *data_ref; 821 int err; 822 823 av_assert0(position >= 0 && position <= frag->nb_units); 824 825 if (data_buf) 826 data_ref = av_buffer_ref(data_buf); 827 else 828 data_ref = av_buffer_create(data, data_size, NULL, NULL, 0); 829 if (!data_ref) { 830 if (!data_buf) 831 av_free(data); 832 return AVERROR(ENOMEM); 833 } 834 835 err = cbs_insert_unit(frag, position); 836 if (err < 0) { 837 av_buffer_unref(&data_ref); 838 return err; 839 } 840 841 unit = &frag->units[position]; 842 unit->type = type; 843 unit->data = data; 844 unit->data_size = data_size; 845 unit->data_ref = data_ref; 846 847 return 0; 848 } 849 850 int ff_cbs_append_unit_data(CodedBitstreamFragment *frag, 851 CodedBitstreamUnitType type, 852 uint8_t *data, size_t data_size, 853 AVBufferRef *data_buf) 854 { 855 return cbs_insert_unit_data(frag, type, 856 data, data_size, data_buf, 857 frag->nb_units); 858 } 859 860 void ff_cbs_delete_unit(CodedBitstreamFragment *frag, 861 int position) 862 { 863 av_assert0(0 <= position && position < frag->nb_units 864 && "Unit to be deleted not in fragment."); 865 866 cbs_unit_uninit(&frag->units[position]); 867 868 --frag->nb_units; 869 870 if (frag->nb_units > 0) 871 memmove(frag->units + position, 872 frag->units + position + 1, 873 (frag->nb_units - position) * sizeof(*frag->units)); 874 } 875 876 static void cbs_default_free_unit_content(AVRefStructOpaque opaque, void *content) 877 { 878 const CodedBitstreamUnitTypeDescriptor *desc = opaque.c; 879 880 for (int i = 0; i < desc->type.ref.nb_offsets; i++) { 881 void **ptr = (void**)((char*)content + desc->type.ref.offsets[i]); 882 av_buffer_unref((AVBufferRef**)(ptr + 1)); 883 } 884 } 885 886 static const CodedBitstreamUnitTypeDescriptor 887 *cbs_find_unit_type_desc(CodedBitstreamContext *ctx, 888 CodedBitstreamUnit *unit) 889 { 890 const CodedBitstreamUnitTypeDescriptor *desc; 891 int i, j; 892 893 if (!ctx->codec->unit_types) 894 return NULL; 895 896 for (i = 0;; i++) { 897 desc = &ctx->codec->unit_types[i]; 898 if (desc->nb_unit_types == 0) 899 break; 900 if (desc->nb_unit_types == CBS_UNIT_TYPE_RANGE) { 901 if (unit->type >= desc->unit_type.range.start && 902 unit->type <= desc->unit_type.range.end) 903 return desc; 904 } else { 905 for (j = 0; j < desc->nb_unit_types; j++) { 906 if (desc->unit_type.list[j] == unit->type) 907 return desc; 908 } 909 } 910 } 911 return NULL; 912 } 913 914 static void *cbs_alloc_content(const CodedBitstreamUnitTypeDescriptor *desc) 915 { 916 return av_refstruct_alloc_ext_c(desc->content_size, 0, 917 (AVRefStructOpaque){ .c = desc }, 918 desc->content_type == CBS_CONTENT_TYPE_COMPLEX 919 ? desc->type.complex.content_free 920 : cbs_default_free_unit_content); 921 } 922 923 int ff_cbs_alloc_unit_content(CodedBitstreamContext *ctx, 924 CodedBitstreamUnit *unit) 925 { 926 const CodedBitstreamUnitTypeDescriptor *desc; 927 928 av_assert0(!unit->content && !unit->content_ref); 929 930 desc = cbs_find_unit_type_desc(ctx, unit); 931 if (!desc) 932 return AVERROR(ENOSYS); 933 934 unit->content_ref = cbs_alloc_content(desc); 935 if (!unit->content_ref) 936 return AVERROR(ENOMEM); 937 unit->content = unit->content_ref; 938 939 return 0; 940 } 941 942 static int cbs_clone_noncomplex_unit_content(void **clonep, 943 const CodedBitstreamUnit *unit, 944 const CodedBitstreamUnitTypeDescriptor *desc) 945 { 946 const uint8_t *src; 947 uint8_t *copy; 948 int err, i; 949 950 av_assert0(unit->content); 951 src = unit->content; 952 953 copy = cbs_alloc_content(desc); 954 if (!copy) 955 return AVERROR(ENOMEM); 956 memcpy(copy, src, desc->content_size); 957 for (int i = 0; i < desc->type.ref.nb_offsets; i++) { 958 void **ptr = (void**)(copy + desc->type.ref.offsets[i]); 959 /* Zero all the AVBufferRefs as they are owned by src. */ 960 *(ptr + 1) = NULL; 961 } 962 963 for (i = 0; i < desc->type.ref.nb_offsets; i++) { 964 const uint8_t *const *src_ptr = (const uint8_t* const*)(src + desc->type.ref.offsets[i]); 965 const AVBufferRef *src_buf = *(AVBufferRef**)(src_ptr + 1); 966 uint8_t **copy_ptr = (uint8_t**)(copy + desc->type.ref.offsets[i]); 967 AVBufferRef **copy_buf = (AVBufferRef**)(copy_ptr + 1); 968 969 if (!*src_ptr) { 970 av_assert0(!src_buf); 971 continue; 972 } 973 if (!src_buf) { 974 // We can't handle a non-refcounted pointer here - we don't 975 // have enough information to handle whatever structure lies 976 // at the other end of it. 977 err = AVERROR(EINVAL); 978 goto fail; 979 } 980 981 *copy_buf = av_buffer_ref(src_buf); 982 if (!*copy_buf) { 983 err = AVERROR(ENOMEM); 984 goto fail; 985 } 986 } 987 *clonep = copy; 988 989 return 0; 990 991 fail: 992 av_refstruct_unref(©); 993 return err; 994 } 995 996 /* 997 * On success, unit->content and unit->content_ref are updated with 998 * the new content; unit is untouched on failure. 999 * Any old content_ref is simply overwritten and not freed. 1000 */ 1001 static int cbs_clone_unit_content(CodedBitstreamContext *ctx, 1002 CodedBitstreamUnit *unit) 1003 { 1004 const CodedBitstreamUnitTypeDescriptor *desc; 1005 void *new_content; 1006 int err; 1007 1008 desc = cbs_find_unit_type_desc(ctx, unit); 1009 if (!desc) 1010 return AVERROR(ENOSYS); 1011 1012 switch (desc->content_type) { 1013 case CBS_CONTENT_TYPE_INTERNAL_REFS: 1014 err = cbs_clone_noncomplex_unit_content(&new_content, unit, desc); 1015 break; 1016 1017 case CBS_CONTENT_TYPE_COMPLEX: 1018 if (!desc->type.complex.content_clone) 1019 return AVERROR_PATCHWELCOME; 1020 err = desc->type.complex.content_clone(&new_content, unit); 1021 break; 1022 1023 default: 1024 av_assert0(0 && "Invalid content type."); 1025 } 1026 1027 if (err < 0) 1028 return err; 1029 1030 unit->content_ref = new_content; 1031 unit->content = new_content; 1032 return 0; 1033 } 1034 1035 int ff_cbs_make_unit_refcounted(CodedBitstreamContext *ctx, 1036 CodedBitstreamUnit *unit) 1037 { 1038 av_assert0(unit->content); 1039 if (unit->content_ref) 1040 return 0; 1041 return cbs_clone_unit_content(ctx, unit); 1042 } 1043 1044 int ff_cbs_make_unit_writable(CodedBitstreamContext *ctx, 1045 CodedBitstreamUnit *unit) 1046 { 1047 void *ref = unit->content_ref; 1048 int err; 1049 1050 av_assert0(unit->content); 1051 if (ref && av_refstruct_exclusive(ref)) 1052 return 0; 1053 1054 err = cbs_clone_unit_content(ctx, unit); 1055 if (err < 0) 1056 return err; 1057 av_refstruct_unref(&ref); 1058 return 0; 1059 } 1060 1061 void ff_cbs_discard_units(CodedBitstreamContext *ctx, 1062 CodedBitstreamFragment *frag, 1063 enum AVDiscard skip, 1064 int flags) 1065 { 1066 if (!ctx->codec->discarded_unit) 1067 return; 1068 1069 for (int i = frag->nb_units - 1; i >= 0; i--) { 1070 if (ctx->codec->discarded_unit(ctx, &frag->units[i], skip)) { 1071 // discard all units 1072 if (!(flags & DISCARD_FLAG_KEEP_NON_VCL)) { 1073 ff_cbs_fragment_free(frag); 1074 return; 1075 } 1076 1077 ff_cbs_delete_unit(frag, i); 1078 } 1079 } 1080 }