[Git][NTPsec/ntpsec][master] Eliminate homebrew strtouv64() function for parsing long integer literals...

Eric S. Raymond gitlab at mg.gitlab.com
Sun Dec 11 20:53:27 UTC 2016


Eric S. Raymond pushed to branch master at NTPsec / ntpsec


Commits:
6f07d603 by Eric S. Raymond at 2016-12-11T15:48:43-05:00
Eliminate homebrew strtouv64() function for parsing long integer literals...

...in favor of strtoull(3)

Because we assume that the compiler has a native int64_t/uint64_t type,
it is silly to imagine that unsigned long long won't be 64-bit.

- - - - -


4 changed files:

- include/vint64ops.h
- libntp/vint64ops.c
- ntpd/ntp_leapsec.c
- tests/libntp/vi64ops.c


Changes:

=====================================
include/vint64ops.h
=====================================
--- a/include/vint64ops.h
+++ b/include/vint64ops.h
@@ -24,7 +24,4 @@ extern vint64 subv64(const vint64 *lhs, const vint64 *rhs);
 extern vint64 subv64i32(const vint64 * lhs, int32_t rhs);
 extern vint64 subv64u32(const vint64 * lhs, uint32_t rhs);
 
-/* parsing. works like strtoul() or strtoull() */
-extern vint64 strtouv64(const char * begp, char ** endp, int base);
-
 #endif /* GUARD_VINT64OPS_H */


=====================================
libntp/vint64ops.c
=====================================
--- a/libntp/vint64ops.c
+++ b/libntp/vint64ops.c
@@ -18,94 +18,6 @@
 #include "ntp_fp.h"
 #include "vint64ops.h"
 
-/* ---------------------------------------------------------------------
- * GCC is rather sticky with its 'const' attribute. We have to do it more
- * explicit than with a cast if we want to get rid of a CONST qualifier.
- * Greetings from the PASCAL world, where casting was only possible via
- * untagged unions...
- */
-static inline void*
-noconst(
-	const void* ptr
-	)
-{
-	union {
-		const void * cp;
-		void *       vp;
-	} tmp;
-	tmp.cp = ptr;
-	return tmp.vp;
-}
-
-/* -------------------------------------------------------------------------*/
-
-vint64
-strtouv64(
-	const char * begp,
-	char **      endp,
-	int          base
-	)
-{
-	vint64  res;
-	uint8_t  digit;
-	int     sig, num;
-	const uint8_t *src;
-	
-	num = sig = 0;
-	src = (const uint8_t*)begp;
-	while (isspace(*src))
-		src++;
-
-	if (*src == '-') {
-		src++;
-		sig = 1;
-	} else  if (*src == '+') {
-		src++;
-	}
-
-	if (base == 0) {
-		base = 10;
-		if (*src == '0') {
-			base = 8;
-			if (toupper(*++src) == 'X') {
-				src++;
-				base = 16;
-			}
-		}
-	} else if (base == 16) { /* remove optional leading '0x' or '0X' */
-		if (src[0] == '0' && toupper(src[1]) == 'X')
-			src += 2;
-	} else if (base <= 2 || base > 36) {
-		memset(&res, 0xFF, sizeof(res));
-		errno = ERANGE;
-		return res;
-	}
-	
-	memset(&res, 0, sizeof(res));
-	while (*src) {
-		if (isdigit(*src))
-			digit = *src - '0';
-		else if (isupper(*src))
-			digit = *src - 'A' + 10;
-		else if (islower(*src))
-			digit = *src - 'a' + 10;
-		else
-			break;
-		if (digit >= base)
-			break;
-		num = 1;
-		setvint64u(res, vint64u(res) * base + digit);
-		src++;
-	}
-	if (!num)
-		errno = EINVAL;
-	if (endp)
-		*endp = (char*)noconst(src);
-	if (sig)
-		negvint64(res);
-	return res;
-}
-
 /* -------------------------------------------------------------------------*/
 
 int


=====================================
ntpd/ntp_leapsec.c
=====================================
--- a/ntpd/ntp_leapsec.c
+++ b/ntpd/ntp_leapsec.c
@@ -7,6 +7,10 @@
  * This is an attempt to get the leap second handling into a dedicated
  * module to make the somewhat convoluted logic testable.
  *
