summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorjbj <jbj>2008-03-10 08:13:09 +0000
committerjbj <jbj>2008-03-10 08:13:09 +0000
commit01a321cf28210e1678ded8a30c0489feb556dbbe (patch)
tree25428ec15fb64b8cc7374268f064dc675611285e
parent0b205ccce0e93f55126a38dd286f2097d389df25 (diff)
downloadlibpopt-01a321cf28210e1678ded8a30c0489feb556dbbe.tar.gz
- jbj: study the mess with splint. Sigh, splint is so easily confused ...
- jbj: rewrite findProgramPath & move to popt.c. Nuke the findme.{c,h} toys. - jbj: use stpcpy several more places (Wayne Davison<wayned@samba.org>).
-rw-r--r--CHANGES3
-rw-r--r--Makefile.am4
-rw-r--r--findme.c55
-rw-r--r--findme.h20
-rw-r--r--popt.c88
-rw-r--r--poptconfig.c3
-rw-r--r--popthelp.c38
-rw-r--r--poptint.c2
8 files changed, 98 insertions, 115 deletions
diff --git a/CHANGES b/CHANGES
index efae8f6..133bcce 100644
--- a/CHANGES
+++ b/CHANGES
@@ -1,4 +1,7 @@
1.13 -> 1.14:
+ - jbj: study the mess with splint. Sigh, splint is so easily confused ...
+ - jbj: rewrite findProgramPath & move to popt.c. Nuke the findme.{c,h} toys.
+ - jbj: use stpcpy several more places (Wayne Davison<wayned@samba.org>).
- jbj: enable equal after short option (Wayne Davison<wayned@samba.org>).
- jbj: permit "#define POPT_fprintf fprintf" to lose the malloc'ing fprintf.
- jbj: use vasprintf(3) when available (Wayne Davison<wayned@samba.org>).
diff --git a/Makefile.am b/Makefile.am
index 27461d8..71206e7 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -14,7 +14,7 @@ SUBDIRS = po
INCLUDES = -I. -I$(top_srcdir)
-noinst_HEADERS = findme.h poptint.h system.h
+noinst_HEADERS = poptint.h system.h
noinst_PROGRAMS = test1 test2 test3
test1_SOURCES = test1.c
@@ -39,7 +39,7 @@ include_HEADERS = popt.h
usrlibdir = $(libdir)
usrlib_LTLIBRARIES = libpopt.la
-libpopt_la_SOURCES = popt.c findme.c poptparse.c poptconfig.c popthelp.c poptint.c
+libpopt_la_SOURCES = popt.c poptparse.c poptconfig.c popthelp.c poptint.c
libpopt_la_LDFLAGS = -no-undefined @LTLIBINTL@
if HAVE_LD_VERSION_SCRIPT
diff --git a/findme.c b/findme.c
deleted file mode 100644
index 82c5ce6..0000000
--- a/findme.c
+++ /dev/null
@@ -1,55 +0,0 @@
-/** \ingroup popt
- * \file popt/findme.c
- */
-
-/* (C) 1998-2002 Red Hat, Inc. -- Licensing details are in the COPYING
- file accompanying popt source distributions, available from
- ftp://ftp.rpm.org/pub/rpm/dist. */
-
-#include "system.h"
-#include "findme.h"
-
-const char * POPT_findProgramPath(const char * argv0)
-{
- char * path = getenv("PATH");
- char * pathbuf = NULL;
- char * start, * chptr;
- char * buf = NULL;
-
- if (argv0 == NULL) return NULL; /* XXX can't happen */
- /* If there is a / in the argv[0], it has to be an absolute path */
- if (strchr(argv0, '/'))
- return xstrdup(argv0);
-
- if (path == NULL) return NULL;
-
- start = pathbuf = malloc(strlen(path) + 1);
- if (pathbuf == NULL) goto exit;
- buf = malloc(strlen(path) + strlen(argv0) + sizeof("/"));
- if (buf == NULL) goto exit;
- strcpy(pathbuf, path);
-
- chptr = NULL;
- do {
- if ((chptr = strchr(start, ':')))
- *chptr = '\0';
- (void) stpcpy(stpcpy(stpcpy(buf, start), "/"), argv0);
- if (!access(buf, X_OK)) {
- free(pathbuf);
- return buf;
- }
-
- if (chptr)
- start = chptr + 1;
- else
- start = NULL;
- } while (start && *start);
-
-exit:
- if (pathbuf)
- free(pathbuf);
- if (buf)
- free(buf);
-
- return NULL;
-}
diff --git a/findme.h b/findme.h
deleted file mode 100644
index a92c3fa..0000000
--- a/findme.h
+++ /dev/null
@@ -1,20 +0,0 @@
-/** \ingroup popt
- * \file popt/findme.h
- */
-
-/* (C) 1998-2000 Red Hat, Inc. -- Licensing details are in the COPYING
- file accompanying popt source distributions, available from
- ftp://ftp.rpm.org/pub/rpm/dist. */
-
-#ifndef H_FINDME
-#define H_FINDME
-
-/**
- * Return absolute path to executable by searching PATH.
- * @param argv0 name of executable
- * @return (malloc'd) absolute path to executable (or NULL)
- */
-/*@null@*/ const char * POPT_findProgramPath(/*@null@*/ const char * argv0)
- /*@*/;
-
-#endif
diff --git a/popt.c b/popt.c
index 6b77e21..f906c97 100644
--- a/popt.c
+++ b/popt.c
@@ -23,7 +23,6 @@ extern long long int strtoll(const char *nptr, /*@null@*/ char **endptr,
#endif
#include <math.h>
-#include "findme.h"
#include "poptint.h"
#ifdef MYDEBUG
@@ -196,10 +195,8 @@ poptContext poptGetContext(const char * name, int argc, const char ** argv,
if (getenv("POSIXLY_CORRECT") || getenv("POSIX_ME_HARDER"))
con->flags |= POPT_CONTEXT_POSIXMEHARDER;
- if (name) {
- char * t = malloc(strlen(name) + 1);
- if (t) con->appName = strcpy(t, name);
- }
+ if (name)
+ con->appName = xstrdup(name);
invokeCallbacksPRE(con, con->options);
@@ -385,6 +382,57 @@ static int handleAlias(/*@special@*/ poptContext con,
return (rc ? rc : 1);
}
+/**
+ * Return absolute path to executable by searching PATH.
+ * @param argv0 name of executable
+ * @return (malloc'd) absolute path to executable (or NULL)
+ */
+static /*@null@*/
+const char * findProgramPath(/*@null@*/ const char * argv0)
+ /*@*/
+{
+ char *path = NULL, *s = NULL, *se;
+ char *t = NULL;
+
+ if (argv0 == NULL) return NULL; /* XXX can't happen */
+
+ /* If there is a / in argv[0], it has to be an absolute path. */
+ /* XXX Hmmm, why not if (argv0[0] == '/') ... instead? */
+ if (strchr(argv0, '/'))
+ return xstrdup(argv0);
+
+ if ((path = getenv("PATH")) == NULL || (path = xstrdup(path)) == NULL)
+ return NULL;
+
+ /* The return buffer in t is big enough for any path. */
+ if ((t = malloc(strlen(path) + strlen(argv0) + sizeof("/"))) != NULL)
+ for (s = path; s && *s; s = se) {
+
+ /* Snip PATH element into [s,se). */
+ if ((se = strchr(s, ':')))
+ *se++ = '\0';
+
+ /* Append argv0 to PATH element. */
+ (void) stpcpy(stpcpy(stpcpy(t, s), "/"), argv0);
+
+ /* If file is executable, bingo! */
+ if (!access(t, X_OK))
+ break;
+ }
+
+ /* If no executable was found in PATH, return NULL. */
+ if (!(s && *s) && t != NULL) {
+ free(t);
+ t = NULL;
+ }
+/*@-modobserver -observertrans -usedef @*/
+ if (path != NULL)
+ free(path);
+/*@=modobserver =observertrans =usedef @*/
+
+ return t;
+}
+
static int execCommand(poptContext con)
/*@globals internalState @*/
/*@modifies internalState @*/
@@ -413,7 +461,7 @@ static int execCommand(poptContext con)
argv[argc] = s;
} else
- argv[argc] = POPT_findProgramPath(item->argv[0]);
+ argv[argc] = findProgramPath(item->argv[0]);
if (argv[argc++] == NULL) {
ec = POPT_ERROR_NOARG;
goto exit;
@@ -593,13 +641,13 @@ expandNextArg(/*@special@*/ poptContext con, const char * s)
/*@modifies con @*/
{
const char * a = NULL;
- size_t alen;
char *t, *te;
size_t tn = strlen(s) + 1;
char c;
- te = t = malloc(tn);;
+ te = t = malloc(tn);
if (t == NULL) return NULL; /* XXX can't happen */
+ *t = '\0';
while ((c = *s++) != '\0') {
switch (c) {
#if 0 /* XXX can't do this */
@@ -617,12 +665,11 @@ expandNextArg(/*@special@*/ poptContext con, const char * s)
}
s += 3;
- alen = strlen(a);
- tn += alen;
- *te = '\0';
- t = realloc(t, tn);
- te = t + strlen(t);
- strncpy(te, a, alen); te += alen;
+ tn += strlen(a);
+ { size_t pos = (size_t) (te - t);
+ t = realloc(t, tn);
+ te = stpcpy(t + pos, a);
+ }
continue;
/*@notreached@*/ /*@switchbreak@*/ break;
default:
@@ -630,8 +677,15 @@ expandNextArg(/*@special@*/ poptContext con, const char * s)
}
*te++ = c;
}
- *te = '\0';
- t = realloc(t, strlen(t) + 1); /* XXX memory leak, hard to plug */
+ *te++ = '\0';
+ /* If the new string is longer than needed, shorten. */
+ if ((t + tn) > te) {
+/*@-usereleased@*/ /* XXX splint can't follow the pointers. */
+ if ((te = realloc(t, (size_t)(te - t))) == NULL)
+ free(t);
+ t = te;
+/*@=usereleased@*/
+ }
return t;
}
@@ -932,7 +986,7 @@ int poptGetNextOpt(poptContext con)
origOptString++;
if (*origOptString != '\0')
- con->os->nextCharArg = origOptString + (*origOptString == '=');
+ con->os->nextCharArg = origOptString + (int)(*origOptString == '=');
}
if (opt == NULL) return POPT_ERROR_BADOPT; /* XXX can't happen */
diff --git a/poptconfig.c b/poptconfig.c
index bf8fef3..e2b5385 100644
--- a/poptconfig.c
+++ b/poptconfig.c
@@ -224,8 +224,7 @@ int poptReadDefaultConfig(poptContext con, /*@unused@*/ UNUSED(int useEnv))
if ((home = getenv("HOME"))) {
fn = malloc(strlen(home) + 20);
if (fn != NULL) {
- strcpy(fn, home);
- strcat(fn, "/.popt");
+ (void) stpcpy(stpcpy(fn, home), "/.popt");
rc = poptReadConfigFile(con, fn);
free(fn);
} else
diff --git a/popthelp.c b/popthelp.c
index bd64d2c..258cd76 100644
--- a/popthelp.c
+++ b/popthelp.c
@@ -237,7 +237,7 @@ singleOptionDefaultValue(size_t lineLength,
if (le == NULL) return NULL; /* XXX can't happen */
*le = '\0';
*le++ = '(';
- strcpy(le, defstr); le += strlen(le);
+ le = stpcpy(le, defstr);
*le++ = ':';
*le++ = ' ';
if (opt->arg) { /* XXX programmer error */
@@ -268,9 +268,9 @@ singleOptionDefaultValue(size_t lineLength,
break;
case POPT_ARG_STRING:
{ const char * s = arg.argv[0];
- if (s == NULL) {
- strcpy(le, "null"); le += strlen(le);
- } else {
+ if (s == NULL)
+ le = stpcpy(le, "null");
+ else {
size_t slen = 4*lineLength - (le - l) - sizeof("\"...\")");
*le++ = '"';
strncpy(le, s, slen); le[slen] = '\0'; le += strlen(le);
@@ -332,18 +332,21 @@ static void singleOptionHelp(FILE * fp, columns_t columns,
#define prtlong (opt->longName != NULL) /* XXX splint needs a clue */
if (!(prtshort || prtlong))
goto out;
- if (prtshort && prtlong)
- sprintf(left, "-%c, %s%s", opt->shortName,
- (F_ISSET(opt, ONEDASH) ? "-" : "--"),
- opt->longName);
- else if (prtshort)
- sprintf(left, "-%c", opt->shortName);
- else if (prtlong)
+ if (prtshort && prtlong) {
+ char *dash = F_ISSET(opt, ONEDASH) ? "-" : "--";
+ left[0] = '-';
+ left[1] = opt->shortName;
+ (void) stpcpy(stpcpy(stpcpy(left+2, ", "), dash), opt->longName);
+ } else if (prtshort) {
+ left[0] = '-';
+ left[1] = opt->shortName;
+ left[2] = '\0';
+ } else if (prtlong) {
/* XXX --long always padded for alignment with/without "-X, ". */
- sprintf(left, " %s%s",
- (poptArgType(opt) == POPT_ARG_MAINCALL ? "" :
- (F_ISSET(opt, ONEDASH) ? "-" : "--")),
- opt->longName);
+ char *dash = poptArgType(opt) == POPT_ARG_MAINCALL ? ""
+ : (F_ISSET(opt, ONEDASH) ? "-" : "--");
+ (void) stpcpy(stpcpy(stpcpy(left, " "), dash), opt->longName);
+ }
#undef prtlong
if (argDescrip) {
@@ -361,9 +364,8 @@ static void singleOptionHelp(FILE * fp, columns_t columns,
if (t) {
char * te = t;
*te = '\0';
- if (help) {
- strcpy(te, help); te += strlen(te);
- }
+ if (help)
+ te = stpcpy(te, help);
*te++ = ' ';
strcpy(te, defs);
defs = _free(defs);
diff --git a/poptint.c b/poptint.c
index 264ec3b..6c135ad 100644
--- a/poptint.c
+++ b/poptint.c
@@ -157,7 +157,7 @@ POPT_fprintf (FILE * stream, const char * format, ...)
int rc;
va_list ap;
-#if defined(HAVE_VASPRINTF)
+#if defined(HAVE_VASPRINTF) && !defined(__LCLINT__)
va_start(ap, format);
if ((rc = vasprintf(&b, format, ap)) < 0)
b = NULL;