散光400度是什么概念| tnt是什么意思| 左边头疼是什么原因| 箱变是什么| 治疗狐臭最好的方法是什么| 考级有什么用| 厅局级是什么级别| 荨麻疹要注意什么| 士官是什么级别| 肋下未及是什么意思| 甘草有什么作用| 什么是性瘾症| 下面干涩是什么原因导致的| 什么的兵马俑| baby是什么意思| 睡眠不好总做梦是什么原因| 什么情况要打破伤风| 高丽参适合什么人吃| 黄瓜片贴脸上有什么效果| 你干什么呢| 梦见狗咬人是什么预兆| 口腔溃疡可以吃什么药| 蒸鱼豉油什么时候放| 胃酸过多吃什么药| 玉米笋是什么| 刚出生的小猫吃什么| 拔智齿当天可以吃什么| 什么药治便秘| 陈醋和香醋有什么区别| 皇太后是皇上的什么人| 跑得最快的是什么生肖| 疤痕体质是什么原因| 八月初八是什么星座| 臭菜是什么菜| 肠道紊乱有什么症状| 口干是什么病| 五定是什么| 杨梅酒有什么功效| 生目念什么| fredperry是什么牌子| 脆肉鲩是什么鱼| 什么是潜意识| 牙龈肿痛用什么药好得快| 蛇遇猪就得哭什么意思| 凌寒独自开的凌是什么意思| 脚一直出汗是什么原因| 腿脚肿是什么原因| 相害是什么意思| gi食物是什么意思| 怀孕为什么会肚子痛| 屈原姓什么| 飧泄是什么意思| 一什么黑暗| 天然气什么味道| 医院门特是什么意思| cj什么意思| 睡觉经常做梦是什么原因| 膏肓是什么意思| 吹风样杂音见于什么病| 蒲公英泡水喝有什么副作用| 普拉提是什么意思| 太妃是皇上的什么人| 12月初是什么星座| 素女是什么意思| 人为什么会死| 肾囊肿有什么症状表现| 叉烧是什么肉做的| ad是什么缩写| 飞蚊症用什么滴眼液| 红豆和赤小豆有什么区别| 尿失禁吃什么药最好| 丫鬟是什么意思| 4朵玫瑰代表什么意思| 打招呼是什么意思| 1月25号什么星座| 尿里有红细胞是什么原因| 貂蝉是什么意思| 农历今天什么日子| 什么时候做nt| 承欢膝下是什么意思| 看月经挂什么科| 口周读什么| 手机壳为什么会发黄| 左眼皮一直跳什么预兆| 什么的围巾| 金匮肾气丸主治什么病| 521代表什么含义| 红豆泥是什么意思| 大腿根疼是什么原因| 12月5号是什么星座| 斗志昂扬是什么意思| 像什么| 序五行属什么| 小暑是什么时候| 左侧肋骨下面是什么器官| 女人叫床最好喊什么| 后人是什么意思| 子孙满堂是什么生肖| 别开生面是什么意思| 强龙不压地头蛇是什么生肖| 什么原因导致脱发| 这是什么石头| 咽炎要注意什么饮食| 面瘫是什么引起的| 马眼是什么| 冬菇有什么功效与作用| 菁是什么意思| 大象灰配什么颜色好看| 代谢慢的人吃什么有助于新陈代谢| 什么的嘴巴| 半套什么意思| 鸡胗是什么| 冰妹什么意思| hr是什么| 祎字五行属什么| 四件套包括什么| 无所不用其极什么意思| 为什么老被蚊子咬| 空窗期是什么意思| 坪效是什么意思| 狼吞虎咽什么意思| 样板间是什么意思| 皮肤干燥是什么原因| 辩证法是什么| 伤口溃烂不愈合用什么药| 电信诈骗是什么意思| 沉香有什么作用与功效| 彼岸花是什么花| 口腔溃疡用什么药治疗| 985什么意思| 德艺双馨是什么意思| 75年的兔是什么命| 脚脖子抽筋是什么原因| 节育环嵌顿是什么意思| 农历五月初五是什么节日| 去拉萨需要准备什么| 黑户是什么| 哔哩哔哩会员有什么用| 血尿酸偏高是什么原因| 暂时无法接通是什么意思| 肝不好吃什么药| 这什么| 天才是指什么生肖| 粘假牙用什么胶| 11月27日是什么星座| 什么是根管治疗牙齿| 北方五行属什么| 蛇属于什么动物| 筋膜炎是什么| 乙肝235阳性是什么意思| 安痛定又叫什么名字| 病是什么结构的字| p波代表什么| 眼睛感染用什么眼药水| 十月6号是什么星座| 蜂蜜不能和什么一起吃| 氨味是什么味道| 喉咙痛吃什么药好得最快| cybex是什么牌子| 冰妹是什么| 北极熊的毛是什么颜色的| 身上为什么会起湿疹| 1.15是什么星座| 脸黑的人适合穿什么颜色的衣服| 纯是什么意思| 蜂蜜吃有什么好处| 胆囊息肉是什么原因造成的| 超声波是什么| 感冒有黄痰是什么原因| 梓代表什么意思| 踩指压板有什么好处| 人生的意义是什么| 保底和底薪有什么区别| 青皮是什么皮| 戊土是什么土| 1984年属鼠的是什么命| 低压高什么症状| 头痛是什么原因造成的| 岂是什么意思| 11月1日什么星座| 哮喘是什么| 经血是什么血| 舌头上有裂纹是什么原因| 刚柔并济是什么意思| 尿酸高平时要注意什么| 西汉后面是什么朝代| 尿检白细胞阳性是什么意思| 阴毛的作用是什么| 罄竹难书是什么意思| 溃疡是什么意思| uma是什么意思| 血沉偏高是什么原因| 268是什么意思| 40什么意思| 惊鸿是什么意思| 肠胃不好吃什么药效果好| 小叶紫檀五行属什么| 凉瓜是什么瓜| 慧命是什么意思| 1977年属什么生肖| 疣是一种什么病| 什么人不能吃西洋参| 鲁班发明了什么东西| 呈味核苷酸二钠是什么| 老人喝什么牛奶比较好| ba是什么元素| 哕是什么意思| 什么水果是寒性的| 不完全性右束支阻滞是什么意思| 无什么无| 婴儿采足底血是查什么| hr是什么牌子| 避孕药叫什么名字| 人流后什么叫重体力活| 美女的胸长什么样| 丝状疣是什么| 医生属于什么编制| 红曲红是什么| 侍郎是什么官职| 什么是黄色视频| 脚底干燥是什么原因| 西安有什么玩的| 打磨工为什么没人干| 有什么好听的歌曲| 用什么泡脚可以脸上祛斑| 经常口臭的人是什么原因引起的| 狗狗感冒了是什么症状| 桑叶茶有什么好处| 尿频什么原因| 痔疮是什么东西| 延年益寿的益是什么意思| 锁舌是什么| 孩子长个子吃什么有利于长高| 什么的坐着| 一什么酒店| 达人是什么意思| 子宫肌瘤是什么症状| 老年人总睡觉是什么原因| 扁桃体结石有什么危害| wi-fi是什么意思| 灭吐灵又叫什么名字| 登革热是什么病| 乐子是什么意思| 清热燥湿是什么意思| 瓞是什么意思| 挂号是什么意思| 霉菌性阴道炎用什么药效果好| 文房四宝是什么| 硬不起吃什么药| 吃止痛药有什么副作用| 电泳是什么| 晨尿泡沫多是什么原因| 蜜獾为什么什么都不怕| 吃什么会拉肚子| 为什么怀孕会孕酮低| 什么食物含蛋白质多| 儿童牙龈肿痛吃什么药| 护理部是干什么的| 新疆人是什么民族| 什么是乳腺结节| 生不逢时什么意思| 蟹黄是螃蟹的什么东西| 什么花一年四季都开花| 梦见做春梦是什么意思| 百度

