* m4/macros/header_templates.m4: extern template for strlcat().
authorErez Zadok <ezk@cs.sunysb.edu>
Thu, 7 Jul 2005 23:34:23 +0000 (23:34 +0000)
committerErez Zadok <ezk@cs.sunysb.edu>
Thu, 7 Jul 2005 23:34:23 +0000 (23:34 +0000)
* amd/get_args.c (get_version_string): use safer strlcat (or
replacement strlcat).  Use new wrapper xsnprintf() function, which
will use the safer vsnprintf() if available, else default to plain
sprintf.

* configure.in: check for existence of strlcat() and its extern,
replacing with libamu/strlcat.c as needed.

* libamu/Makefile.am (EXTRA_DIST): add strlcat.c to distro.

* include/am_defs.h: optional strlcat() extern.

* include/am_utils.h: extern for new xvsnprintf().

Check for snprintf function and extern.

ChangeLog
NEWS
amd/get_args.c
configure.in
include/am_defs.h
include/am_utils.h
libamu/Makefile.am
libamu/strlcat.c [new file with mode: 0644]
libamu/xutil.c
m4/macros/header_templates.m4

index d71b40b302b808061b7c3f78a3e9747721422383..acb4cf0ea86ac31db653a7c5902ec877567b9dc8 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,6 +1,23 @@
 2005-07-07  Erez Zadok  <ezk@cs.sunysb.edu>
 
+       * m4/macros/header_templates.m4: extern template for strlcat().
+
+       * amd/get_args.c (get_version_string): use safer strlcat (or
+       replacement strlcat).  Use new wrapper xsnprintf() function, which
+       will use the safer vsnprintf() if available, else default to plain
+       sprintf.
+
+       * configure.in: check for existence of strlcat() and its extern,
+       replacing with libamu/strlcat.c as needed.
+
+       * libamu/Makefile.am (EXTRA_DIST): add strlcat.c to distro.
+
+       * include/am_defs.h: optional strlcat() extern.
+
+       * include/am_utils.h: extern for new xvsnprintf().
+
        * configure.in: overdue new major libtool shlib version.
+       Check for snprintf function and extern.
 
 2005-07-06  Erez Zadok  <ezk@cs.sunysb.edu>
 
diff --git a/NEWS b/NEWS
index 11a3aa46bc994ddf436d1d7ea70a71d8c03980ed..a5e17fbd8e6a7895eb2df8372a08f3fc1c4e7196 100644 (file)
--- a/NEWS
+++ b/NEWS
@@ -14,6 +14,7 @@
        * possible running off end of exported_ap[] array.
        * buffer overflow in pawd.
        * aix4 clean build.
+       * use strlcat/snprintf in a few places for safety.
 
 *** Notes specific to am-utils version 6.1
 
index cf7cc0b6cc04b4f7f3e432cf3e0d4f637683b8ab..8639c8e8adc03a121b09c8d123097e9aeb2f2232 100644 (file)
@@ -37,7 +37,7 @@
  * SUCH DAMAGE.
  *
  *
- * $Id: get_args.c,v 1.32 2005/06/04 16:34:33 ezk Exp $
+ * $Id: get_args.c,v 1.33 2005/07/07 23:34:23 ezk Exp $
  *
  */
 
@@ -71,52 +71,57 @@ get_version_string(void)
   char tmpbuf[1024];
   char *wire_buf;
   int wire_buf_len = 0;
+  size_t len;                  /* max allocated length (to avoid buf overflow) */
 
-  /* first get dynamic string listing all known networks */
+  /*
+   * First get dynamic string listing all known networks.
+   * This could be a long list, if host has lots of interfaces.
+   */
   wire_buf = print_wires();
   if (wire_buf)
     wire_buf_len = strlen(wire_buf);
 
