[or-cvs] Make a bounds-checking replacement for strtol with slightly...

Nick Mathewson nickm at seul.org
Tue Oct 12 19:32:44 UTC 2004


Update of /home/or/cvsroot/src/common
In directory moria.mit.edu:/tmp/cvs-serv9151/src/common

Modified Files:
	util.c util.h 
Log Message:
Make a bounds-checking replacement for strtol with slightly easier error-checking in the common case

Index: util.c
===================================================================
RCS file: /home/or/cvsroot/src/common/util.c,v
retrieving revision 1.142
retrieving revision 1.143
diff -u -d -r1.142 -r1.143
--- util.c	12 Oct 2004 19:01:53 -0000	1.142
+++ util.c	12 Oct 2004 19:32:41 -0000	1.143
@@ -2051,10 +2051,9 @@
   colon = strchr(addrport, ':');
   if (colon) {
     _address = tor_strndup(addrport, colon-addrport);
-    _port = atoi(colon+1);
-    if (_port<1 || _port>65535) {
+    _port = (int) tor_parse_long(colon+1,10,1,65535,NULL,NULL);
+    if (!_port) {
       log_fn(LOG_WARN, "Port '%s' out of range", colon+1);
-      _port = 0;
       ok = 0;
     }
   } else {
@@ -2084,6 +2083,68 @@
   return ok ? 0 : -1;
 }
 
+/** Extract a long from the start of s, in the given numeric base.  If
+ * there is unconverted data and next is provided, set *next to the
+ * first unconverted character.  An error has occurred if no characters
+ * are converted; or if there are unconverted characters and next is NULL; or
+ * if the parsed value is not between min and max.  When no error occurs,
+ * return the parsed value and set *ok (if provided) to 1.  When an error
+ * ocurs, return 0 and set *ok (if provided) to 0.
+ */
+long
+tor_parse_long(const char *s, int base, long min, long max,
+               int *ok, char **next)
+{
+  char *endptr;
+  long r;
+
+  r = strtol(s, &endptr, base);
+  /* Was at least one character converted? */
+  if (endptr == s)
+    goto err;
+  /* Were there unexpected unconverted characters? */
+  if (!next && *endptr)
+    goto err;
+  /* Is r within limits? */
+  if (r < min || r > max)
+    goto err;
+
+  if (ok) *ok = 1;
+  if (next) *next = endptr;
+  return r;
+ err:
+  if (ok) *ok = 0;
+  if (next) *next = endptr;
+  return 0;
+}
+
+unsigned long
+tor_parse_ulong(const char *s, int base, unsigned long min,
+                unsigned long max, int *ok, char **next)
+{
+  char *endptr;
+  unsigned long r;
+
+  r = strtol(s, &endptr, base);
+  /* Was at least one character converted? */
+  if (endptr == s)
+    goto err;
+  /* Were there unexpected unconverted characters? */
+  if (!next && *endptr)
+    goto err;
+  /* Is r within limits? */
+  if (r < min || r > max)
+    goto err;
+
+  if (ok) *ok = 1;
+  if (next) *next = endptr;
+  return r;
+ err:
+  if (ok) *ok = 0;
+  if (next) *next = endptr;
+  return 0;
+}
+
 #ifndef MS_WINDOWS
 struct tor_mutex_t {
 };

Index: util.h
===================================================================
RCS file: /home/or/cvsroot/src/common/util.h,v
retrieving revision 1.93
retrieving revision 1.94
diff -u -d -r1.93 -r1.94
--- util.h	12 Oct 2004 15:48:30 -0000	1.93
+++ util.h	12 Oct 2004 19:32:41 -0000	1.94
@@ -94,6 +94,10 @@
 int tor_strpartition(char *dest, size_t dest_len,
                      const char *s, const char *insert, size_t n,
                      part_finish_rule_t rule);
+long tor_parse_long(const char *s, int base, long min,
+                    long max, int *ok, char **next);
+unsigned long tor_parse_ulong(const char *s, int base, unsigned long min,
+                              unsigned long max, int *ok, char **next);
 
 
 /* Some platforms segfault when you try to access a multi-byte type



More information about the tor-commits mailing list