From 539bb39322d43b2b98b0f10c0fddd7e99ac80cf6 Mon Sep 17 00:00:00 2001 From: moritz Date: Fri, 2 Mar 2007 12:52:10 +0000 Subject: [PATCH] Improve string to integer conversion stuff, and have another stab at the config file parsing. Ezstream now prints each error it can find and then bails out, instead of bailing out on the first error. Tweak URL parsing as well, and do some cosmetic changes to the error messages. git-svn-id: https://svn.xiph.org/trunk/ezstream@12603 0101bb08-14d6-0310-b084-bc0e0c8e3800 --- configure.in | 2 +- src/Makefile.am | 2 +- src/configfile.c | 205 +++++++++++++++++++++++++++++++---------------- src/ezstream.c | 91 +++++++++++---------- src/strfctns.h | 23 ++++++ src/strlcat.c | 2 +- src/strlcpy.c | 2 +- src/strlfctns.h | 18 ----- src/strtonum.c | 81 +++++++++++++++++++ 9 files changed, 294 insertions(+), 132 deletions(-) create mode 100644 src/strfctns.h delete mode 100644 src/strlfctns.h create mode 100644 src/strtonum.c diff --git a/configure.in b/configure.in index 65d50a5..b31fedb 100644 --- a/configure.in +++ b/configure.in @@ -71,7 +71,7 @@ dnl LIBRARY FUNCTIONS AC_CHECK_LIB(gen, basename) AC_CHECK_FUNCS(arc4random gettimeofday random srandomdev stat) -AC_REPLACE_FUNCS(getopt strlcat strlcpy) +AC_REPLACE_FUNCS(getopt strlcat strlcpy strtonum) if test x"$ac_cv_header_signal_h" = "xyes"; then AC_CHECK_FUNCS([sigaction], [ AC_DEFINE(HAVE_SIGNALS, 1, [Define whether we have BSD signals]) diff --git a/src/Makefile.am b/src/Makefile.am index 792fb1c..f495f53 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -8,6 +8,6 @@ ezstream_LDADD = @LIBOBJS@ @XIPH_LIBS@ AM_CFLAGS = @XIPH_CFLAGS@ AM_CPPFLAGS = @XIPH_CPPFLAGS@ -EXTRA_DIST = configfile.h getopt.h playlist.h strlfctns.h util.h +EXTRA_DIST = configfile.h getopt.h playlist.h strfctns.h util.h CLEANFILES = core *.core *~ .*~ diff --git a/src/configfile.c b/src/configfile.c index 25c68a0..3c9a36c 100644 --- a/src/configfile.c +++ b/src/configfile.c @@ -28,12 +28,15 @@ #include #include "configfile.h" +#include "strfctns.h" #include "util.h" #ifndef PATH_MAX # define PATH_MAX 256 #endif +extern char *__progname; + static EZCONFIG ezConfig; static const char *blankString = ""; @@ -142,6 +145,7 @@ parseConfig(const char *fileName) char *ls_xmlContentPtr; int program_set, reconnect_set, shuffle_set, streamOnce_set, svrinfopublic_set; + unsigned int config_error; xmlLineNumbersDefault(1); if ((doc = xmlParseFile(fileName)) == NULL) { @@ -159,6 +163,7 @@ parseConfig(const char *fileName) memset(&ezConfig, '\000', sizeof(ezConfig)); + config_error = 0; program_set = 0; reconnect_set = 0; shuffle_set = 0; @@ -168,9 +173,10 @@ parseConfig(const char *fileName) while (cur != NULL) { if (!xmlStrcmp(cur->name, BAD_CAST "url")) { if (ezConfig.URL != NULL) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur)); - goto config_error; + config_error++; + continue; } if (cur->xmlChildrenNode != NULL) { ls_xmlContentPtr = (char *)xmlNodeListGetString(doc, cur->xmlChildrenNode, 1); @@ -180,9 +186,10 @@ parseConfig(const char *fileName) } if (!xmlStrcmp(cur->name, BAD_CAST "sourcepassword")) { if (ezConfig.password != NULL) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur)); - goto config_error; + config_error++; + continue; } if (cur->xmlChildrenNode != NULL) { ls_xmlContentPtr = (char *)xmlNodeListGetString(doc, cur->xmlChildrenNode, 1); @@ -192,9 +199,10 @@ parseConfig(const char *fileName) } if (!xmlStrcmp(cur->name, BAD_CAST "format")) { if (ezConfig.format != NULL) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur)); - goto config_error; + config_error++; + continue; } if (cur->xmlChildrenNode != NULL) { char *p; @@ -208,16 +216,18 @@ parseConfig(const char *fileName) } if (!xmlStrcmp(cur->name, BAD_CAST "filename")) { if (ezConfig.fileName != NULL) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur)); - goto config_error; + config_error++; + continue; } if (cur->xmlChildrenNode != NULL) { ls_xmlContentPtr = (char *)xmlNodeListGetString(doc, cur->xmlChildrenNode, 1); if (strlen(ls_xmlContentPtr) > PATH_MAX - 1) { - printf("%s[%ld]: Error: Path or filename in is too long.\n", + printf("%s[%ld]: Error: Path or filename in is too long\n", fileName, xmlGetLineNo(cur)); - goto config_error; + config_error++; + continue; } ezConfig.fileName = xstrdup(ls_xmlContentPtr); xmlFree(ls_xmlContentPtr); @@ -225,70 +235,98 @@ parseConfig(const char *fileName) } if (!xmlStrcmp(cur->name, BAD_CAST "playlist_program")) { if (program_set) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur)); - goto config_error; + config_error++; + continue; } if (cur->xmlChildrenNode != NULL) { - int tmp; + const char *errstr; ls_xmlContentPtr = (char *)xmlNodeListGetString(doc, cur->xmlChildrenNode, 1); - tmp = atoi(ls_xmlContentPtr); - ezConfig.fileNameIsProgram = (tmp == 0) ? 0 : 1; + ezConfig.fileNameIsProgram = strtonum(ls_xmlContentPtr, 0, 1, &errstr); + if (errstr) { + printf("%s[%ld]: Error: may only contain 1 or 0\n", + fileName, xmlGetLineNo(cur)); + config_error++; + continue; + } xmlFree(ls_xmlContentPtr); program_set = 1; } } if (!xmlStrcmp(cur->name, BAD_CAST "shuffle")) { if (shuffle_set) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur)); - goto config_error; + config_error++; + continue; } if (cur->xmlChildrenNode != NULL) { - int tmp; + const char *errstr; ls_xmlContentPtr = (char *)xmlNodeListGetString(doc, cur->xmlChildrenNode, 1); - tmp = atoi(ls_xmlContentPtr); - ezConfig.shuffle = (tmp == 0) ? 0 : 1; + ezConfig.shuffle = strtonum(ls_xmlContentPtr, 0, 1, &errstr); + if (errstr) { + printf("%s[%ld]: Error: may only contain 1 or 0\n", + fileName, xmlGetLineNo(cur)); + config_error++; + continue; + } xmlFree(ls_xmlContentPtr); shuffle_set = 1; } } if (!xmlStrcmp(cur->name, BAD_CAST "stream_once")) { if (streamOnce_set) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur)); - goto config_error; + config_error++; + continue; } if (cur->xmlChildrenNode != NULL) { - int tmp; + const char *errstr; ls_xmlContentPtr = (char *)xmlNodeListGetString(doc, cur->xmlChildrenNode, 1); - tmp = atoi(ls_xmlContentPtr); - ezConfig.streamOnce = (tmp == 0) ? 0 : 1; + ezConfig.streamOnce = strtonum(ls_xmlContentPtr, 0, 1, &errstr); + if (errstr) { + printf("%s[%ld]: Error: may only contain 1 or 0\n", + fileName, xmlGetLineNo(cur)); + config_error++; + continue; + } xmlFree(ls_xmlContentPtr); streamOnce_set = 1; } } if (!xmlStrcmp(cur->name, BAD_CAST "reconnect_tries")) { if (reconnect_set) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur)); - goto config_error; + config_error++; + continue; } if (cur->xmlChildrenNode != NULL) { + const char *errstr; + ls_xmlContentPtr = (char *)xmlNodeListGetString(doc, cur->xmlChildrenNode, 1); - ezConfig.reconnectAttempts = atoi(ls_xmlContentPtr); + ezConfig.reconnectAttempts = strtonum(ls_xmlContentPtr, 0, UINT_MAX, &errstr); + if (errstr) { + printf("%s[%ld]: Error: In : '%s' is %s\n", + fileName, xmlGetLineNo(cur), ls_xmlContentPtr, errstr); + config_error++; + continue; + } xmlFree(ls_xmlContentPtr); reconnect_set = 1; } } if (!xmlStrcmp(cur->name, BAD_CAST "svrinfoname")) { if (ezConfig.serverName != NULL) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur)); - goto config_error; + config_error++; + continue; } if (cur->xmlChildrenNode != NULL) { ls_xmlContentPtr = (char *)xmlNodeListGetString(doc, cur->xmlChildrenNode, 1); @@ -298,9 +336,10 @@ parseConfig(const char *fileName) } if (!xmlStrcmp(cur->name, BAD_CAST "svrinfourl")) { if (ezConfig.serverURL != NULL) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur)); - goto config_error; + config_error++; + continue; } if (cur->xmlChildrenNode != NULL) { ls_xmlContentPtr = (char *)xmlNodeListGetString(doc, cur->xmlChildrenNode, 1); @@ -310,9 +349,10 @@ parseConfig(const char *fileName) } if (!xmlStrcmp(cur->name, BAD_CAST "svrinfogenre")) { if (ezConfig.serverGenre != NULL) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur)); - goto config_error; + config_error++; + continue; } if (cur->xmlChildrenNode != NULL) { ls_xmlContentPtr = (char *)xmlNodeListGetString(doc, cur->xmlChildrenNode, 1); @@ -322,9 +362,10 @@ parseConfig(const char *fileName) } if (!xmlStrcmp(cur->name, BAD_CAST "svrinfodescription")) { if (ezConfig.serverDescription != NULL) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur)); - goto config_error; + config_error++; + continue; } if (cur->xmlChildrenNode != NULL) { ls_xmlContentPtr = (char *)xmlNodeListGetString(doc, cur->xmlChildrenNode, 1); @@ -334,9 +375,10 @@ parseConfig(const char *fileName) } if (!xmlStrcmp(cur->name, BAD_CAST "svrinfobitrate")) { if (ezConfig.serverBitrate != NULL) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur)); - goto config_error; + config_error++; + continue; } if (cur->xmlChildrenNode != NULL) { ls_xmlContentPtr = (char *)xmlNodeListGetString(doc, cur->xmlChildrenNode, 1); @@ -347,9 +389,10 @@ parseConfig(const char *fileName) if (!xmlStrcmp(cur->name, BAD_CAST "svrinfochannels")) { if (ezConfig.serverChannels != NULL) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur)); - goto config_error; + config_error++; + continue; } if (cur->xmlChildrenNode != NULL) { ls_xmlContentPtr = (char *)xmlNodeListGetString(doc, cur->xmlChildrenNode, 1); @@ -359,9 +402,10 @@ parseConfig(const char *fileName) } if (!xmlStrcmp(cur->name, BAD_CAST "svrinfosamplerate")) { if (ezConfig.serverSamplerate != NULL) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur)); - goto config_error; + config_error++; + continue; } if (cur->xmlChildrenNode != NULL) { ls_xmlContentPtr = (char *)xmlNodeListGetString(doc, cur->xmlChildrenNode, 1); @@ -371,9 +415,10 @@ parseConfig(const char *fileName) } if (!xmlStrcmp(cur->name, BAD_CAST "svrinfoquality")) { if (ezConfig.serverQuality != NULL) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur)); - goto config_error; + config_error++; + continue; } if (cur->xmlChildrenNode != NULL) { ls_xmlContentPtr = (char *)xmlNodeListGetString(doc, cur->xmlChildrenNode, 1); @@ -383,16 +428,22 @@ parseConfig(const char *fileName) } if (!xmlStrcmp(cur->name, BAD_CAST "svrinfopublic")) { if (svrinfopublic_set) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur)); - goto config_error; + config_error++; + continue; } if (cur->xmlChildrenNode != NULL) { - int tmp; + const char *errstr; ls_xmlContentPtr = (char *)xmlNodeListGetString(doc, cur->xmlChildrenNode, 1); - tmp = atoi(ls_xmlContentPtr); - ezConfig.serverPublic = (tmp == 0) ? 0 : 1; + ezConfig.serverPublic = strtonum(ls_xmlContentPtr, 0, 1, &errstr); + if (errstr) { + printf("%s[%ld]: Error: may only contain 1 or 0\n", + fileName, xmlGetLineNo(cur)); + config_error++; + continue; + } xmlFree(ls_xmlContentPtr); svrinfopublic_set = 1; } @@ -406,16 +457,22 @@ parseConfig(const char *fileName) while (cur2 != NULL) { if (!xmlStrcmp(cur2->name, BAD_CAST "enable")) { if (enable_set) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur)); - goto config_error; + config_error++; + continue; } if (cur2->xmlChildrenNode != NULL) { - int tmp; + const char *errstr; ls_xmlContentPtr = (char *)xmlNodeListGetString(doc, cur2->xmlChildrenNode, 1); - tmp = atoi(ls_xmlContentPtr); - ezConfig.reencode = (tmp == 0) ? 0 : 1; + ezConfig.reencode = strtonum(ls_xmlContentPtr, 0, 1, &errstr); + if (errstr) { + printf("%s[%ld]: Error: may only contain 1 or 0\n", + fileName, xmlGetLineNo(cur)); + config_error++; + continue; + } xmlFree(ls_xmlContentPtr); enable_set = 1; } @@ -431,9 +488,10 @@ parseConfig(const char *fileName) while (cur3 != NULL) { if (!xmlStrcmp(cur3->name, BAD_CAST "format")) { if (pformatEncDec->format != NULL) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur3)); - goto config_error; + config_error++; + continue; } if (cur3->xmlChildrenNode != NULL) { char *p; @@ -447,9 +505,10 @@ parseConfig(const char *fileName) } if (!xmlStrcmp(cur3->name, BAD_CAST "match")) { if (pformatEncDec->match != NULL) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur3)); - goto config_error; + config_error++; + continue; } if (cur3->xmlChildrenNode != NULL) { char *p; @@ -463,9 +522,10 @@ parseConfig(const char *fileName) } if (!xmlStrcmp(cur3->name, BAD_CAST "decode")) { if (pformatEncDec->decoder != NULL) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur3)); - goto config_error; + config_error++; + continue; } if (cur3->xmlChildrenNode != NULL) { ls_xmlContentPtr = (char *)xmlNodeListGetString(doc, cur3->xmlChildrenNode, 1); @@ -476,7 +536,8 @@ parseConfig(const char *fileName) if ((p = strstr(p, TRACK_PLACEHOLDER)) != NULL) { printf("%s[%ld]: Error: Multiple `%s' placeholders in decoder command\n", fileName, xmlGetLineNo(cur3), TRACK_PLACEHOLDER); - goto config_error; + config_error++; + continue; } } if ((p = strstr(pformatEncDec->decoder, METADATA_PLACEHOLDER)) != NULL) { @@ -484,16 +545,18 @@ parseConfig(const char *fileName) if ((p = strstr(p, METADATA_PLACEHOLDER)) != NULL) { printf("%s[%ld]: Error: Multiple `%s' placeholders in decoder command\n", fileName, xmlGetLineNo(cur3), METADATA_PLACEHOLDER); - goto config_error; + config_error++; + continue; } } } } if (!xmlStrcmp(cur3->name, BAD_CAST "encode")) { if (pformatEncDec->encoder != NULL) { - printf("%s[%ld]: Error: Cannot have multiple elements.\n", + printf("%s[%ld]: Error: Cannot have multiple elements\n", fileName, xmlGetLineNo(cur3)); - goto config_error; + config_error++; + continue; } if (cur3->xmlChildrenNode != NULL) { ls_xmlContentPtr = (char *)xmlNodeListGetString(doc, cur3->xmlChildrenNode, 1); @@ -502,14 +565,16 @@ parseConfig(const char *fileName) if ((p = strstr(pformatEncDec->encoder, TRACK_PLACEHOLDER)) != NULL) { printf("%s[%ld]: Error: `%s' placeholder not allowed in encoder command\n", fileName, xmlGetLineNo(cur3), TRACK_PLACEHOLDER); - goto config_error; + config_error++; + continue; } if ((p = strstr(pformatEncDec->encoder, METADATA_PLACEHOLDER)) != NULL) { p += strlen(METADATA_PLACEHOLDER); if ((p = strstr(p, METADATA_PLACEHOLDER)) != NULL) { printf("%s[%ld]: Error: Multiple `%s' placeholders in encoder command\n", fileName, xmlGetLineNo(cur3), METADATA_PLACEHOLDER); - goto config_error; + config_error++; + continue; } } } @@ -526,11 +591,13 @@ parseConfig(const char *fileName) } xmlFreeDoc(doc); - return(1); -config_error: + if (config_error == 0) + return (1); - xmlFreeDoc(doc); freeConfig(&ezConfig); + printf("%s: %u configuration errors in %s\n", __progname, + config_error, fileName); + return (0); } diff --git a/src/ezstream.c b/src/ezstream.c index f785005..cb36bb6 100644 --- a/src/ezstream.c +++ b/src/ezstream.c @@ -57,11 +57,9 @@ #ifndef HAVE_GETOPT # include "getopt.h" #endif -#if !defined(HAVE_STRLCAT) || !defined(HAVE_STRLCPY) -# include "strlfctns.h" -#endif #include "configfile.h" #include "playlist.h" +#include "strfctns.h" #include "util.h" #ifndef PATH_MAX @@ -187,9 +185,10 @@ strrcmp(const char *s, const char *sub) int urlParse(const char *url, char **hostname, int *port, char **mountname) { - char *p1, *p2, *p3; - char tmpPort[25] = ""; - size_t hostsiz, mountsiz; + char *p1, *p2, *p3; + char tmpPort[6] = ""; + size_t hostsiz, mountsiz; + const char *errstr; if (hostname == NULL || port == NULL || mountname == NULL) { printf("%s: urlParse(): Internal error: Bad arguments\n", @@ -197,24 +196,40 @@ urlParse(const char *url, char **hostname, int *port, char **mountname) exit(1); } - if (strncmp(url, "http://", strlen("http://")) != 0) + if (strncmp(url, "http://", strlen("http://")) != 0) { + printf("%s: Error: Invalid : Not an HTTP address\n", + __progname); return (0); + } p1 = (char *)(url) + strlen("http://"); p2 = strchr(p1, ':'); - if (p2 == NULL) + if (p2 == NULL) { + printf("%s: Error: Invalid : Missing port\n", + __progname); return (0); + } hostsiz = (p2 - p1) + 1; *hostname = xmalloc(hostsiz); strlcpy(*hostname, p1, hostsiz); p2++; p3 = strchr(p2, '/'); - if (p3 == NULL || p3 - p2 >= (int)sizeof(tmpPort)) + if (p3 == NULL || p3 - p2 >= (int)sizeof(tmpPort)) { + printf("%s: Error: Invalid : Missing mountpoint or too long port number\n", + __progname); + xfree(*hostname); return (0); + } strlcpy(tmpPort, p2, (p3 - p2) + 1); - *port = atoi(tmpPort); + *port = strtonum(tmpPort, 1, 65535, &errstr); + if (errstr) { + printf("%s: Error: Invalid : Port '%s' is %s\n", + __progname, tmpPort, errstr); + xfree(*hostname); + return (0); + } mountsiz = strlen(p3) + 1; *mountname = xmalloc(mountsiz); @@ -269,7 +284,7 @@ buildCommandString(const char *extension, const char *fileName, decoder = xstrdup(getFormatDecoder(extension)); if (strlen(decoder) == 0) { - printf("%s: Unknown extension '%s', cannot decode '%s'.\n", + printf("%s: Unknown extension '%s', cannot decode '%s'\n", __progname, extension, fileName); xfree(decoder); return (NULL); @@ -371,27 +386,27 @@ processMetadata(shout_t *shout, const char *extension, const char *fileName) if ((ret = ov_open(filepstream, &vf, NULL, 0)) != 0) { switch (ret) { case OV_EREAD: - printf("%s: No metadata support: %s: Media read error.\n", + printf("%s: No metadata support: %s: Media read error\n", __progname, fileName); break; case OV_ENOTVORBIS: - printf("%s: No metadata support: %s: Invalid Vorbis bitstream.\n", + printf("%s: No metadata support: %s: Invalid Vorbis bitstream\n", __progname, fileName); break; case OV_EVERSION: - printf("%s: No metadata support: %s: Vorbis version mismatch.\n", + printf("%s: No metadata support: %s: Vorbis version mismatch\n", __progname, fileName); break; case OV_EBADHEADER: - printf("%s: No metadata support: %s: Invalid Vorbis bitstream header.\n", + printf("%s: No metadata support: %s: Invalid Vorbis bitstream header\n", __progname, fileName); break; case OV_EFAULT: - printf("%s: Fatal: Internal libvorbisfile fault.\n", + printf("%s: Fatal: Internal libvorbisfile fault\n", __progname); abort(); default: - printf("%s: No metadata support: %s: ov_read() returned unknown error.\n", + printf("%s: No metadata support: %s: ov_read() returned unknown error\n", __progname, fileName); break; } @@ -487,7 +502,7 @@ openResource(shout_t *shout, const char *fileName, int *popenFlag, if (strcmp(fileName, "stdin") == 0) { if (vFlag) - printf("%s: Reading from standard input.\n", + printf("%s: Reading from standard input\n", __progname); if (isStdin != NULL) *isStdin = 1; @@ -555,7 +570,7 @@ openResource(shout_t *shout, const char *fileName, int *popenFlag, if (qFlag) dup2(stderr_fd, STDERR_FILENO); } else - printf("%s: Error: Cannot determine file type of '%s'.\n", + printf("%s: Error: Cannot determine file type of '%s'\n", __progname, fileName); xfree(pMetadata); @@ -577,7 +592,7 @@ reconnectServer(shout_t *shout, int closeConn) unsigned int i; int close_conn = closeConn; - printf("%s: Connection to %s lost.\n", __progname, pezConfig->URL); + printf("%s: Connection to %s lost\n", __progname, pezConfig->URL); i = 0; while (++i) { @@ -593,7 +608,7 @@ reconnectServer(shout_t *shout, int closeConn) else shout_close(shout); if (shout_open(shout) == SHOUTERR_SUCCESS) { - printf("OK\n%s: Reconnect to %s successful.\n", + printf("OK\n%s: Reconnect to %s successful\n", __progname, pezConfig->URL); return (1); } @@ -613,7 +628,7 @@ reconnectServer(shout_t *shout, int closeConn) #endif }; - printf("%s: Giving up.\n", __progname); + printf("%s: Giving up\n", __progname); return (0); } @@ -650,7 +665,7 @@ sendStream(shout_t *shout, FILE *filepstream, const char *fileName, if (rereadPlaylist_notify) { rereadPlaylist_notify = 0; if (!pezConfig->fileNameIsProgram) - printf("%s: SIGHUP signal received, will reread playlist after this file.\n", + printf("%s: SIGHUP signal received, will reread playlist after this file\n", __progname); } if (skipTrack) { @@ -776,7 +791,7 @@ streamFile(shout_t *shout, const char *fileName) if (ret == STREAM_SKIP || skipTrack) { skipTrack = 0; if (!isStdin && vFlag) - printf("%s: SIGUSR1 signal received, skipping current track.\n", + printf("%s: SIGUSR1 signal received, skipping current track\n", __progname); retval = 1; ret = STREAM_DONE; @@ -914,7 +929,7 @@ main(int argc, char *argv[]) switch (c) { case 'c': if (configFile != NULL) { - printf("Error: multiple -c arguments given.\n"); + printf("Error: multiple -c arguments given\n"); usage(); return (2); } @@ -959,10 +974,10 @@ main(int argc, char *argv[]) return (2); } if (vFlag && (st.st_mode & (S_IRGRP | S_IROTH))) - printf("%s: Warning: %s is group and/or world readable.\n", + printf("%s: Warning: %s is group and/or world readable\n", __progname, configFile); if (st.st_mode & (S_IWGRP | S_IWOTH)) { - printf("%s: Error: %s is group and/or world writeable.\n", + printf("%s: Error: %s is group and/or world writeable\n", __progname, configFile); return (2); } @@ -989,36 +1004,30 @@ main(int argc, char *argv[]) return (2); } if (!urlParse(pezConfig->URL, &host, &port, &mount)) { - printf("%s: Error: Invalid :\n", configFile); - printf("Must be of the form ``http://server:port/mountpoint''.\n"); + printf("Must be of the form ``http://server:port/mountpoint''\n"); return (2); } - if ((host == NULL)) { + if (strlen(host) == 0) { printf("%s: Error: Invalid : Missing server:\n", configFile); - printf("Must be of the form ``http://server:port/mountpoint''.\n"); + printf("Must be of the form ``http://server:port/mountpoint''\n"); return (2); } - if ((port < 1 || port > 65535)) { - printf("%s: Error: Invalid : Missing or invalid port:\n", configFile); - printf("Must be of the form ``http://server:port/mountpoint''.\n"); - return (2); - } - if ((mount == NULL)) { + if (strlen(mount) == 0) { printf("%s: Error: Invalid : Missing mountpoint:\n", configFile); - printf("Must be of the form ``http://server:port/mountpoint''.\n"); + printf("Must be of the form ``http://server:port/mountpoint''\n"); return (2); } - if ((pezConfig->password == NULL)) { + if (pezConfig->password == NULL) { printf("%s: Error: Missing \n", configFile); return (2); } - if ((pezConfig->fileName == NULL)) { + if (pezConfig->fileName == NULL) { printf("%s: Error: Missing \n", configFile); return (2); } if (pezConfig->format == NULL) { printf("%s: Warning: Missing :\n", configFile); - printf("Specify a stream format of either MP3, VORBIS or THEORA.\n"); + printf("Specify a stream format of either MP3, VORBIS or THEORA\n"); } xfree(configFile); diff --git a/src/strfctns.h b/src/strfctns.h new file mode 100644 index 0000000..83316fa --- /dev/null +++ b/src/strfctns.h @@ -0,0 +1,23 @@ +#ifndef __STRLFCTNS_H__ +#define __STRLFCTNS_H__ + +#ifdef HAVE_CONFIG_H +# include "config.h" +#endif + +#ifndef HAVE_STRLCAT +# define strlcat local_strlcat +#endif +size_t local_strlcat(char *, const char *, size_t); + +#ifndef HAVE_STRLCPY +# define strlcpy local_strlcpy +#endif +size_t local_strlcpy(char *, const char *, size_t); + +#ifndef HAVE_STRTONUM +# define strtonum local_strtonum +#endif +long long local_strtonum(const char *, long long, long long, const char **); + +#endif /* __STRLFCTNS_H__ */ diff --git a/src/strlcat.c b/src/strlcat.c index c9317c3..3307fb1 100644 --- a/src/strlcat.c +++ b/src/strlcat.c @@ -24,7 +24,7 @@ # include #endif #include -#include "strlfctns.h" +#include "strfctns.h" /* * Appends src to string dst of size siz (unlike strncat, siz is the diff --git a/src/strlcpy.c b/src/strlcpy.c index c64ca2a..e7b807b 100644 --- a/src/strlcpy.c +++ b/src/strlcpy.c @@ -24,7 +24,7 @@ # include #endif #include -#include "strlfctns.h" +#include "strfctns.h" /* * Copy src to string dst of size siz. At most siz-1 characters diff --git a/src/strlfctns.h b/src/strlfctns.h deleted file mode 100644 index e187a0d..0000000 --- a/src/strlfctns.h +++ /dev/null @@ -1,18 +0,0 @@ -#ifndef __STRLFCTNS_H__ -#define __STRLFCTNS_H__ - -#ifdef HAVE_CONFIG_H -# include "config.h" -#endif - -#ifndef HAVE_STRLCAT -# define strlcat local_strlcat -#endif -size_t local_strlcat(char *, const char *, size_t); - -#ifndef HAVE_STRLCPY -# define strlcpy local_strlcpy -#endif -size_t local_strlcpy(char *, const char *, size_t); - -#endif /* __STRLFCTNS_H__ */ diff --git a/src/strtonum.c b/src/strtonum.c new file mode 100644 index 0000000..d2720f5 --- /dev/null +++ b/src/strtonum.c @@ -0,0 +1,81 @@ +/* $OpenBSD: strtonum.c,v 1.6 2004/08/03 19:38:01 millert Exp $ */ + +/* + * Copyright (c) 2004 Ted Unangst and Todd Miller + * All rights reserved. + * + * Permission to use, copy, modify, and distribute this software for any + * purpose with or without fee is hereby granted, provided that the above + * copyright notice and this permission notice appear in all copies. + * + * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES + * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR + * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES + * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN + * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF + * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + */ + +#ifdef HAVE_CONFIG_H +# include "config.h" +#endif + +#include +#include +#include +#include "strfctns.h" + +#define INVALID 1 +#define TOOSMALL 2 +#define TOOLARGE 3 + +#if !defined(LLONG_MIN) || !defined(LLONG_MAX) +# undef LLONG_MIN +# undef LLONG_MAX +# define LLONG_MIN LONG_LONG_MIN +# define LLONG_MAX LONG_LONG_MAX +#endif + +#ifdef WIN32 +# define strtoll _strtoi64 +#endif + +long long +local_strtonum(const char *numstr, long long minval, long long maxval, + const char **errstrp) +{ + long long ll = 0; + char *ep; + int error = 0; + struct errval { + const char *errstr; + int err; + } ev[4] = { + { NULL, 0 }, + { "invalid", EINVAL }, + { "too small", ERANGE }, + { "too large", ERANGE }, + }; + + ev[0].err = errno; + errno = 0; + if (minval > maxval) + error = INVALID; + else { + ll = strtoll(numstr, &ep, 10); + if (numstr == ep || *ep != '\0') + error = INVALID; + else if ((ll == LLONG_MIN && errno == ERANGE) || ll < minval) + error = TOOSMALL; + else if ((ll == LLONG_MAX && errno == ERANGE) || ll > maxval) + error = TOOLARGE; + } + if (errstrp != NULL) + *errstrp = ev[error].errstr; + errno = ev[error].err; + if (error) + ll = 0; + + return (ll); +}