X-Git-Url: https://git.distorted.org.uk/~mdw/disorder/blobdiff_plain/3680ef53ec6a3d5769c8703caed4a58e18a91bc6..ec9c046264b6c4ee76e2d08cf46ee928b026fe74:/lib/client.c diff --git a/lib/client.c b/lib/client.c index cb65114..c907e7c 100644 --- a/lib/client.c +++ b/lib/client.c @@ -151,12 +151,16 @@ static int check_response(disorder_client *c, char **rp) { } } +/** @brief Marker for a command body */ +static const char disorder_body[1]; + +/** @brief Marker for a list of args */ +static const char disorder_list[1]; + /** @brief Issue a command and parse a simple response * @param c Client * @param rp Where to store result, or NULL * @param cmd Command - * @param body Body or NULL - * @param nbody Length of body or -1 * @param ap Arguments (UTF-8), terminated by (char *)0 * @return 0 on success, non-0 on error * @@ -168,22 +172,29 @@ static int check_response(disorder_client *c, char **rp) { * NB that the response will NOT be converted to the local encoding * nor will quotes be stripped. See dequote(). * - * If @p body is not NULL then the body is sent immediately after the - * command. @p nbody should be the number of lines or @c -1 to count - * them if @p body is NULL-terminated. + * Put @ref disorder_body in the argument list followed by a char ** + * and int giving the body to follow the command. If the int is @c -1 + * then the list is assumed to be NULL-terminated. This may be used + * only once. + * + * Put @ref disorder_list in the argument list followed by a char ** + * and int giving a list of arguments to include. If the int is @c -1 + * then the list is assumed to be NULL-terminated. This may be used + * any number of times. * * Usually you would call this via one of the following interfaces: * - disorder_simple() - * - disorder_simple_body() * - disorder_simple_list() */ static int disorder_simple_v(disorder_client *c, char **rp, const char *cmd, - char **body, int nbody, va_list ap) { const char *arg; struct dynstr d; + char **body = NULL; + int nbody = 0; + int has_body = 0; if(!c->fpout) { c->last = "not connected"; @@ -194,8 +205,25 @@ static int disorder_simple_v(disorder_client *c, dynstr_init(&d); dynstr_append_string(&d, cmd); while((arg = va_arg(ap, const char *))) { - dynstr_append(&d, ' '); - dynstr_append_string(&d, quoteutf8(arg)); + if(arg == disorder_body) { + body = va_arg(ap, char **); + nbody = va_arg(ap, int); + has_body = 1; + } else if(arg == disorder_list) { + char **list = va_arg(ap, char **); + int nlist = va_arg(ap, int); + if(nlist < 0) { + for(nlist = 0; list[nlist]; ++nlist) + ; + } + for(int n = 0; n < nlist; ++n) { + dynstr_append(&d, ' '); + dynstr_append_string(&d, quoteutf8(arg)); + } + } else { + dynstr_append(&d, ' '); + dynstr_append_string(&d, quoteutf8(arg)); + } } dynstr_append(&d, '\n'); dynstr_terminate(&d); @@ -203,7 +231,7 @@ static int disorder_simple_v(disorder_client *c, if(fputs(d.vec, c->fpout) < 0) goto write_error; xfree(d.vec); - if(body) { + if(has_body) { if(nbody < 0) for(nbody = 0; body[nbody]; ++nbody) ; @@ -253,30 +281,7 @@ static int disorder_simple(disorder_client *c, int ret; va_start(ap, cmd); - ret = disorder_simple_v(c, rp, cmd, 0, 0, ap); - va_end(ap); - return ret; -} - -/** @brief Issue a command with a body and parse a simple response - * @param c Client - * @param rp Where to store result, or NULL (UTF-8) - * @param body Pointer to body - * @param nbody Size of body - * @param cmd Command - * @return 0 on success, non-0 on error - * - * See disorder_simple(). - */ -static int disorder_simple_body(disorder_client *c, - char **rp, - char **body, int nbody, - const char *cmd, ...) { - va_list ap; - int ret; - - va_start(ap, cmd); - ret = disorder_simple_v(c, rp, cmd, body, nbody, ap); + ret = disorder_simple_v(c, rp, cmd, ap); va_end(ap); return ret; } @@ -522,54 +527,24 @@ int disorder_close(disorder_client *c) { return ret; } -/** @brief Play a track - * @param c Client - * @param track Track to play (UTF-8) - * @return 0 on success, non-0 on error - */ -int disorder_play(disorder_client *c, const char *track) { - return disorder_simple(c, 0, "play", track, (char *)0); -} - -/** @brief Move a track - * @param c Client - * @param track Track to move (UTF-8) - * @param delta Distance to move by - * @return 0 on success, non-0 on error - */ -int disorder_move(disorder_client *c, const char *track, int delta) { - char d[16]; - - byte_snprintf(d, sizeof d, "%d", delta); - return disorder_simple(c, 0, "move", track, d, (char *)0); -} - -/** @brief Shut down the server - * @param c Client - * @return 0 on success, non-0 on error - */ -int disorder_shutdown(disorder_client *c) { - return disorder_simple(c, 0, "shutdown", (char *)0); -} - static void client_error(const char *msg, void attribute((unused)) *u) { disorder_error(0, "error parsing reply: %s", msg); } -/** @brief Get currently playing track +/** @brief Get a single queue entry * @param c Client + * @param cmd Command * @param qp Where to store track information * @return 0 on success, non-0 on error - * - * @p qp gets NULL if no track is playing. */ -int disorder_playing(disorder_client *c, struct queue_entry **qp) { +static int onequeue(disorder_client *c, const char *cmd, + struct queue_entry **qp) { char *r; struct queue_entry *q; int rc; - if((rc = disorder_simple(c, &r, "playing", (char *)0))) + if((rc = disorder_simple(c, &r, cmd, (char *)0))) return rc; if(r) { q = xmalloc(sizeof *q); @@ -582,8 +557,8 @@ int disorder_playing(disorder_client *c, struct queue_entry **qp) { } /** @brief Fetch the queue, recent list, etc */ -static int disorder_somequeue(disorder_client *c, - const char *cmd, struct queue_entry **qp) { +static int somequeue(disorder_client *c, + const char *cmd, struct queue_entry **qp) { struct queue_entry *qh, **qt = &qh, *q; char *l; int rc; @@ -614,28 +589,6 @@ static int disorder_somequeue(disorder_client *c, return -1; } -/** @brief Get recently played tracks - * @param c Client - * @param qp Where to store track information - * @return 0 on success, non-0 on error - * - * The last entry in the list is the most recently played track. - */ -int disorder_recent(disorder_client *c, struct queue_entry **qp) { - return disorder_somequeue(c, "recent", qp); -} - -/** @brief Get queue - * @param c Client - * @param qp Where to store track information - * @return 0 on success, non-0 on error - * - * The first entry in the list will be played next. - */ -int disorder_queue(disorder_client *c, struct queue_entry **qp) { - return disorder_somequeue(c, "queue", qp); -} - /** @brief Read a dot-stuffed list * @param c Client * @param vecp Where to store list (UTF-8) @@ -692,7 +645,7 @@ static int disorder_simple_list(disorder_client *c, int ret; va_start(ap, cmd); - ret = disorder_simple_v(c, 0, cmd, 0, 0, ap); + ret = disorder_simple_v(c, 0, cmd, ap); va_end(ap); if(ret) return ret; return readlist(c, vecp, nvecp); @@ -759,25 +712,6 @@ static int boolean(const char *cmd, const char *value, return 0; } -/** @brief Get the length of a track - * @param c Client - * @param track Track name (UTF-8) - * @param valuep Where to store length in seconds - * @return 0 on success, non-0 on error - * - * If the length is unknown 0 is returned. - */ -int disorder_length(disorder_client *c, const char *track, - long *valuep) { - char *value; - int rc; - - if((rc = disorder_simple(c, &value, "length", track, (char *)0))) - return rc; - *valuep = atol(value); - return 0; -} - /** @brief Set volume * @param c Client * @param left New left channel value @@ -943,21 +877,6 @@ int disorder_schedule_add(disorder_client *c, return rc; } -/** @brief Set the contents of a playlst - * @param c Client - * @param playlist Playlist to modify - * @param tracks List of tracks - * @param ntracks Length of @p tracks (or -1 to count up to the first NULL) - * @return 0 on success, non-0 on error - */ -int disorder_playlist_set(disorder_client *c, - const char *playlist, - char **tracks, - int ntracks) { - return disorder_simple_body(c, 0, tracks, ntracks, - "playlist-set", playlist, (char *)0); -} - #include "client-stubs.c" /*