Mercurial > mplayer.hg
comparison libmpdemux/muxer_mpeg.c @ 18248:595d94213ad0
when muxing mpeg audio streams analyze the first 32 KB of data to obtain the most likely correct layer, otherwise every misdetection during parse_audio() will lead to wrong timestamps and loss of synchrony
author | nicodvb |
---|---|
date | Mon, 24 Apr 2006 14:04:10 +0000 |
parents | 01b1d174ec73 |
children | 00864f9fb5c0 |
comparison
equal
deleted
inserted
replaced
18247:3c1418657a36 | 18248:595d94213ad0 |
---|---|
167 unsigned char *pack; | 167 unsigned char *pack; |
168 int pack_offset, pes_offset, pes_set, payload_offset; | 168 int pack_offset, pes_offset, pes_set, payload_offset; |
169 int frames; | 169 int frames; |
170 int last_frame_rest; //the rest of the previous frame | 170 int last_frame_rest; //the rest of the previous frame |
171 int is_ready; | 171 int is_ready; |
172 int mpa_layer; | |
172 } muxer_headers_t; | 173 } muxer_headers_t; |
173 | 174 |
174 #define PULLDOWN32 1 | 175 #define PULLDOWN32 1 |
175 #define TELECINE_FILM2PAL 2 | 176 #define TELECINE_FILM2PAL 2 |
176 | 177 |
2038 mp_msg(MSGT_MUXER, MSGL_DBG2, "\r\nAdded frame, size: %u, idur: %llu, dts: %llu, pts: %llu, used: %u\r\n", len, idur, dts, pts, spriv->framebuf_used); | 2039 mp_msg(MSGT_MUXER, MSGL_DBG2, "\r\nAdded frame, size: %u, idur: %llu, dts: %llu, pts: %llu, used: %u\r\n", len, idur, dts, pts, spriv->framebuf_used); |
2039 | 2040 |
2040 return idx; | 2041 return idx; |
2041 } | 2042 } |
2042 | 2043 |
2044 static int analyze_mpa(muxer_stream_t *s) | |
2045 { | |
2046 int i = 0, len, max, chans, srate, spf, layer; | |
2047 int score[4] = {0, 0, 0, 0}; | |
2048 | |
2049 while(i < s->b_buffer_len + 3) | |
2050 { | |
2051 if(s->b_buffer[i] == 0xFF && ((s->b_buffer[i+1] & 0xE0) == 0xE0)) | |
2052 { | |
2053 len = mp_get_mp3_header(&(s->b_buffer[i]), &chans, &srate, &spf, &layer, NULL); | |
2054 if(len > 0 && (srate == s->wf->nSamplesPerSec) && (i + len <= s->b_buffer_len)) | |
2055 { | |
2056 score[layer]++; | |
2057 i += len; | |
2058 } | |
2059 } | |
2060 i++; | |
2061 } | |
2062 | |
2063 max = 0; | |
2064 layer = 2; | |
2065 for(i = 1; i <= 3; i++) | |
2066 { | |
2067 if(score[i] >= max) | |
2068 { | |
2069 max = score[i]; | |
2070 layer = i; | |
2071 } | |
2072 } | |
2073 | |
2074 return layer; //actual layer with the highest score | |
2075 } | |
2043 | 2076 |
2044 extern int aac_parse_frame(uint8_t *buf, int *srate, int *num); | 2077 extern int aac_parse_frame(uint8_t *buf, int *srate, int *num); |
2045 | 2078 |
2046 static int parse_audio(muxer_stream_t *s, int finalize, unsigned int *nf, double *timer, double delay, int drop) | 2079 static int parse_audio(muxer_stream_t *s, int finalize, unsigned int *nf, double *timer, double delay, int drop) |
2047 { | 2080 { |
2069 } | 2102 } |
2070 | 2103 |
2071 if(s->b_buffer[i] == 0xFF && ((s->b_buffer[i+1] & 0xE0) == 0xE0)) | 2104 if(s->b_buffer[i] == 0xFF && ((s->b_buffer[i+1] & 0xE0) == 0xE0)) |
2072 { | 2105 { |
2073 len = mp_get_mp3_header(&(s->b_buffer[i]), &chans, &srate, &spf, &layer, NULL); | 2106 len = mp_get_mp3_header(&(s->b_buffer[i]), &chans, &srate, &spf, &layer, NULL); |
2074 if(len > 0 && (srate == s->wf->nSamplesPerSec) && (i + len <= s->b_buffer_len)) | 2107 if(len > 0 && (srate == s->wf->nSamplesPerSec) && (i + len <= s->b_buffer_len) |
2108 && layer == spriv->mpa_layer) | |
2075 { | 2109 { |
2076 dur = (double) spf / (double) srate; | 2110 dur = (double) spf / (double) srate; |
2077 idur = (27000000ULL * spf) / srate; | 2111 idur = (27000000ULL * spf) / srate; |
2078 } | 2112 } |
2079 else | 2113 else |
2198 muxer_t *muxer = stream->muxer; | 2232 muxer_t *muxer = stream->muxer; |
2199 muxer_priv_t *priv = muxer->priv; | 2233 muxer_priv_t *priv = muxer->priv; |
2200 | 2234 |
2201 if(stream->type == MUXER_TYPE_AUDIO) | 2235 if(stream->type == MUXER_TYPE_AUDIO) |
2202 { | 2236 { |
2237 spriv->is_ready = 1; | |
2203 spriv->max_buffer_size = 4*1024; | 2238 spriv->max_buffer_size = 4*1024; |
2204 if(stream->wf->wFormatTag == AUDIO_A52) | 2239 if(stream->wf->wFormatTag == AUDIO_A52) |
2205 { | 2240 { |
2206 stream->ckid = be2me_32 (0x1bd); | 2241 stream->ckid = be2me_32 (0x1bd); |
2207 if(priv->is_genmpeg1 || priv->is_genmpeg2) | 2242 if(priv->is_genmpeg1 || priv->is_genmpeg2) |
2211 } | 2246 } |
2212 else if(stream->wf->wFormatTag == AUDIO_AAC1 || stream->wf->wFormatTag == AUDIO_AAC2) | 2247 else if(stream->wf->wFormatTag == AUDIO_AAC1 || stream->wf->wFormatTag == AUDIO_AAC2) |
2213 { | 2248 { |
2214 priv->use_psm = 1; | 2249 priv->use_psm = 1; |
2215 } | 2250 } |
2251 else if(stream->wf->wFormatTag == AUDIO_MP2 || stream->wf->wFormatTag == AUDIO_MP3) | |
2252 spriv->is_ready = 0; | |
2216 } | 2253 } |
2217 else //video | 2254 else //video |
2218 { | 2255 { |
2219 if(priv->is_dvd) | 2256 if(priv->is_dvd) |
2220 spriv->max_buffer_size = 232*1024; | 2257 spriv->max_buffer_size = 232*1024; |
2292 } else { // MUXER_TYPE_AUDIO | 2329 } else { // MUXER_TYPE_AUDIO |
2293 double fake_timer; | 2330 double fake_timer; |
2294 spriv->type = 0; | 2331 spriv->type = 0; |
2295 stream_format = s->wf->wFormatTag; | 2332 stream_format = s->wf->wFormatTag; |
2296 | 2333 |
2297 if(! spriv->vframes) | |
2298 mp_msg(MSGT_MUXER, MSGL_INFO, "AINIT: %.3lf\r\n", (double) spriv->last_pts/27000000.0f); | |
2299 if(s->b_buffer_size - s->b_buffer_len < len) | 2334 if(s->b_buffer_size - s->b_buffer_len < len) |
2300 { | 2335 { |
2301 s->b_buffer = realloc(s->b_buffer, len + s->b_buffer_len); | 2336 s->b_buffer = realloc(s->b_buffer, len + s->b_buffer_len); |
2302 if(s->b_buffer == NULL) | 2337 if(s->b_buffer == NULL) |
2303 { | 2338 { |
2309 mp_msg(MSGT_MUXER, MSGL_DBG2, "REALLOC(%d) bytes to AUDIO backbuffer\n", s->b_buffer_size); | 2344 mp_msg(MSGT_MUXER, MSGL_DBG2, "REALLOC(%d) bytes to AUDIO backbuffer\n", s->b_buffer_size); |
2310 } | 2345 } |
2311 memcpy(&(s->b_buffer[s->b_buffer_ptr + s->b_buffer_len]), s->buffer, len); | 2346 memcpy(&(s->b_buffer[s->b_buffer_ptr + s->b_buffer_len]), s->buffer, len); |
2312 s->b_buffer_len += len; | 2347 s->b_buffer_len += len; |
2313 | 2348 |
2349 if(!spriv->is_ready) | |
2350 { | |
2351 if(s->b_buffer_len >= 32*1024) | |
2352 { | |
2353 spriv->mpa_layer = analyze_mpa(s); | |
2354 spriv->is_ready = 1; | |
2355 } | |
2356 } | |
2357 else | |
2358 { | |
2314 parse_audio(s, 0, &nf, &fake_timer, priv->init_adelay, priv->drop); | 2359 parse_audio(s, 0, &nf, &fake_timer, priv->init_adelay, priv->drop); |
2315 spriv->vframes += nf; | 2360 spriv->vframes += nf; |
2316 sz = max(len, 2 * priv->packet_size); | 2361 sz = max(len, 2 * priv->packet_size); |
2362 if(! spriv->vframes) | |
2363 mp_msg(MSGT_MUXER, MSGL_INFO, "AINIT: %.3lf\r\n", (double) spriv->last_pts/27000000.0f); | |
2364 } | |
2317 } | 2365 } |
2318 | 2366 |
2319 | 2367 |
2320 if(spriv->psm_fixed == 0) { | 2368 if(spriv->psm_fixed == 0) { |
2321 add_to_psm(priv, spriv->id, stream_format); | 2369 add_to_psm(priv, spriv->id, stream_format); |