-  vers = xmalloc(2048 + wire_buf_len);
-  sprintf(vers, "%s\n%s\n%s\n%s\n",
-         "Copyright (c) 1997-2005 Erez Zadok",
-         "Copyright (c) 1990 Jan-Simon Pendry",
-         "Copyright (c) 1990 Imperial College of Science, Technology & Medicine",
-         "Copyright (c) 1990 The Regents of the University of California.");
-  sprintf(tmpbuf, "%s version %s (build %d).\n",
-         PACKAGE_NAME, PACKAGE_VERSION, AMU_BUILD_VERSION);
-  strcat(vers, tmpbuf);
-  sprintf(tmpbuf, "Report bugs to %s.\n", PACKAGE_BUGREPORT);
-  strcat(vers, tmpbuf);
-  sprintf(tmpbuf, "Configured by %s@%s on date %s.\n",
-         USER_NAME, HOST_NAME, CONFIG_DATE);
-  strcat(vers, tmpbuf);
-  sprintf(tmpbuf, "Built by %s@%s on date %s.\n",
-         BUILD_USER, BUILD_HOST, BUILD_DATE);
-  strcat(vers, tmpbuf);
-  sprintf(tmpbuf, "cpu=%s (%s-endian), arch=%s, karch=%s.\n",
-         cpu, endian, gopt.arch, gopt.karch);
-  strcat(vers, tmpbuf);
-  sprintf(tmpbuf, "full_os=%s, os=%s, osver=%s, vendor=%s, distro=%s.\n",
-         gopt.op_sys_full, gopt.op_sys, gopt.op_sys_ver, gopt.op_sys_vendor, DISTRO_NAME);
-  strcat(vers, tmpbuf);
-  sprintf(tmpbuf, "domain=%s, host=%s, hostd=%s.\n",
-         hostdomain, am_get_hostname(), hostd);
-  strcat(vers, tmpbuf);
-
-  strcat(vers, "Map support for: ");
+  len = 2048 + wire_buf_len;
+  vers = xmalloc(len);
+  xsnprintf(vers, len, "%s\n%s\n%s\n%s\n",
+           "Copyright (c) 1997-2005 Erez Zadok",
+           "Copyright (c) 1990 Jan-Simon Pendry",
+           "Copyright (c) 1990 Imperial College of Science, Technology & Medicine",
+           "Copyright (c) 1990 The Regents of the University of California.");
+  xsnprintf(tmpbuf, sizeof(tmpbuf), "%s version %s (build %d).\n",
+           PACKAGE_NAME, PACKAGE_VERSION, AMU_BUILD_VERSION);
+  strlcat(vers, tmpbuf, len);
+  xsnprintf(tmpbuf, sizeof(tmpbuf), "Report bugs to %s.\n", PACKAGE_BUGREPORT);
+  strlcat(vers, tmpbuf, len);
+  xsnprintf(tmpbuf, sizeof(tmpbuf), "Configured by %s@%s on date %s.\n",
+           USER_NAME, HOST_NAME, CONFIG_DATE);
+  strlcat(vers, tmpbuf, len);
+  xsnprintf(tmpbuf, sizeof(tmpbuf), "Built by %s@%s on date %s.\n",
+           BUILD_USER, BUILD_HOST, BUILD_DATE);
+  strlcat(vers, tmpbuf, len);
+  xsnprintf(tmpbuf, sizeof(tmpbuf), "cpu=%s (%s-endian), arch=%s, karch=%s.\n",
+           cpu, endian, gopt.arch, gopt.karch);
+  strlcat(vers, tmpbuf, len);
+  xsnprintf(tmpbuf, sizeof(tmpbuf), "full_os=%s, os=%s, osver=%s, vendor=%s, distro=%s.\n",
+           gopt.op_sys_full, gopt.op_sys, gopt.op_sys_ver, gopt.op_sys_vendor, DISTRO_NAME);
+  strlcat(vers, tmpbuf, len);
+  xsnprintf(tmpbuf, sizeof(tmpbuf), "domain=%s, host=%s, hostd=%s.\n",
+           hostdomain, am_get_hostname(), hostd);
+  strlcat(vers, tmpbuf, len);
+
+  strlcat(vers, "Map support for: ", len);
   mapc_showtypes(tmpbuf);
-  strcat(vers, tmpbuf);
-  strcat(vers, ".\nAMFS: ");
+  strlcat(vers, tmpbuf, len);
+  strlcat(vers, ".\nAMFS: ", len);
   ops_showamfstypes(tmpbuf);
-  strcat(vers, tmpbuf);
-  strcat(vers, ", inherit.\nFS: "); /* hack: "show" that we support type:=inherit */
+  strlcat(vers, tmpbuf, len);
+  strlcat(vers, ", inherit.\nFS: ", len); /* hack: "show" that we support type:=inherit */
   ops_showfstypes(tmpbuf);
