1 /*****************************************************************************
3 *****************************************************************************
4 * Copyright (C) 2011-2015 L-SMASH project
6 * Authors: Yusuke Nakamura <muken.the.vfrmaniac@gmail.com>
8 * Permission to use, copy, modify, and/or distribute this software for any
9 * purpose with or without fee is hereby granted, provided that the above
10 * copyright notice and this permission notice appear in all copies.
12 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
13 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
14 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
15 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
16 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
17 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
18 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
19 *****************************************************************************/
21 /* This file is available under an ISC license. */
23 #include "common/internal.h" /* must be placed first */
27 #define LSMASH_IMPORTER_INTERNAL
30 /***************************************************************************
32 ETSI TS 102 366 V1.2.1 (2008-08)
33 ***************************************************************************/
34 #include "codecs/a52.h"
36 #define AC3_SAMPLE_DURATION 1536 /* 256 (samples per audio block) * 6 (audio blocks) */
41 uint64_t next_frame_pos
;
43 uint8_t buffer
[AC3_MAX_SYNCFRAME_LENGTH
];
47 static void remove_ac3_importer( ac3_importer_t
*ac3_imp
)
51 lsmash_bits_cleanup( ac3_imp
->info
.bits
);
52 lsmash_free( ac3_imp
);
55 static ac3_importer_t
*create_ac3_importer( importer_t
*importer
)
57 ac3_importer_t
*ac3_imp
= (ac3_importer_t
*)lsmash_malloc_zero( sizeof(ac3_importer_t
) );
60 ac3_imp
->info
.bits
= lsmash_bits_create( importer
->bs
);
61 if( !ac3_imp
->info
.bits
)
63 lsmash_free( ac3_imp
);
69 static void ac3_importer_cleanup( importer_t
*importer
)
71 debug_if( importer
&& importer
->info
)
72 remove_ac3_importer( importer
->info
);
75 static const uint32_t ac3_frame_size_table
[19][3] =
99 static lsmash_audio_summary_t
*ac3_create_summary( ac3_info_t
*info
)
101 lsmash_audio_summary_t
*summary
= (lsmash_audio_summary_t
*)lsmash_create_summary( LSMASH_SUMMARY_TYPE_AUDIO
);
104 lsmash_ac3_specific_parameters_t
*param
= &info
->dac3_param
;
105 lsmash_codec_specific_t
*cs
= lsmash_create_codec_specific_data( LSMASH_CODEC_SPECIFIC_DATA_TYPE_ISOM_AUDIO_AC_3
,
106 LSMASH_CODEC_SPECIFIC_FORMAT_UNSTRUCTURED
);
109 lsmash_cleanup_summary( (lsmash_summary_t
*)summary
);
112 cs
->data
.unstructured
= lsmash_create_ac3_specific_info( &info
->dac3_param
, &cs
->size
);
113 if( !cs
->data
.unstructured
114 || lsmash_add_entry( &summary
->opaque
->list
, cs
) < 0 )
116 lsmash_cleanup_summary( (lsmash_summary_t
*)summary
);
117 lsmash_destroy_codec_specific_data( cs
);
120 summary
->sample_type
= ISOM_CODEC_TYPE_AC_3_AUDIO
;
121 summary
->max_au_length
= AC3_MAX_SYNCFRAME_LENGTH
;
122 summary
->aot
= MP4A_AUDIO_OBJECT_TYPE_NULL
; /* no effect */
123 summary
->frequency
= ac3_get_sample_rate( param
);
124 summary
->channels
= ac3_get_channel_count( param
);
125 summary
->sample_size
= 16; /* no effect */
126 summary
->samples_in_frame
= AC3_SAMPLE_DURATION
;
127 summary
->sbr_mode
= MP4A_AAC_SBR_NOT_SPECIFIED
; /* no effect */
131 static int ac3_compare_specific_param( lsmash_ac3_specific_parameters_t
*a
, lsmash_ac3_specific_parameters_t
*b
)
133 return (a
->fscod
!= b
->fscod
)
134 || (a
->bsid
!= b
->bsid
)
135 || (a
->bsmod
!= b
->bsmod
)
136 || (a
->acmod
!= b
->acmod
)
137 || (a
->lfeon
!= b
->lfeon
)
138 || ((a
->frmsizecod
>> 1) != (b
->frmsizecod
>> 1));
141 static int ac3_buffer_frame( uint8_t *buffer
, lsmash_bs_t
*bs
)
143 uint64_t remain_size
= lsmash_bs_get_remaining_buffer_size( bs
);
144 if( remain_size
< AC3_MAX_SYNCFRAME_LENGTH
)
146 int err
= lsmash_bs_read( bs
, bs
->buffer
.max_size
);
149 remain_size
= lsmash_bs_get_remaining_buffer_size( bs
);
151 uint64_t copy_size
= LSMASH_MIN( remain_size
, AC3_MAX_SYNCFRAME_LENGTH
);
152 memcpy( buffer
, lsmash_bs_get_buffer_data( bs
), copy_size
);
156 static int ac3_importer_get_accessunit( importer_t
*importer
, uint32_t track_number
, lsmash_sample_t
**p_sample
)
158 if( !importer
->info
)
159 return LSMASH_ERR_NAMELESS
;
160 if( track_number
!= 1 )
161 return LSMASH_ERR_FUNCTION_PARAM
;
162 lsmash_audio_summary_t
*summary
= (lsmash_audio_summary_t
*)lsmash_get_entry_data( importer
->summaries
, track_number
);
164 return LSMASH_ERR_NAMELESS
;
165 ac3_importer_t
*ac3_imp
= (ac3_importer_t
*)importer
->info
;
166 ac3_info_t
*info
= &ac3_imp
->info
;
167 importer_status current_status
= importer
->status
;
168 if( current_status
== IMPORTER_ERROR
)
169 return LSMASH_ERR_NAMELESS
;
170 if( current_status
== IMPORTER_EOF
)
172 lsmash_ac3_specific_parameters_t
*param
= &info
->dac3_param
;
173 uint32_t frame_size
= ac3_frame_size_table
[ param
->frmsizecod
>> 1 ][ param
->fscod
];
174 if( param
->fscod
== 0x1 && param
->frmsizecod
& 0x1 )
176 if( current_status
== IMPORTER_CHANGE
)
178 lsmash_codec_specific_t
*cs
= isom_get_codec_specific( summary
->opaque
, LSMASH_CODEC_SPECIFIC_DATA_TYPE_ISOM_AUDIO_AC_3
);
181 cs
->destruct( cs
->data
.unstructured
);
182 cs
->data
.unstructured
= ac3_imp
->next_dac3
;
184 summary
->frequency
= ac3_get_sample_rate( param
);
185 summary
->channels
= ac3_get_channel_count( param
);
186 //summary->layout_tag = ac3_channel_layout_table[ param->acmod ][ param->lfeon ];
188 lsmash_sample_t
*sample
= lsmash_create_sample( frame_size
);
190 return LSMASH_ERR_MEMORY_ALLOC
;
192 memcpy( sample
->data
, ac3_imp
->buffer
, frame_size
);
193 sample
->length
= frame_size
;
194 sample
->dts
= ac3_imp
->au_number
++ * summary
->samples_in_frame
;
195 sample
->cts
= sample
->dts
;
196 sample
->prop
.ra_flags
= ISOM_SAMPLE_RANDOM_ACCESS_FLAG_SYNC
;
197 sample
->prop
.pre_roll
.distance
= 1; /* MDCT */
198 lsmash_bs_t
*bs
= info
->bits
->bs
;
199 ac3_imp
->next_frame_pos
+= frame_size
;
200 lsmash_bs_read_seek( bs
, ac3_imp
->next_frame_pos
, SEEK_SET
);
201 uint8_t syncword
[2] =
203 lsmash_bs_show_byte( bs
, 0 ),
204 lsmash_bs_show_byte( bs
, 1 )
206 if( bs
->eob
|| (bs
->eof
&& 0 == lsmash_bs_get_remaining_buffer_size( bs
)) )
207 importer
->status
= IMPORTER_EOF
;
210 /* Parse the next syncframe header. */
211 if( syncword
[0] != 0x0b
212 || syncword
[1] != 0x77
213 || ac3_buffer_frame( ac3_imp
->buffer
, bs
) < 0 )
215 importer
->status
= IMPORTER_ERROR
;
216 return current_status
;
218 lsmash_ac3_specific_parameters_t current_param
= info
->dac3_param
;
219 ac3_parse_syncframe_header( info
);
220 if( ac3_compare_specific_param( ¤t_param
, &info
->dac3_param
) )
223 uint8_t *dac3
= lsmash_create_ac3_specific_info( &info
->dac3_param
, &dummy
);
226 importer
->status
= IMPORTER_ERROR
;
227 return current_status
;
229 ac3_imp
->next_dac3
= dac3
;
230 importer
->status
= IMPORTER_CHANGE
;
233 importer
->status
= IMPORTER_OK
;
235 return current_status
;
238 static int ac3_importer_probe( importer_t
*importer
)
240 ac3_importer_t
*ac3_imp
= create_ac3_importer( importer
);
242 return LSMASH_ERR_MEMORY_ALLOC
;
243 lsmash_bits_t
*bits
= ac3_imp
->info
.bits
;
244 lsmash_bs_t
*bs
= bits
->bs
;
245 bs
->buffer
.max_size
= AC3_MAX_SYNCFRAME_LENGTH
;
246 /* Check the syncword and parse the syncframe header */
248 if( lsmash_bs_show_byte( bs
, 0 ) != 0x0b
249 || lsmash_bs_show_byte( bs
, 1 ) != 0x77 )
251 err
= LSMASH_ERR_INVALID_DATA
;
254 if( (err
= ac3_buffer_frame( ac3_imp
->buffer
, bs
)) < 0
255 || (err
= ac3_parse_syncframe_header( &ac3_imp
->info
)) < 0 )
257 lsmash_audio_summary_t
*summary
= ac3_create_summary( &ac3_imp
->info
);
260 err
= LSMASH_ERR_NAMELESS
;
263 if( lsmash_add_entry( importer
->summaries
, summary
) < 0 )
265 lsmash_cleanup_summary( (lsmash_summary_t
*)summary
);
266 err
= LSMASH_ERR_MEMORY_ALLOC
;
269 ac3_imp
->au_number
= 0;
270 importer
->info
= ac3_imp
;
271 importer
->status
= IMPORTER_OK
;
274 remove_ac3_importer( ac3_imp
);
278 static uint32_t ac3_importer_get_last_delta( importer_t
*importer
, uint32_t track_number
)
280 debug_if( !importer
|| !importer
->info
)
282 ac3_importer_t
*ac3_imp
= (ac3_importer_t
*)importer
->info
;
283 if( !ac3_imp
|| track_number
!= 1 || importer
->status
!= IMPORTER_EOF
)
285 return AC3_SAMPLE_DURATION
;
288 const importer_functions ac3_importer
=
293 ac3_importer_get_accessunit
,
294 ac3_importer_get_last_delta
,
298 /***************************************************************************
299 Enhanced AC-3 importer
300 ETSI TS 102 366 V1.2.1 (2008-08)
301 ***************************************************************************/
302 #define EAC3_MIN_SAMPLE_DURATION 256
307 uint64_t next_frame_pos
;
308 uint32_t next_dec3_length
;
310 uint8_t current_fscod2
;
311 uint8_t buffer
[EAC3_MAX_SYNCFRAME_LENGTH
];
312 lsmash_multiple_buffers_t
*au_buffers
;
314 uint8_t *incomplete_au
;
316 uint32_t incomplete_au_length
;
318 uint32_t syncframe_count_in_au
;
321 static void remove_eac3_importer( eac3_importer_t
*eac3_imp
)
325 lsmash_destroy_multiple_buffers( eac3_imp
->au_buffers
);
326 lsmash_bits_cleanup( eac3_imp
->info
.bits
);
327 lsmash_free( eac3_imp
);
330 static eac3_importer_t
*create_eac3_importer( importer_t
*importer
)
332 eac3_importer_t
*eac3_imp
= (eac3_importer_t
*)lsmash_malloc_zero( sizeof(eac3_importer_t
) );
335 eac3_info_t
*info
= &eac3_imp
->info
;
336 info
->bits
= lsmash_bits_create( importer
->bs
);
339 lsmash_free( eac3_imp
);
342 eac3_imp
->au_buffers
= lsmash_create_multiple_buffers( 2, EAC3_MAX_SYNCFRAME_LENGTH
);
343 if( !eac3_imp
->au_buffers
)
345 lsmash_bits_cleanup( info
->bits
);
346 lsmash_free( eac3_imp
);
349 eac3_imp
->au
= lsmash_withdraw_buffer( eac3_imp
->au_buffers
, 1 );
350 eac3_imp
->incomplete_au
= lsmash_withdraw_buffer( eac3_imp
->au_buffers
, 2 );
354 static void eac3_importer_cleanup( importer_t
*importer
)
356 debug_if( importer
&& importer
->info
)
357 remove_eac3_importer( importer
->info
);
360 static int eac3_importer_get_next_accessunit_internal( importer_t
*importer
)
362 int au_completed
= 0;
363 eac3_importer_t
*eac3_imp
= (eac3_importer_t
*)importer
->info
;
364 eac3_info_t
*info
= &eac3_imp
->info
;
365 lsmash_bs_t
*bs
= info
->bits
->bs
;
366 while( !au_completed
)
368 /* Read data from the stream if needed. */
369 eac3_imp
->next_frame_pos
+= info
->frame_size
;
370 lsmash_bs_read_seek( bs
, eac3_imp
->next_frame_pos
, SEEK_SET
);
371 uint64_t remain_size
= lsmash_bs_get_remaining_buffer_size( bs
);
372 if( remain_size
< EAC3_MAX_SYNCFRAME_LENGTH
)
374 int err
= lsmash_bs_read( bs
, bs
->buffer
.max_size
);
377 lsmash_log( importer
, LSMASH_LOG_ERROR
, "failed to read data from the stream.\n" );
380 remain_size
= lsmash_bs_get_remaining_buffer_size( bs
);
382 uint64_t copy_size
= LSMASH_MIN( remain_size
, EAC3_MAX_SYNCFRAME_LENGTH
);
383 memcpy( eac3_imp
->buffer
, lsmash_bs_get_buffer_data( bs
), copy_size
);
384 /* Check the remainder length of the buffer.
385 * If there is enough length, then parse the syncframe in it.
386 * The length 5 is the required byte length to get frame size. */
387 if( bs
->eob
|| (bs
->eof
&& remain_size
< 5) )
389 /* Reached the end of stream.
390 * According to ETSI TS 102 366 V1.2.1 (2008-08),
391 * one access unit consists of 6 audio blocks and begins with independent substream 0.
392 * The specification doesn't mention the case where a enhanced AC-3 stream ends at non-mod6 audio blocks.
393 * At the end of the stream, therefore, we might make an access unit which has less than 6 audio blocks anyway. */
394 importer
->status
= IMPORTER_EOF
;
395 au_completed
= !!eac3_imp
->incomplete_au_length
;
398 /* No more access units in the stream. */
399 if( lsmash_bs_get_remaining_buffer_size( bs
) )
401 lsmash_log( importer
, LSMASH_LOG_WARNING
, "the stream is truncated at the end.\n" );
402 return LSMASH_ERR_INVALID_DATA
;
406 if( !info
->dec3_param_initialized
)
407 eac3_update_specific_param( info
);
411 /* Check the syncword. */
412 if( lsmash_bs_show_byte( bs
, 0 ) != 0x0b
413 || lsmash_bs_show_byte( bs
, 1 ) != 0x77 )
415 lsmash_log( importer
, LSMASH_LOG_ERROR
, "a syncword is not found.\n" );
416 return LSMASH_ERR_INVALID_DATA
;
418 /* Parse syncframe. */
419 info
->frame_size
= 0;
420 int err
= eac3_parse_syncframe( info
);
423 lsmash_log( importer
, LSMASH_LOG_ERROR
, "failed to parse syncframe.\n" );
426 if( remain_size
< info
->frame_size
)
428 lsmash_log( importer
, LSMASH_LOG_ERROR
, "a frame is truncated.\n" );
429 return LSMASH_ERR_INVALID_DATA
;
431 int independent
= info
->strmtyp
!= 0x1;
432 if( independent
&& info
->substreamid
== 0x0 )
434 if( info
->number_of_audio_blocks
== 6 )
436 /* Encountered the first syncframe of the next access unit. */
437 info
->number_of_audio_blocks
= 0;
440 else if( info
->number_of_audio_blocks
> 6 )
442 lsmash_log( importer
, LSMASH_LOG_ERROR
, "greater than 6 consecutive independent substreams.\n" );
443 return LSMASH_ERR_INVALID_DATA
;
445 info
->number_of_audio_blocks
+= eac3_audio_block_table
[ info
->numblkscod
];
446 info
->number_of_independent_substreams
= 0;
447 eac3_imp
->current_fscod2
= info
->fscod2
;
449 else if( info
->syncframe_count
== 0 )
451 /* The first syncframe in an AU must be independent and assigned substream ID 0. */
452 lsmash_log( importer
, LSMASH_LOG_ERROR
, "the first syncframe is NOT an independent substream.\n" );
453 return LSMASH_ERR_INVALID_DATA
;
456 info
->independent_info
[info
->number_of_independent_substreams
++].num_dep_sub
= 0;
458 ++ info
->independent_info
[info
->number_of_independent_substreams
- 1].num_dep_sub
;
462 memcpy( eac3_imp
->au
, eac3_imp
->incomplete_au
, eac3_imp
->incomplete_au_length
);
463 eac3_imp
->au_length
= eac3_imp
->incomplete_au_length
;
464 eac3_imp
->incomplete_au_length
= 0;
465 eac3_imp
->syncframe_count_in_au
= info
->syncframe_count
;
466 info
->syncframe_count
= 0;
467 if( importer
->status
== IMPORTER_EOF
)
470 /* Increase buffer size to store AU if short. */
471 if( eac3_imp
->incomplete_au_length
+ info
->frame_size
> eac3_imp
->au_buffers
->buffer_size
)
473 lsmash_multiple_buffers_t
*temp
= lsmash_resize_multiple_buffers( eac3_imp
->au_buffers
,
474 eac3_imp
->au_buffers
->buffer_size
+ EAC3_MAX_SYNCFRAME_LENGTH
);
476 return LSMASH_ERR_MEMORY_ALLOC
;
477 eac3_imp
->au_buffers
= temp
;
478 eac3_imp
->au
= lsmash_withdraw_buffer( eac3_imp
->au_buffers
, 1 );
479 eac3_imp
->incomplete_au
= lsmash_withdraw_buffer( eac3_imp
->au_buffers
, 2 );
481 /* Append syncframe data. */
482 memcpy( eac3_imp
->incomplete_au
+ eac3_imp
->incomplete_au_length
, eac3_imp
->buffer
, info
->frame_size
);
483 eac3_imp
->incomplete_au_length
+= info
->frame_size
;
484 ++ info
->syncframe_count
;
486 return bs
->error
? LSMASH_ERR_NAMELESS
: 0;
489 static int eac3_importer_get_accessunit( importer_t
*importer
, uint32_t track_number
, lsmash_sample_t
**p_sample
)
491 if( !importer
->info
)
492 return LSMASH_ERR_NAMELESS
;
493 if( track_number
!= 1 )
494 return LSMASH_ERR_FUNCTION_PARAM
;
495 lsmash_audio_summary_t
*summary
= (lsmash_audio_summary_t
*)lsmash_get_entry_data( importer
->summaries
, track_number
);
497 return LSMASH_ERR_NAMELESS
;
498 eac3_importer_t
*eac3_imp
= (eac3_importer_t
*)importer
->info
;
499 eac3_info_t
*info
= &eac3_imp
->info
;
500 importer_status current_status
= importer
->status
;
501 if( current_status
== IMPORTER_ERROR
)
502 return LSMASH_ERR_NAMELESS
;
503 if( current_status
== IMPORTER_EOF
&& eac3_imp
->au_length
== 0 )
505 if( current_status
== IMPORTER_CHANGE
)
507 lsmash_codec_specific_t
*cs
= isom_get_codec_specific( summary
->opaque
, LSMASH_CODEC_SPECIFIC_DATA_TYPE_ISOM_AUDIO_EC_3
);
510 cs
->destruct( cs
->data
.unstructured
);
511 cs
->data
.unstructured
= eac3_imp
->next_dec3
;
512 cs
->size
= eac3_imp
->next_dec3_length
;
514 summary
->max_au_length
= eac3_imp
->syncframe_count_in_au
* EAC3_MAX_SYNCFRAME_LENGTH
;
515 eac3_update_sample_rate( &summary
->frequency
, &info
->dec3_param
, &eac3_imp
->current_fscod2
);
516 eac3_update_channel_count( &summary
->channels
, &info
->dec3_param
);
518 lsmash_sample_t
*sample
= lsmash_create_sample( eac3_imp
->au_length
);
520 return LSMASH_ERR_MEMORY_ALLOC
;
522 memcpy( sample
->data
, eac3_imp
->au
, eac3_imp
->au_length
);
523 sample
->length
= eac3_imp
->au_length
;
524 sample
->dts
= eac3_imp
->au_number
++ * summary
->samples_in_frame
;
525 sample
->cts
= sample
->dts
;
526 sample
->prop
.ra_flags
= ISOM_SAMPLE_RANDOM_ACCESS_FLAG_SYNC
;
527 sample
->prop
.pre_roll
.distance
= 1; /* MDCT */
528 if( importer
->status
== IMPORTER_EOF
)
530 eac3_imp
->au_length
= 0;
533 uint32_t old_syncframe_count_in_au
= eac3_imp
->syncframe_count_in_au
;
534 if( eac3_importer_get_next_accessunit_internal( importer
) < 0 )
536 importer
->status
= IMPORTER_ERROR
;
537 return current_status
;
539 if( eac3_imp
->syncframe_count_in_au
)
541 /* Check sample description change. */
543 uint8_t *dec3
= lsmash_create_eac3_specific_info( &info
->dec3_param
, &new_length
);
546 importer
->status
= IMPORTER_ERROR
;
547 return current_status
;
549 lsmash_codec_specific_t
*cs
= isom_get_codec_specific( summary
->opaque
, LSMASH_CODEC_SPECIFIC_DATA_TYPE_ISOM_AUDIO_EC_3
);
550 if( (eac3_imp
->syncframe_count_in_au
> old_syncframe_count_in_au
)
551 || (cs
&& (new_length
!= cs
->size
|| memcmp( dec3
, cs
->data
.unstructured
, cs
->size
))) )
553 importer
->status
= IMPORTER_CHANGE
;
554 eac3_imp
->next_dec3
= dec3
;
555 eac3_imp
->next_dec3_length
= new_length
;
559 if( importer
->status
!= IMPORTER_EOF
)
560 importer
->status
= IMPORTER_OK
;
564 return current_status
;
567 static lsmash_audio_summary_t
*eac3_create_summary( eac3_importer_t
*eac3_imp
)
569 lsmash_audio_summary_t
*summary
= (lsmash_audio_summary_t
*)lsmash_create_summary( LSMASH_SUMMARY_TYPE_AUDIO
);
572 eac3_info_t
*info
= &eac3_imp
->info
;
573 lsmash_codec_specific_t
*cs
= lsmash_create_codec_specific_data( LSMASH_CODEC_SPECIFIC_DATA_TYPE_ISOM_AUDIO_EC_3
,
574 LSMASH_CODEC_SPECIFIC_FORMAT_UNSTRUCTURED
);
577 lsmash_cleanup_summary( (lsmash_summary_t
*)summary
);
580 cs
->data
.unstructured
= lsmash_create_eac3_specific_info( &info
->dec3_param
, &cs
->size
);
581 if( !cs
->data
.unstructured
582 || lsmash_add_entry( &summary
->opaque
->list
, cs
) < 0 )
584 lsmash_cleanup_summary( (lsmash_summary_t
*)summary
);
585 lsmash_destroy_codec_specific_data( cs
);
588 summary
->sample_type
= ISOM_CODEC_TYPE_EC_3_AUDIO
;
589 summary
->max_au_length
= eac3_imp
->syncframe_count_in_au
* EAC3_MAX_SYNCFRAME_LENGTH
;
590 summary
->aot
= MP4A_AUDIO_OBJECT_TYPE_NULL
; /* no effect */
591 summary
->sample_size
= 16; /* no effect */
592 summary
->samples_in_frame
= EAC3_MIN_SAMPLE_DURATION
* 6; /* 256 (samples per audio block) * 6 (audio blocks) */
593 summary
->sbr_mode
= MP4A_AAC_SBR_NOT_SPECIFIED
; /* no effect */
594 eac3_update_sample_rate( &summary
->frequency
, &info
->dec3_param
, &eac3_imp
->current_fscod2
);
595 eac3_update_channel_count( &summary
->channels
, &info
->dec3_param
);
599 static int eac3_importer_probe( importer_t
*importer
)
601 eac3_importer_t
*eac3_imp
= create_eac3_importer( importer
);
603 return LSMASH_ERR_MEMORY_ALLOC
;
604 lsmash_bits_t
*bits
= eac3_imp
->info
.bits
;
605 lsmash_bs_t
*bs
= bits
->bs
;
606 bs
->buffer
.max_size
= EAC3_MAX_SYNCFRAME_LENGTH
;
607 importer
->info
= eac3_imp
;
608 int err
= eac3_importer_get_next_accessunit_internal( importer
);
611 lsmash_audio_summary_t
*summary
= eac3_create_summary( eac3_imp
);
614 err
= LSMASH_ERR_NAMELESS
;
617 if( importer
->status
!= IMPORTER_EOF
)
618 importer
->status
= IMPORTER_OK
;
619 eac3_imp
->au_number
= 0;
620 if( lsmash_add_entry( importer
->summaries
, summary
) < 0 )
622 lsmash_cleanup_summary( (lsmash_summary_t
*)summary
);
623 err
= LSMASH_ERR_MEMORY_ALLOC
;
628 remove_eac3_importer( eac3_imp
);
629 importer
->info
= NULL
;
633 static uint32_t eac3_importer_get_last_delta( importer_t
*importer
, uint32_t track_number
)
635 debug_if( !importer
|| !importer
->info
)
637 eac3_importer_t
*eac3_imp
= (eac3_importer_t
*)importer
->info
;
638 if( !eac3_imp
|| track_number
!= 1 || importer
->status
!= IMPORTER_EOF
|| eac3_imp
->au_length
)
640 return EAC3_MIN_SAMPLE_DURATION
* eac3_imp
->info
.number_of_audio_blocks
;
643 const importer_functions eac3_importer
=
645 { "Enhanced AC-3", offsetof( importer_t
, log_level
) },
648 eac3_importer_get_accessunit
,
649 eac3_importer_get_last_delta
,
650 eac3_importer_cleanup