Commit 5ed5aa99 authored by Max Kellermann's avatar Max Kellermann

path: allocate buffer in fs_charset conversion functions

Don't use fixed static buffers. GLib allocates a new string for us anyway, let's just return this one instead of copying it.
parent f0980283
...@@ -91,16 +91,19 @@ void mapper_finish(void) ...@@ -91,16 +91,19 @@ void mapper_finish(void)
char * char *
map_uri_fs(const char *uri) map_uri_fs(const char *uri)
{ {
char buffer[MPD_PATH_MAX]; char *uri_fs, *path_fs;
assert(uri != NULL); assert(uri != NULL);
assert(*uri != '/'); assert(*uri != '/');
uri = utf8_to_fs_charset(buffer, uri); uri_fs = utf8_to_fs_charset(uri);
if (uri == NULL) if (uri_fs == NULL)
return NULL; return NULL;
return g_build_filename(music_dir, uri, NULL); path_fs = g_build_filename(music_dir, uri_fs, NULL);
g_free(uri_fs);
return path_fs;
} }
char * char *
...@@ -116,8 +119,7 @@ map_directory_fs(const struct directory *directory) ...@@ -116,8 +119,7 @@ map_directory_fs(const struct directory *directory)
char * char *
map_directory_child_fs(const struct directory *directory, const char *name) map_directory_child_fs(const struct directory *directory, const char *name)
{ {
char buffer[MPD_PATH_MAX]; char *name_fs, *parent_fs, *path;
char *parent_fs, *path;
/* check for invalid or unauthorized base names */ /* check for invalid or unauthorized base names */
if (*name == 0 || strchr(name, '/') != NULL || if (*name == 0 || strchr(name, '/') != NULL ||
...@@ -128,30 +130,33 @@ map_directory_child_fs(const struct directory *directory, const char *name) ...@@ -128,30 +130,33 @@ map_directory_child_fs(const struct directory *directory, const char *name)
if (parent_fs == NULL) if (parent_fs == NULL)
return NULL; return NULL;
name = utf8_to_fs_charset(buffer, name); name_fs = utf8_to_fs_charset(name);
path = g_build_filename(parent_fs, name, NULL); if (name_fs == NULL) {
g_free(parent_fs);
return NULL;
}
path = g_build_filename(parent_fs, name_fs, NULL);
g_free(parent_fs); g_free(parent_fs);
g_free(name_fs);
return path; return path;
} }
char * char *
map_song_fs(const struct song *song) map_song_fs(const struct song *song)
{ {
char buffer[MPD_PATH_MAX];
assert(song_is_file(song)); assert(song_is_file(song));
if (song_in_database(song)) if (song_in_database(song))
return map_directory_child_fs(song->parent, song->url); return map_directory_child_fs(song->parent, song->url);
else else
return g_strdup(utf8_to_fs_charset(buffer, song->url)); return utf8_to_fs_charset(song->url);
} }
char * char *
map_fs_to_utf8(const char *path_fs) map_fs_to_utf8(const char *path_fs)
{ {
char buffer[MPD_PATH_MAX];
if (strncmp(path_fs, music_dir, music_dir_length) == 0 && if (strncmp(path_fs, music_dir, music_dir_length) == 0 &&
path_fs[music_dir_length] == '/') path_fs[music_dir_length] == '/')
/* remove musicDir prefix */ /* remove musicDir prefix */
...@@ -160,7 +165,7 @@ map_fs_to_utf8(const char *path_fs) ...@@ -160,7 +165,7 @@ map_fs_to_utf8(const char *path_fs)
/* not within musicDir */ /* not within musicDir */
return NULL; return NULL;
return g_strdup(fs_charset_to_utf8(buffer, path_fs)); return fs_charset_to_utf8(path_fs);
} }
const char * const char *
......
...@@ -29,36 +29,27 @@ ...@@ -29,36 +29,27 @@
static char *fs_charset; static char *fs_charset;
char *fs_charset_to_utf8(char *dst, const char *str) char *
fs_charset_to_utf8(const char *path_fs)
{ {
gchar *p; return g_convert(path_fs, -1,
"utf-8", fs_charset,
p = g_convert(str, -1, NULL, NULL, NULL);
"utf-8", fs_charset,
NULL, NULL, NULL);
if (p == NULL)
/* no fallback */
return NULL;
g_strlcpy(dst, p, MPD_PATH_MAX);
g_free(p);
return dst;
} }
char *utf8_to_fs_charset(char *dst, const char *str) char *
utf8_to_fs_charset(const char *path_utf8)
{ {
gchar *p; gchar *p;
p = g_convert(str, -1, p = g_convert(path_utf8, -1,
fs_charset, "utf-8", fs_charset, "utf-8",
NULL, NULL, NULL); NULL, NULL, NULL);
if (p == NULL) if (p == NULL)
/* fall back to UTF-8 */ /* fall back to UTF-8 */
return strcpy(dst, str); p = g_strdup(path_utf8);
g_strlcpy(dst, p, MPD_PATH_MAX); return p;
g_free(p);
return dst;
} }
void path_set_fs_charset(const char *charset) void path_set_fs_charset(const char *charset)
......
...@@ -36,9 +36,19 @@ void path_global_init(void); ...@@ -36,9 +36,19 @@ void path_global_init(void);
void path_global_finish(void); void path_global_finish(void);
char *fs_charset_to_utf8(char *dst, const char *str); /**
* Converts a file name in the filesystem charset to UTF-8. Returns
* NULL on failure.
*/
char *
fs_charset_to_utf8(const char *path_fs);
char *utf8_to_fs_charset(char *dst, const char *str); /**
* Converts a file name in UTF-8 to the filesystem charset. Returns a
* duplicate of the UTF-8 string on failure.
*/
char *
utf8_to_fs_charset(const char *path_utf8);
void path_set_fs_charset(const char *charset); void path_set_fs_charset(const char *charset);
......
...@@ -36,27 +36,26 @@ playlist_print_song(FILE *file, const struct song *song) ...@@ -36,27 +36,26 @@ playlist_print_song(FILE *file, const struct song *song)
g_free(path); g_free(path);
} }
} else { } else {
char *uri = song_get_uri(song); char *uri = song_get_uri(song), *uri_fs;
char tmp2[MPD_PATH_MAX];
utf8_to_fs_charset(tmp2, uri); uri_fs = utf8_to_fs_charset(uri);
g_free(uri); g_free(uri);
fprintf(file, "%s\n", uri); fprintf(file, "%s\n", uri_fs);
g_free(uri_fs);
} }
} }
void void
playlist_print_uri(FILE *file, const char *uri) playlist_print_uri(FILE *file, const char *uri)
{ {
char tmp[MPD_PATH_MAX];
char *s; char *s;
if (playlist_saveAbsolutePaths && !uri_has_scheme(uri) && if (playlist_saveAbsolutePaths && !uri_has_scheme(uri) &&
uri[0] != '/') uri[0] != '/')
s = map_uri_fs(uri); s = map_uri_fs(uri);
else else
s = g_strdup(utf8_to_fs_charset(tmp, uri)); s = utf8_to_fs_charset(uri);
if (s != NULL) { if (s != NULL) {
fprintf(file, "%s\n", s); fprintf(file, "%s\n", s);
......
...@@ -37,7 +37,7 @@ static struct stored_playlist_info * ...@@ -37,7 +37,7 @@ static struct stored_playlist_info *
load_playlist_info(const char *parent_path_fs, const char *name_fs) load_playlist_info(const char *parent_path_fs, const char *name_fs)
{ {
size_t name_length = strlen(name_fs); size_t name_length = strlen(name_fs);
char buffer[MPD_PATH_MAX], *path_fs, *name, *name_utf8; char *path_fs, *name, *name_utf8;
int ret; int ret;
struct stat st; struct stat st;
struct stored_playlist_info *playlist; struct stored_playlist_info *playlist;
...@@ -60,13 +60,13 @@ load_playlist_info(const char *parent_path_fs, const char *name_fs) ...@@ -60,13 +60,13 @@ load_playlist_info(const char *parent_path_fs, const char *name_fs)
name = g_strdup(name_fs); name = g_strdup(name_fs);
name[name_length - sizeof(PLAYLIST_FILE_SUFFIX)] = 0; name[name_length - sizeof(PLAYLIST_FILE_SUFFIX)] = 0;
name_utf8 = fs_charset_to_utf8(buffer, name); name_utf8 = fs_charset_to_utf8(name);
g_free(name); g_free(name);
if (name_utf8 == NULL) if (name_utf8 == NULL)
return NULL; return NULL;
playlist = g_new(struct stored_playlist_info, 1); playlist = g_new(struct stored_playlist_info, 1);
playlist->name = g_strdup(name_utf8); playlist->name = name_utf8;
playlist->mtime = st.st_mtime; playlist->mtime = st.st_mtime;
return playlist; return playlist;
} }
......
...@@ -545,15 +545,19 @@ updateDirectory(struct directory *directory, const struct stat *st) ...@@ -545,15 +545,19 @@ updateDirectory(struct directory *directory, const struct stat *st)
if (skip_path(ent->d_name)) if (skip_path(ent->d_name))
continue; continue;
utf8 = fs_charset_to_utf8(path_max_tmp, ent->d_name); utf8 = fs_charset_to_utf8(ent->d_name);
if (utf8 == NULL || skip_symlink(directory, utf8)) if (utf8 == NULL || skip_symlink(directory, utf8)) {
g_free(utf8);
continue; continue;
}
if (stat_directory_child(directory, utf8, &st2) == 0) if (stat_directory_child(directory, utf8, &st2) == 0)
updateInDirectory(directory, updateInDirectory(directory,
path_max_tmp, &st2); path_max_tmp, &st2);
else else
delete_name_in(directory, path_max_tmp); delete_name_in(directory, path_max_tmp);
g_free(utf8);
} }
closedir(dir); closedir(dir);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment