aboutsummaryrefslogtreecommitdiffstats
path: root/src/decoder
diff options
context:
space:
mode:
Diffstat (limited to 'src/decoder')
-rw-r--r--src/decoder/_flac_common.c118
-rw-r--r--src/decoder/mad_plugin.c34
2 files changed, 91 insertions, 61 deletions
diff --git a/src/decoder/_flac_common.c b/src/decoder/_flac_common.c
index 7b3453854..09f7269bd 100644
--- a/src/decoder/_flac_common.c
+++ b/src/decoder/_flac_common.c
@@ -40,53 +40,57 @@ flac_data_init(struct flac_data *data, struct decoder * decoder,
data->tag = NULL;
}
-static bool
+static void
flac_find_float_comment(const FLAC__StreamMetadata *block,
- const char *cmnt, float *fl)
+ const char *cmnt, float *fl, bool *found_r)
{
- int offset =
- FLAC__metadata_object_vorbiscomment_find_entry_from(block, 0, cmnt);
-
- if (offset >= 0) {
- size_t pos = strlen(cmnt) + 1; /* 1 is for '=' */
- int len = block->data.vorbis_comment.comments[offset].length
- - pos;
- if (len > 0) {
- unsigned char tmp;
- unsigned char *p = &(block->data.vorbis_comment.
- comments[offset].entry[pos]);
- tmp = p[len];
- p[len] = '\0';
- *fl = (float)atof((char *)p);
- p[len] = tmp;
-
- return true;
- }
- }
+ int offset;
+ size_t pos;
+ int len;
+ unsigned char tmp, *p;
+
+ offset = FLAC__metadata_object_vorbiscomment_find_entry_from(block, 0,
+ cmnt);
+ if (offset < 0)
+ return;
- return false;
+ pos = strlen(cmnt) + 1; /* 1 is for '=' */
+ len = block->data.vorbis_comment.comments[offset].length - pos;
+ if (len <= 0)
+ return;
+
+ p = &block->data.vorbis_comment.comments[offset].entry[pos];
+ tmp = p[len];
+ p[len] = '\0';
+ *fl = (float)atof((char *)p);
+ p[len] = tmp;
+
+ *found_r = true;
}
-/* replaygain stuff by AliasMrJones */
static void
flac_parse_replay_gain(const FLAC__StreamMetadata *block,
struct flac_data *data)
{
- bool found;
+ bool found = false;
if (data->replay_gain_info)
replay_gain_info_free(data->replay_gain_info);
data->replay_gain_info = replay_gain_info_new();
- found = flac_find_float_comment(block, "replaygain_album_gain",
- &data->replay_gain_info->tuples[REPLAY_GAIN_ALBUM].gain) ||
- flac_find_float_comment(block, "replaygain_album_peak",
- &data->replay_gain_info->tuples[REPLAY_GAIN_ALBUM].peak) ||
- flac_find_float_comment(block, "replaygain_track_gain",
- &data->replay_gain_info->tuples[REPLAY_GAIN_TRACK].gain) ||
- flac_find_float_comment(block, "replaygain_track_peak",
- &data->replay_gain_info->tuples[REPLAY_GAIN_TRACK].peak);
+ flac_find_float_comment(block, "replaygain_album_gain",
+ &data->replay_gain_info->tuples[REPLAY_GAIN_ALBUM].gain,
+ &found);
+ flac_find_float_comment(block, "replaygain_album_peak",
+ &data->replay_gain_info->tuples[REPLAY_GAIN_ALBUM].peak,
+ &found);
+ flac_find_float_comment(block, "replaygain_track_gain",
+ &data->replay_gain_info->tuples[REPLAY_GAIN_TRACK].gain,
+ &found);
+ flac_find_float_comment(block, "replaygain_track_peak",
+ &data->replay_gain_info->tuples[REPLAY_GAIN_TRACK].peak,
+ &found);
if (!found) {
replay_gain_info_free(data->replay_gain_info);
@@ -106,25 +110,27 @@ flac_comment_value(const FLAC__StreamMetadata_VorbisComment_Entry *entry,
size_t char_tnum_length = 0;
const char *comment = (const char*)entry->entry;
- if (entry->length > name_length &&
- g_ascii_strncasecmp(comment, name, name_length) == 0) {
- if (char_tnum != NULL) {
- char_tnum_length = strlen(char_tnum);
- if (entry->length > name_length + char_tnum_length + 2 &&
- comment[name_length] == '[' &&
- g_ascii_strncasecmp(comment + name_length + 1,
- char_tnum, char_tnum_length) == 0 &&
- comment[name_length + char_tnum_length + 1] == ']')
- name_length = name_length + char_tnum_length + 2;
- else if (entry->length > name_length + char_tnum_length &&
- g_ascii_strncasecmp(comment + name_length,
- char_tnum, char_tnum_length) == 0)
- name_length = name_length + char_tnum_length;
- }
- if (comment[name_length] == '=') {
- *length_r = entry->length - name_length - 1;
- return comment + name_length + 1;
- }
+ if (entry->length <= name_length ||
+ g_ascii_strncasecmp(comment, name, name_length) != 0)
+ return NULL;
+
+ if (char_tnum != NULL) {
+ char_tnum_length = strlen(char_tnum);
+ if (entry->length > name_length + char_tnum_length + 2 &&
+ comment[name_length] == '[' &&
+ g_ascii_strncasecmp(comment + name_length + 1,
+ char_tnum, char_tnum_length) == 0 &&
+ comment[name_length + char_tnum_length + 1] == ']')
+ name_length = name_length + char_tnum_length + 2;
+ else if (entry->length > name_length + char_tnum_length &&
+ g_ascii_strncasecmp(comment + name_length,
+ char_tnum, char_tnum_length) == 0)
+ name_length = name_length + char_tnum_length;
+ }
+
+ if (comment[name_length] == '=') {
+ *length_r = entry->length - name_length - 1;
+ return comment + name_length + 1;
}
return NULL;
@@ -370,13 +376,15 @@ char*
flac_cue_track( const char* pathname,
const unsigned int tnum)
{
- FLAC__StreamMetadata* cs = FLAC__metadata_object_new(FLAC__METADATA_TYPE_CUESHEET);
+ FLAC__bool success;
+ FLAC__StreamMetadata* cs;
- FLAC__metadata_get_cuesheet(pathname, &cs);
-
- if (cs == NULL)
+ success = FLAC__metadata_get_cuesheet(pathname, &cs);
+ if (!success)
return NULL;
+ assert(cs != NULL);
+
if (cs->data.cue_sheet.num_tracks <= 1)
{
FLAC__metadata_object_delete(cs);
diff --git a/src/decoder/mad_plugin.c b/src/decoder/mad_plugin.c
index 85f4506d2..c5287564f 100644
--- a/src/decoder/mad_plugin.c
+++ b/src/decoder/mad_plugin.c
@@ -350,11 +350,11 @@ parse_id3_replay_gain_info(struct id3_tag *tag)
}
#endif
-#ifdef HAVE_ID3TAG
static void mp3_parse_id3(struct mp3_data *data, size_t tagsize,
struct tag **mpd_tag,
struct replay_gain_info **replay_gain_info_r)
{
+#ifdef HAVE_ID3TAG
struct id3_tag *id3_tag = NULL;
id3_length_t count;
id3_byte_t const *id3_data;
@@ -418,8 +418,34 @@ static void mp3_parse_id3(struct mp3_data *data, size_t tagsize,
id3_tag_delete(id3_tag);
g_free(allocated);
-}
+#else /* !HAVE_ID3TAG */
+ (void)mpd_tag;
+ (void)replay_gain_info_r;
+
+ /* This code is enabled when libid3tag is disabled. Instead
+ of parsing the ID3 frame, it just skips it. */
+
+ mad_stream_skip(&data->stream, tagsize);
#endif
+}
+
+#ifndef HAVE_ID3TAG
+/**
+ * This function emulates libid3tag when it is disabled. Instead of
+ * doing a real analyzation of the frame, it just checks whether the
+ * frame begins with the string "ID3". If so, it returns the full
+ * length.
+ */
+static signed long
+id3_tag_query(const void *p0, size_t length)
+{
+ const char *p = p0;
+
+ return length > 3 && memcmp(p, "ID3", 3) == 0
+ ? length
+ : 0;
+}
+#endif /* !HAVE_ID3TAG */
static enum mp3_action
decode_next_frame_header(struct mp3_data *data, G_GNUC_UNUSED struct tag **tag,
@@ -433,7 +459,6 @@ decode_next_frame_header(struct mp3_data *data, G_GNUC_UNUSED struct tag **tag,
return DECODE_BREAK;
}
if (mad_header_decode(&data->frame.header, &data->stream)) {
-#ifdef HAVE_ID3TAG
if ((data->stream).error == MAD_ERROR_LOSTSYNC &&
(data->stream).this_frame) {
signed long tagsize = id3_tag_query((data->stream).
@@ -454,7 +479,6 @@ decode_next_frame_header(struct mp3_data *data, G_GNUC_UNUSED struct tag **tag,
return DECODE_CONT;
}
}
-#endif
if (MAD_RECOVERABLE((data->stream).error)) {
return DECODE_SKIP;
} else {
@@ -493,7 +517,6 @@ decodeNextFrame(struct mp3_data *data)
return DECODE_BREAK;
}
if (mad_frame_decode(&data->frame, &data->stream)) {
-#ifdef HAVE_ID3TAG
if ((data->stream).error == MAD_ERROR_LOSTSYNC) {
signed long tagsize = id3_tag_query((data->stream).
this_frame,
@@ -506,7 +529,6 @@ decodeNextFrame(struct mp3_data *data)
return DECODE_CONT;
}
}
-#endif
if (MAD_RECOVERABLE((data->stream).error)) {
return DECODE_SKIP;
} else {