You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

473 lines
14KB

  1. /*
  2. * Kodak PhotoCD (a.k.a. ImagePac) image decoder
  3. *
  4. * Copyright (c) 1996-2002 Gerd Knorr
  5. * Copyright (c) 2010 Kenneth Vermeirsch
  6. * Copyright (c) 2020 Paul B Mahol
  7. *
  8. * This file is part of FFmpeg.
  9. *
  10. * FFmpeg is free software; you can redistribute it and/or
  11. * modify it under the terms of the GNU Lesser General Public
  12. * License as published by the Free Software Foundation; either
  13. * version 2.1 of the License, or (at your option) any later version.
  14. *
  15. * FFmpeg is distributed in the hope that it will be useful,
  16. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  17. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  18. * Lesser General Public License for more details.
  19. *
  20. * You should have received a copy of the GNU Lesser General Public
  21. * License along with FFmpeg; if not, write to the Free Software
  22. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
  23. */
  24. /**
  25. * @file
  26. * Kodak PhotoCD (a.k.a. ImagePac) image decoder
  27. *
  28. * Supports resolutions up to 3072x2048.
  29. */
  30. #define CACHED_BITSTREAM_READER !ARCH_X86_32
  31. #include "libavutil/avassert.h"
  32. #include "libavutil/intreadwrite.h"
  33. #include "libavutil/opt.h"
  34. #include "avcodec.h"
  35. #include "bytestream.h"
  36. #include "get_bits.h"
  37. #include "internal.h"
  38. #include "thread.h"
  39. typedef struct PhotoCDContext {
  40. AVClass *class;
  41. int lowres;
  42. GetByteContext gb;
  43. int thumbnails; //* number of thumbnails; 0 for normal image */
  44. int resolution;
  45. int orientation;
  46. int streampos;
  47. uint8_t bits[256];
  48. uint16_t codes[256];
  49. uint8_t syms[256];
  50. VLC vlc[3];
  51. } PhotoCDContext;
  52. typedef struct ImageInfo {
  53. uint32_t start;
  54. uint16_t width, height;
  55. } ImageInfo;
  56. static const ImageInfo img_info[6] = {
  57. {8192, 192, 128},
  58. {47104, 384, 256},
  59. {196608, 768, 512},
  60. {0, 1536, 1024},
  61. {0, 3072, 2048},
  62. {0, 6144, 4096},
  63. };
  64. static av_noinline void interp_lowres(PhotoCDContext *s, AVFrame *picture,
  65. int width, int height)
  66. {
  67. GetByteContext *gb = &s->gb;
  68. int start = s->streampos + img_info[2].start;
  69. uint8_t *ptr, *ptr1, *ptr2;
  70. uint8_t *dst;
  71. int fill;
  72. ptr = picture->data[0];
  73. ptr1 = picture->data[1];
  74. ptr2 = picture->data[2];
  75. bytestream2_seek(gb, start, SEEK_SET);
  76. for (int y = 0; y < height; y += 2) {
  77. dst = ptr;
  78. for (int x = 0; x < width - 1; x++) {
  79. fill = bytestream2_get_byte(gb);
  80. *(dst++) = fill;
  81. *(dst++) = (fill + bytestream2_peek_byte(gb) + 1) >> 1;
  82. }
  83. fill = bytestream2_get_byte(gb);
  84. *(dst++) = fill;
  85. *(dst++) = fill;
  86. ptr += picture->linesize[0] << 1;
  87. dst = ptr;
  88. for (int x = 0; x < width - 1; x++) {
  89. fill = bytestream2_get_byte(gb);
  90. *(dst++) = fill;
  91. *(dst++) = (fill + bytestream2_peek_byte(gb) + 1) >> 1;
  92. }
  93. fill = bytestream2_get_byte(gb);
  94. *(dst++) = fill;
  95. *(dst++) = fill;
  96. ptr += picture->linesize[0] << 1;
  97. dst = ptr1;
  98. for (int x = 0; x < (width >> 1) - 1; x++) {
  99. fill = bytestream2_get_byte(gb);
  100. *(dst++) = fill;
  101. *(dst++) = (fill + bytestream2_peek_byte(gb) + 1) >> 1;
  102. }
  103. fill = bytestream2_get_byte(gb);
  104. *(dst++) = fill;
  105. *(dst++) = fill;
  106. ptr1 += picture->linesize[1] << 1;
  107. dst = ptr2;
  108. for (int x = 0; x < (width >> 1) - 1; x++) {
  109. fill = bytestream2_get_byte(gb);
  110. *(dst++) = fill;
  111. *(dst++) = (fill + bytestream2_peek_byte(gb) + 1) >> 1;
  112. }
  113. fill = bytestream2_get_byte(gb);
  114. *(dst++) = fill;
  115. *(dst++) = fill;
  116. ptr2 += picture->linesize[2] << 1;
  117. }
  118. s->streampos += bytestream2_tell(gb) - start;
  119. }
  120. static av_noinline void interp_lines(uint8_t *ptr, int linesize,
  121. int width, int height)
  122. {
  123. const uint8_t *src1;
  124. uint8_t *dst;
  125. int x;
  126. for (int y = 0; y < height - 2; y += 2) {
  127. const uint8_t *src1 = ptr;
  128. uint8_t *dst = ptr + linesize;
  129. const uint8_t *src2 = dst + linesize;
  130. for (x = 0; x < width - 2; x += 2) {
  131. dst[x] = (src1[x] + src2[x] + 1) >> 1;
  132. dst[x + 1] = (src1[x] + src2[x] + src1[x + 2] + src2[x + 2] + 2) >> 2;
  133. }
  134. dst[x] = dst[x + 1] = (src1[x] + src2[x] + 1) >> 1;
  135. ptr += linesize << 1;
  136. }
  137. src1 = ptr;
  138. dst = ptr + linesize;
  139. for (x = 0; x < width - 2; x += 2) {
  140. dst[x] = src1[x];
  141. dst[x + 1] = (src1[x] + src1[x + 2] + 1) >> 1;
  142. }
  143. dst[x] = dst[x + 1] = src1[x];
  144. }
  145. static av_noinline void interp_pixels(uint8_t *ptr, int linesize,
  146. int width, int height)
  147. {
  148. for (int y = height - 2; y >= 0; y -= 2) {
  149. const uint8_t *src = ptr + (y >> 1) * linesize;
  150. uint8_t *dst = ptr + y * linesize;
  151. dst[width - 2] = dst[width - 1] = src[(width >> 1) - 1];
  152. for (int x = width - 4; x >= 0; x -= 2) {
  153. dst[x] = src[x >> 1];
  154. dst[x + 1] = (src[x >> 1] + src[(x >> 1) + 1] + 1) >> 1;
  155. }
  156. }
  157. }
  158. static av_noinline int read_hufftable(AVCodecContext *avctx, VLC *vlc)
  159. {
  160. PhotoCDContext *s = avctx->priv_data;
  161. GetByteContext *gb = &s->gb;
  162. int start = s->streampos;
  163. int count, ret;
  164. bytestream2_seek(gb, start, SEEK_SET);
  165. count = bytestream2_get_byte(gb) + 1;
  166. if (bytestream2_get_bytes_left(gb) < count * 4)
  167. return AVERROR_INVALIDDATA;
  168. for (int j = 0; j < count; j++) {
  169. const int bit = bytestream2_get_byteu(gb) + 1;
  170. const int code = bytestream2_get_be16u(gb);
  171. const int sym = bytestream2_get_byteu(gb);
  172. if (bit > 16)
  173. return AVERROR_INVALIDDATA;
  174. s->bits[j] = bit;
  175. s->codes[j] = code >> (16 - bit);
  176. s->syms[j] = sym;
  177. }
  178. ff_free_vlc(vlc);
  179. ret = ff_init_vlc_sparse(vlc, 12, count,
  180. s->bits, sizeof(*s->bits), sizeof(*s->bits),
  181. s->codes, sizeof(*s->codes), sizeof(*s->codes),
  182. s->syms, sizeof(*s->syms), sizeof(*s->syms), 0);
  183. s->streampos = bytestream2_tell(gb);
  184. return ret;
  185. }
  186. static av_noinline int decode_huff(AVCodecContext *avctx, AVFrame *frame,
  187. int target_res, int curr_res)
  188. {
  189. PhotoCDContext *s = avctx->priv_data;
  190. GetBitContext g;
  191. GetByteContext *gb = &s->gb;
  192. int ret, y = 0, type, height;
  193. int start = s->streampos;
  194. unsigned shiftreg;
  195. const int scaling = target_res - curr_res;
  196. const uint8_t type2idx[] = { 0, 0xff, 1, 2 };
  197. bytestream2_seek(gb, start, SEEK_SET);
  198. ret = init_get_bits8(&g, gb->buffer, bytestream2_get_bytes_left(gb));
  199. if (ret < 0)
  200. return ret;
  201. height = img_info[curr_res].height;
  202. while (y < height) {
  203. uint8_t *data;
  204. int x2, idx;
  205. for (; get_bits_left(&g) > 0;) {
  206. if ((show_bits(&g, 24) & 0xfff000) == 0xfff000)
  207. break;
  208. skip_bits(&g, 8);
  209. }
  210. shiftreg = show_bits_long(&g, 32) & 0xffffff00;
  211. while (shiftreg != 0xfffffe00) {
  212. if (get_bits_left(&g) <= 0)
  213. return AVERROR_INVALIDDATA;
  214. skip_bits(&g, 1);
  215. shiftreg = show_bits_long(&g, 32) & 0xffffff00;
  216. }
  217. skip_bits(&g, 16);
  218. y = show_bits_long(&g, 23) & 0x1fff;
  219. skip_bits(&g, 8);
  220. if (y >= height)
  221. break;
  222. type = get_bits(&g, 2);
  223. skip_bits(&g, 14);
  224. if (type == 1)
  225. return AVERROR_INVALIDDATA;
  226. idx = type2idx[type];
  227. data = frame->data[idx] + (y >> !!idx) * frame->linesize[idx];
  228. x2 = avctx->width >> (scaling + !!idx);
  229. for (int x = 0; x < x2; x++) {
  230. int m;
  231. if (get_bits_left(&g) <= 0)
  232. return AVERROR_INVALIDDATA;
  233. m = get_vlc2(&g, s->vlc[idx].table, s->vlc[idx].bits, 2);
  234. if (m < 0)
  235. return AVERROR_INVALIDDATA;
  236. m = sign_extend(m, 8);
  237. data[x] = av_clip_uint8(data[x] + m);
  238. }
  239. }
  240. s->streampos += (get_bits_count(&g) + 7) >> 3;
  241. s->streampos = (s->streampos + 0x6000 + 2047) & ~0x7ff;
  242. return 0;
  243. }
  244. static int photocd_decode_frame(AVCodecContext *avctx, void *data,
  245. int *got_frame, AVPacket *avpkt)
  246. {
  247. PhotoCDContext *s = avctx->priv_data;
  248. ThreadFrame frame = { .f = data };
  249. const uint8_t *buf = avpkt->data;
  250. GetByteContext *gb = &s->gb;
  251. AVFrame *p = data;
  252. uint8_t *ptr, *ptr1, *ptr2;
  253. int ret;
  254. if (avpkt->size < img_info[0].start)
  255. return AVERROR_INVALIDDATA;
  256. if (!memcmp("PCD_OPA", buf, 7)) {
  257. s->thumbnails = AV_RL16(buf + 10);
  258. av_log(avctx, AV_LOG_WARNING, "this is a thumbnails file, "
  259. "reading first thumbnail only\n");
  260. } else if (avpkt->size < 786432) {
  261. return AVERROR_INVALIDDATA;
  262. } else if (memcmp("PCD_IPI", buf + 0x800, 7)) {
  263. return AVERROR_INVALIDDATA;
  264. }
  265. s->orientation = s->thumbnails ? buf[12] & 3 : buf[0x48] & 3;
  266. if (s->thumbnails)
  267. s->resolution = 0;
  268. else if (avpkt->size <= 788480)
  269. s->resolution = 2;
  270. else
  271. s->resolution = av_clip(4 - s->lowres, 0, 4);
  272. avctx->width = img_info[s->resolution].width;
  273. avctx->height = img_info[s->resolution].height;
  274. if ((ret = ff_thread_get_buffer(avctx, &frame, 0)) < 0)
  275. return ret;
  276. p->pict_type = AV_PICTURE_TYPE_I;
  277. p->key_frame = 1;
  278. bytestream2_init(gb, avpkt->data, avpkt->size);
  279. if (s->resolution < 3) {
  280. ptr = p->data[0];
  281. ptr1 = p->data[1];
  282. ptr2 = p->data[2];
  283. if (s->thumbnails)
  284. bytestream2_seek(gb, 10240, SEEK_SET);
  285. else
  286. bytestream2_seek(gb, img_info[s->resolution].start, SEEK_SET);
  287. for (int y = 0; y < avctx->height; y += 2) {
  288. bytestream2_get_buffer(gb, ptr, avctx->width);
  289. ptr += p->linesize[0];
  290. bytestream2_get_buffer(gb, ptr, avctx->width);
  291. ptr += p->linesize[0];
  292. bytestream2_get_buffer(gb, ptr1, avctx->width >> 1);
  293. ptr1 += p->linesize[1];
  294. bytestream2_get_buffer(gb, ptr2, avctx->width >> 1);
  295. ptr2 += p->linesize[2];
  296. }
  297. } else {
  298. s->streampos = 0;
  299. ptr = p->data[0];
  300. ptr1 = p->data[1];
  301. ptr2 = p->data[2];
  302. interp_lowres(s, p, img_info[2].width, img_info[2].height);
  303. interp_lines(ptr1, p->linesize[1], img_info[2].width, img_info[2].height);
  304. interp_lines(ptr2, p->linesize[2], img_info[2].width, img_info[2].height);
  305. if (s->resolution == 4) {
  306. interp_pixels(ptr1, p->linesize[1], img_info[3].width, img_info[3].height);
  307. interp_lines (ptr1, p->linesize[1], img_info[3].width, img_info[3].height);
  308. interp_pixels(ptr2, p->linesize[2], img_info[3].width, img_info[3].height);
  309. interp_lines (ptr2, p->linesize[2], img_info[3].width, img_info[3].height);
  310. }
  311. interp_lines(ptr, p->linesize[0], img_info[3].width, img_info[3].height);
  312. s->streampos = 0xc2000;
  313. for (int n = 0; n < 3; n++) {
  314. if ((ret = read_hufftable(avctx, &s->vlc[n])) < 0)
  315. return ret;
  316. }
  317. s->streampos = (s->streampos + 2047) & ~0x3ff;
  318. if (decode_huff(avctx, p, s->resolution, 3) < 0)
  319. return AVERROR_INVALIDDATA;
  320. if (s->resolution == 4) {
  321. interp_pixels(ptr, p->linesize[0], img_info[4].width, img_info[4].height);
  322. interp_lines (ptr, p->linesize[0], img_info[4].width, img_info[4].height);
  323. for (int n = 0; n < 3; n++) {
  324. if ((ret = read_hufftable(avctx, &s->vlc[n])) < 0)
  325. return ret;
  326. }
  327. s->streampos = (s->streampos + 2047) & ~0x3ff;
  328. if (decode_huff(avctx, p, 4, 4) < 0)
  329. return AVERROR_INVALIDDATA;
  330. }
  331. }
  332. {
  333. ptr1 = p->data[1];
  334. ptr2 = p->data[2];
  335. for (int y = 0; y < avctx->height >> 1; y++) {
  336. for (int x = 0; x < avctx->width >> 1; x++) {
  337. ptr1[x] = av_clip_uint8(ptr1[x] - 28);
  338. ptr2[x] = av_clip_uint8(ptr2[x] - 9);
  339. }
  340. ptr1 += p->linesize[1];
  341. ptr2 += p->linesize[2];
  342. }
  343. }
  344. *got_frame = 1;
  345. return 0;
  346. }
  347. static av_cold int photocd_decode_init(AVCodecContext *avctx)
  348. {
  349. avctx->pix_fmt = AV_PIX_FMT_YUV420P;
  350. avctx->colorspace = AVCOL_SPC_BT709;
  351. avctx->color_primaries = AVCOL_PRI_BT709;
  352. avctx->color_trc = AVCOL_TRC_IEC61966_2_1;
  353. avctx->color_range = AVCOL_RANGE_JPEG;
  354. return 0;
  355. }
  356. static av_cold int photocd_decode_close(AVCodecContext *avctx)
  357. {
  358. PhotoCDContext *s = avctx->priv_data;
  359. for (int i = 0; i < 3; i++)
  360. ff_free_vlc(&s->vlc[i]);
  361. return 0;
  362. }
  363. #define OFFSET(x) offsetof(PhotoCDContext, x)
  364. #define VD AV_OPT_FLAG_VIDEO_PARAM | AV_OPT_FLAG_DECODING_PARAM
  365. static const AVOption options[] = {
  366. { "lowres", "Lower the decoding resolution by a power of two",
  367. OFFSET(lowres), AV_OPT_TYPE_INT, { .i64 = 0 }, 0, 4, VD },
  368. { NULL },
  369. };
  370. static const AVClass photocd_class = {
  371. .class_name = "photocd",
  372. .item_name = av_default_item_name,
  373. .option = options,
  374. .version = LIBAVUTIL_VERSION_INT,
  375. };
  376. AVCodec ff_photocd_decoder = {
  377. .name = "photocd",
  378. .type = AVMEDIA_TYPE_VIDEO,
  379. .id = AV_CODEC_ID_PHOTOCD,
  380. .priv_data_size = sizeof(PhotoCDContext),
  381. .priv_class = &photocd_class,
  382. .init = photocd_decode_init,
  383. .close = photocd_decode_close,
  384. .decode = photocd_decode_frame,
  385. .capabilities = AV_CODEC_CAP_DR1 | AV_CODEC_CAP_FRAME_THREADS,
  386. .long_name = NULL_IF_CONFIG_SMALL("Kodak Photo CD"),
  387. };