FFmpeg
Loading...
Searching...
No Matches
mss12.c
Go to the documentation of this file.
1/*
2 * Copyright (c) 2012 Konstantin Shishkov
3 *
4 * This file is part of FFmpeg.
5 *
6 * FFmpeg is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
10 *
11 * FFmpeg is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
15 *
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with FFmpeg; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
19 */
20
21/**
22 * @file
23 * Common functions for Microsoft Screen 1 and 2
24 */
25
26#include <inttypes.h>
27
28#include "libavutil/intfloat.h"
30#include "libavutil/mem.h"
31#include "avcodec.h"
32#include "mss12.h"
33
39
40static const int sec_order_sizes[4] = { 1, 7, 6, 1 };
41
48
50{
51 int thr;
52
53 thr = 2 * m->weights[m->num_syms] - 1;
54 thr = ((thr >> 1) + 4 * m->cum_prob[0]) / thr;
55
56 return FFMIN(thr, 0x3FFF);
57}
58
59static void model_reset(Model *m)
60{
61 int i;
62
63 for (i = 0; i <= m->num_syms; i++) {
64 m->weights[i] = 1;
65 m->cum_prob[i] = m->num_syms - i;
66 }
67 m->weights[0] = 0;
68 for (i = 0; i < m->num_syms; i++)
69 m->idx2sym[i + 1] = i;
70}
71
72static av_cold void model_init(Model *m, int num_syms, int thr_weight)
73{
74 m->num_syms = num_syms;
75 m->thr_weight = thr_weight;
76 m->threshold = num_syms * thr_weight;
77}
78
80{
81 int i;
82 int cum_prob;
83
86 while (m->cum_prob[0] > m->threshold) {
87 cum_prob = 0;
88 for (i = m->num_syms; i >= 0; i--) {
89 m->cum_prob[i] = cum_prob;
90 m->weights[i] = (m->weights[i] + 1) >> 1;
91 cum_prob += m->weights[i];
92 }
93 }
94}
95
97{
98 int i;
99
100 if (m->weights[val] == m->weights[val - 1]) {
101 for (i = val; m->weights[i - 1] == m->weights[val]; i--);
102 if (i != val) {
103 int sym1, sym2;
104
105 sym1 = m->idx2sym[val];
106 sym2 = m->idx2sym[i];
107
108 m->idx2sym[val] = sym2;
109 m->idx2sym[i] = sym1;
110
111 val = i;
112 }
113 }
114 m->weights[val]++;
115 for (i = val - 1; i >= 0; i--)
116 m->cum_prob[i]++;
118}
119
121{
122 int i, j;
123
124 if (!ctx->special_initial_cache)
125 for (i = 0; i < ctx->cache_size; i++)
126 ctx->cache[i] = i;
127 else {
128 ctx->cache[0] = 1;
129 ctx->cache[1] = 2;
130 ctx->cache[2] = 4;
131 }
132
133 model_reset(&ctx->cache_model);
134 model_reset(&ctx->full_model);
135
136 for (i = 0; i < 15; i++)
137 for (j = 0; j < 4; j++)
138 model_reset(&ctx->sec_models[i][j]);
139}
140
141static av_cold void pixctx_init(PixContext *ctx, int cache_size,
142 int full_model_syms, int special_initial_cache)
143{
144 int i, j, k, idx;
145
146 ctx->cache_size = cache_size + 4;
147 ctx->num_syms = cache_size;
148 ctx->special_initial_cache = special_initial_cache;
149
150 model_init(&ctx->cache_model, ctx->num_syms + 1, THRESH_LOW);
151 model_init(&ctx->full_model, full_model_syms, THRESH_HIGH);
152
153 for (i = 0, idx = 0; i < 4; i++)
154 for (j = 0; j < sec_order_sizes[i]; j++, idx++)
155 for (k = 0; k < 4; k++)
156 model_init(&ctx->sec_models[idx][k], 2 + i,
158}
159
161 uint8_t *ngb, int num_ngb, int any_ngb)
162{
163 int i, val, pix;
164
165 if (acoder->overread > MAX_OVERREAD)
166 return AVERROR_INVALIDDATA;
167 val = acoder->get_model_sym(acoder, &pctx->cache_model);
168 if (val < pctx->num_syms) {
169 if (any_ngb) {
170 int idx, j;
171
172 idx = 0;
173 for (i = 0; i < pctx->cache_size; i++) {
174 for (j = 0; j < num_ngb; j++)
175 if (pctx->cache[i] == ngb[j])
176 break;
177 if (j == num_ngb) {
178 if (idx == val)
179 break;
180 idx++;
181 }
182 }
183 val = FFMIN(i, pctx->cache_size - 1);
184 }
185 pix = pctx->cache[val];
186 } else {
187 pix = acoder->get_model_sym(acoder, &pctx->full_model);
188 for (i = 0; i < pctx->cache_size - 1; i++)
189 if (pctx->cache[i] == pix)
190 break;
191 val = i;
192 }
193 if (val) {
194 for (i = val; i > 0; i--)
195 pctx->cache[i] = pctx->cache[i - 1];
196 pctx->cache[0] = pix;
197 }
198
199 return pix;
200}
201
203 uint8_t *src, ptrdiff_t stride, int x, int y,
204 int has_right)
205{
206 uint8_t neighbours[4];
207 uint8_t ref_pix[4];
208 int nlen;
209 int layer = 0, sub;
210 int pix;
211 int i, j;
212
213 if (!y) {
214 memset(neighbours, src[-1], 4);
215 } else {
216 neighbours[TOP] = src[-stride];
217 if (!x) {
218 neighbours[TOP_LEFT] = neighbours[LEFT] = neighbours[TOP];
219 } else {
220 neighbours[TOP_LEFT] = src[-stride - 1];
221 neighbours[ LEFT] = src[-1];
222 }
223 if (has_right)
224 neighbours[TOP_RIGHT] = src[-stride + 1];
225 else
226 neighbours[TOP_RIGHT] = neighbours[TOP];
227 }
228
229 sub = 0;
230 if (x >= 2 && src[-2] == neighbours[LEFT])
231 sub = 1;
232 if (y >= 2 && src[-2 * stride] == neighbours[TOP])
233 sub |= 2;
234
235 nlen = 1;
236 ref_pix[0] = neighbours[0];
237 for (i = 1; i < 4; i++) {
238 for (j = 0; j < nlen; j++)
239 if (ref_pix[j] == neighbours[i])
240 break;
241 if (j == nlen)
242 ref_pix[nlen++] = neighbours[i];
243 }
244
245 switch (nlen) {
246 case 1:
247 layer = 0;
248 break;
249 case 2:
250 if (neighbours[TOP] == neighbours[TOP_LEFT]) {
251 if (neighbours[TOP_RIGHT] == neighbours[TOP_LEFT])
252 layer = 1;
253 else if (neighbours[LEFT] == neighbours[TOP_LEFT])
254 layer = 2;
255 else
256 layer = 3;
257 } else if (neighbours[TOP_RIGHT] == neighbours[TOP_LEFT]) {
258 if (neighbours[LEFT] == neighbours[TOP_LEFT])
259 layer = 4;
260 else
261 layer = 5;
262 } else if (neighbours[LEFT] == neighbours[TOP_LEFT]) {
263 layer = 6;
264 } else {
265 layer = 7;
266 }
267 break;
268 case 3:
269 if (neighbours[TOP] == neighbours[TOP_LEFT])
270 layer = 8;
271 else if (neighbours[TOP_RIGHT] == neighbours[TOP_LEFT])
272 layer = 9;
273 else if (neighbours[LEFT] == neighbours[TOP_LEFT])
274 layer = 10;
275 else if (neighbours[TOP_RIGHT] == neighbours[TOP])
276 layer = 11;
277 else if (neighbours[TOP] == neighbours[LEFT])
278 layer = 12;
279 else
280 layer = 13;
281 break;
282 case 4:
283 layer = 14;
284 break;
285 }
286
287 pix = acoder->get_model_sym(acoder,
288 &pctx->sec_models[layer][sub]);
289 if (pix < nlen)
290 return ref_pix[pix];
291 else
292 return decode_pixel(acoder, pctx, ref_pix, nlen, 1);
293}
294
295static int decode_region(ArithCoder *acoder, uint8_t *dst, uint8_t *rgb_dst,
296 int x, int y, int width, int height, ptrdiff_t stride,
297 ptrdiff_t rgb_stride, PixContext *pctx,
298 const uint32_t *pal)
299{
300 int i, j, p;
301
302 rgb_stride = rgb_dst ? rgb_stride : 0;
303 rgb_dst = rgb_dst ? rgb_dst + x * 3 + y * rgb_stride : NULL;
304 dst += x + y * stride;
305
306 for (j = 0; j < height; j++) {
307 for (i = 0; i < width; i++) {
308 if (!i && !j)
309 p = decode_pixel(acoder, pctx, NULL, 0, 0);
310 else
311 p = decode_pixel_in_context(acoder, pctx, dst + i, stride,
312 i, j, width - i - 1);
313 if (p < 0)
314 return p;
315 dst[i] = p;
316
317 if (rgb_dst)
318 AV_WB24(rgb_dst + i * 3, pal[p]);
319 }
320 dst += stride;
321 rgb_dst = FF_PTR_ADD(rgb_dst, rgb_stride);
322 }
323
324 return 0;
325}
326
327static void copy_rectangles(MSS12Context const *c,
328 int x, int y, int width, int height)
329{
330 int j;
331
332 if (c->last_rgb_pic)
333 for (j = y; j < y + height; j++) {
334 memcpy(c->rgb_pic + j * c->rgb_stride + x * 3,
335 c->last_rgb_pic + j * c->rgb_stride + x * 3,
336 width * 3);
337 memcpy(c->pal_pic + j * c->pal_stride + x,
338 c->last_pal_pic + j * c->pal_stride + x,
339 width);
340 }
341}
342
344 int x, int y, int width, int height)
345{
346 if (x + c->mvX < 0 || x + c->mvX + width > c->avctx->width ||
347 y + c->mvY < 0 || y + c->mvY + height > c->avctx->height ||
348 !c->rgb_pic)
349 return -1;
350 else {
351 uint8_t *dst = c->pal_pic + x + y * c->pal_stride;
352 uint8_t *rgb_dst = c->rgb_pic + x * 3 + y * c->rgb_stride;
353 uint8_t *src;
354 uint8_t *rgb_src;
355 int j;
356 x += c->mvX;
357 y += c->mvY;
358 if (c->last_rgb_pic) {
359 src = c->last_pal_pic + x + y * c->pal_stride;
360 rgb_src = c->last_rgb_pic + x * 3 + y * c->rgb_stride;
361 } else {
362 src = c->pal_pic + x + y * c->pal_stride;
363 rgb_src = c->rgb_pic + x * 3 + y * c->rgb_stride;
364 }
365 for (j = 0; j < height; j++) {
366 memmove(dst, src, width);
367 memmove(rgb_dst, rgb_src, width * 3);
368 dst += c->pal_stride;
369 src += c->pal_stride;
370 rgb_dst += c->rgb_stride;
371 rgb_src += c->rgb_stride;
372 }
373 }
374 return 0;
375}
376
378 uint8_t *dst, ptrdiff_t stride, uint8_t *mask,
379 ptrdiff_t mask_stride, int x, int y,
380 int width, int height,
381 PixContext *pctx)
382{
383 int i, j, p;
384 uint8_t *rgb_dst = c->rgb_pic + x * 3 + y * c->rgb_stride;
385
386 dst += x + y * stride;
387 mask += x + y * mask_stride;
388
389 for (j = 0; j < height; j++) {
390 for (i = 0; i < width; i++) {
391 if (c->avctx->err_recognition & AV_EF_EXPLODE &&
392 ( c->rgb_pic && mask[i] != 0x01 && mask[i] != 0x02 && mask[i] != 0x04 ||
393 !c->rgb_pic && mask[i] != 0x80 && mask[i] != 0xFF))
394 return -1;
395
396 if (mask[i] == 0x02) {
397 copy_rectangles(c, x + i, y + j, 1, 1);
398 } else if (mask[i] == 0x04) {
399 if (motion_compensation(c, x + i, y + j, 1, 1))
400 return -1;
401 } else if (mask[i] != 0x80) {
402 if (!i && !j)
403 p = decode_pixel(acoder, pctx, NULL, 0, 0);
404 else
405 p = decode_pixel_in_context(acoder, pctx, dst + i, stride,
406 i, j, width - i - 1);
407 if (p < 0)
408 return p;
409 dst[i] = p;
410 if (c->rgb_pic)
411 AV_WB24(rgb_dst + i * 3, c->pal[p]);
412 }
413 }
414 dst += stride;
415 mask += mask_stride;
416 rgb_dst += c->rgb_stride;
417 }
418
419 return 0;
420}
421
423 int version, int full_model_syms)
424{
429 model_init(&sc->pivot, 3, THRESH_LOW);
430
431 pixctx_init(&sc->intra_pix_ctx, 8, full_model_syms, 0);
432
433 pixctx_init(&sc->inter_pix_ctx, version ? 3 : 2,
434 full_model_syms, version ? 1 : 0);
435}
436
447
448static int decode_pivot(SliceContext *sc, ArithCoder *acoder, int base)
449{
450 int val, inv;
451
452 inv = acoder->get_model_sym(acoder, &sc->edge_mode);
453 val = acoder->get_model_sym(acoder, &sc->pivot) + 1;
454
455 if (val > 2) {
456 if ((base + 1) / 2 - 2 <= 0)
457 return -1;
458
459 val = acoder->get_number(acoder, (base + 1) / 2 - 2) + 3;
460 }
461
462 if ((unsigned)val >= base)
463 return -1;
464
465 return inv ? base - val : val;
466}
467
469 int x, int y, int width, int height)
470{
471 MSS12Context const *c = sc->c;
472 int mode;
473
474 mode = acoder->get_model_sym(acoder, &sc->intra_region);
475
476 if (!mode) {
477 int i, j, pix, rgb_pix;
478 ptrdiff_t stride = c->pal_stride;
479 ptrdiff_t rgb_stride = c->rgb_stride;
480 uint8_t *dst = c->pal_pic + x + y * stride;
481 uint8_t *rgb_dst = c->rgb_pic ? c->rgb_pic + x * 3 + y * rgb_stride : NULL;
482
483 pix = decode_pixel(acoder, &sc->intra_pix_ctx, NULL, 0, 0);
484 if (pix < 0)
485 return pix;
486 rgb_pix = c->pal[pix];
487 for (i = 0; i < height; i++, dst += stride) {
488 memset(dst, pix, width);
489 if (rgb_dst) {
490 for (j = 0; j < width * 3; j += 3)
491 AV_WB24(rgb_dst + j, rgb_pix);
492 rgb_dst += rgb_stride;
493 }
494 }
495 } else {
496 return decode_region(acoder, c->pal_pic, c->rgb_pic,
497 x, y, width, height, c->pal_stride, c->rgb_stride,
498 &sc->intra_pix_ctx, &c->pal[0]);
499 }
500
501 return 0;
502}
503
505 int x, int y, int width, int height)
506{
507 MSS12Context const *c = sc->c;
508 int mode;
509
510 mode = acoder->get_model_sym(acoder, &sc->inter_region);
511
512 if (!mode) {
513 mode = decode_pixel(acoder, &sc->inter_pix_ctx, NULL, 0, 0);
514 if (mode < 0)
515 return mode;
516
517 if (c->avctx->err_recognition & AV_EF_EXPLODE &&
518 ( c->rgb_pic && mode != 0x01 && mode != 0x02 && mode != 0x04 ||
519 !c->rgb_pic && mode != 0x80 && mode != 0xFF))
520 return -1;
521
522 if (mode == 0x02)
523 copy_rectangles(c, x, y, width, height);
524 else if (mode == 0x04)
525 return motion_compensation(c, x, y, width, height);
526 else if (mode != 0x80)
527 return decode_region_intra(sc, acoder, x, y, width, height);
528 } else {
529 if (decode_region(acoder, c->mask, NULL,
530 x, y, width, height, c->mask_stride, 0,
531 &sc->inter_pix_ctx, &c->pal[0]) < 0)
532 return -1;
533 return decode_region_masked(c, acoder, c->pal_pic,
534 c->pal_stride, c->mask,
535 c->mask_stride,
536 x, y, width, height,
537 &sc->intra_pix_ctx);
538 }
539
540 return 0;
541}
542
544 int x, int y, int width, int height)
545{
546 int mode, pivot;
547 if (acoder->overread > MAX_OVERREAD)
548 return AVERROR_INVALIDDATA;
549
550 mode = acoder->get_model_sym(acoder, &sc->split_mode);
551
552 switch (mode) {
553 case SPLIT_VERT:
554 if ((pivot = decode_pivot(sc, acoder, height)) < 1)
555 return -1;
556 if (ff_mss12_decode_rect(sc, acoder, x, y, width, pivot))
557 return -1;
558 if (ff_mss12_decode_rect(sc, acoder, x, y + pivot, width, height - pivot))
559 return -1;
560 break;
561 case SPLIT_HOR:
562 if ((pivot = decode_pivot(sc, acoder, width)) < 1)
563 return -1;
564 if (ff_mss12_decode_rect(sc, acoder, x, y, pivot, height))
565 return -1;
566 if (ff_mss12_decode_rect(sc, acoder, x + pivot, y, width - pivot, height))
567 return -1;
568 break;
569 case SPLIT_NONE:
570 if (sc->c->keyframe)
571 return decode_region_intra(sc, acoder, x, y, width, height);
572 else
573 return decode_region_inter(sc, acoder, x, y, width, height);
574 default:
575 return -1;
576 }
577
578 return 0;
579}
580
582 SliceContext* sc1, SliceContext *sc2)
583{
584 AVCodecContext *avctx = c->avctx;
585 int i;
586
587 if (avctx->extradata_size < 52 + 256 * 3) {
588 av_log(avctx, AV_LOG_ERROR, "Insufficient extradata size %d\n",
589 avctx->extradata_size);
590 return AVERROR_INVALIDDATA;
591 }
592
593 if (AV_RB32(avctx->extradata) < avctx->extradata_size) {
594 av_log(avctx, AV_LOG_ERROR,
595 "Insufficient extradata size: expected %"PRIu32" got %d\n",
596 AV_RB32(avctx->extradata),
597 avctx->extradata_size);
598 return AVERROR_INVALIDDATA;
599 }
600
601 avctx->coded_width = FFMAX(AV_RB32(avctx->extradata + 20), avctx->width);
602 avctx->coded_height = FFMAX(AV_RB32(avctx->extradata + 24), avctx->height);
603 if (avctx->coded_width > 4096 || avctx->coded_height > 4096) {
604 av_log(avctx, AV_LOG_ERROR, "Frame dimensions %dx%d too large",
605 avctx->coded_width, avctx->coded_height);
606 return AVERROR_INVALIDDATA;
607 }
608 if (avctx->coded_width < 1 || avctx->coded_height < 1) {
609 av_log(avctx, AV_LOG_ERROR, "Frame dimensions %dx%d too small",
610 avctx->coded_width, avctx->coded_height);
611 return AVERROR_INVALIDDATA;
612 }
613
614 av_log(avctx, AV_LOG_DEBUG, "Encoder version %"PRIu32".%"PRIu32"\n",
615 AV_RB32(avctx->extradata + 4), AV_RB32(avctx->extradata + 8));
616 if (version != AV_RB32(avctx->extradata + 4) > 1) {
617 av_log(avctx, AV_LOG_ERROR,
618 "Header version doesn't match codec tag\n");
619 return -1;
620 }
621
622 c->free_colours = AV_RB32(avctx->extradata + 48);
623 if ((unsigned)c->free_colours > 256) {
624 av_log(avctx, AV_LOG_ERROR,
625 "Incorrect number of changeable palette entries: %d\n",
626 c->free_colours);
627 return AVERROR_INVALIDDATA;
628 }
629 av_log(avctx, AV_LOG_DEBUG, "%d free colour(s)\n", c->free_colours);
630
631 av_log(avctx, AV_LOG_DEBUG, "Display dimensions %"PRIu32"x%"PRIu32"\n",
632 AV_RB32(avctx->extradata + 12), AV_RB32(avctx->extradata + 16));
633 av_log(avctx, AV_LOG_DEBUG, "Coded dimensions %dx%d\n",
634 avctx->coded_width, avctx->coded_height);
635 av_log(avctx, AV_LOG_DEBUG, "%g frames per second\n",
636 av_int2float(AV_RB32(avctx->extradata + 28)));
637 av_log(avctx, AV_LOG_DEBUG, "Bitrate %"PRIu32" bps\n",
638 AV_RB32(avctx->extradata + 32));
639 av_log(avctx, AV_LOG_DEBUG, "Max. lead time %g ms\n",
640 av_int2float(AV_RB32(avctx->extradata + 36)));
641 av_log(avctx, AV_LOG_DEBUG, "Max. lag time %g ms\n",
642 av_int2float(AV_RB32(avctx->extradata + 40)));
643 av_log(avctx, AV_LOG_DEBUG, "Max. seek time %g ms\n",
644 av_int2float(AV_RB32(avctx->extradata + 44)));
645
646 if (version) {
647 if (avctx->extradata_size < 60 + 256 * 3) {
648 av_log(avctx, AV_LOG_ERROR,
649 "Insufficient extradata size %d for v2\n",
650 avctx->extradata_size);
651 return AVERROR_INVALIDDATA;
652 }
653
654 c->slice_split = AV_RB32(avctx->extradata + 52);
655 av_log(avctx, AV_LOG_DEBUG, "Slice split %d\n", c->slice_split);
656
657 c->full_model_syms = AV_RB32(avctx->extradata + 56);
658 if (c->full_model_syms < 2 || c->full_model_syms > 256) {
659 av_log(avctx, AV_LOG_ERROR,
660 "Incorrect number of used colours %d\n",
661 c->full_model_syms);
662 return AVERROR_INVALIDDATA;
663 }
664 av_log(avctx, AV_LOG_DEBUG, "Used colours %d\n",
665 c->full_model_syms);
666 } else {
667 c->slice_split = 0;
668 c->full_model_syms = 256;
669 }
670
671 for (i = 0; i < 256; i++)
672 c->pal[i] = 0xFFU << 24 | AV_RB24(avctx->extradata + 52 +
673 (version ? 8 : 0) + i * 3);
674
675 c->mask_stride = FFALIGN(avctx->width, 16);
676 c->mask = av_malloc_array(c->mask_stride, avctx->height);
677 if (!c->mask) {
678 av_log(avctx, AV_LOG_ERROR, "Cannot allocate mask plane\n");
679 return AVERROR(ENOMEM);
680 }
681
682 sc1->c = c;
683 slicecontext_init(sc1, version, c->full_model_syms);
684 if (c->slice_split) {
685 sc2->c = c;
686 slicecontext_init(sc2, version, c->full_model_syms);
687 }
688 c->corrupted = 1;
689
690 return 0;
691}
692
694{
695 av_freep(&c->mask);
696
697 return 0;
698}
uint8_t ptrdiff_t const uint8_t ptrdiff_t int intptr_t intptr_t int int16_t * dst
Definition dsp.h:87
static double val(void *priv, double ch)
Definition aeval.c:77
Libavcodec external API header.
#define i(width, name, range_min, range_max)
Definition cbs_h264.c:63
#define LEFT
Definition cdgraphics.c:168
#define NULL
Definition coverity.c:32
#define AV_EF_EXPLODE
abort decoding on minor error detection
Definition defs.h:51
#define AVERROR_INVALIDDATA
Invalid data found when processing input.
Definition error.h:61
#define AVERROR(e)
Definition error.h:45
#define AV_LOG_DEBUG
Stuff which is only useful for libav* developers.
Definition log.h:231
#define AV_LOG_ERROR
Something went wrong and cannot losslessly be recovered.
Definition log.h:210
static av_always_inline float av_int2float(uint32_t i)
Reinterpret a 32-bit integer as a float.
Definition intfloat.h:40
#define AV_WB24(p, d)
#define AV_RB32(p)
#define AV_RB24(x)
#define MAX_OVERREAD
Definition lagarithrac.h:49
#define av_always_inline
Definition attributes.h:72
#define av_cold
Definition attributes.h:117
#define FF_PTR_ADD(ptr, off)
Definition internal.h:74
version
Definition libkvazaar.c:313
static const uint16_t mask[17]
Definition lzw.c:38
#define FFMIN(a, b)
Definition macros.h:49
#define FFMAX(a, b)
Definition macros.h:47
#define FFALIGN(x, a)
Definition macros.h:78
Memory handling functions.
#define TOP_LEFT
Definition movtextdec.c:50
#define TOP_RIGHT
Definition movtextdec.c:52
static void model_reset(Model *m)
Definition mss12.c:59
static int model_calc_threshold(Model *m)
Definition mss12.c:49
ContextDirection
Definition mss12.c:42
static av_cold void model_init(Model *m, int num_syms, int thr_weight)
Definition mss12.c:72
static int decode_region_intra(SliceContext *sc, ArithCoder *acoder, int x, int y, int width, int height)
Definition mss12.c:468
static int decode_pivot(SliceContext *sc, ArithCoder *acoder, int base)
Definition mss12.c:448
int ff_mss12_decode_rect(SliceContext *sc, ArithCoder *acoder, int x, int y, int width, int height)
Definition mss12.c:543
static void pixctx_reset(PixContext *ctx)
Definition mss12.c:120
av_cold int ff_mss12_decode_end(MSS12Context *c)
Definition mss12.c:693
static int decode_region(ArithCoder *acoder, uint8_t *dst, uint8_t *rgb_dst, int x, int y, int width, int height, ptrdiff_t stride, ptrdiff_t rgb_stride, PixContext *pctx, const uint32_t *pal)
Definition mss12.c:295
static av_cold void slicecontext_init(SliceContext *sc, int version, int full_model_syms)
Definition mss12.c:422
SplitMode
Definition mss12.c:34
@ SPLIT_HOR
Definition mss12.c:36
@ SPLIT_NONE
Definition mss12.c:37
@ SPLIT_VERT
Definition mss12.c:35
av_cold int ff_mss12_decode_init(MSS12Context *c, int version, SliceContext *sc1, SliceContext *sc2)
Definition mss12.c:581
static int decode_region_masked(MSS12Context const *c, ArithCoder *acoder, uint8_t *dst, ptrdiff_t stride, uint8_t *mask, ptrdiff_t mask_stride, int x, int y, int width, int height, PixContext *pctx)
Definition mss12.c:377
static void model_rescale_weights(Model *m)
Definition mss12.c:79
static av_always_inline int decode_pixel(ArithCoder *acoder, PixContext *pctx, uint8_t *ngb, int num_ngb, int any_ngb)
Definition mss12.c:160
static int decode_pixel_in_context(ArithCoder *acoder, PixContext *pctx, uint8_t *src, ptrdiff_t stride, int x, int y, int has_right)
Definition mss12.c:202
static const int sec_order_sizes[4]
Definition mss12.c:40
static av_cold void pixctx_init(PixContext *ctx, int cache_size, int full_model_syms, int special_initial_cache)
Definition mss12.c:141
void ff_mss12_model_update(Model *m, int val)
Definition mss12.c:96
static void copy_rectangles(MSS12Context const *c, int x, int y, int width, int height)
Definition mss12.c:327
static int decode_region_inter(SliceContext *sc, ArithCoder *acoder, int x, int y, int width, int height)
Definition mss12.c:504
void ff_mss12_slicecontext_reset(SliceContext *sc)
Definition mss12.c:437
static int motion_compensation(MSS12Context const *c, int x, int y, int width, int height)
Definition mss12.c:343
Common header for Microsoft Screen 1 and 2.
#define THRESH_HIGH
Definition mss12.h:38
#define THRESH_LOW
Definition mss12.h:37
#define THRESH_ADAPTIVE
Definition mss12.h:36
enum AVPixelFormat pix
Definition ohcodec.c:55
#define TOP
Definition scpr.c:33
main external API structure.
Definition avcodec.h:443
int width
picture width / height.
Definition avcodec.h:604
uint8_t * extradata
Out-of-band global headers that may be used by some codecs.
Definition avcodec.h:526
int extradata_size
Definition avcodec.h:527
int coded_width
Bitstream width / height, may be different from width/height e.g.
Definition avcodec.h:619
int overread
Definition mss12.h:50
int(* get_number)(struct ArithCoder *c, int n)
Definition mss12.h:57
int(* get_model_sym)(struct ArithCoder *c, Model *m)
Definition mss12.h:56
int keyframe
Definition mss12.h:89
Definition mss12.h:40
int16_t cum_prob[MODEL_MAX_SYMS+1]
Definition mss12.h:41
uint8_t idx2sym[MODEL_MAX_SYMS+1]
Definition mss12.h:43
int thr_weight
Definition mss12.h:45
int16_t weights[MODEL_MAX_SYMS+1]
Definition mss12.h:42
int threshold
Definition mss12.h:45
int num_syms
Definition mss12.h:44
uint8_t cache[12]
Definition mss12.h:62
Model cache_model
Definition mss12.h:63
Model full_model
Definition mss12.h:63
int cache_size
Definition mss12.h:61
Model sec_models[15][4]
Definition mss12.h:64
PixContext inter_pix_ctx
Definition mss12.h:74
Model split_mode
Definition mss12.h:73
Model edge_mode
Definition mss12.h:73
Model pivot
Definition mss12.h:73
Model inter_region
Definition mss12.h:72
PixContext intra_pix_ctx
Definition mss12.h:74
const struct MSS12Context * c
Definition mss12.h:71
Model intra_region
Definition mss12.h:72
Definition swscale.c:71
#define stride
#define av_malloc_array(a, b)
#define av_freep(p)
#define av_log(a,...)
#define src
Definition vp8dsp.c:248
static AVFormatContext * ctx
Definition movenc.c:49
#define height
Definition dsp.h:89
#define width
Definition dsp.h:89
uint8_t base
Definition vp3data.h:128
static double c[64]