-  strcat(vers, tmpbuf);
+  strlcat(vers, tmpbuf, len);
 
   /* append list of networks if available */
   if (wire_buf) {
-    strcat(vers, wire_buf);
+    strlcat(vers, wire_buf, len);
     XFREE(wire_buf);
   }
 
index 7d812f7822303c007d3939b640773cb9bbccfe45..7f709b2e1875438eb1f75bb772107ad796996c4c 100644 (file)
@@ -55,7 +55,7 @@ AH_BOTTOM([
 dnl
 dnl AC_CONFIG_AUX_DIR(m4)
 AC_PREREQ(2.52)
-AC_REVISION($Revision: 1.101 $)
+AC_REVISION($Revision: 1.102 $)
 AC_COPYRIGHT([Copyright (c) 1997-2005 Erez Zadok])
 dnl find out system type
 AC_MSG_NOTICE(*** SYSTEM TYPES ***)
@@ -315,11 +315,12 @@ AC_CHECK_FUNCS(                   \
        signal                  \
        sigsuspend              \
        socket                  \
-       strchr                  \
        strcasecmp              \
+       strchr                  \
        strcspn                 \
        strdup                  \
        strerror                \
+       strlcat                 \
        strlcpy                 \
        strspn                  \
        strstr                  \
@@ -345,6 +346,7 @@ AC_REPLACE_FUNCS(           \
        strcasecmp              \
        strdup                  \
        strerror                \
+       strlcat                 \
        strlcpy                 \
        strstr                  \
        ualarm                  \
@@ -770,6 +772,7 @@ AMU_CHECK_EXTERNS(
        sleep                   \
        strcasecmp              \
        strdup                  \
+       strlcat                 \
        strlcpy                 \
        strstr                  \
        ualarm                  \
index be503670f932d59d72435b185f4551345f86d7a0..cfbcba72bc21c56bb4c1569fd2cce21c160a315d 100644 (file)
@@ -37,7 +37,7 @@
  * SUCH DAMAGE.
  *
  *
- * $Id: am_defs.h,v 1.60 2005/06/23 20:46:11 ezk Exp $
+ * $Id: am_defs.h,v 1.61 2005/07/07 23:34:23 ezk Exp $
  *
  */
 
@@ -1511,6 +1511,14 @@ extern int strcasecmp(const char *s1, const char *s2);
 extern char *strdup(const char *s);
 #endif /* not HAVE_EXTERN_STRDUP */
 
+#ifndef HAVE_EXTERN_STRLCAT
+/*
+ * define this extern even if function does not exist, for it will
+ * be filled in by libamu/strlcat.c
+ */
+extern size_t strlcat(char *dst, const char *src, size_t siz);
+#endif /* not HAVE_EXTERN_STRLCAT */
+
 #ifndef HAVE_EXTERN_STRLCPY
 /*
  * define this extern even if function does not exist, for it will
index 3e8938b90fefc9a3d1d847c32a30cbad564b7b83..571aac4f114abb595710582eb1dee7f2a08c0854 100644 (file)
@@ -37,7 +37,7 @@
  * SUCH DAMAGE.
  *
  *
- * $Id: am_utils.h,v 1.65 2005/04/07 23:31:07 ezk Exp $
+ * $Id: am_utils.h,v 1.66 2005/07/07 23:34:23 ezk Exp $
  *
  */
 
@@ -325,6 +325,7 @@ extern voidp xzalloc(int);
 extern int check_pmap_up(char *host, struct sockaddr_in* sin);
 extern u_long get_nfs_version(char *host, struct sockaddr_in *sin, u_long nfs_version, const char *proto);
 extern long get_server_pid(void);
+extern int xsnprintf(char *str, size_t size, const char *format, ...);
 
 
 #ifdef MOUNT_TABLE_ON_FILE
index 1eac5ab5c39f7f26a3fea8ccbea42fb462def2e6..fc9f50811b58b0c8e379e06598402ff3df23fd34 100644 (file)
@@ -30,6 +30,7 @@ EXTRA_DIST = memcmp.c \
        strcasecmp.c    \
        strdup.c        \
        strerror.c      \
+       strlcat.c       \
        strlcpy.c       \
        strstr.c        \
        ualarm.c
diff --git a/libamu/strlcat.c b/libamu/strlcat.c
new file mode 100644 (file)
index 0000000..1b61aab
--- /dev/null
@@ -0,0 +1,87 @@
+/*
+ * Copyright (c) 1997-2005 Erez Zadok
+ * Copyright (c) 1990 Jan-Simon Pendry
+ * Copyright (c) 1990 Imperial College of Science, Technology & Medicine
+ * Copyright (c) 1990 The Regents of the University of California.
+ * All rights reserved.
+ *
+ * This code is derived from software contributed to Berkeley by
+ * Jan-Simon Pendry at Imperial College, London.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgment:
+ *      This product includes software developed by the University of
+ *      California, Berkeley and its contributors.
+ * 4. Neither the name of the University nor the names of its contributors
+ *    may be used to endorse or promote products derived from this software
+ *    without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ *
+ * $Id: strlcat.c,v 1.1 2005/07/07 23:34:23 ezk Exp $
+ *
+ */
+
+#ifdef HAVE_CONFIG_H
+# include <config.h>
+#endif /* HAVE_CONFIG_H */
+#include <am_defs.h>
+#include <amu.h>
+
+/*
+ * Implementation of strlcat(3) from OpenBSD/NetBSD.
+ */
+
+/*
+ * Appends src to string dst of size siz (unlike strncat, siz is the
+ * full size of dst, not space left).  At most siz-1 characters
+ * will be copied.  Always NUL terminates (unless siz <= strlen(dst)).
+ * Returns strlen(src) + MIN(siz, strlen(initial dst)).
+ * If retval >= siz, truncation occurred.
+ */
+size_t
+strlcat(char *dst, const char *src, size_t siz)
+{
+  char *d = dst;
+  const char *s = src;
+  size_t n = siz;
+  size_t dlen;
+
+  /* Find the end of dst and adjust bytes left but don't go past end */
+  while (n-- != 0 && *d != '\0')
+    d++;
+  dlen = d - dst;
+  n = siz - dlen;
+
+  if (n == 0)
+    return(dlen + strlen(s));
+  while (*s != '\0') {
+    if (n != 1) {
+      *d++ = *s;
+      n--;
+    }
+    s++;
+  }
+  *d = '\0';
+
+  return(dlen + (s - src));    /* count does not include NUL */
+}
index c5ef2c6b6cc05fc1c6f8c2571c5108d3b0e85b38..7d68aa69c78724abb80b08a8f47b7812fe8b3928 100644 (file)
@@ -37,7 +37,7 @@
  * SUCH DAMAGE.
  *
  *
- * $Id: xutil.c,v 1.37 2005/04/07 05:50:39 ezk Exp $
+ * $Id: xutil.c,v 1.38 2005/07/07 23:34:23 ezk Exp $
  *
  */
 
@@ -951,3 +951,21 @@ amu_release_controlling_tty(void)
 
   plog(XLOG_ERROR, "unable to release controlling tty");
 }
+
+
+/* our version of snprintf */
+int
+xsnprintf(char *str, size_t size, const char *format, ...)
+{
+  va_list ap;
+  int ret;
+
+  va_start(ap, format);
+#ifdef HAVE_VSNPRINTF
+  ret = vsnprintf(str, size, format, ap);
+#else /* not HAVE_VSNPRINTF */
+  ret = sprintf(str, format, ap); /* less secure version */
+#endif /* not HAVE_VSNPRINTF */
+  va_end(ap);
+  return ret;
+}
index 9a7698cafda89f6308446bf1d35ee0bccfa7ecf7..210f799abcbd741853d712fe19e752d64dc1e880 100644 (file)
@@ -919,6 +919,9 @@ AH_TEMPLATE([HAVE_EXTERN_STRCASECMP],
 AH_TEMPLATE([HAVE_EXTERN_STRDUP],
 [does extern definition for strdup() exist?])
 
+AH_TEMPLATE([HAVE_EXTERN_STRLCAT],
+[does extern definition for strlcat() exist?])
+
 AH_TEMPLATE([HAVE_EXTERN_STRLCPY],
 [does extern definition for strlcpy() exist?])