svn commit: r300775 - head/lib/libc/stdlib

Ed Schouten ed at FreeBSD.org
Thu May 26 20:55:16 UTC 2016


Author: ed
Date: Thu May 26 20:55:15 2016
New Revision: 300775
URL: https://svnweb.freebsd.org/changeset/base/300775

Log:
  Let l64a() properly null terminate its result.
  
  Though the buffer used by l64a() is initialized with null bytes,
  repetetive calls may end up having trailing garbage of previous
  invocations because we don't end up terminating the string.
  
  Instead of importing NetBSD's fix, use this opportunity to simplify this
  function dramatically, for example by just storing the Base64 character
  set in a string. There is also no need to do the bitmasking, as we can
  just use the proper integer type from <stdint.h>.
  
  MFC after:	1 month
  Differential Revision:	https://reviews.freebsd.org/D6511

Modified:
  head/lib/libc/stdlib/l64a.c

Modified: head/lib/libc/stdlib/l64a.c
==============================================================================
--- head/lib/libc/stdlib/l64a.c	Thu May 26 20:37:49 2016	(r300774)
+++ head/lib/libc/stdlib/l64a.c	Thu May 26 20:55:15 2016	(r300775)
@@ -12,18 +12,13 @@ __RCSID("$NetBSD: l64a.c,v 1.13 2003/07/
 #include <sys/cdefs.h>
 __FBSDID("$FreeBSD$");
 
+#include <stdint.h>
 #include <stdlib.h>
 
-#define	ADOT	46		/* ASCII '.' */
-#define	ASLASH	ADOT + 1	/* ASCII '/' */
-#define	A0	48		/* ASCII '0' */
-#define	AA	65		/* ASCII 'A' */
-#define	Aa	97		/* ASCII 'a' */
-
 char *
 l64a(long value)
 {
-	static char buf[8];
+	static char buf[7];
 
 	(void)l64a_r(value, buf, sizeof(buf));
 	return (buf);
@@ -32,21 +27,18 @@ l64a(long value)
 int
 l64a_r(long value, char *buffer, int buflen)
 {
-	long v;
-	int digit;
-
-	v = value & (long)0xffffffff;
-	for (; v != 0 && buflen > 1; buffer++, buflen--) {
-		digit = v & 0x3f;
-		if (digit < 2)
-			*buffer = digit + ADOT;
-		else if (digit < 12)
-			*buffer = digit + A0 - 2;
-		else if (digit < 38)
-			*buffer = digit + AA - 12;
-		else
-			*buffer = digit + Aa - 38;
+	static const char chars[] =
+	    "./0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
+	uint32_t v;
+
+	v = value;
+	while (buflen-- > 0) {
+		if (v == 0) {
+			*buffer = '\0';
+			return (0);
+		}
+		*buffer++ = chars[v & 0x3f];
 		v >>= 6;
 	}
-	return (v == 0 ? 0 : -1);
+	return (-1);
 }


More information about the svn-src-head mailing list