commit e3762e0937fb89b2f950d9df9e24e07c013bd520
parent a184e99368ab1af4c39c7dbe50415da2d74526c0
Author: Hiltjo Posthuma <hiltjo@codemadness.org>
Date: Fri, 26 Dec 2014 22:56:26 +0100
rework tokenizer
simplified cmd arg parsing only one argument is allowed now, this is maybe
_too_ simplified, but adding filenames containing spaces or quotes ("'") should
work now.
Diffstat:
M | Makefile | | | 2 | +- |
M | cmd.c | | | 78 | ++++++++++++++++++++++++++++++++++++++++++------------------------------------ |
M | sad.h | | | 2 | +- |
D | tokenizer.c | | | 106 | ------------------------------------------------------------------------------- |
4 files changed, 44 insertions(+), 144 deletions(-)
diff --git a/Makefile b/Makefile
@@ -7,7 +7,7 @@ CFLAGS = -I/usr/local/include -g
LDFLAGS = -L /usr/local/lib
LDLIBS = -lsndfile -lmpg123 -lsndio -logg -lvorbis -lvorbisfile
-OBJ = sndio.o cmd.o mp3.o wav.o vorbis.o playlist.o sad.o tokenizer.o decoder.o
+OBJ = sndio.o cmd.o mp3.o wav.o vorbis.o playlist.o sad.o decoder.o
BIN = sad
# non-OpenBSD
diff --git a/cmd.c b/cmd.c
@@ -1,5 +1,6 @@
#include <sys/select.h>
+#include <ctype.h>
#include <err.h>
#include <fcntl.h>
#include <limits.h>
@@ -12,21 +13,21 @@
#include "sad.h"
static void
-cmdstatus(int fd, int argc, char **argv)
+cmdstatus(int fd, char *arg)
{
}
static void
-cmdvolume(int fd, int argc, char **argv)
+cmdvolume(int fd, char *arg)
{
int vol;
- if (argc != 2) {
+ if (!arg[0]) {
dprintf(fd, "ERR \"expected volume\"\n");
return;
}
- vol = atoi(argv[1]);
+ vol = atoi(arg);
if (vol < 0 || vol > 100) {
dprintf(fd, "ERR \"volume should be between [0, 100]\"\n");
return;
@@ -39,11 +40,11 @@ cmdvolume(int fd, int argc, char **argv)
}
static void
-cmdnext(int fd, int argc, char **argv)
+cmdnext(int fd, char *arg)
{
Song *s, *next;
- if (argc != 1) {
+ if (arg[0]) {
dprintf(fd, "ERR \"unexpected argument\"\n");
return;
}
@@ -63,17 +64,17 @@ cmdnext(int fd, int argc, char **argv)
}
static void
-cmdpause(int fd, int argc, char **argv)
+cmdpause(int fd, char *arg)
{
Song *s;
int pause;
- if (argc != 2) {
+ if (!arg[0]) {
dprintf(fd, "ERR \"argument should be 0 or 1\"\n");
return;
}
- pause = atoi(argv[1]);
+ pause = atoi(arg);
if (pause != 0 && pause != 1) {
dprintf(fd, "ERR \"argument should be 0 or 1\"\n");
return;
@@ -101,17 +102,17 @@ cmdpause(int fd, int argc, char **argv)
}
static void
-cmdplay(int fd, int argc, char **argv)
+cmdplay(int fd, char *arg)
{
Song *s, *cur;
int id;
- if (argc != 2) {
+ if (!arg[0]) {
dprintf(fd, "ERR \"expected song id\"\n");
return;
}
- id = atoi(argv[1]);
+ id = atoi(arg);
s = findsongid(id);
if (!s) {
dprintf(fd, "ERR \"invalid song id\"\n");
@@ -131,11 +132,11 @@ cmdplay(int fd, int argc, char **argv)
}
static void
-cmdprev(int fd, int argc, char **argv)
+cmdprev(int fd, char *arg)
{
Song *s, *prev;
- if (argc != 1) {
+ if (arg[0]) {
dprintf(fd, "ERR \"unexpected argument\"\n");
return;
}
@@ -155,11 +156,11 @@ cmdprev(int fd, int argc, char **argv)
}
static void
-cmdstop(int fd, int argc, char **argv)
+cmdstop(int fd, char *arg)
{
Song *s;
- if (argc != 1) {
+ if (arg[0]) {
dprintf(fd, "ERR \"unexpected argument\"\n");
return;
}
@@ -175,21 +176,21 @@ cmdstop(int fd, int argc, char **argv)
}
static void
-cmdadd(int fd, int argc, char **argv)
+cmdadd(int fd, char *arg)
{
Song *s;
- if (argc != 2) {
+ if (!arg[0]) {
dprintf(fd, "ERR \"expected file path\"\n");
return;
}
- if (access(argv[1], F_OK) < 0) {
- dprintf(fd, "ERR \"file doesn't exist\"\n");
+ if (access(arg, F_OK) < 0) {
+ dprintf(fd, "ERR \"file doesn't exist: %s\"\n", arg);
return;
}
- s = addplaylist(argv[1]);
+ s = addplaylist(arg);
if (!s) {
- dprintf(fd, "ERR \"cannot add %s\"\n", argv[1]);
+ dprintf(fd, "ERR \"cannot add file: %s\"\n", arg);
return;
}
printf("Added song with path %s and id %d\n",
@@ -198,11 +199,11 @@ cmdadd(int fd, int argc, char **argv)
}
static void
-cmdclear(int fd, int argc, char **argv)
+cmdclear(int fd, char *arg)
{
Song *s;
- if (argc != 1) {
+ if (arg[0]) {
dprintf(fd, "ERR \"unexpected argument\"\n");
return;
}
@@ -217,14 +218,14 @@ cmdclear(int fd, int argc, char **argv)
}
static void
-cmddelete(int fd, int argc, char **argv)
+cmddelete(int fd, char *arg)
{
}
static void
-cmdplaylist(int fd, int argc, char **argv)
+cmdplaylist(int fd, char *arg)
{
- if (argc != 1) {
+ if (arg[0]) {
dprintf(fd, "ERR \"unexpected argument\"\n");
return;
}
@@ -234,14 +235,14 @@ cmdplaylist(int fd, int argc, char **argv)
}
static void
-cmdclose(int fd, int argc, char **argv)
+cmdclose(int fd, char *arg)
{
}
static void
-cmdkill(int fd, int argc, char **argv)
+cmdkill(int fd, char *arg)
{
- if (argc != 1) {
+ if (arg[0]) {
dprintf(fd, "ERR \"unexpected argument\"\n");
return;
}
@@ -249,9 +250,9 @@ cmdkill(int fd, int argc, char **argv)
}
static void
-cmdping(int fd, int argc, char **argv)
+cmdping(int fd, char *arg)
{
- if (argc != 1) {
+ if (arg[0]) {
dprintf(fd, "ERR \"unexpected argument\"\n");
return;
}
@@ -284,8 +285,9 @@ docmd(int clifd)
static size_t sz;
static size_t resid;
ssize_t n;
+ size_t cmdlen;
char *new_buf;
- int i;
+ int i, c;
int argc;
char *argv[2];
@@ -319,10 +321,14 @@ docmd(int clifd)
*/
if (*p == '\n') {
*p = '\0';
- argc = tokenize(buf, argv, 2);
for (i = 0; i < LEN(cmds); i++) {
- if (!strcmp(cmds[i].name, argv[0])) {
- cmds[i].fn(clifd, argc, argv);
+ cmdlen = strlen(cmds[i].name);
+ if (!strncmp(cmds[i].name, buf, cmdlen) &&
+ (buf[cmdlen] == '\0' || isspace(buf[cmdlen]))) {
+ /* strip leading whitespace */
+ for (c = cmdlen; buf[c] && isspace(buf[c]); c++)
+ ;
+ cmds[i].fn(clifd, &buf[c]);
break;
}
}
diff --git a/sad.h b/sad.h
@@ -7,7 +7,7 @@
typedef struct {
char *name;
- void (*fn)(int, int, char **);
+ void (*fn)(int, char *);
} Cmd;
enum {
diff --git a/tokenizer.c b/tokenizer.c
@@ -1,106 +0,0 @@
-#include <string.h>
-
-static char qsep[] = " \t\r\n";
-
-static char*
-qtoken(char *s, char *sep)
-{
- int quoting;
- char *t;
-
- quoting = 0;
- t = s; /* s is output string, t is input string */
- while(*t!='\0' && (quoting || strchr(sep, *t)==NULL)) {
- if(*t != '\'') {
- *s++ = *t++;
- continue;
- }
- /* *t is a quote */
- if(!quoting) {
- quoting = 1;
- t++;
- continue;
- }
- /* quoting and we're on a quote */
- if(t[1] != '\'') {
- /* end of quoted section; absorb closing quote */
- t++;
- quoting = 0;
- continue;
- }
- /* doubled quote; fold one quote into two */
- t++;
- *s++ = *t++;
- }
- if(*s != '\0') {
- *s = '\0';
- if(t == s)
- t++;
- }
- return t;
-}
-
-static char*
-etoken(char *t, char *sep)
-{
- int quoting;
-
- /* move to end of next token */
- quoting = 0;
- while(*t!='\0' && (quoting || strchr(sep, *t)==NULL)) {
- if(*t != '\'') {
- t++;
- continue;
- }
- /* *t is a quote */
- if(!quoting) {
- quoting = 1;
- t++;
- continue;
- }
- /* quoting and we're on a quote */
- if(t[1] != '\'') {
- /* end of quoted section; absorb closing quote */
- t++;
- quoting = 0;
- continue;
- }
- /* doubled quote; fold one quote into two */
- t += 2;
- }
- return t;
-}
-
-int
-gettokens(char *s, char **args, int maxargs, char *sep)
-{
- int nargs;
-
- for(nargs=0; nargs<maxargs; nargs++) {
- while(*s!='\0' && strchr(sep, *s)!=NULL)
- *s++ = '\0';
- if(*s == '\0')
- break;
- args[nargs] = s;
- s = etoken(s, sep);
- }
-
- return nargs;
-}
-
-int
-tokenize(char *s, char **args, int maxargs)
-{
- int nargs;
-
- for(nargs=0; nargs<maxargs; nargs++) {
- while(*s!='\0' && strchr(qsep, *s)!=NULL)
- s++;
- if(*s == '\0')
- break;
- args[nargs] = s;
- s = qtoken(s, qsep);
- }
-
- return nargs;
-}