diff options
Diffstat (limited to 'apps/metadata/au.c')
-rw-r--r-- | apps/metadata/au.c | 73 |
1 files changed, 27 insertions, 46 deletions
diff --git a/apps/metadata/au.c b/apps/metadata/au.c index 0639bd11e6..94e7453644 100644 --- a/apps/metadata/au.c +++ b/apps/metadata/au.c | |||
@@ -20,8 +20,6 @@ | |||
20 | ****************************************************************************/ | 20 | ****************************************************************************/ |
21 | #include <stdio.h> | 21 | #include <stdio.h> |
22 | #include <string.h> | 22 | #include <string.h> |
23 | #include <stdlib.h> | ||
24 | #include <ctype.h> | ||
25 | #include <inttypes.h> | 23 | #include <inttypes.h> |
26 | 24 | ||
27 | #include "system.h" | 25 | #include "system.h" |
@@ -30,62 +28,42 @@ | |||
30 | #include "metadata_parsers.h" | 28 | #include "metadata_parsers.h" |
31 | #include "logf.h" | 29 | #include "logf.h" |
32 | 30 | ||
33 | /* table of bits per sample / 8 */ | 31 | static const unsigned char bitspersamples[9] = { |
34 | static const unsigned char bitspersamples[28] = { | 32 | 0, /* encoding */ |
35 | 0, | 33 | 8, /* 1: G.711 MULAW */ |
36 | 1, /* G.711 MULAW */ | 34 | 8, /* 2: Linear PCM 8bit */ |
37 | 1, /* 8bit */ | 35 | 16, /* 3: Linear PCM 16bit */ |
38 | 2, /* 16bit */ | 36 | 24, /* 4: Linear PCM 24bit */ |
39 | 3, /* 24bit */ | 37 | 32, /* 5: Linear PCM 32bit */ |
40 | 4, /* 32bit */ | 38 | 32, /* 6: IEEE float 32bit */ |
41 | 4, /* 32bit */ | 39 | 64, /* 7: IEEE float 64bit */ |
42 | 8, /* 64bit */ | 40 | /* encoding 8 - 26 unsupported. */ |
43 | 0, /* Fragmented sample data */ | 41 | 8, /* 27: G.711 ALAW */ |
44 | 0, /* DSP program */ | ||
45 | 0, /* 8bit fixed point */ | ||
46 | 0, /* 16bit fixed point */ | ||
47 | 0, /* 24bit fixed point */ | ||
48 | 0, /* 32bit fixed point */ | ||
49 | 0, | ||
50 | 0, | ||
51 | 0, | ||
52 | 0, | ||
53 | 0, /* 16bit linear with emphasis */ | ||
54 | 0, /* 16bit linear compressed */ | ||
55 | 0, /* 16bit linear with emphasis and compression */ | ||
56 | 0, /* Music kit DSP commands */ | ||
57 | 0, | ||
58 | 0, /* G.721 MULAW */ | ||
59 | 0, /* G.722 */ | ||
60 | 0, /* G.723 3bit */ | ||
61 | 0, /* G.723 5bit */ | ||
62 | 1, /* G.711 ALAW */ | ||
63 | }; | 42 | }; |
64 | 43 | ||
65 | static inline unsigned char get_au_bitspersample(unsigned int encoding) | 44 | static inline unsigned char get_au_bitspersample(unsigned int encoding) |
66 | { | 45 | { |
67 | if (encoding > 27) | 46 | if (encoding < 8) |
68 | return 0; | 47 | return bitspersamples[encoding]; |
69 | return bitspersamples[encoding]; | 48 | else if (encoding == 27) |
49 | return bitspersamples[8]; | ||
50 | |||
51 | return 0; | ||
70 | } | 52 | } |
71 | 53 | ||
72 | bool get_au_metadata(int fd, struct mp3entry* id3) | 54 | bool get_au_metadata(int fd, struct mp3entry* id3) |
73 | { | 55 | { |
74 | /* Use the trackname part of the id3 structure as a temporary buffer */ | 56 | /* temporary buffer */ |
75 | unsigned char* buf = (unsigned char *)id3->path; | 57 | unsigned char* buf = (unsigned char *)id3->path; |
76 | unsigned long numbytes = 0; | 58 | unsigned long numbytes = 0; |
77 | int read_bytes; | ||
78 | int offset; | 59 | int offset; |
79 | unsigned char bits_ch; /* bitspersample * channels */ | ||
80 | 60 | ||
81 | id3->vbr = false; /* All Sun audio files are CBR */ | 61 | id3->vbr = false; /* All Sun audio files are CBR */ |
82 | id3->filesize = filesize(fd); | 62 | id3->filesize = filesize(fd); |
83 | id3->length = 0; | 63 | id3->length = 0; |
84 | 64 | ||
85 | if ((lseek(fd, 0, SEEK_SET) < 0) || ((read_bytes = read(fd, buf, 24)) < 0)) | 65 | lseek(fd, 0, SEEK_SET); |
86 | return false; | 66 | if ((read(fd, buf, 24) < 24) || (memcmp(buf, ".snd", 4) != 0)) |
87 | |||
88 | if (read_bytes < 24 || (memcmp(buf, ".snd", 4) != 0)) | ||
89 | { | 67 | { |
90 | /* | 68 | /* |
91 | * no header | 69 | * no header |
@@ -96,10 +74,12 @@ bool get_au_metadata(int fd, struct mp3entry* id3) | |||
96 | */ | 74 | */ |
97 | numbytes = id3->filesize; | 75 | numbytes = id3->filesize; |
98 | id3->frequency = 8000; | 76 | id3->frequency = 8000; |
99 | bits_ch = 1; | 77 | id3->bitrate = 8; |
100 | } | 78 | } |
101 | else | 79 | else |
102 | { | 80 | { |
81 | /* parse header */ | ||
82 | |||
103 | /* data offset */ | 83 | /* data offset */ |
104 | offset = get_long_be(buf + 4); | 84 | offset = get_long_be(buf + 4); |
105 | if (offset < 24) | 85 | if (offset < 24) |
@@ -112,13 +92,14 @@ bool get_au_metadata(int fd, struct mp3entry* id3) | |||
112 | if (numbytes == (uint32_t)0xffffffff) | 92 | if (numbytes == (uint32_t)0xffffffff) |
113 | numbytes = id3->filesize - offset; | 93 | numbytes = id3->filesize - offset; |
114 | 94 | ||
115 | bits_ch = get_au_bitspersample(get_long_be(buf + 12)) * get_long_be(buf + 20); | ||
116 | id3->frequency = get_long_be(buf + 16); | 95 | id3->frequency = get_long_be(buf + 16); |
96 | id3->bitrate = get_au_bitspersample(get_long_be(buf + 12)) * get_long_be(buf + 20) | ||
97 | * id3->frequency / 1000; | ||
117 | } | 98 | } |
118 | 99 | ||
119 | /* Calculate track length [ms] */ | 100 | /* Calculate track length [ms] */ |
120 | if (bits_ch) | 101 | if (id3->bitrate) |
121 | id3->length = ((int64_t)numbytes * 1000LL) / (bits_ch * id3->frequency); | 102 | id3->length = (numbytes << 3) / id3->bitrate; |
122 | 103 | ||
123 | return true; | 104 | return true; |
124 | } | 105 | } |