Complete.Org: Mailing Lists: Archives: freeciv-dev: December 1999:
[Freeciv-Dev] patch: mystrlcpy(), mystrlcat() (PR#211)
Home

[Freeciv-Dev] patch: mystrlcpy(), mystrlcat() (PR#211)

[Top] [All Lists]

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index] [Thread Index]
To: freeciv-dev@xxxxxxxxxxx
Cc: bugs@xxxxxxxxxxxxxxxxxxx
Subject: [Freeciv-Dev] patch: mystrlcpy(), mystrlcat() (PR#211)
From: David Pfitzner <dwp@xxxxxxxxxxxxxx>
Date: Tue, 28 Dec 1999 04:37:26 -0800 (PST)

This patch provides convenient functions mystrlcpy() and mystrlcat(),
with semantics from OpenBSD (see comments in patch).

-- David
diff -u -r --exclude-from exclude_auto freeciv-cvs/common/support.c 
fc-adv/common/support.c
--- freeciv-cvs/common/support.c        Mon Dec 27 23:14:38 1999
+++ fc-adv/common/support.c     Tue Dec 28 23:28:34 1999
@@ -51,6 +51,85 @@
 
 #include "support.h"
 
+/**********************************************************************
+ mystrlcpy() and mystrlcat() provide (non-standard) functions
+ strlcpy() and strlcat(), with semantics following OpenBSD (and
+ maybe others).  They are intended as more user-friendly
+ versions of stncpy and strncat, in particular easier to
+ use safely and correctly, and ensuring nul-terminated results
+ while being able to detect truncation.
+
+ n is the full size of the destination buffer, including
+ space for trailing nul, and including the pre-existing
+ string for mystrlcat().  Thus can eg use sizeof(buffer),
+ or exact size malloc-ed.
+
+ Result is always nul-terminated, whether or not truncation occurs,
+ and the return value is the strlen the destination would have had
+ without truncation.  Ie, a return value >= input n indicates
+ truncation occured.
+
+ Will assume that if configure found strlcpy/strlcat they are ok.
+ For replacement implementations, will keep it simple rather
+ than try for super-efficiency.
+
+ Not sure about the asserts below, but they are easier than
+ trying to ensure correct behaviour on strange inputs.
+ In particular note that n==0 is prohibited (eg, since there
+ must at least be room for a nul); could consider other options.
+***********************************************************************/
+size_t mystrlcpy(char *dest, const char *src, size_t n)
+{
+  assert(dest);
+  assert(src);
+  assert(n>0);
+#ifdef HAVE_STRLCPY
+  return strlcpy(dest, src, n);
+#else
+  {
+    size_t len = strlen(src);
+    size_t num_to_copy = (len >= n) ? n-1 : len;
+    if (num_to_copy>0)
+      memcpy(dest, src, num_to_copy);
+    dest[num_to_copy] = '\0';
+    return len;
+  }
+#endif
+}
+
+size_t mystrlcat(char *dest, const char *src, size_t n)
+{
+  assert(dest);
+  assert(src);
+  assert(n>0);
+#ifdef HAVE_STRLCAT
+  return strlcat(dest, src, n);
+#else
+  {
+    size_t num_to_copy, len_dest, len_src;
+    
+    len_dest = strlen(dest);
+    assert(len_dest<n);
+    /* Otherwise have bad choice of leaving dest not nul-terminated
+     * within the specified length n (which should be assumable as
+     * a post-condition of mystrlcat), or modifying dest before end
+     * of existing string (which breaks strcat semantics).
+     */
+       
+    dest += len_dest;
+    n -= len_dest;
+    
+    len_src = strlen(src);
+    num_to_copy = (len_src >= n) ? n-1 : len_src;
+    if (num_to_copy>0)
+      memcpy(dest, src, num_to_copy);
+    dest[num_to_copy] = '\0';
+    return len_dest + len_src;
+  }
+#endif
+}
+
+
 #ifdef HAVE_VSNPRINTF
 /**********************************************************************
  Convenience function used by check_native_vsnprintf() below.
diff -u -r --exclude-from exclude_auto freeciv-cvs/common/support.h 
fc-adv/common/support.h
--- freeciv-cvs/common/support.h        Tue Dec 28 23:03:43 1999
+++ fc-adv/common/support.h     Tue Dec 28 23:28:34 1999
@@ -27,6 +27,9 @@
 
 #include "attribute.h"
 
+size_t mystrlcpy(char *dest, const char *src, size_t n);
+size_t mystrlcat(char *dest, const char *src, size_t n);
+
 int my_snprintf(char *str, size_t n, const char *format, ...)
      fc__attribute((format (printf, 3, 4)));
 
diff -u -r --exclude-from exclude_auto freeciv-cvs/configure.in 
fc-adv/configure.in
--- freeciv-cvs/configure.in    Tue Dec 28 21:52:45 1999
+++ fc-adv/configure.in Tue Dec 28 23:28:34 1999
@@ -361,7 +361,7 @@
 AC_TYPE_SIGNAL
 AC_FUNC_VPRINTF
 AC_CHECK_FUNCS(fdopen gethostname getpwuid gettimeofday select \
-               snooze strerror strstr usleep vsnprintf)
+               snooze strerror strlcat strlcpy strstr usleep vsnprintf)
 
 dnl We would AC_CHECK_FUNCS for socket as well, except it is complicated
 dnl by the fact that the -lsocket is in X_EXTRA_LIBS and/or SERVER_LIBS,

[Prev in Thread] Current Thread [Next in Thread]
  • [Freeciv-Dev] patch: mystrlcpy(), mystrlcat() (PR#211), David Pfitzner <=