* Copyright (c) 2003 Alex Beregszaszi
* Copyright (c) 2003-2004 Michael Niedermayer
*
+ * Support for external huffman table, various fixes (AVID workaround),
+ * aspecting, new decode_frame mechanism and apple mjpeg-b support
+ * by Alex Beregszaszi
+ *
* This file is part of FFmpeg.
*
* FFmpeg is free software; you can redistribute it and/or
* You should have received a copy of the GNU Lesser General Public
* License along with FFmpeg; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
- *
- * Support for external huffman table, various fixes (AVID workaround),
- * aspecting, new decode_frame mechanism and apple mjpeg-b support
- * by Alex Beregszaszi
*/
/**
ff_mjpeg_val_ac_chrominance, 251, 0, 1);
}
-int ff_mjpeg_decode_init(AVCodecContext *avctx)
+av_cold int ff_mjpeg_decode_init(AVCodecContext *avctx)
{
MJpegDecodeContext *s = avctx->priv_data;
else
s->avctx->pix_fmt = PIX_FMT_GRAY8;
break;
+ case 0x110000:
+ s->avctx->pix_fmt = PIX_FMT_GRAY8;
+ break;
+ case 0x121111:
+ s->avctx->pix_fmt = s->cs_itu601 ? PIX_FMT_YUV440P : PIX_FMT_YUVJ440P;
+ break;
case 0x211111:
case 0x221212:
s->avctx->pix_fmt = s->cs_itu601 ? PIX_FMT_YUV422P : PIX_FMT_YUVJ422P;
break;
- default:
case 0x221111:
s->avctx->pix_fmt = s->cs_itu601 ? PIX_FMT_YUV420P : PIX_FMT_YUVJ420P;
break;
+ default:
+ av_log(s->avctx, AV_LOG_ERROR, "Unhandled pixel format 0x%x\n", pix_fmt_id);
+ return -1;
}
if(s->ls){
if(s->nb_components > 1)
av_log(s->avctx, AV_LOG_ERROR, "get_buffer() failed\n");
return -1;
}
- s->picture.pict_type= I_TYPE;
+ s->picture.pict_type= FF_I_TYPE;
s->picture.key_frame= 1;
for(i=0; i<3; i++){
static int mjpeg_decode_scan(MJpegDecodeContext *s, int nb_components, int ss, int se, int Ah, int Al){
int i, mb_x, mb_y;
int EOBRUN = 0;
+ uint8_t* data[MAX_COMPONENTS];
+ int linesize[MAX_COMPONENTS];
if(Ah) return 0; /* TODO decode refinement planes too */
+
+ for(i=0; i < nb_components; i++) {
+ int c = s->comp_index[i];
+ data[c] = s->picture.data[c];
+ linesize[c]=s->linesize[c];
+ if(s->avctx->codec->id==CODEC_ID_AMV) {
+ //picture should be flipped upside-down for this codec
+ assert(!(s->avctx->flags & CODEC_FLAG_EMU_EDGE));
+ data[c] += (linesize[c] * (s->v_scount[i] * (8 * s->mb_height -((s->height/s->v_max)&7)) - 1 ));
+ linesize[c] *= -1;
+ }
+ }
+
for(mb_y = 0; mb_y < s->mb_height; mb_y++) {
for(mb_x = 0; mb_x < s->mb_width; mb_x++) {
if (s->restart_interval && !s->restart_count)
return -1;
}
// av_log(s->avctx, AV_LOG_DEBUG, "mb: %d %d processed\n", mb_y, mb_x);
- ptr = s->picture.data[c] +
- (((s->linesize[c] * (v * mb_y + y) * 8) +
+ ptr = data[c] +
+ (((linesize[c] * (v * mb_y + y) * 8) +
(h * mb_x + x) * 8) >> s->avctx->lowres);
if (s->interlaced && s->bottom_field)
- ptr += s->linesize[c] >> 1;
+ ptr += linesize[c] >> 1;
//av_log(NULL, AV_LOG_DEBUG, "%d %d %d %d %d %d %d %d \n", mb_x, mb_y, x, y, c, s->bottom_field, (v * mb_y + y) * 8, (h * mb_x + x) * 8);
if(!s->progressive)
- s->dsp.idct_put(ptr, s->linesize[c], s->block);
+ s->dsp.idct_put(ptr, linesize[c], s->block);
else
- s->dsp.idct_add(ptr, s->linesize[c], s->block);
+ s->dsp.idct_add(ptr, linesize[c], s->block);
if (++x == h) {
x = 0;
y++;
/* return the 8 bit start code value and update the search
state. Return -1 if no start code found */
-static int find_marker(uint8_t **pbuf_ptr, uint8_t *buf_end)
+static int find_marker(const uint8_t **pbuf_ptr, const uint8_t *buf_end)
{
- uint8_t *buf_ptr;
+ const uint8_t *buf_ptr;
unsigned int v, v2;
int val;
#ifdef DEBUG
int ff_mjpeg_decode_frame(AVCodecContext *avctx,
void *data, int *data_size,
- uint8_t *buf, int buf_size)
+ const uint8_t *buf, int buf_size)
{
MJpegDecodeContext *s = avctx->priv_data;
- uint8_t *buf_end, *buf_ptr;
+ const uint8_t *buf_end, *buf_ptr;
int start_code;
AVFrame *picture = data;
if (start_code < 0) {
goto the_end;
} else {
- av_log(avctx, AV_LOG_DEBUG, "marker=%x avail_size_in_buf=%d\n", start_code, buf_end - buf_ptr);
+ av_log(avctx, AV_LOG_DEBUG, "marker=%x avail_size_in_buf=%td\n", start_code, buf_end - buf_ptr);
if ((buf_end - buf_ptr) > s->buffer_size)
{
/* unescape buffer of SOS, use special treatment for JPEG-LS */
if (start_code == SOS && !s->ls)
{
- uint8_t *src = buf_ptr;
+ const uint8_t *src = buf_ptr;
uint8_t *dst = s->buffer;
while (src<buf_end)
}
init_get_bits(&s->gb, s->buffer, (dst - s->buffer)*8);
- av_log(avctx, AV_LOG_DEBUG, "escaping removed %d bytes\n",
+ av_log(avctx, AV_LOG_DEBUG, "escaping removed %td bytes\n",
(buf_end - buf_ptr) - (dst - s->buffer));
}
else if(start_code == SOS && s->ls){
- uint8_t *src = buf_ptr;
+ const uint8_t *src = buf_ptr;
uint8_t *dst = s->buffer;
int bit_count = 0;
int t = 0, b = 0;
*data_size = sizeof(AVFrame);
if(!s->lossless){
- picture->quality= FFMAX(FFMAX(s->qscale[0], s->qscale[1]), s->qscale[2]);
+ picture->quality= FFMAX3(s->qscale[0], s->qscale[1], s->qscale[2]);
picture->qstride= 0;
picture->qscale_table= s->qscale_table;
memset(picture->qscale_table, picture->quality, (s->width+15)/16);
}
}
the_end:
- av_log(avctx, AV_LOG_DEBUG, "mjpeg decode frame unused %d bytes\n", buf_end - buf_ptr);
+ av_log(avctx, AV_LOG_DEBUG, "mjpeg decode frame unused %td bytes\n", buf_end - buf_ptr);
// return buf_end - buf_ptr;
return buf_ptr - buf;
}
-int ff_mjpeg_decode_end(AVCodecContext *avctx)
+av_cold int ff_mjpeg_decode_end(AVCodecContext *avctx)
{
MJpegDecodeContext *s = avctx->priv_data;
int i, j;
ff_mjpeg_decode_end,
ff_mjpeg_decode_frame,
CODEC_CAP_DR1,
- NULL
+ NULL,
+ .long_name = "MJPEG (Motion JPEG)",
};
AVCodec thp_decoder = {
ff_mjpeg_decode_end,
ff_mjpeg_decode_frame,
CODEC_CAP_DR1,
- NULL
+ NULL,
+ .long_name = "Nintendo Gamecube THP video",
};