Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
M
mpd
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Registry
Registry
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
Иван Мажукин
mpd
Commits
ca419c84
Commit
ca419c84
authored
Sep 11, 2011
by
Max Kellermann
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
stored_playlist: return GError, code is playlist_result
Improve error reporting and handling. command.c gets the new function print_error(), which sends a GError to the client.
parent
aede71b1
Hide whitespace changes
Inline
Side-by-side
Showing
10 changed files
with
320 additions
and
197 deletions
+320
-197
command.c
src/command.c
+72
-51
dbUtils.c
src/dbUtils.c
+9
-3
dbUtils.h
src/dbUtils.h
+6
-1
playlist_error.h
src/playlist_error.h
+12
-0
playlist_print.c
src/playlist_print.c
+3
-2
playlist_print.h
src/playlist_print.h
+3
-1
playlist_save.c
src/playlist_save.c
+5
-5
playlist_save.h
src/playlist_save.h
+3
-2
stored_playlist.c
src/stored_playlist.c
+190
-114
stored_playlist.h
src/stored_playlist.h
+17
-18
No files found.
src/command.c
View file @
ca419c84
...
@@ -24,6 +24,7 @@
...
@@ -24,6 +24,7 @@
#include "playlist_print.h"
#include "playlist_print.h"
#include "playlist_save.h"
#include "playlist_save.h"
#include "playlist_queue.h"
#include "playlist_queue.h"
#include "playlist_error.h"
#include "queue_print.h"
#include "queue_print.h"
#include "ls.h"
#include "ls.h"
#include "uri.h"
#include "uri.h"
...
@@ -376,6 +377,33 @@ print_playlist_result(struct client *client,
...
@@ -376,6 +377,33 @@ print_playlist_result(struct client *client,
return
COMMAND_RETURN_ERROR
;
return
COMMAND_RETURN_ERROR
;
}
}
/**
* Send the GError to the client and free the GError.
*/
static
enum
command_return
print_error
(
struct
client
*
client
,
GError
*
error
)
{
assert
(
client
!=
NULL
);
assert
(
error
!=
NULL
);
g_warning
(
"%s"
,
error
->
message
);
if
(
error
->
domain
==
playlist_quark
())
{
enum
playlist_result
result
=
error
->
code
;
g_error_free
(
error
);
return
print_playlist_result
(
client
,
result
);
}
else
if
(
error
->
domain
==
g_file_error_quark
())
{
command_error
(
client
,
ACK_ERROR_SYSTEM
,
"%s"
,
g_strerror
(
error
->
code
));
g_error_free
(
error
);
return
COMMAND_RETURN_ERROR
;
}
g_error_free
(
error
);
command_error
(
client
,
ACK_ERROR_UNKNOWN
,
"error"
);
return
COMMAND_RETURN_ERROR
;
}
static
void
static
void
print_spl_list
(
struct
client
*
client
,
GPtrArray
*
list
)
print_spl_list
(
struct
client
*
client
,
GPtrArray
*
list
)
{
{
...
@@ -766,9 +794,11 @@ handle_load(struct client *client, G_GNUC_UNUSED int argc, char *argv[])
...
@@ -766,9 +794,11 @@ handle_load(struct client *client, G_GNUC_UNUSED int argc, char *argv[])
if
(
result
!=
PLAYLIST_RESULT_NO_SUCH_LIST
)
if
(
result
!=
PLAYLIST_RESULT_NO_SUCH_LIST
)
return
print_playlist_result
(
client
,
result
);
return
print_playlist_result
(
client
,
result
);
result
=
playlist_load_spl
(
&
g_playlist
,
client
->
player_control
,
GError
*
error
=
NULL
;
argv
[
1
]);
return
playlist_load_spl
(
&
g_playlist
,
client
->
player_control
,
return
print_playlist_result
(
client
,
result
);
argv
[
1
],
&
error
)
?
COMMAND_RETURN_OK
:
print_error
(
client
,
error
);
}
}
static
enum
command_return
static
enum
command_return
...
@@ -777,15 +807,10 @@ handle_listplaylist(struct client *client, G_GNUC_UNUSED int argc, char *argv[])
...
@@ -777,15 +807,10 @@ handle_listplaylist(struct client *client, G_GNUC_UNUSED int argc, char *argv[])
if
(
playlist_file_print
(
client
,
argv
[
1
],
false
))
if
(
playlist_file_print
(
client
,
argv
[
1
],
false
))
return
COMMAND_RETURN_OK
;
return
COMMAND_RETURN_OK
;
bool
ret
;
GError
*
error
=
NULL
;
return
spl_print
(
client
,
argv
[
1
],
false
,
&
error
)
ret
=
spl_print
(
client
,
argv
[
1
],
false
);
?
COMMAND_RETURN_OK
if
(
!
ret
)
{
:
print_error
(
client
,
error
);
command_error
(
client
,
ACK_ERROR_NO_EXIST
,
"No such playlist"
);
return
COMMAND_RETURN_ERROR
;
}
return
COMMAND_RETURN_OK
;
}
}
static
enum
command_return
static
enum
command_return
...
@@ -795,15 +820,10 @@ handle_listplaylistinfo(struct client *client,
...
@@ -795,15 +820,10 @@ handle_listplaylistinfo(struct client *client,
if
(
playlist_file_print
(
client
,
argv
[
1
],
true
))
if
(
playlist_file_print
(
client
,
argv
[
1
],
true
))
return
COMMAND_RETURN_OK
;
return
COMMAND_RETURN_OK
;
bool
ret
;
GError
*
error
=
NULL
;
return
spl_print
(
client
,
argv
[
1
],
true
,
&
error
)
ret
=
spl_print
(
client
,
argv
[
1
],
true
);
?
COMMAND_RETURN_OK
if
(
!
ret
)
{
:
print_error
(
client
,
error
);
command_error
(
client
,
ACK_ERROR_NO_EXIST
,
"No such playlist"
);
return
COMMAND_RETURN_ERROR
;
}
return
COMMAND_RETURN_OK
;
}
}
static
enum
command_return
static
enum
command_return
...
@@ -828,7 +848,7 @@ handle_lsinfo(struct client *client, int argc, char *argv[])
...
@@ -828,7 +848,7 @@ handle_lsinfo(struct client *client, int argc, char *argv[])
directory_print
(
client
,
directory
);
directory_print
(
client
,
directory
);
if
(
isRootDirectory
(
uri
))
{
if
(
isRootDirectory
(
uri
))
{
GPtrArray
*
list
=
spl_list
();
GPtrArray
*
list
=
spl_list
(
NULL
);
if
(
list
!=
NULL
)
{
if
(
list
!=
NULL
)
{
print_spl_list
(
client
,
list
);
print_spl_list
(
client
,
list
);
spl_list_free
(
list
);
spl_list_free
(
list
);
...
@@ -841,19 +861,19 @@ handle_lsinfo(struct client *client, int argc, char *argv[])
...
@@ -841,19 +861,19 @@ handle_lsinfo(struct client *client, int argc, char *argv[])
static
enum
command_return
static
enum
command_return
handle_rm
(
struct
client
*
client
,
G_GNUC_UNUSED
int
argc
,
char
*
argv
[])
handle_rm
(
struct
client
*
client
,
G_GNUC_UNUSED
int
argc
,
char
*
argv
[])
{
{
enum
playlist_result
result
;
GError
*
error
=
NULL
;
return
spl_delete
(
argv
[
1
],
&
error
)
result
=
spl_delete
(
argv
[
1
]);
?
COMMAND_RETURN_OK
return
print_playlist_result
(
client
,
result
);
:
print_error
(
client
,
error
);
}
}
static
enum
command_return
static
enum
command_return
handle_rename
(
struct
client
*
client
,
G_GNUC_UNUSED
int
argc
,
char
*
argv
[])
handle_rename
(
struct
client
*
client
,
G_GNUC_UNUSED
int
argc
,
char
*
argv
[])
{
{
enum
playlist_result
result
;
GError
*
error
=
NULL
;
return
spl_rename
(
argv
[
1
],
argv
[
2
],
&
error
)
result
=
spl_rename
(
argv
[
1
],
argv
[
2
]);
?
COMMAND_RETURN_OK
return
print_playlist_result
(
client
,
result
);
:
print_error
(
client
,
error
);
}
}
static
enum
command_return
static
enum
command_return
...
@@ -1064,13 +1084,14 @@ handle_playlistdelete(struct client *client,
...
@@ -1064,13 +1084,14 @@ handle_playlistdelete(struct client *client,
G_GNUC_UNUSED
int
argc
,
char
*
argv
[])
{
G_GNUC_UNUSED
int
argc
,
char
*
argv
[])
{
char
*
playlist
=
argv
[
1
];
char
*
playlist
=
argv
[
1
];
int
from
;
int
from
;
enum
playlist_result
result
;
if
(
!
check_int
(
client
,
&
from
,
argv
[
2
],
check_integer
,
argv
[
2
]))
if
(
!
check_int
(
client
,
&
from
,
argv
[
2
],
check_integer
,
argv
[
2
]))
return
COMMAND_RETURN_ERROR
;
return
COMMAND_RETURN_ERROR
;
result
=
spl_remove_index
(
playlist
,
from
);
GError
*
error
=
NULL
;
return
print_playlist_result
(
client
,
result
);
return
spl_remove_index
(
playlist
,
from
,
&
error
)
?
COMMAND_RETURN_OK
:
print_error
(
client
,
error
);
}
}
static
enum
command_return
static
enum
command_return
...
@@ -1078,15 +1099,16 @@ handle_playlistmove(struct client *client, G_GNUC_UNUSED int argc, char *argv[])
...
@@ -1078,15 +1099,16 @@ handle_playlistmove(struct client *client, G_GNUC_UNUSED int argc, char *argv[])
{
{
char
*
playlist
=
argv
[
1
];
char
*
playlist
=
argv
[
1
];
int
from
,
to
;
int
from
,
to
;
enum
playlist_result
result
;
if
(
!
check_int
(
client
,
&
from
,
argv
[
2
],
check_integer
,
argv
[
2
]))
if
(
!
check_int
(
client
,
&
from
,
argv
[
2
],
check_integer
,
argv
[
2
]))
return
COMMAND_RETURN_ERROR
;
return
COMMAND_RETURN_ERROR
;
if
(
!
check_int
(
client
,
&
to
,
argv
[
3
],
check_integer
,
argv
[
3
]))
if
(
!
check_int
(
client
,
&
to
,
argv
[
3
],
check_integer
,
argv
[
3
]))
return
COMMAND_RETURN_ERROR
;
return
COMMAND_RETURN_ERROR
;
result
=
spl_move_index
(
playlist
,
from
,
to
);
GError
*
error
=
NULL
;
return
print_playlist_result
(
client
,
result
);
return
spl_move_index
(
playlist
,
from
,
to
,
&
error
)
?
COMMAND_RETURN_OK
:
print_error
(
client
,
error
);
}
}
static
enum
command_return
static
enum
command_return
...
@@ -1642,10 +1664,10 @@ handle_not_commands(struct client *client,
...
@@ -1642,10 +1664,10 @@ handle_not_commands(struct client *client,
static
enum
command_return
static
enum
command_return
handle_playlistclear
(
struct
client
*
client
,
G_GNUC_UNUSED
int
argc
,
char
*
argv
[])
handle_playlistclear
(
struct
client
*
client
,
G_GNUC_UNUSED
int
argc
,
char
*
argv
[])
{
{
enum
playlist_result
result
;
GError
*
error
=
NULL
;
return
spl_clear
(
argv
[
1
],
&
error
)
result
=
spl_clear
(
argv
[
1
]);
?
COMMAND_RETURN_OK
return
print_playlist_result
(
client
,
result
);
:
print_error
(
client
,
error
);
}
}
static
enum
command_return
static
enum
command_return
...
@@ -1653,8 +1675,9 @@ handle_playlistadd(struct client *client, G_GNUC_UNUSED int argc, char *argv[])
...
@@ -1653,8 +1675,9 @@ handle_playlistadd(struct client *client, G_GNUC_UNUSED int argc, char *argv[])
{
{
char
*
playlist
=
argv
[
1
];
char
*
playlist
=
argv
[
1
];
char
*
uri
=
argv
[
2
];
char
*
uri
=
argv
[
2
];
enum
playlist_result
result
;
bool
success
;
GError
*
error
=
NULL
;
if
(
uri_has_scheme
(
uri
))
{
if
(
uri_has_scheme
(
uri
))
{
if
(
!
uri_supported_scheme
(
uri
))
{
if
(
!
uri_supported_scheme
(
uri
))
{
command_error
(
client
,
ACK_ERROR_NO_EXIST
,
command_error
(
client
,
ACK_ERROR_NO_EXIST
,
...
@@ -1662,29 +1685,27 @@ handle_playlistadd(struct client *client, G_GNUC_UNUSED int argc, char *argv[])
...
@@ -1662,29 +1685,27 @@ handle_playlistadd(struct client *client, G_GNUC_UNUSED int argc, char *argv[])
return
COMMAND_RETURN_ERROR
;
return
COMMAND_RETURN_ERROR
;
}
}
result
=
spl_append_uri
(
uri
,
playlist
);
success
=
spl_append_uri
(
argv
[
1
],
playlist
,
&
error
);
}
else
}
else
result
=
addAllInToStoredPlaylist
(
uri
,
playlist
);
success
=
addAllInToStoredPlaylist
(
uri
,
playlist
,
&
error
);
if
(
result
==
(
enum
playlist_result
)
-
1
)
{
if
(
!
success
&&
error
==
NULL
)
{
command_error
(
client
,
ACK_ERROR_NO_EXIST
,
command_error
(
client
,
ACK_ERROR_NO_EXIST
,
"directory or file not found"
);
"directory or file not found"
);
return
COMMAND_RETURN_ERROR
;
return
COMMAND_RETURN_ERROR
;
}
}
return
print_playlist_result
(
client
,
result
);
return
success
?
COMMAND_RETURN_OK
:
print_error
(
client
,
error
);
}
}
static
enum
command_return
static
enum
command_return
handle_listplaylists
(
struct
client
*
client
,
handle_listplaylists
(
struct
client
*
client
,
G_GNUC_UNUSED
int
argc
,
G_GNUC_UNUSED
char
*
argv
[])
G_GNUC_UNUSED
int
argc
,
G_GNUC_UNUSED
char
*
argv
[])
{
{
GPtrArray
*
list
=
spl_list
();
GError
*
error
=
NULL
;
if
(
list
==
NULL
)
{
GPtrArray
*
list
=
spl_list
(
&
error
);
command_error
(
client
,
ACK_ERROR_SYSTEM
,
if
(
list
==
NULL
)
"failed to get list of stored playlists"
);
return
print_error
(
client
,
error
);
return
COMMAND_RETURN_ERROR
;
}
print_spl_list
(
client
,
list
);
print_spl_list
(
client
,
list
);
spl_list_free
(
list
);
spl_list_free
(
list
);
...
...
src/dbUtils.c
View file @
ca419c84
...
@@ -36,6 +36,7 @@ directoryAddSongToPlaylist(struct song *song, void *data)
...
@@ -36,6 +36,7 @@ directoryAddSongToPlaylist(struct song *song, void *data)
struct
add_data
{
struct
add_data
{
const
char
*
path
;
const
char
*
path
;
GError
**
error_r
;
};
};
static
int
static
int
...
@@ -43,8 +44,10 @@ directoryAddSongToStoredPlaylist(struct song *song, void *_data)
...
@@ -43,8 +44,10 @@ directoryAddSongToStoredPlaylist(struct song *song, void *_data)
{
{
struct
add_data
*
data
=
_data
;
struct
add_data
*
data
=
_data
;
if
(
spl_append_song
(
data
->
path
,
song
)
!=
0
)
if
(
!
spl_append_song
(
data
->
path
,
song
,
data
->
error_r
))
{
return
-
1
;
return
-
1
;
}
return
0
;
return
0
;
}
}
...
@@ -54,13 +57,16 @@ addAllIn(struct player_control *pc, const char *name)
...
@@ -54,13 +57,16 @@ addAllIn(struct player_control *pc, const char *name)
return
db_walk
(
name
,
directoryAddSongToPlaylist
,
NULL
,
pc
);
return
db_walk
(
name
,
directoryAddSongToPlaylist
,
NULL
,
pc
);
}
}
int
addAllInToStoredPlaylist
(
const
char
*
name
,
const
char
*
utf8file
)
bool
addAllInToStoredPlaylist
(
const
char
*
name
,
const
char
*
utf8file
,
GError
**
error_r
)
{
{
struct
add_data
data
=
{
struct
add_data
data
=
{
.
path
=
utf8file
,
.
path
=
utf8file
,
.
error_r
=
error_r
,
};
};
return
db_walk
(
name
,
directoryAddSongToStoredPlaylist
,
NULL
,
&
data
);
return
db_walk
(
name
,
directoryAddSongToStoredPlaylist
,
NULL
,
&
data
)
==
0
;
}
}
struct
find_add_data
{
struct
find_add_data
{
...
...
src/dbUtils.h
View file @
ca419c84
...
@@ -20,13 +20,18 @@
...
@@ -20,13 +20,18 @@
#ifndef MPD_DB_UTILS_H
#ifndef MPD_DB_UTILS_H
#define MPD_DB_UTILS_H
#define MPD_DB_UTILS_H
#include <glib.h>
#include <stdbool.h>
struct
locate_item_list
;
struct
locate_item_list
;
struct
player_control
;
struct
player_control
;
int
int
addAllIn
(
struct
player_control
*
pc
,
const
char
*
name
);
addAllIn
(
struct
player_control
*
pc
,
const
char
*
name
);
int
addAllInToStoredPlaylist
(
const
char
*
name
,
const
char
*
utf8file
);
bool
addAllInToStoredPlaylist
(
const
char
*
uri_utf8
,
const
char
*
path_utf8
,
GError
**
error_r
);
int
int
findAddIn
(
struct
player_control
*
pc
,
const
char
*
name
,
findAddIn
(
struct
player_control
*
pc
,
const
char
*
name
,
...
...
src/playlist_error.h
View file @
ca419c84
...
@@ -20,6 +20,8 @@
...
@@ -20,6 +20,8 @@
#ifndef MPD_PLAYLIST_ERROR_H
#ifndef MPD_PLAYLIST_ERROR_H
#define MPD_PLAYLIST_ERROR_H
#define MPD_PLAYLIST_ERROR_H
#include <glib.h>
enum
playlist_result
{
enum
playlist_result
{
PLAYLIST_RESULT_SUCCESS
,
PLAYLIST_RESULT_SUCCESS
,
PLAYLIST_RESULT_ERRNO
,
PLAYLIST_RESULT_ERRNO
,
...
@@ -34,4 +36,14 @@ enum playlist_result {
...
@@ -34,4 +36,14 @@ enum playlist_result {
PLAYLIST_RESULT_DISABLED
,
PLAYLIST_RESULT_DISABLED
,
};
};
/**
* Quark for GError.domain; the code is an enum #playlist_result.
*/
G_GNUC_CONST
static
inline
GQuark
playlist_quark
(
void
)
{
return
g_quark_from_static_string
(
"playlist"
);
}
#endif
#endif
src/playlist_print.c
View file @
ca419c84
...
@@ -117,11 +117,12 @@ playlist_print_changes_position(struct client *client,
...
@@ -117,11 +117,12 @@ playlist_print_changes_position(struct client *client,
}
}
bool
bool
spl_print
(
struct
client
*
client
,
const
char
*
name_utf8
,
bool
detail
)
spl_print
(
struct
client
*
client
,
const
char
*
name_utf8
,
bool
detail
,
GError
**
error_r
)
{
{
GPtrArray
*
list
;
GPtrArray
*
list
;
list
=
spl_load
(
name_utf8
);
list
=
spl_load
(
name_utf8
,
error_r
);
if
(
list
==
NULL
)
if
(
list
==
NULL
)
return
false
;
return
false
;
...
...
src/playlist_print.h
View file @
ca419c84
...
@@ -20,6 +20,7 @@
...
@@ -20,6 +20,7 @@
#ifndef PLAYLIST_PRINT_H
#ifndef PLAYLIST_PRINT_H
#define PLAYLIST_PRINT_H
#define PLAYLIST_PRINT_H
#include <glib.h>
#include <stdbool.h>
#include <stdbool.h>
#include <stdint.h>
#include <stdint.h>
...
@@ -99,7 +100,8 @@ playlist_print_changes_position(struct client *client,
...
@@ -99,7 +100,8 @@ playlist_print_changes_position(struct client *client,
* @return true on success, false if the playlist does not exist
* @return true on success, false if the playlist does not exist
*/
*/
bool
bool
spl_print
(
struct
client
*
client
,
const
char
*
name_utf8
,
bool
detail
);
spl_print
(
struct
client
*
client
,
const
char
*
name_utf8
,
bool
detail
,
GError
**
error_r
);
/**
/**
* Send the playlist file to the client.
* Send the playlist file to the client.
...
...
src/playlist_save.c
View file @
ca419c84
...
@@ -110,15 +110,15 @@ spl_save_playlist(const char *name_utf8, const struct playlist *playlist)
...
@@ -110,15 +110,15 @@ spl_save_playlist(const char *name_utf8, const struct playlist *playlist)
return
spl_save_queue
(
name_utf8
,
&
playlist
->
queue
);
return
spl_save_queue
(
name_utf8
,
&
playlist
->
queue
);
}
}
enum
playlist_result
bool
playlist_load_spl
(
struct
playlist
*
playlist
,
struct
player_control
*
pc
,
playlist_load_spl
(
struct
playlist
*
playlist
,
struct
player_control
*
pc
,
const
char
*
name_utf8
)
const
char
*
name_utf8
,
GError
**
error_r
)
{
{
GPtrArray
*
list
;
GPtrArray
*
list
;
list
=
spl_load
(
name_utf8
);
list
=
spl_load
(
name_utf8
,
error_r
);
if
(
list
==
NULL
)
if
(
list
==
NULL
)
return
PLAYLIST_RESULT_NO_SUCH_LIST
;
return
false
;
for
(
unsigned
i
=
0
;
i
<
list
->
len
;
++
i
)
{
for
(
unsigned
i
=
0
;
i
<
list
->
len
;
++
i
)
{
const
char
*
temp
=
g_ptr_array_index
(
list
,
i
);
const
char
*
temp
=
g_ptr_array_index
(
list
,
i
);
...
@@ -139,5 +139,5 @@ playlist_load_spl(struct playlist *playlist, struct player_control *pc,
...
@@ -139,5 +139,5 @@ playlist_load_spl(struct playlist *playlist, struct player_control *pc,
}
}
spl_free
(
list
);
spl_free
(
list
);
return
PLAYLIST_RESULT_SUCCESS
;
return
true
;
}
}
src/playlist_save.h
View file @
ca419c84
...
@@ -22,6 +22,7 @@
...
@@ -22,6 +22,7 @@
#include "playlist_error.h"
#include "playlist_error.h"
#include <stdbool.h>
#include <stdio.h>
#include <stdio.h>
struct
song
;
struct
song
;
...
@@ -51,8 +52,8 @@ spl_save_playlist(const char *name_utf8, const struct playlist *playlist);
...
@@ -51,8 +52,8 @@ spl_save_playlist(const char *name_utf8, const struct playlist *playlist);
* Loads a stored playlist file, and append all songs to the global
* Loads a stored playlist file, and append all songs to the global
* playlist.
* playlist.
*/
*/
enum
playlist_result
bool
playlist_load_spl
(
struct
playlist
*
playlist
,
struct
player_control
*
pc
,
playlist_load_spl
(
struct
playlist
*
playlist
,
struct
player_control
*
pc
,
const
char
*
name_utf8
);
const
char
*
name_utf8
,
GError
**
error_r
);
#endif
#endif
src/stored_playlist.c
View file @
ca419c84
...
@@ -28,6 +28,7 @@
...
@@ -28,6 +28,7 @@
#include "database.h"
#include "database.h"
#include "idle.h"
#include "idle.h"
#include "conf.h"
#include "conf.h"
#include "glib_compat.h"
#include <assert.h>
#include <assert.h>
#include <sys/types.h>
#include <sys/types.h>
...
@@ -72,6 +73,67 @@ spl_valid_name(const char *name_utf8)
...
@@ -72,6 +73,67 @@ spl_valid_name(const char *name_utf8)
strchr
(
name_utf8
,
'\r'
)
==
NULL
;
strchr
(
name_utf8
,
'\r'
)
==
NULL
;
}
}
static
const
char
*
spl_map
(
GError
**
error_r
)
{
const
char
*
path_fs
=
map_spl_path
();
if
(
path_fs
==
NULL
)
g_set_error_literal
(
error_r
,
playlist_quark
(),
PLAYLIST_RESULT_DISABLED
,
"Stored playlists are disabled"
);
return
path_fs
;
}
static
bool
spl_check_name
(
const
char
*
name_utf8
,
GError
**
error_r
)
{
if
(
!
spl_valid_name
(
name_utf8
))
{
g_set_error_literal
(
error_r
,
playlist_quark
(),
PLAYLIST_RESULT_BAD_NAME
,
"Bad playlist name"
);
return
false
;
}
return
true
;
}
static
char
*
spl_map_to_fs
(
const
char
*
name_utf8
,
GError
**
error_r
)
{
if
(
spl_map
(
error_r
)
==
NULL
||
!
spl_check_name
(
name_utf8
,
error_r
))
return
NULL
;
char
*
path_fs
=
map_spl_utf8_to_fs
(
name_utf8
);
if
(
path_fs
==
NULL
)
g_set_error_literal
(
error_r
,
playlist_quark
(),
PLAYLIST_RESULT_BAD_NAME
,
"Bad playlist name"
);
return
path_fs
;
}
/**
* Create a GError for the current errno.
*/
static
void
playlist_errno
(
GError
**
error_r
)
{
switch
(
errno
)
{
case
ENOENT
:
g_set_error_literal
(
error_r
,
playlist_quark
(),
PLAYLIST_RESULT_NO_SUCH_LIST
,
"No such playlist"
);
break
;
default:
g_set_error_literal
(
error_r
,
g_file_error_quark
(),
errno
,
g_strerror
(
errno
));
break
;
}
}
static
struct
stored_playlist_info
*
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
)
{
{
...
@@ -108,9 +170,9 @@ load_playlist_info(const char *parent_path_fs, const char *name_fs)
...
@@ -108,9 +170,9 @@ load_playlist_info(const char *parent_path_fs, const char *name_fs)
}
}
GPtrArray
*
GPtrArray
*
spl_list
(
void
)
spl_list
(
GError
**
error_r
)
{
{
const
char
*
parent_path_fs
=
map_spl_path
(
);
const
char
*
parent_path_fs
=
spl_map
(
error_r
);
DIR
*
dir
;
DIR
*
dir
;
struct
dirent
*
ent
;
struct
dirent
*
ent
;
GPtrArray
*
list
;
GPtrArray
*
list
;
...
@@ -120,8 +182,11 @@ spl_list(void)
...
@@ -120,8 +182,11 @@ spl_list(void)
return
NULL
;
return
NULL
;
dir
=
opendir
(
parent_path_fs
);
dir
=
opendir
(
parent_path_fs
);
if
(
dir
==
NULL
)
if
(
dir
==
NULL
)
{
g_set_error_literal
(
error_r
,
g_file_error_quark
(),
errno
,
g_strerror
(
errno
));
return
NULL
;
return
NULL
;
}
list
=
g_ptr_array_new
();
list
=
g_ptr_array_new
();
...
@@ -148,25 +213,26 @@ spl_list_free(GPtrArray *list)
...
@@ -148,25 +213,26 @@ spl_list_free(GPtrArray *list)
g_ptr_array_free
(
list
,
true
);
g_ptr_array_free
(
list
,
true
);
}
}
static
enum
playlist_result
static
bool
spl_save
(
GPtrArray
*
list
,
const
char
*
utf8path
)
spl_save
(
GPtrArray
*
list
,
const
char
*
utf8path
,
GError
**
error_r
)
{
{
FILE
*
file
;
FILE
*
file
;
char
*
path_fs
;
assert
(
utf8path
!=
NULL
);
assert
(
utf8path
!=
NULL
);
if
(
map_spl_path
(
)
==
NULL
)
if
(
spl_map
(
error_r
)
==
NULL
)
return
PLAYLIST_RESULT_DISABLED
;
return
false
;
path_fs
=
map_spl_utf8_to_fs
(
utf8path
);
char
*
path_fs
=
spl_map_to_fs
(
utf8path
,
error_r
);
if
(
path_fs
==
NULL
)
if
(
path_fs
==
NULL
)
return
PLAYLIST_RESULT_BAD_NAME
;
return
false
;
file
=
fopen
(
path_fs
,
"w"
);
file
=
fopen
(
path_fs
,
"w"
);
g_free
(
path_fs
);
g_free
(
path_fs
);
if
(
file
==
NULL
)
if
(
file
==
NULL
)
{
return
PLAYLIST_RESULT_ERRNO
;
playlist_errno
(
error_r
);
return
false
;
}
for
(
unsigned
i
=
0
;
i
<
list
->
len
;
++
i
)
{
for
(
unsigned
i
=
0
;
i
<
list
->
len
;
++
i
)
{
const
char
*
uri
=
g_ptr_array_index
(
list
,
i
);
const
char
*
uri
=
g_ptr_array_index
(
list
,
i
);
...
@@ -174,27 +240,29 @@ spl_save(GPtrArray *list, const char *utf8path)
...
@@ -174,27 +240,29 @@ spl_save(GPtrArray *list, const char *utf8path)
}
}
fclose
(
file
);
fclose
(
file
);
return
PLAYLIST_RESULT_SUCCESS
;
return
true
;
}
}
GPtrArray
*
GPtrArray
*
spl_load
(
const
char
*
utf8path
)
spl_load
(
const
char
*
utf8path
,
GError
**
error_r
)
{
{
FILE
*
file
;
FILE
*
file
;
GPtrArray
*
list
;
GPtrArray
*
list
;
char
*
path_fs
;
char
*
path_fs
;
if
(
!
spl_valid_name
(
utf8path
)
||
map_spl_path
(
)
==
NULL
)
if
(
spl_map
(
error_r
)
==
NULL
)
return
NULL
;
return
NULL
;
path_fs
=
map_spl_utf8_to_fs
(
utf8path
);
path_fs
=
spl_map_to_fs
(
utf8path
,
error_r
);
if
(
path_fs
==
NULL
)
if
(
path_fs
==
NULL
)
return
NULL
;
return
NULL
;
file
=
fopen
(
path_fs
,
"r"
);
file
=
fopen
(
path_fs
,
"r"
);
g_free
(
path_fs
);
g_free
(
path_fs
);
if
(
file
==
NULL
)
if
(
file
==
NULL
)
{
playlist_errno
(
error_r
);
return
NULL
;
return
NULL
;
}
list
=
g_ptr_array_new
();
list
=
g_ptr_array_new
();
...
@@ -260,30 +328,33 @@ spl_insert_index_internal(GPtrArray *list, unsigned idx, char *uri)
...
@@ -260,30 +328,33 @@ spl_insert_index_internal(GPtrArray *list, unsigned idx, char *uri)
g_ptr_array_index
(
list
,
idx
)
=
uri
;
g_ptr_array_index
(
list
,
idx
)
=
uri
;
}
}
enum
playlist_result
bool
spl_move_index
(
const
char
*
utf8path
,
unsigned
src
,
unsigned
dest
)
spl_move_index
(
const
char
*
utf8path
,
unsigned
src
,
unsigned
dest
,
GError
**
error_r
)
{
{
GPtrArray
*
list
;
char
*
uri
;
char
*
uri
;
enum
playlist_result
result
;
if
(
src
==
dest
)
if
(
src
==
dest
)
/* this doesn't check whether the playlist exists, but
/* this doesn't check whether the playlist exists, but
what the hell.. */
what the hell.. */
return
PLAYLIST_RESULT_SUCCESS
;
return
true
;
if
(
!
(
list
=
spl_load
(
utf8path
)))
GPtrArray
*
list
=
spl_load
(
utf8path
,
error_r
);
return
PLAYLIST_RESULT_NO_SUCH_LIST
;
if
(
list
==
NULL
)
return
false
;
if
(
src
>=
list
->
len
||
dest
>=
list
->
len
)
{
if
(
src
>=
list
->
len
||
dest
>=
list
->
len
)
{
spl_free
(
list
);
spl_free
(
list
);
return
PLAYLIST_RESULT_BAD_RANGE
;
g_set_error_literal
(
error_r
,
playlist_quark
(),
PLAYLIST_RESULT_BAD_RANGE
,
"Bad range"
);
return
false
;
}
}
uri
=
spl_remove_index_internal
(
list
,
src
);
uri
=
spl_remove_index_internal
(
list
,
src
);
spl_insert_index_internal
(
list
,
dest
,
uri
);
spl_insert_index_internal
(
list
,
dest
,
uri
);
result
=
spl_save
(
list
,
utf8path
);
bool
result
=
spl_save
(
list
,
utf8path
,
error_r
);
spl_free
(
list
);
spl_free
(
list
);
...
@@ -291,78 +362,72 @@ spl_move_index(const char *utf8path, unsigned src, unsigned dest)
...
@@ -291,78 +362,72 @@ spl_move_index(const char *utf8path, unsigned src, unsigned dest)
return
result
;
return
result
;
}
}
enum
playlist_result
bool
spl_clear
(
const
char
*
utf8path
)
spl_clear
(
const
char
*
utf8path
,
GError
**
error_r
)
{
{
char
*
path_fs
;
FILE
*
file
;
FILE
*
file
;
if
(
map_spl_path
()
==
NULL
)
if
(
spl_map
(
error_r
)
==
NULL
)
return
PLAYLIST_RESULT_DISABLED
;
return
false
;
if
(
!
spl_valid_name
(
utf8path
))
return
PLAYLIST_RESULT_BAD_NAME
;
path_fs
=
map_spl_utf8_to_fs
(
utf8path
);
char
*
path_fs
=
spl_map_to_fs
(
utf8path
,
error_r
);
if
(
path_fs
==
NULL
)
if
(
path_fs
==
NULL
)
return
PLAYLIST_RESULT_BAD_NAME
;
return
false
;
file
=
fopen
(
path_fs
,
"w"
);
file
=
fopen
(
path_fs
,
"w"
);
g_free
(
path_fs
);
g_free
(
path_fs
);
if
(
file
==
NULL
)
if
(
file
==
NULL
)
{
return
PLAYLIST_RESULT_ERRNO
;
playlist_errno
(
error_r
);
return
false
;
}
fclose
(
file
);
fclose
(
file
);
idle_add
(
IDLE_STORED_PLAYLIST
);
idle_add
(
IDLE_STORED_PLAYLIST
);
return
PLAYLIST_RESULT_SUCCESS
;
return
true
;
}
}
enum
playlist_result
bool
spl_delete
(
const
char
*
name_utf8
)
spl_delete
(
const
char
*
name_utf8
,
GError
**
error_r
)
{
{
char
*
path_fs
;
char
*
path_fs
;
int
ret
;
int
ret
;
if
(
map_spl_path
()
==
NULL
)
path_fs
=
spl_map_to_fs
(
name_utf8
,
error_r
);
return
PLAYLIST_RESULT_DISABLED
;
if
(
!
spl_valid_name
(
name_utf8
))
return
PLAYLIST_RESULT_BAD_NAME
;
path_fs
=
map_spl_utf8_to_fs
(
name_utf8
);
if
(
path_fs
==
NULL
)
if
(
path_fs
==
NULL
)
return
PLAYLIST_RESULT_BAD_NAME
;
return
false
;
ret
=
unlink
(
path_fs
);
ret
=
unlink
(
path_fs
);
g_free
(
path_fs
);
g_free
(
path_fs
);
if
(
ret
<
0
)
if
(
ret
<
0
)
{
return
errno
==
ENOENT
playlist_errno
(
error_r
);
?
PLAYLIST_RESULT_NO_SUCH_LIST
return
false
;
:
PLAYLIST_RESULT_ERRNO
;
}
idle_add
(
IDLE_STORED_PLAYLIST
);
idle_add
(
IDLE_STORED_PLAYLIST
);
return
PLAYLIST_RESULT_SUCCESS
;
return
true
;
}
}
enum
playlist_result
bool
spl_remove_index
(
const
char
*
utf8path
,
unsigned
pos
)
spl_remove_index
(
const
char
*
utf8path
,
unsigned
pos
,
GError
**
error_r
)
{
{
GPtrArray
*
list
;
char
*
uri
;
char
*
uri
;
enum
playlist_result
result
;
if
(
!
(
list
=
spl_load
(
utf8path
)))
GPtrArray
*
list
=
spl_load
(
utf8path
,
error_r
);
return
PLAYLIST_RESULT_NO_SUCH_LIST
;
if
(
list
==
NULL
)
return
false
;
if
(
pos
>=
list
->
len
)
{
if
(
pos
>=
list
->
len
)
{
spl_free
(
list
);
spl_free
(
list
);
return
PLAYLIST_RESULT_BAD_RANGE
;
g_set_error_literal
(
error_r
,
playlist_quark
(),
PLAYLIST_RESULT_BAD_RANGE
,
"Bad range"
);
return
false
;
}
}
uri
=
spl_remove_index_internal
(
list
,
pos
);
uri
=
spl_remove_index_internal
(
list
,
pos
);
g_free
(
uri
);
g_free
(
uri
);
result
=
spl_save
(
list
,
utf8path
);
bool
result
=
spl_save
(
list
,
utf8path
,
error_r
);
spl_free
(
list
);
spl_free
(
list
);
...
@@ -370,38 +435,38 @@ spl_remove_index(const char *utf8path, unsigned pos)
...
@@ -370,38 +435,38 @@ spl_remove_index(const char *utf8path, unsigned pos)
return
result
;
return
result
;
}
}
enum
playlist_result
bool
spl_append_song
(
const
char
*
utf8path
,
struct
song
*
song
)
spl_append_song
(
const
char
*
utf8path
,
struct
song
*
song
,
GError
**
error_r
)
{
{
FILE
*
file
;
FILE
*
file
;
struct
stat
st
;
struct
stat
st
;
char
*
path_fs
;
if
(
map_spl_path
(
)
==
NULL
)
if
(
spl_map
(
error_r
)
==
NULL
)
return
PLAYLIST_RESULT_DISABLED
;
return
false
;
if
(
!
spl_valid_name
(
utf8path
))
char
*
path_fs
=
spl_map_to_fs
(
utf8path
,
error_r
);
return
PLAYLIST_RESULT_BAD_NAME
;
path_fs
=
map_spl_utf8_to_fs
(
utf8path
);
if
(
path_fs
==
NULL
)
if
(
path_fs
==
NULL
)
return
PLAYLIST_RESULT_BAD_NAME
;
return
false
;
file
=
fopen
(
path_fs
,
"a"
);
file
=
fopen
(
path_fs
,
"a"
);
g_free
(
path_fs
);
g_free
(
path_fs
);
if
(
file
==
NULL
)
if
(
file
==
NULL
)
{
return
PLAYLIST_RESULT_ERRNO
;
playlist_errno
(
error_r
);
return
false
;
}
if
(
fstat
(
fileno
(
file
),
&
st
)
<
0
)
{
if
(
fstat
(
fileno
(
file
),
&
st
)
<
0
)
{
int
save_errno
=
errno
;
playlist_errno
(
error_r
)
;
fclose
(
file
);
fclose
(
file
);
errno
=
save_errno
;
return
false
;
return
PLAYLIST_RESULT_ERRNO
;
}
}
if
(
st
.
st_size
/
(
MPD_PATH_MAX
+
1
)
>=
(
off_t
)
playlist_max_length
)
{
if
(
st
.
st_size
/
(
MPD_PATH_MAX
+
1
)
>=
(
off_t
)
playlist_max_length
)
{
fclose
(
file
);
fclose
(
file
);
return
PLAYLIST_RESULT_TOO_LARGE
;
g_set_error_literal
(
error_r
,
playlist_quark
(),
PLAYLIST_RESULT_TOO_LARGE
,
"Stored playlist is too large"
);
return
false
;
}
}
playlist_print_song
(
file
,
song
);
playlist_print_song
(
file
,
song
);
...
@@ -409,68 +474,79 @@ spl_append_song(const char *utf8path, struct song *song)
...
@@ -409,68 +474,79 @@ spl_append_song(const char *utf8path, struct song *song)
fclose
(
file
);
fclose
(
file
);
idle_add
(
IDLE_STORED_PLAYLIST
);
idle_add
(
IDLE_STORED_PLAYLIST
);
return
PLAYLIST_RESULT_SUCCESS
;
return
true
;
}
}
enum
playlist_result
bool
spl_append_uri
(
const
char
*
url
,
const
char
*
utf8file
)
spl_append_uri
(
const
char
*
url
,
const
char
*
utf8file
,
GError
**
error_r
)
{
{
struct
song
*
song
;
struct
song
*
song
;
if
(
uri_has_scheme
(
url
))
{
if
(
uri_has_scheme
(
url
))
{
enum
playlist_result
ret
;
song
=
song_remote_new
(
url
);
song
=
song_remote_new
(
url
);
ret
=
spl_append_song
(
utf8file
,
song
);
bool
success
=
spl_append_song
(
utf8file
,
song
,
error_r
);
song_free
(
song
);
song_free
(
song
);
return
ret
;
return
success
;
}
else
{
}
else
{
song
=
db_get_song
(
url
);
song
=
db_get_song
(
url
);
if
(
song
==
NULL
)
if
(
song
==
NULL
)
{
return
PLAYLIST_RESULT_NO_SUCH_SONG
;
g_set_error_literal
(
error_r
,
playlist_quark
(),
PLAYLIST_RESULT_NO_SUCH_SONG
,
return
spl_append_song
(
utf8file
,
song
);
"No such song"
);
return
false
;
}
return
spl_append_song
(
utf8file
,
song
,
error_r
);
}
}
}
}
static
enum
playlist_result
static
bool
spl_rename_internal
(
const
char
*
from_path_fs
,
const
char
*
to_path_fs
)
spl_rename_internal
(
const
char
*
from_path_fs
,
const
char
*
to_path_fs
,
GError
**
error_r
)
{
{
if
(
!
g_file_test
(
from_path_fs
,
G_FILE_TEST_IS_REGULAR
))
if
(
!
g_file_test
(
from_path_fs
,
G_FILE_TEST_IS_REGULAR
))
{
return
PLAYLIST_RESULT_NO_SUCH_LIST
;
g_set_error_literal
(
error_r
,
playlist_quark
(),
PLAYLIST_RESULT_NO_SUCH_LIST
,
"No such playlist"
);
return
false
;
}
if
(
g_file_test
(
to_path_fs
,
G_FILE_TEST_EXISTS
))
if
(
g_file_test
(
to_path_fs
,
G_FILE_TEST_EXISTS
))
{
return
PLAYLIST_RESULT_LIST_EXISTS
;
g_set_error_literal
(
error_r
,
playlist_quark
(),
PLAYLIST_RESULT_LIST_EXISTS
,
"Playlist exists already"
);
return
false
;
}
if
(
rename
(
from_path_fs
,
to_path_fs
)
<
0
)
if
(
rename
(
from_path_fs
,
to_path_fs
)
<
0
)
{
return
PLAYLIST_RESULT_ERRNO
;
playlist_errno
(
error_r
);
return
false
;
}
idle_add
(
IDLE_STORED_PLAYLIST
);
idle_add
(
IDLE_STORED_PLAYLIST
);
return
PLAYLIST_RESULT_SUCCESS
;
return
true
;
}
}
enum
playlist_result
bool
spl_rename
(
const
char
*
utf8from
,
const
char
*
utf8to
)
spl_rename
(
const
char
*
utf8from
,
const
char
*
utf8to
,
GError
**
error_r
)
{
{
char
*
from_path_fs
,
*
to_path_fs
;
if
(
spl_map
(
error_r
)
==
NULL
)
static
enum
playlist_result
ret
;
return
false
;
if
(
map_spl_path
()
==
NULL
)
return
PLAYLIST_RESULT_DISABLED
;
if
(
!
spl_valid_name
(
utf8from
)
||
!
spl_valid_name
(
utf8to
))
char
*
from_path_fs
=
spl_map_to_fs
(
utf8from
,
error_r
);
return
PLAYLIST_RESULT_BAD_NAME
;
if
(
from_path_fs
==
NULL
)
return
false
;
from_path_fs
=
map_spl_utf8_to_fs
(
utf8from
);
char
*
to_path_fs
=
spl_map_to_fs
(
utf8to
,
error_r
);
to_path_fs
=
map_spl_utf8_to_fs
(
utf8to
);
if
(
to_path_fs
==
NULL
)
{
g_free
(
from_path_fs
);
return
false
;
}
if
(
from_path_fs
!=
NULL
&&
to_path_fs
!=
NULL
)
bool
success
=
spl_rename_internal
(
from_path_fs
,
to_path_fs
,
error_r
);
ret
=
spl_rename_internal
(
from_path_fs
,
to_path_fs
);
else
ret
=
PLAYLIST_RESULT_BAD_NAME
;
g_free
(
from_path_fs
);
g_free
(
from_path_fs
);
g_free
(
to_path_fs
);
g_free
(
to_path_fs
);
return
ret
;
return
success
;
}
}
src/stored_playlist.h
View file @
ca419c84
...
@@ -20,8 +20,6 @@
...
@@ -20,8 +20,6 @@
#ifndef MPD_STORED_PLAYLIST_H
#ifndef MPD_STORED_PLAYLIST_H
#define MPD_STORED_PLAYLIST_H
#define MPD_STORED_PLAYLIST_H
#include "playlist_error.h"
#include <glib.h>
#include <glib.h>
#include <stdbool.h>
#include <stdbool.h>
#include <time.h>
#include <time.h>
...
@@ -54,36 +52,37 @@ spl_valid_name(const char *name_utf8);
...
@@ -54,36 +52,37 @@ spl_valid_name(const char *name_utf8);
* NULL if an error occurred.
* NULL if an error occurred.
*/
*/
GPtrArray
*
GPtrArray
*
spl_list
(
void
);
spl_list
(
GError
**
error_r
);
void
void
spl_list_free
(
GPtrArray
*
list
);
spl_list_free
(
GPtrArray
*
list
);
GPtrArray
*
GPtrArray
*
spl_load
(
const
char
*
utf8path
);
spl_load
(
const
char
*
utf8path
,
GError
**
error_r
);
void
void
spl_free
(
GPtrArray
*
list
);
spl_free
(
GPtrArray
*
list
);
enum
playlist_result
bool
spl_move_index
(
const
char
*
utf8path
,
unsigned
src
,
unsigned
dest
);
spl_move_index
(
const
char
*
utf8path
,
unsigned
src
,
unsigned
dest
,
GError
**
error_r
);
enum
playlist_result
bool
spl_clear
(
const
char
*
utf8path
);
spl_clear
(
const
char
*
utf8path
,
GError
**
error_r
);
enum
playlist_result
bool
spl_delete
(
const
char
*
name_utf8
);
spl_delete
(
const
char
*
name_utf8
,
GError
**
error_r
);
enum
playlist_result
bool
spl_remove_index
(
const
char
*
utf8path
,
unsigned
pos
);
spl_remove_index
(
const
char
*
utf8path
,
unsigned
pos
,
GError
**
error_r
);
enum
playlist_result
bool
spl_append_song
(
const
char
*
utf8path
,
struct
song
*
song
);
spl_append_song
(
const
char
*
utf8path
,
struct
song
*
song
,
GError
**
error_r
);
enum
playlist_result
bool
spl_append_uri
(
const
char
*
file
,
const
char
*
utf8file
);
spl_append_uri
(
const
char
*
file
,
const
char
*
utf8file
,
GError
**
error_r
);
enum
playlist_result
bool
spl_rename
(
const
char
*
utf8from
,
const
char
*
utf8to
);
spl_rename
(
const
char
*
utf8from
,
const
char
*
utf8to
,
GError
**
error_r
);
#endif
#endif
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment