| 2786 | } |
| 2787 | |
| 2788 | static int decode_anim(AVCodecContext *avctx, int *got_frame_ptr) |
| 2789 | { |
| 2790 | SANMVideoContext *ctx = avctx->priv_data; |
| 2791 | int i, ret, to_store = 0, have_img = 0; |
| 2792 | |
| 2793 | ctx->first_fob = 1; |
| 2794 | while (bytestream2_get_bytes_left(&ctx->gb) >= 8) { |
| 2795 | uint32_t sig, size; |
| 2796 | int pos; |
| 2797 | |
| 2798 | sig = bytestream2_get_be32u(&ctx->gb); |
| 2799 | size = bytestream2_get_be32u(&ctx->gb); |
| 2800 | pos = bytestream2_tell(&ctx->gb); |
| 2801 | |
| 2802 | if (bytestream2_get_bytes_left(&ctx->gb) < size) { |
| 2803 | av_log(avctx, AV_LOG_ERROR, "Incorrect chunk size %"PRIu32".\n", size); |
| 2804 | break; |
| 2805 | } |
| 2806 | switch (sig) { |
| 2807 | case MKBETAG('N', 'P', 'A', 'L'): |
| 2808 | if (size != PALETTE_SIZE * 3) { |
| 2809 | av_log(avctx, AV_LOG_ERROR, |
| 2810 | "Incorrect palette block size %"PRIu32".\n", size); |
| 2811 | return AVERROR_INVALIDDATA; |
| 2812 | } |
| 2813 | for (i = 0; i < PALETTE_SIZE; i++) |
| 2814 | ctx->pal[i] = 0xFFU << 24 | bytestream2_get_be24u(&ctx->gb); |
| 2815 | if (ctx->subversion < 2) |
| 2816 | ctx->pal[0] = 0xFFU << 24; |
| 2817 | break; |
| 2818 | case MKBETAG('F', 'O', 'B', 'J'): |
| 2819 | if (size < 16) |
| 2820 | return AVERROR_INVALIDDATA; |
| 2821 | GetByteContext fc; |
| 2822 | bytestream2_init(&fc, ctx->gb.buffer, size); |
| 2823 | if (ret = process_frame_obj(ctx, &fc, 0, 0)) { |
| 2824 | return ret; |
| 2825 | } |
| 2826 | have_img = 1; |
| 2827 | |
| 2828 | /* STOR: for ANIMv0/1 store the whole FOBJ datablock, as it |
| 2829 | * needs to be replayed on FTCH, since none of the codecs |
| 2830 | * it uses work on the full buffer. |
| 2831 | * For ANIMv2, it's enough to store the current framebuffer. |
| 2832 | */ |
| 2833 | if (to_store) { |
| 2834 | to_store = 0; |
| 2835 | if (ctx->subversion < 2) { |
| 2836 | if (size <= ctx->stored_frame_size) { |
| 2837 | bytestream2_seek(&fc, 0, SEEK_SET); |
| 2838 | bytestream2_get_bufferu(&fc, ctx->stored_frame, size); |
| 2839 | ctx->stor_size = size; |
| 2840 | } else { |
| 2841 | av_log(avctx, AV_LOG_ERROR, "FOBJ too large for STOR\n"); |
| 2842 | ret = AVERROR(ENOMEM); |
| 2843 | } |
| 2844 | } else { |
| 2845 | memcpy(ctx->stored_frame, ctx->fbuf, ctx->buf_size); |
no test coverage detected