+ * Note: Ths code assumes that the unsigned long long return value of
+ * strtoull(3) is large enough to parse any integer literal found in these
+ * files, and that C will promote such values to uint64_t properly.
+ *
  * Copyright 2015 by the NTPsec project contributors
  * SPDX-License-Identifier: NTP
  */
@@ -201,18 +205,18 @@ leapsec_load(
 			cp++;
 			if (*cp == '@') {
 				cp = skipws(cp+1);
-				pt->head.expire = strtouv64(cp, &ep, 10);
+				setvint64u(pt->head.expire, strtoull(cp, &ep, 10));
 				if (parsefail(cp, ep))
 					goto fail_read;
 				pt->lsig.etime = vint64lo(pt->head.expire);
 			} else if (*cp == '$') {
 				cp = skipws(cp+1);
-				pt->head.update = strtouv64(cp, &ep, 10);
+				setvint64u(pt->head.update, strtoull(cp, &ep, 10));
 				if (parsefail(cp, ep))
 					goto fail_read;
 			}		    
 		} else if (isdigit((uint8_t)*cp)) {
-			ttime = strtouv64(cp, &ep, 10);
+		    setvint64u(ttime, strtoull(cp, &ep, 10));
 			if (parsefail(cp, ep))
 				goto fail_read;
 			cp = skipws(ep);


=====================================
tests/libntp/vi64ops.c
=====================================
--- a/tests/libntp/vi64ops.c
+++ b/tests/libntp/vi64ops.c
@@ -13,56 +13,6 @@ TEST_TEAR_DOWN(vi64ops) {}
 
 #include "vint64ops.h"
 
-bool IsEqual(const vint64 *expected, const vint64 *actual) {
-	if (0 == memcmp(expected, actual, sizeof(vint64))) {
-		return true;
-	} else {
-		printf("Expected: %04x.%04x but was: %04x.%04x\n", vint64hiu(*expected), vint64lo(*expected), vint64hiu(*actual), vint64lo(*actual));
-		return false;
-	}
-}
-
-// ----------------------------------------------------------------------
-// test number parser
-TEST(vi64ops, ParseVUI64_pos) {
-	vint64 act, exp;
-	const char *sp;
-	char       *ep;
-
-	sp         = "1234x";
-	setvint64hiu(exp, 0);
-	setvint64lo(exp, 1234);
-	act        = strtouv64(sp, &ep, 0);
-	TEST_ASSERT_TRUE(IsEqual(&exp, &act));
-	TEST_ASSERT_EQUAL(*ep, 'x');
-}
-
-TEST(vi64ops, ParseVUI64_neg) {
-	vint64 act, exp;
-	const char *sp;
-	char       *ep;
-
-	sp         = "-1234x";
-	setvint64hiu(exp, ~0);
-	setvint64lo(exp, -1234);
-	act        = strtouv64(sp, &ep, 0);
-	TEST_ASSERT_TRUE(IsEqual(&exp, &act));
-	TEST_ASSERT_EQUAL(*ep, 'x');
-}
-
-TEST(vi64ops, ParseVUI64_case) {
-	vint64 act, exp;
-	const char *sp;
-	char       *ep;
-
-	sp         = "0123456789AbCdEf";
-	setvint64hiu(exp, 0x01234567);
-	setvint64lo(exp, 0x89ABCDEF);
-	act        = strtouv64(sp, &ep, 16);
-	TEST_ASSERT_TRUE(IsEqual(&exp, &act));
-	TEST_ASSERT_EQUAL(*ep, '\0');
-}
-
 TEST(vi64ops, HiLoVUI64uh) {
 	vint64 exp;
 
@@ -124,9 +74,6 @@ TEST(vi64ops, NegVUI64) {
 }
 
 TEST_GROUP_RUNNER(vi64ops) {
-	RUN_TEST_CASE(vi64ops, ParseVUI64_pos);
-	RUN_TEST_CASE(vi64ops, ParseVUI64_neg);
-	RUN_TEST_CASE(vi64ops, ParseVUI64_case);
 	RUN_TEST_CASE(vi64ops, HiLoVUI64uh);
 	RUN_TEST_CASE(vi64ops, HiLoVUI64ul);
 	RUN_TEST_CASE(vi64ops, HiLoVUI64sh);



View it on GitLab: https://gitlab.com/NTPsec/ntpsec/commit/6f07d603b05d2ee5d480118e6c3461e6476034b6
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.ntpsec.org/pipermail/vc/attachments/20161211/28e7a9f0/attachment.html>


More information about the vc mailing list