X-Git-Url: https://git.sesse.net/?a=blobdiff_plain;f=libavcodec%2Fcook.c;h=6dec2566a73ec8c356d7148c5c303d6694a423a3;hb=43a6ca2c3d2fd3ebd262e08b249e57d6f0902aba;hp=59d3ef23f98daddd0419b300db6b5bef463ea3d4;hpb=4a291c90fe7f51eb32742a4a04cdaf144521334a;p=ffmpeg diff --git a/libavcodec/cook.c b/libavcodec/cook.c index 59d3ef23f98..6dec2566a73 100644 --- a/libavcodec/cook.c +++ b/libavcodec/cook.c @@ -136,7 +136,7 @@ typedef struct cook { AVLFG random_state; /* transform data */ - MDCTContext mdct_ctx; + FFTContext mdct_ctx; float* mlt_window; /* VLC data */ @@ -259,7 +259,7 @@ static av_cold int init_cook_mlt(COOKContext *q) { q->mlt_window[j] *= sqrt(2.0 / q->samples_per_channel); /* Initialize the MDCT. */ - if (ff_mdct_init(&q->mdct_ctx, av_log2(mlt_size)+1, 1)) { + if (ff_mdct_init(&q->mdct_ctx, av_log2(mlt_size)+1, 1, 1.0)) { av_free(q->mlt_window); return -1; } @@ -1008,6 +1008,15 @@ static int cook_decode_frame(AVCodecContext *avctx, /* estimate subpacket sizes */ q->subpacket[0].size = avctx->block_align; + for(i=1;inum_subpackets;i++){ + q->subpacket[i].size = 2 * buf[avctx->block_align - q->num_subpackets + i]; + q->subpacket[0].size -= q->subpacket[i].size + 1; + if (q->subpacket[0].size < 0) { + av_log(avctx,AV_LOG_DEBUG,"frame subpacket size total > avctx->block_align!\n"); + return -1; + } + } + /* decode supbackets */ *data_size = 0; for(i=0;inum_subpackets;i++){ @@ -1033,23 +1042,23 @@ static void dump_cook_context(COOKContext *q) //int i=0; #define PRINT(a,b) av_log(q->avctx,AV_LOG_ERROR," %s = %d\n", a, b); av_log(q->avctx,AV_LOG_ERROR,"COOKextradata\n"); - av_log(q->avctx,AV_LOG_ERROR,"cookversion=%x\n",q->cookversion); - if (q->cookversion > STEREO) { - PRINT("js_subband_start",q->js_subband_start); - PRINT("js_vlc_bits",q->js_vlc_bits); + av_log(q->avctx,AV_LOG_ERROR,"cookversion=%x\n",q->subpacket[0].cookversion); + if (q->subpacket[0].cookversion > STEREO) { + PRINT("js_subband_start",q->subpacket[0].js_subband_start); + PRINT("js_vlc_bits",q->subpacket[0].js_vlc_bits); } av_log(q->avctx,AV_LOG_ERROR,"COOKContext\n"); PRINT("nb_channels",q->nb_channels); PRINT("bit_rate",q->bit_rate); PRINT("sample_rate",q->sample_rate); - PRINT("samples_per_channel",q->samples_per_channel); - PRINT("samples_per_frame",q->samples_per_frame); - PRINT("subbands",q->subbands); + PRINT("samples_per_channel",q->subpacket[0].samples_per_channel); + PRINT("samples_per_frame",q->subpacket[0].samples_per_frame); + PRINT("subbands",q->subpacket[0].subbands); PRINT("random_state",q->random_state); - PRINT("js_subband_start",q->js_subband_start); - PRINT("log2_numvector_size",q->log2_numvector_size); - PRINT("numvector_size",q->numvector_size); - PRINT("total_subbands",q->total_subbands); + PRINT("js_subband_start",q->subpacket[0].js_subband_start); + PRINT("log2_numvector_size",q->subpacket[0].log2_numvector_size); + PRINT("numvector_size",q->subpacket[0].numvector_size); + PRINT("total_subbands",q->subpacket[0].total_subbands); } #endif @@ -1076,6 +1085,7 @@ static av_cold int cook_decode_init(AVCodecContext *avctx) const uint8_t *edata_ptr_end = edata_ptr + avctx->extradata_size; int extradata_size = avctx->extradata_size; int s = 0; + unsigned int channel_mask = 0; q->avctx = avctx; /* Take care of the codec specific extradata. */ @@ -1091,7 +1101,7 @@ static av_cold int cook_decode_init(AVCodecContext *avctx) q->bit_rate = avctx->bit_rate; /* Initialize RNG. */ - av_lfg_init(&q->random_state, ff_random_get_seed()); + av_lfg_init(&q->random_state, 0); while(edata_ptr < edata_ptr_end){ /* 8 for mono, 16 for stereo, ? for multichannel @@ -1131,9 +1141,10 @@ static av_cold int cook_decode_init(AVCodecContext *avctx) av_log(avctx,AV_LOG_DEBUG,"MONO\n"); break; case STEREO: - if (q->nb_channels != 1) + if (q->nb_channels != 1) { q->subpacket[s].bits_per_subpdiv = 1; - q->subpacket[s].num_channels = 2; + q->subpacket[s].num_channels = 2; + } av_log(avctx,AV_LOG_DEBUG,"STEREO\n"); break; case JOINT_STEREO: @@ -1155,8 +1166,25 @@ static av_cold int cook_decode_init(AVCodecContext *avctx) } break; case MC_COOK: - av_log(avctx,AV_LOG_ERROR,"MC_COOK not supported!\n"); - return -1; + av_log(avctx,AV_LOG_DEBUG,"MULTI_CHANNEL\n"); + if(extradata_size >= 4) + channel_mask |= q->subpacket[s].channel_mask = bytestream_get_be32(&edata_ptr); + + if(cook_count_channels(q->subpacket[s].channel_mask) > 1){ + q->subpacket[s].total_subbands = q->subpacket[s].subbands + q->subpacket[s].js_subband_start; + q->subpacket[s].joint_stereo = 1; + q->subpacket[s].num_channels = 2; + q->subpacket[s].samples_per_channel = q->subpacket[s].samples_per_frame >> 1; + + if (q->subpacket[s].samples_per_channel > 256) { + q->subpacket[s].log2_numvector_size = 6; + } + if (q->subpacket[s].samples_per_channel > 512) { + q->subpacket[s].log2_numvector_size = 7; + } + }else + q->subpacket[s].samples_per_channel = q->subpacket[s].samples_per_frame; + break; default: av_log(avctx,AV_LOG_ERROR,"Unknown Cook version, report sample!\n"); @@ -1196,6 +1224,10 @@ static av_cold int cook_decode_init(AVCodecContext *avctx) q->num_subpackets++; s++; + if (s > MAX_SUBPACKETS) { + av_log(avctx,AV_LOG_ERROR,"Too many subpackets > 5, report file!\n"); + return -1; + } } /* Generate tables */ init_pow2table(); @@ -1240,7 +1272,10 @@ static av_cold int cook_decode_init(AVCodecContext *avctx) } avctx->sample_fmt = SAMPLE_FMT_S16; - avctx->channel_layout = (avctx->channels==2) ? CH_LAYOUT_STEREO : CH_LAYOUT_MONO; + if (channel_mask) + avctx->channel_layout = channel_mask; + else + avctx->channel_layout = (avctx->channels==2) ? CH_LAYOUT_STEREO : CH_LAYOUT_MONO; #ifdef COOKDEBUG dump_cook_context(q);