aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorEric Wong <normalperson@yhbt.net>2008-10-03 02:19:54 -0700
committerEric Wong <normalperson@yhbt.net>2008-10-03 17:27:21 -0700
commitc5a17794b0bb8112079dd100a334b0175aec4cfa (patch)
tree6a839075bd140f7246b54e8e52853b10be614bf1 /src
parent1d9e9a408798358ea40012adc26eb6e670755337 (diff)
downloadmpd-c5a17794b0bb8112079dd100a334b0175aec4cfa.tar.gz
mpd-c5a17794b0bb8112079dd100a334b0175aec4cfa.tar.xz
mpd-c5a17794b0bb8112079dd100a334b0175aec4cfa.zip
song: start avoiding race in updateSongInfo
This is still not SMP-safe yet, as it needs at least a barrier before calling tag_free(old_tag).
Diffstat (limited to 'src')
-rw-r--r--src/song.c21
1 files changed, 12 insertions, 9 deletions
diff --git a/src/song.c b/src/song.c
index 5c5024391..dc100899a 100644
--- a/src/song.c
+++ b/src/song.c
@@ -207,19 +207,22 @@ int updateSongInfo(Song * song)
unsigned int next = 0;
char path_max_tmp[MPD_PATH_MAX];
char abs_path[MPD_PATH_MAX];
+ struct mpd_tag *old_tag = song->tag;
+ struct mpd_tag *new_tag = NULL;
utf8_to_fs_charset(abs_path, get_song_url(path_max_tmp, song));
rmp2amp_r(abs_path, abs_path);
- if (song->tag)
- tag_free(song->tag);
-
- song->tag = NULL;
-
- while (!song->tag && (plugin = isMusic(abs_path,
- &(song->mtime),
- next++))) {
- song->tag = plugin->tagDupFunc(abs_path);
+ while ((plugin = isMusic(abs_path, &song->mtime, next++))) {
+ if ((new_tag = plugin->tagDupFunc(abs_path)))
+ break;
+ }
+ if (new_tag && tag_equal(new_tag, old_tag)) {
+ tag_free(new_tag);
+ } else {
+ song->tag = new_tag;
+ if (old_tag)
+ tag_free(old_tag);
}
if (!song->tag || song->tag->time < 0)
return -1;