diff options
Diffstat (limited to 'apps')
-rw-r--r-- | apps/codecs/aac.c | 4 | ||||
-rw-r--r-- | apps/metadata.h | 4 | ||||
-rw-r--r-- | apps/metadata/mp4.c | 27 |
3 files changed, 25 insertions, 10 deletions
diff --git a/apps/codecs/aac.c b/apps/codecs/aac.c index 37e525e61a..0b27eed472 100644 --- a/apps/codecs/aac.c +++ b/apps/codecs/aac.c | |||
@@ -145,8 +145,8 @@ next_track: | |||
145 | } | 145 | } |
146 | 146 | ||
147 | #ifdef SBR_DEC | 147 | #ifdef SBR_DEC |
148 | /* The file uses SBR. */ | 148 | /* Check for need of special handling for seek/resume and elapsed time. */ |
149 | if (decoder->forceUpSampling) { | 149 | if (ci->id3->needs_upsampling_correction) { |
150 | sbr_fac = 2; | 150 | sbr_fac = 2; |
151 | } else { | 151 | } else { |
152 | sbr_fac = 1; | 152 | sbr_fac = 1; |
diff --git a/apps/metadata.h b/apps/metadata.h index f366aea61c..93b9891763 100644 --- a/apps/metadata.h +++ b/apps/metadata.h | |||
@@ -240,6 +240,10 @@ struct mp3entry { | |||
240 | /* Added for ATRAC3 */ | 240 | /* Added for ATRAC3 */ |
241 | unsigned int channels; /* Number of channels in the stream */ | 241 | unsigned int channels; /* Number of channels in the stream */ |
242 | unsigned int extradata_size; /* Size (in bytes) of the codec's extradata from the container */ | 242 | unsigned int extradata_size; /* Size (in bytes) of the codec's extradata from the container */ |
243 | |||
244 | /* Added for AAC HE SBR */ | ||
245 | bool needs_upsampling_correction; /* flag used by aac codec */ | ||
246 | |||
243 | /* these following two fields are used for local buffering */ | 247 | /* these following two fields are used for local buffering */ |
244 | char id3v2buf[ID3V2_BUF_SIZE]; | 248 | char id3v2buf[ID3V2_BUF_SIZE]; |
245 | char id3v1buf[4][92]; | 249 | char id3v1buf[4][92]; |
diff --git a/apps/metadata/mp4.c b/apps/metadata/mp4.c index c9c691f0c4..a3721f0e9a 100644 --- a/apps/metadata/mp4.c +++ b/apps/metadata/mp4.c | |||
@@ -639,7 +639,10 @@ static bool read_mp4_container(int fd, struct mp3entry* id3, | |||
639 | { | 639 | { |
640 | uint32_t entries; | 640 | uint32_t entries; |
641 | unsigned int i; | 641 | unsigned int i; |
642 | 642 | ||
643 | /* Reset to false. */ | ||
644 | id3->needs_upsampling_correction = true; | ||
645 | |||
643 | lseek(fd, 4, SEEK_CUR); | 646 | lseek(fd, 4, SEEK_CUR); |
644 | read_uint32be(fd, &entries); | 647 | read_uint32be(fd, &entries); |
645 | id3->samples = 0; | 648 | id3->samples = 0; |
@@ -651,7 +654,21 @@ static bool read_mp4_container(int fd, struct mp3entry* id3, | |||
651 | 654 | ||
652 | read_uint32be(fd, &n); | 655 | read_uint32be(fd, &n); |
653 | read_uint32be(fd, &l); | 656 | read_uint32be(fd, &l); |
654 | id3->samples += n * l; | 657 | |
658 | /* Some SBR files use upsampling. In this case the number | ||
659 | * of output samples is doubled to a maximum of 2048 | ||
660 | * samples per frame. This means that files which already | ||
661 | * report a frame size of 2048 in their header will not | ||
662 | * need any further special handling. */ | ||
663 | if (SBR_upsampling_used && l<=1024) | ||
664 | { | ||
665 | id3->samples += n * l * 2; | ||
666 | id3->needs_upsampling_correction = true; | ||
667 | } | ||
668 | else | ||
669 | { | ||
670 | id3->samples += n * l; | ||
671 | } | ||
655 | } | 672 | } |
656 | 673 | ||
657 | size = 0; | 674 | size = 0; |
@@ -760,12 +777,6 @@ bool get_mp4_metadata(int fd, struct mp3entry* id3) | |||
760 | logf("Not an ALAC or AAC file"); | 777 | logf("Not an ALAC or AAC file"); |
761 | return false; | 778 | return false; |
762 | } | 779 | } |
763 | |||
764 | /* SBR upsampling will output double amount of samples per frame. */ | ||
765 | if (SBR_upsampling_used) | ||
766 | { | ||
767 | id3->samples *= 2; | ||
768 | } | ||
769 | 780 | ||
770 | id3->length = ((int64_t) id3->samples * 1000) / id3->frequency; | 781 | id3->length = ((int64_t) id3->samples * 1000) / id3->frequency; |
771 | 782 | ||