diff options
Diffstat (limited to 'apps')
-rw-r--r-- | apps/metadata.c | 71 |
1 files changed, 41 insertions, 30 deletions
diff --git a/apps/metadata.c b/apps/metadata.c index ea631171f2..34686a68dd 100644 --- a/apps/metadata.c +++ b/apps/metadata.c | |||
@@ -581,6 +581,34 @@ static bool read_vorbis_tags(int fd, struct mp3entry *id3, | |||
581 | return true; | 581 | return true; |
582 | } | 582 | } |
583 | 583 | ||
584 | /* Skip an ID3v2 tag if it can be found. We assume the tag is located at the | ||
585 | * start of the file, which should be true in all cases where we need to skip it. | ||
586 | * Returns true if successfully skipped or not skipped, and false if | ||
587 | * something went wrong while skipping. | ||
588 | */ | ||
589 | static bool skip_id3v2(int fd, struct mp3entry *id3) | ||
590 | { | ||
591 | char buf[4]; | ||
592 | |||
593 | read(fd, buf, 4); | ||
594 | if (memcmp(buf, "ID3", 3) == 0) | ||
595 | { | ||
596 | /* We have found an ID3v2 tag at the start of the file - find its | ||
597 | length and then skip it. */ | ||
598 | if ((id3->first_frame_offset = getid3v2len(fd)) == 0) | ||
599 | return false; | ||
600 | |||
601 | if ((lseek(fd, id3->first_frame_offset, SEEK_SET) < 0)) | ||
602 | return false; | ||
603 | |||
604 | return true; | ||
605 | } else { | ||
606 | lseek(fd, 0, SEEK_SET); | ||
607 | id3->first_frame_offset = 0; | ||
608 | return true; | ||
609 | } | ||
610 | } | ||
611 | |||
584 | /* A simple parser to read vital metadata from an Ogg Vorbis file. Returns | 612 | /* A simple parser to read vital metadata from an Ogg Vorbis file. Returns |
585 | * false if metadata needed by the Vorbis codec couldn't be read. | 613 | * false if metadata needed by the Vorbis codec couldn't be read. |
586 | */ | 614 | */ |
@@ -781,32 +809,12 @@ static bool get_flac_metadata(int fd, struct mp3entry* id3) | |||
781 | unsigned char* buf = id3->path; | 809 | unsigned char* buf = id3->path; |
782 | bool rc = false; | 810 | bool rc = false; |
783 | 811 | ||
784 | if ((lseek(fd, 0, SEEK_SET) < 0) || (read(fd, buf, 4) < 4)) | 812 | if (!skip_id3v2(fd, id3) || (read(fd, buf, 4) < 4)) |
785 | { | 813 | { |
786 | return rc; | 814 | return rc; |
787 | } | 815 | } |
788 | 816 | ||
789 | if (memcmp(buf,"ID3",3) == 0) | 817 | if (memcmp(buf, "fLaC", 4) != 0) |
790 | { | ||
791 | /* We have found an ID3v2 tag at the start of the file - find its | ||
792 | length and then skip it. | ||
793 | */ | ||
794 | |||
795 | if ((id3->first_frame_offset=getid3v2len(fd)) == 0) | ||
796 | { | ||
797 | return rc; | ||
798 | } | ||
799 | |||
800 | if ((lseek(fd, id3->first_frame_offset, SEEK_SET) < 0) || | ||
801 | (read(fd, buf, 4) < 4)) | ||
802 | { | ||
803 | return rc; | ||
804 | } | ||
805 | } else { | ||
806 | id3->first_frame_offset=0; | ||
807 | } | ||
808 | |||
809 | if (memcmp(buf,"fLaC",4) != 0) | ||
810 | { | 818 | { |
811 | return rc; | 819 | return rc; |
812 | } | 820 | } |
@@ -1259,9 +1267,10 @@ static bool get_musepack_metadata(int fd, struct mp3entry *id3) | |||
1259 | const int32_t sfreqs_sv7[4] = { 44100, 48000, 37800, 32000 }; | 1267 | const int32_t sfreqs_sv7[4] = { 44100, 48000, 37800, 32000 }; |
1260 | uint32_t header[8]; | 1268 | uint32_t header[8]; |
1261 | uint64_t samples = 0; | 1269 | uint64_t samples = 0; |
1262 | unsigned i; | 1270 | int i; |
1263 | 1271 | ||
1264 | /* TODO: libmpcdec skips id3v2 header, perhaps we should as well */ | 1272 | if (!skip_id3v2(fd, id3)) |
1273 | return false; | ||
1265 | if (read(fd, header, 4*8) != 4*8) return false; | 1274 | if (read(fd, header, 4*8) != 4*8) return false; |
1266 | /* Musepack files are little endian, might need swapping */ | 1275 | /* Musepack files are little endian, might need swapping */ |
1267 | for (i = 1; i < 8; i++) | 1276 | for (i = 1; i < 8; i++) |
@@ -1295,12 +1304,14 @@ static bool get_musepack_metadata(int fd, struct mp3entry *id3) | |||
1295 | id3->album_gain = get_replaygain_int(album_gain); | 1304 | id3->album_gain = get_replaygain_int(album_gain); |
1296 | id3->album_peak = ((uint16_t)(header[4] & 0xffff)) << 9; | 1305 | id3->album_peak = ((uint16_t)(header[4] & 0xffff)) << 9; |
1297 | 1306 | ||
1298 | /* Write replaygain values to strings for use in id3 screen */ | 1307 | /* Write replaygain values to strings for use in id3 screen. We use |
1299 | id3->track_gain_string = id3->id3v2buf; | 1308 | the XING header as buffer space since Musepack files shouldn't |
1300 | bufused = snprintf(id3->track_gain_string, sizeof(id3->id3v2buf), | 1309 | need to use it in any other way */ |
1310 | id3->track_gain_string = id3->toc; | ||
1311 | bufused = snprintf(id3->track_gain_string, 45, | ||
1301 | "%d.%d dB", track_gain/100, abs(track_gain)%100); | 1312 | "%d.%d dB", track_gain/100, abs(track_gain)%100); |
1302 | id3->album_gain_string = id3->id3v2buf + bufused + 1; | 1313 | id3->album_gain_string = id3->toc + bufused + 1; |
1303 | bufused = snprintf(id3->album_gain_string, 100, | 1314 | bufused = snprintf(id3->album_gain_string, 45, |
1304 | "%d.%d dB", album_gain/100, abs(album_gain)%100); | 1315 | "%d.%d dB", album_gain/100, abs(album_gain)%100); |
1305 | } | 1316 | } |
1306 | } else { | 1317 | } else { |