http://www.tibetinfor.com/lv/20170322-8610.html


Directory: ../../../ffmpeg/
File: src/libavcodec/sga.c
Date: 2025-08-04 00:43:16
Exec Total Coverage
Lines: 0 291 0.0%
Functions: 0 10 0.0%
Branches: 0 198 0.0%

Line Branch Exec Source
1 /*
2 * Copyright (c) 2021 Paul B Mahol
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 #include "libavutil/common.h"
22 #include "libavutil/mem.h"
23 #include "avcodec.h"
24 #include "get_bits.h"
25 #include "bytestream.h"
26 #include "codec_internal.h"
27 #include "decode.h"
28
29 #define PALDATA_FOLLOWS_TILEDATA 4
30 #define HAVE_COMPRESSED_TILEMAP 32
31 #define HAVE_TILEMAP 128
32
33 typedef struct SGAVideoContext {
34 GetByteContext gb;
35
36 int metadata_size;
37 int tiledata_size;
38 int tiledata_offset;
39 int tilemapdata_size;
40 int tilemapdata_offset;
41 int paldata_size;
42 int paldata_offset;
43 int palmapdata_offset;
44 int palmapdata_size;
45
46 int flags;
47 int nb_pal;
48 int nb_tiles;
49 int tiles_w, tiles_h;
50 int shift;
51 int plus;
52 int swap;
53
54 uint32_t pal[256];
55 uint8_t *tileindex_data;
56 unsigned tileindex_size;
57 uint8_t *palmapindex_data;
58 unsigned palmapindex_size;
59 uint8_t uncompressed[65536];
60 } SGAVideoContext;
61
62 static av_cold int sga_decode_init(AVCodecContext *avctx)
63 {
64 avctx->pix_fmt = AV_PIX_FMT_PAL8;
65 return 0;
66 }
67
68 static int decode_palette(GetByteContext *gb, uint32_t *pal)
69 {
70 GetBitContext gbit;
71
72 if (bytestream2_get_bytes_left(gb) < 18)
73 return AVERROR_INVALIDDATA;
74
75 memset(pal, 0, 16 * sizeof(*pal));
76 (void)init_get_bits8(&gbit, gb->buffer, 18);
77
78 for (int RGBIndex = 0; RGBIndex < 3; RGBIndex++) {
79 for (int index = 0; index < 16; index++) {
80 unsigned color = get_bits1(&gbit) << RGBIndex;
81 pal[15 - index] |= color << (5 + 16);
82 }
83 }
84
85 for (int RGBIndex = 0; RGBIndex < 3; RGBIndex++) {
86 for (int index = 0; index < 16; index++) {
87 unsigned color = get_bits1(&gbit) << RGBIndex;
88 pal[15 - index] |= color << (5 + 8);
89 }
90 }
91
92 for (int RGBIndex = 0; RGBIndex < 3; RGBIndex++) {
93 for (int index = 0; index < 16; index++) {
94 unsigned color = get_bits1(&gbit) << RGBIndex;
95 pal[15 - index] |= color << (5 + 0);
96 }
97 }
98
99 for (int index = 0; index < 16; index++)
100 pal[index] = (0xFFU << 24) | pal[index] | (pal[index] >> 3);
101
102 bytestream2_skip(gb, 18);
103
104 return 0;
105 }
106
107 static int decode_index_palmap(SGAVideoContext *s, AVFrame *frame)
108 {
109 const uint8_t *tt = s->tileindex_data;
110
111 for (int y = 0; y < s->tiles_h; y++) {
112 for (int x = 0; x < s->tiles_w; x++) {
113 int pal_idx = s->palmapindex_data[y * s->tiles_w + x] * 16;
114 uint8_t *dst = frame->data[0] + y * 8 * frame->linesize[0] + x * 8;
115
116 for (int yy = 0; yy < 8; yy++) {
117 for (int xx = 0; xx < 8; xx++)
118 dst[xx] = pal_idx + tt[xx];
119 tt += 8;
120
121 dst += frame->linesize[0];
122 }
123 }
124 }
125
126 return 0;
127 }
128
129 static int decode_index_tilemap(SGAVideoContext *s, AVFrame *frame)
130 {
131 GetByteContext *gb = &s->gb, gb2;
132
133 bytestream2_seek(gb, s->tilemapdata_offset, SEEK_SET);
134 if (bytestream2_get_bytes_left(gb) < s->tilemapdata_size)
135 return AVERROR_INVALIDDATA;
136
137 gb2 = *gb;
138
139 for (int y = 0; y < s->tiles_h; y++) {
140 for (int x = 0; x < s->tiles_w; x++) {
141 uint8_t tile[64];
142 int tilemap = bytestream2_get_be16u(&gb2);
143 int flip_x = (tilemap >> 11) & 1;
144 int flip_y = (tilemap >> 12) & 1;
145 int tindex = av_clip((tilemap & 511) - 1, 0, s->nb_tiles - 1);
146 const uint8_t *tt = s->tileindex_data + tindex * 64;
147 int pal_idx = ((tilemap >> 13) & 3) * 16;
148 uint8_t *dst = frame->data[0] + y * 8 * frame->linesize[0] + x * 8;
149
150 if (!flip_x && !flip_y) {
151 memcpy(tile, tt, 64);
152 } else if (flip_x && flip_y) {
153 for (int i = 0; i < 8; i++) {
154 for (int j = 0; j < 8; j++)
155 tile[i * 8 + j] = tt[(7 - i) * 8 + 7 - j];
156 }
157 } else if (flip_x) {
158 for (int i = 0; i < 8; i++) {
159 for (int j = 0; j < 8; j++)
160 tile[i * 8 + j] = tt[i * 8 + 7 - j];
161 }
162 } else {
163 for (int i = 0; i < 8; i++) {
164 for (int j = 0; j < 8; j++)
165 tile[i * 8 + j] = tt[(7 - i) * 8 + j];
166 }
167 }
168
169 for (int yy = 0; yy < 8; yy++) {
170 for (int xx = 0; xx < 8; xx++)
171 dst[xx] = pal_idx + tile[xx + yy * 8];
172
173 dst += frame->linesize[0];
174 }
175 }
176 }
177
178 return 0;
179 }
180
181 static int decode_index(SGAVideoContext *s, AVFrame *frame)
182 {
183 const uint8_t *src = s->tileindex_data;
184 uint8_t *dst = frame->data[0];
185
186 for (int y = 0; y < frame->height; y += 8) {
187 for (int x = 0; x < frame->width; x += 8) {
188 for (int yy = 0; yy < 8; yy++) {
189 for (int xx = 0; xx < 8; xx++)
190 dst[x + xx + yy * frame->linesize[0]] = src[xx];
191 src += 8;
192 }
193 }
194
195 dst += 8 * frame->linesize[0];
196 }
197
198 return 0;
199 }
200
201 static int lzss_decompress(AVCodecContext *avctx,
202 GetByteContext *gb, uint8_t *dst,
203 int dst_size, int shift, int plus)
204 {
205 int oi = 0;
206
207 while (bytestream2_get_bytes_left(gb) > 0 && oi < dst_size) {
208 uint16_t displace, header = bytestream2_get_be16(gb);
209 int count, offset;
210
211 for (int i = 0; i < 16; i++) {
212 switch (header >> 15) {
213 case 0:
214 if (oi + 2 < dst_size) {
215 dst[oi++] = bytestream2_get_byte(gb);
216 dst[oi++] = bytestream2_get_byte(gb);
217 }
218 break;
219 case 1:
220 displace = bytestream2_get_be16(gb);
221 count = displace >> shift;
222 offset = displace & ((1 << shift) - 1);
223
224 if (displace == 0) {
225 while (bytestream2_get_bytes_left(gb) > 0 &&
226 oi < dst_size)
227 dst[oi++] = bytestream2_get_byte(gb);
228 return oi;
229 }
230
231 count += plus;
232
233 if (offset <= 0)
234 offset = 1;
235 if (oi < offset || oi + count * 2 > dst_size)
236 return AVERROR_INVALIDDATA;
237 for (int j = 0; j < count * 2; j++) {
238 dst[oi] = dst[oi - offset];
239 oi++;
240 }
241 break;
242 }
243
244 header <<= 1;
245 }
246 }
247
248 return AVERROR_INVALIDDATA;
249 }
250
251 static int decode_palmapdata(AVCodecContext *avctx)
252 {
253 SGAVideoContext *s = avctx->priv_data;
254 const int bits = (s->nb_pal + 1) / 2;
255 GetByteContext *gb = &s->gb;
256 GetBitContext pm;
257 av_unused int ret;
258
259 bytestream2_seek(gb, s->palmapdata_offset, SEEK_SET);
260 if (bytestream2_get_bytes_left(gb) < s->palmapdata_size)
261 return AVERROR_INVALIDDATA;
262 ret = init_get_bits8(&pm, gb->buffer, s->palmapdata_size);
263 av_assert1(ret >= 0);
264
265 for (int y = 0; y < s->tiles_h; y++) {
266 uint8_t *dst = s->palmapindex_data + y * s->tiles_w;
267
268 for (int x = 0; x < s->tiles_w; x++)
269 dst[x] = get_bits(&pm, bits);
270
271 dst += s->tiles_w;
272 }
273
274 return 0;
275 }
276
277 static int decode_tiledata(AVCodecContext *avctx)
278 {
279 SGAVideoContext *s = avctx->priv_data;
280 GetByteContext *gb = &s->gb;
281 GetBitContext tm;
282 av_unused int ret;
283
284 bytestream2_seek(gb, s->tiledata_offset, SEEK_SET);
285 if (bytestream2_get_bytes_left(gb) < s->tiledata_size)
286 return AVERROR_INVALIDDATA;
287 ret = init_get_bits8(&tm, gb->buffer, s->tiledata_size);
288 av_assert1(ret >= 0);
289
290 for (int n = 0; n < s->nb_tiles; n++) {
291 uint8_t *dst = s->tileindex_data + n * 64;
292
293 for (int yy = 0; yy < 8; yy++) {
294 for (int xx = 0; xx < 8; xx++)
295 dst[xx] = get_bits(&tm, 4);
296
297 dst += 8;
298 }
299 }
300
301 for (int i = 0; i < s->nb_tiles && s->swap; i++) {
302 uint8_t *dst = s->tileindex_data + i * 64;
303
304 for (int j = 8; j < 64; j += 16) {
305 for (int k = 0; k < 8; k += 2)
306 FFSWAP(uint8_t, dst[j + k], dst[j+k+1]);
307 }
308 }
309
310 return 0;
311 }
312
313 static int sga_decode_frame(AVCodecContext *avctx, AVFrame *frame,
314 int *got_frame, AVPacket *avpkt)
315 {
316 SGAVideoContext *s = avctx->priv_data;
317 GetByteContext *gb = &s->gb;
318 int ret, type;
319
320 if (avpkt->size <= 14)
321 return AVERROR_INVALIDDATA;
322
323 s->flags = avpkt->data[8];
324 s->nb_pal = avpkt->data[9];
325 s->tiles_w = avpkt->data[10];
326 s->tiles_h = avpkt->data[11];
327
328 if (s->nb_pal > 4)
329 return AVERROR_INVALIDDATA;
330
331 if ((ret = ff_set_dimensions(avctx,
332 s->tiles_w * 8,
333 s->tiles_h * 8)) < 0)
334 return ret;
335
336 av_fast_padded_malloc(&s->tileindex_data, &s->tileindex_size,
337 avctx->width * avctx->height);
338 if (!s->tileindex_data)
339 return AVERROR(ENOMEM);
340
341 av_fast_padded_malloc(&s->palmapindex_data, &s->palmapindex_size,
342 s->tiles_w * s->tiles_h);
343 if (!s->palmapindex_data)
344 return AVERROR(ENOMEM);
345
346 if ((ret = ff_get_buffer(avctx, frame, 0)) < 0)
347 return ret;
348
349 bytestream2_init(gb, avpkt->data, avpkt->size);
350
351 type = bytestream2_get_byte(gb);
352 s->metadata_size = 12 + ((!!(s->flags & HAVE_TILEMAP)) * 2);
353 s->nb_tiles = s->flags & HAVE_TILEMAP ? AV_RB16(avpkt->data + 12) : s->tiles_w * s->tiles_h;
354 if (s->nb_tiles > s->tiles_w * s->tiles_h)
355 return AVERROR_INVALIDDATA;
356
357 av_log(avctx, AV_LOG_DEBUG, "type: %X flags: %X nb_tiles: %d\n", type, s->flags, s->nb_tiles);
358
359 switch (type) {
360 case 0xE7:
361 case 0xCB:
362 case 0xCD:
363 s->swap = 1;
364 s->shift = 12;
365 s->plus = 1;
366 break;
367 case 0xC9:
368 s->swap = 1;
369 s->shift = 13;
370 s->plus = 1;
371 break;
372 case 0xC8:
373 s->swap = 1;
374 s->shift = 13;
375 s->plus = 0;
376 break;
377 case 0xC7:
378 s->swap = 0;
379 s->shift = 13;
380 s->plus = 1;
381 break;
382 case 0xC6:
383 s->swap = 0;
384 s->shift = 13;
385 s->plus = 0;
386 break;
387 }
388
389 if (type == 0xE7) {
390 int offset = s->metadata_size, left;
391 int sizes[3];
392
393 bytestream2_seek(gb, s->metadata_size, SEEK_SET);
394
395 for (int i = 0; i < 3; i++)
396 sizes[i] = bytestream2_get_be16(gb);
397
398 for (int i = 0; i < 3; i++) {
399 int size = sizes[i];
400 int raw = size >> 15;
401
402 size &= (1 << 15) - 1;
403
404 if (raw) {
405 if (bytestream2_get_bytes_left(gb) < size)
406 return AVERROR_INVALIDDATA;
407
408 if (sizeof(s->uncompressed) - offset < size)
409 return AVERROR_INVALIDDATA;
410
411 memcpy(s->uncompressed + offset, gb->buffer, size);
412 bytestream2_skip(gb, size);
413 } else {
414 GetByteContext gb2;
415
416 if (bytestream2_get_bytes_left(gb) < size)
417 return AVERROR_INVALIDDATA;
418
419 bytestream2_init(&gb2, gb->buffer, size);
420 ret = lzss_decompress(avctx, &gb2, s->uncompressed + offset,
421 sizeof(s->uncompressed) - offset, s->shift, s->plus);
422 if (ret < 0)
423 return ret;
424 bytestream2_skip(gb, size);
425 size = ret;
426 }
427
428 offset += size;
429 }
430
431 left = bytestream2_get_bytes_left(gb);
432 if (sizeof(s->uncompressed) - offset < left)
433 return AVERROR_INVALIDDATA;
434
435 bytestream2_get_buffer(gb, s->uncompressed + offset, left);
436
437 offset += left;
438 bytestream2_init(gb, s->uncompressed, offset);
439 }
440
441 switch (type) {
442 case 0xCD:
443 case 0xCB:
444 case 0xC9:
445 case 0xC8:
446 case 0xC7:
447 case 0xC6:
448 bytestream2_seek(gb, s->metadata_size, SEEK_SET);
449 ret = lzss_decompress(avctx, gb, s->uncompressed + s->metadata_size,
450 sizeof(s->uncompressed) - s->metadata_size, s->shift, s->plus);
451 if (ret < 0)
452 return ret;
453 bytestream2_init(gb, s->uncompressed, ret + s->metadata_size);
454 case 0xE7:
455 case 0xC1:
456 s->tiledata_size = s->nb_tiles * 32;
457 s->paldata_size = s->nb_pal * 18;
458 s->tiledata_offset = s->flags & PALDATA_FOLLOWS_TILEDATA ? s->metadata_size : s->metadata_size + s->paldata_size;
459 s->paldata_offset = s->flags & PALDATA_FOLLOWS_TILEDATA ? s->metadata_size + s->tiledata_size : s->metadata_size;
460 s->palmapdata_offset = (s->flags & HAVE_TILEMAP) ? -1 : s->paldata_offset + s->paldata_size;
461 s->palmapdata_size = (s->flags & HAVE_TILEMAP) || s->nb_pal < 2 ? 0 : (s->tiles_w * s->tiles_h * ((s->nb_pal + 1) / 2) + 7) / 8;
462 s->tilemapdata_size = (s->flags & HAVE_TILEMAP) ? s->tiles_w * s->tiles_h * 2 : 0;
463 s->tilemapdata_offset = (s->flags & HAVE_TILEMAP) ? s->paldata_offset + s->paldata_size: -1;
464
465 bytestream2_seek(gb, s->paldata_offset, SEEK_SET);
466 for (int n = 0; n < s->nb_pal; n++) {
467 ret = decode_palette(gb, s->pal + 16 * n);
468 if (ret < 0)
469 return ret;
470 }
471
472 if (s->tiledata_size > 0) {
473 ret = decode_tiledata(avctx);
474 if (ret < 0)
475 return ret;
476 }
477
478 if (s->palmapdata_size > 0) {
479 ret = decode_palmapdata(avctx);
480 if (ret < 0)
481 return ret;
482 }
483
484 if (s->palmapdata_size > 0 && s->tiledata_size > 0) {
485 ret = decode_index_palmap(s, frame);
486 if (ret < 0)
487 return ret;
488 } else if (s->tilemapdata_size > 0 && s->tiledata_size > 0) {
489 ret = decode_index_tilemap(s, frame);
490 if (ret < 0)
491 return ret;
492 } else if (s->tiledata_size > 0) {
493 ret = decode_index(s, frame);
494 if (ret < 0)
495 return ret;
496 }
497 break;
498 default:
499 av_log(avctx, AV_LOG_ERROR, "Unknown type: %X\n", type);
500 return AVERROR_INVALIDDATA;
501 }
502
503 memcpy(frame->data[1], s->pal, AVPALETTE_SIZE);
504 frame->pict_type = AV_PICTURE_TYPE_I;
505 frame->flags |= AV_FRAME_FLAG_KEY;
506
507 *got_frame = 1;
508
509 return avpkt->size;
510 }
511
512 static av_cold int sga_decode_end(AVCodecContext *avctx)
513 {
514 SGAVideoContext *s = avctx->priv_data;
515
516 av_freep(&s->tileindex_data);
517 s->tileindex_size = 0;
518
519 av_freep(&s->palmapindex_data);
520 s->palmapindex_size = 0;
521
522 return 0;
523 }
524
525 const FFCodec ff_sga_decoder = {
526 .p.name = "sga",
527 CODEC_LONG_NAME("Digital Pictures SGA Video"),
528 .p.type = AVMEDIA_TYPE_VIDEO,
529 .p.id = AV_CODEC_ID_SGA_VIDEO,
530 .priv_data_size = sizeof(SGAVideoContext),
531 .init = sga_decode_init,
532 FF_CODEC_DECODE_CB(sga_decode_frame),
533 .close = sga_decode_end,
534 .p.capabilities = AV_CODEC_CAP_DR1,
535 };
536

怀孕脚浮肿是什么原因引起的 花甲是什么意思 结婚36年是什么婚 甲基苯丙胺是什么 走马观花的走什么意思
凤尾是什么菜 硒中毒有什么症状 幽门螺旋杆菌感染有什么症状 公积金缴存基数是什么意思 中元节是什么时候
儿童手指头脱皮什么原因引起的 胆在什么位置 肉什么结构 晨僵是什么症状 ein是什么意思
哺乳期感冒可以吃什么药 红细胞阳性是什么意思 zoom是什么意思 科员是什么职务 918是什么日子
小肠火吃什么药效果快hcv9jop3ns2r.cn 1月23日是什么星座hcv7jop7ns2r.cn 头晕眼睛模糊是什么原因hcv9jop5ns0r.cn 自字五行属什么hcv7jop9ns1r.cn 空调病是什么症状hcv9jop4ns9r.cn
子宫肌瘤是什么原因引起的hcv8jop1ns5r.cn 理发师代表什么生肖hcv9jop7ns0r.cn 上环什么时候去最合适hcv9jop7ns4r.cn 子宫前位后位有什么区别hcv9jop5ns0r.cn 免疫固定电泳查什么的hcv7jop7ns2r.cn
梦到前夫什么意思hcv7jop7ns3r.cn 20年是什么年hcv9jop1ns0r.cn 脚肿了是什么原因引起的96micro.com 忻字五行属什么hcv8jop8ns8r.cn 什么洗面奶好用hcv9jop8ns0r.cn
王羲之的儿子叫什么名字fenrenren.com 蒹葭苍苍是什么意思hcv9jop1ns8r.cn 4月22日什么星座zhongyiyatai.com 挑染什么颜色好看hcv9jop0ns0r.cn 清清什么zhongyiyatai.com
百度