libmpdserver

Parser combinator library for MPD client commands

git clone https://git.8pit.net/libmpdserver.git

  1#include "fns.h"
  2#include "mpc.h"
  3
  4/* This file provides some custom fold functions for dealing with
  5 * MPD commands taking variadic arguments, if these are needed
  6 * elsewhere at some point the concept needs to be generalized. */
  7
  8static mpc_val_t *
  9mpdf_argvfold(int n, mpc_val_t **xs)
 10{
 11	int i;
 12	mpd_command_t *cmd;
 13
 14	cmd = mpd_new_command(NULL, (size_t)n);
 15	for (i = 0; i < n; i++) {
 16		cmd->argv[i] = xmalloc(sizeof(mpd_argument_t));
 17		cmd->argv[i]->type = MPD_VAL_STR;
 18		cmd->argv[i]->v.sval = (char *)xs[i];
 19	}
 20
 21	return cmd;
 22}
 23
 24static mpc_val_t *
 25mpdf_cmdfold(int n, mpc_val_t **xs)
 26{
 27	size_t i, j, oldargc;
 28	mpd_command_t *cmd;
 29
 30	assert(n >= 3);
 31	cmd = (mpd_command_t *)xs[n - 1];
 32	cmd->name = (char *)xs[0];
 33
 34	n -= 2;
 35	oldargc = cmd->argc;
 36	cmd->argc += (size_t)n;
 37
 38	cmd->argv = xrealloc(cmd->argv, sizeof(mpd_argument_t *) * cmd->argc);
 39	memmove(&cmd->argv[n], cmd->argv, sizeof(mpd_argument_t *) * oldargc);
 40
 41	for (i = 0, j = 1; i < (size_t)n; i++, j++) {
 42		cmd->argv[i] = xmalloc(sizeof(mpd_argument_t));
 43		cmd->argv[i]->type = MPD_VAL_STR;
 44		cmd->argv[i]->v.sval = xs[j];
 45	}
 46
 47	return cmd;
 48}
 49
 50mpdf_fold(tagtypes, MPD_ARG_STRING)
 51
 52static mpc_parser_t *
 53mpd_ping(void)
 54{
 55	return mpd_cmd_noarg("ping");
 56}
 57
 58static mpc_parser_t *
 59mpd_tagtypes_clear(void)
 60{
 61	return mpc_and(2, mpdf_tagtypes, mpc_string("tagtypes"),
 62	               mpd_argument(mpc_string("clear")), free);
 63}
 64
 65static mpc_parser_t *
 66mpd_tagtypes_all(void)
 67{
 68	return mpc_and(2, mpdf_tagtypes, mpc_string("tagtypes"),
 69	               mpd_argument(mpc_string("all")), free);
 70}
 71
 72static mpc_parser_t *
 73mpd_tagtypes_disable(void)
 74{
 75	mpc_parser_t *args;
 76
 77	args = mpc_many1(mpdf_argvfold, mpd_argument(mpd_string()));
 78	return mpc_and(3, mpdf_cmdfold, mpc_string("tagtypes"),
 79	               mpd_argument(mpc_string("disable")), args, free, free);
 80}
 81
 82static mpc_parser_t *
 83mpd_tagtypes_enable(void)
 84{
 85	mpc_parser_t *args;
 86
 87	args = mpc_many1(mpdf_argvfold, mpd_argument(mpd_string()));
 88	return mpc_and(3, mpdf_cmdfold, mpc_string("tagtypes"),
 89	               mpd_argument(mpc_string("enable")), args, free, free);
 90}
 91
 92static mpc_parser_t *
 93mpd_tagtypes(void)
 94{
 95	return mpd_cmd_noarg("tagtypes");
 96}
 97
 98mpc_parser_t *
 99mpd_connection_cmds(void)
100{
101	return mpc_or(6, mpd_ping(), mpd_tagtypes_all(), mpd_tagtypes_clear(),
102	              mpd_tagtypes_disable(), mpd_tagtypes_enable(),
103	              mpd_tagtypes());
104}