summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--bin/expr/expr.y59
-rw-r--r--bin/test/test.c56
-rw-r--r--usr.bin/printf/printf.c31
3 files changed, 96 insertions, 50 deletions
diff --git a/bin/expr/expr.y b/bin/expr/expr.y
index 117270a14f77..5f453733cebc 100644
--- a/bin/expr/expr.y
+++ b/bin/expr/expr.y
@@ -7,12 +7,14 @@
* $FreeBSD$
*/
+#include <sys/types.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <locale.h>
#include <ctype.h>
#include <err.h>
+#include <regex.h>
enum valtype {
integer, numeric_string, string
@@ -22,7 +24,7 @@ struct val {
enum valtype type;
union {
char *s;
- int i;
+ quad_t i;
} u;
} ;
@@ -87,7 +89,7 @@ expr: TOKEN
struct val *
make_integer (i)
-int i;
+quad_t i;
{
struct val *vp;
@@ -139,11 +141,11 @@ struct val *vp;
}
-int
+quad_t
to_integer (vp)
struct val *vp;
{
- int i;
+ quad_t i;
if (vp->type == integer)
return 1;
@@ -152,7 +154,7 @@ struct val *vp;
return 0;
/* vp->type == numeric_string, make it numeric */
- i = atoi(vp->u.s);
+ i = strtoq(vp->u.s, (char**)NULL, 10);
free (vp->u.s);
vp->u.i = i;
vp->type = integer;
@@ -173,7 +175,7 @@ struct val *vp;
errx (2, "malloc() failed");
}
- sprintf (tmp, "%d", vp->u.i);
+ sprintf (tmp, "%qd", vp->u.i);
vp->type = string;
vp->u.s = tmp;
}
@@ -239,7 +241,7 @@ char **argv;
yyparse ();
if (result->type == integer)
- printf ("%d\n", result->u.i);
+ printf ("%qd\n", result->u.i);
else
printf ("%s\n", result->u.s);
@@ -274,7 +276,7 @@ struct val *a, *b;
if (is_zero_or_null (a) || is_zero_or_null (b)) {
free_value (a);
free_value (b);
- return (make_integer (0));
+ return (make_integer ((quad_t)0));
} else {
free_value (b);
return (a);
@@ -290,11 +292,11 @@ struct val *a, *b;
if (isstring (a) || isstring (b)) {
to_string (a);
to_string (b);
- r = make_integer (strcoll (a->u.s, b->u.s) == 0);
+ r = make_integer ((quad_t)(strcoll (a->u.s, b->u.s) == 0));
} else {
(void)to_integer(a);
(void)to_integer(b);
- r = make_integer (a->u.i == b->u.i);
+ r = make_integer ((quad_t)(a->u.i == b->u.i));
}
free_value (a);
@@ -311,11 +313,11 @@ struct val *a, *b;
if (isstring (a) || isstring (b)) {
to_string (a);
to_string (b);
- r = make_integer (strcoll (a->u.s, b->u.s) > 0);
+ r = make_integer ((quad_t)(strcoll (a->u.s, b->u.s) > 0));
} else {
(void)to_integer(a);
(void)to_integer(b);
- r= make_integer (a->u.i > b->u.i);
+ r = make_integer ((quad_t)(a->u.i > b->u.i));
}
free_value (a);
@@ -332,11 +334,11 @@ struct val *a, *b;
if (isstring (a) || isstring (b)) {
to_string (a);
to_string (b);
- r = make_integer (strcoll (a->u.s, b->u.s) < 0);
+ r = make_integer ((quad_t)(strcoll (a->u.s, b->u.s) < 0));
} else {
(void)to_integer(a);
(void)to_integer(b);
- r = make_integer (a->u.i < b->u.i);
+ r = make_integer ((quad_t)(a->u.i < b->u.i));
}
free_value (a);
@@ -353,11 +355,11 @@ struct val *a, *b;
if (isstring (a) || isstring (b)) {
to_string (a);
to_string (b);
- r = make_integer (strcoll (a->u.s, b->u.s) >= 0);
+ r = make_integer ((quad_t)(strcoll (a->u.s, b->u.s) >= 0));
} else {
(void)to_integer(a);
(void)to_integer(b);
- r = make_integer (a->u.i >= b->u.i);
+ r = make_integer ((quad_t)(a->u.i >= b->u.i));
}
free_value (a);
@@ -374,11 +376,11 @@ struct val *a, *b;
if (isstring (a) || isstring (b)) {
to_string (a);
to_string (b);
- r = make_integer (strcoll (a->u.s, b->u.s) <= 0);
+ r = make_integer ((quad_t)(strcoll (a->u.s, b->u.s) <= 0));
} else {
(void)to_integer(a);
(void)to_integer(b);
- r = make_integer (a->u.i <= b->u.i);
+ r = make_integer ((quad_t)(a->u.i <= b->u.i));
}
free_value (a);
@@ -395,11 +397,11 @@ struct val *a, *b;
if (isstring (a) || isstring (b)) {
to_string (a);
to_string (b);
- r = make_integer (strcoll (a->u.s, b->u.s) != 0);
+ r = make_integer ((quad_t)(strcoll (a->u.s, b->u.s) != 0));
} else {
(void)to_integer(a);
(void)to_integer(b);
- r = make_integer (a->u.i != b->u.i);
+ r = make_integer ((quad_t)(a->u.i != b->u.i));
}
free_value (a);
@@ -417,7 +419,7 @@ struct val *a, *b;
errx (2, "non-numeric argument");
}
- r = make_integer (a->u.i + b->u.i);
+ r = make_integer (/*(quad_t)*/(a->u.i + b->u.i));
free_value (a);
free_value (b);
return r;
@@ -433,7 +435,7 @@ struct val *a, *b;
errx (2, "non-numeric argument");
}
- r = make_integer (a->u.i - b->u.i);
+ r = make_integer (/*(quad_t)*/(a->u.i - b->u.i));
free_value (a);
free_value (b);
return r;
@@ -449,7 +451,7 @@ struct val *a, *b;
errx (2, "non-numeric argument");
}
- r = make_integer (a->u.i * b->u.i);
+ r = make_integer (/*(quad_t)*/(a->u.i * b->u.i));
free_value (a);
free_value (b);
return (r);
@@ -469,7 +471,7 @@ struct val *a, *b;
errx (2, "division by zero");
}
- r = make_integer (a->u.i / b->u.i);
+ r = make_integer (/*(quad_t)*/(a->u.i / b->u.i));
free_value (a);
free_value (b);
return r;
@@ -489,15 +491,12 @@ struct val *a, *b;
errx (2, "division by zero");
}
- r = make_integer (a->u.i % b->u.i);
+ r = make_integer (/*(quad_t)*/(a->u.i % b->u.i));
free_value (a);
free_value (b);
return r;
}
-#include <sys/types.h>
-#include <regex.h>
-
struct val *
op_colon (a, b)
struct val *a, *b;
@@ -526,11 +525,11 @@ struct val *a, *b;
v = make_str (a->u.s + rm[1].rm_so);
} else {
- v = make_integer (rm[0].rm_eo - rm[0].rm_so);
+ v = make_integer ((quad_t)(rm[0].rm_eo - rm[0].rm_so));
}
} else {
if (rp.re_nsub == 0) {
- v = make_integer (0);
+ v = make_integer ((quad_t)0);
} else {
v = make_str ("");
}
diff --git a/bin/test/test.c b/bin/test/test.c
index c9df4e3cb758..73e6ebf935df 100644
--- a/bin/test/test.c
+++ b/bin/test/test.c
@@ -153,6 +153,8 @@ static int binop __P((void));
static int filstat __P((char *, enum token));
static int isoperand __P((void));
static int getn __P((const char *));
+static quad_t getq __P((const char *));
+static int intcmp __P((const char *, const char *));
static int newerf __P((const char *, const char *));
static int olderf __P((const char *, const char *));
static int equalf __P((const char *, const char *));
@@ -298,17 +300,17 @@ binop()
case STRGT:
return strcmp(opnd1, opnd2) > 0;
case INTEQ:
- return getn(opnd1) == getn(opnd2);
+ return intcmp(opnd1, opnd2) == 0;
case INTNE:
- return getn(opnd1) != getn(opnd2);
+ return intcmp(opnd1, opnd2) != 0;
case INTGE:
- return getn(opnd1) >= getn(opnd2);
+ return intcmp(opnd1, opnd2) >= 0;
case INTGT:
- return getn(opnd1) > getn(opnd2);
+ return intcmp(opnd1, opnd2) > 0;
case INTLE:
- return getn(opnd1) <= getn(opnd2);
+ return intcmp(opnd1, opnd2) <= 0;
case INTLT:
- return getn(opnd1) < getn(opnd2);
+ return intcmp(opnd1, opnd2) < 0;
case FILNT:
return newerf (opnd1, opnd2);
case FILOT:
@@ -443,6 +445,48 @@ getn(s)
return (int) r;
}
+/* atoi with error detection and 64 bit range */
+static quad_t
+getq(s)
+ const char *s;
+{
+ char *p;
+ quad_t r;
+
+ errno = 0;
+ r = strtoq(s, &p, 10);
+
+ if (errno != 0)
+ errx(2, "%s: out of range", s);
+
+ while (isspace((unsigned char)*p))
+ p++;
+
+ if (*p)
+ errx(2, "%s: bad number", s);
+
+ return r;
+}
+
+static int
+intcmp (s1, s2)
+ const char *s1, *s2;
+{
+ quad_t q1, q2;
+
+
+ q1 = getq(s1);
+ q2 = getq(s2);
+
+ if (q1 > q2)
+ return 1;
+
+ if (q1 < q2)
+ return -1;
+
+ return 0;
+}
+
static int
newerf (f1, f2)
const char *f1, *f2;
diff --git a/usr.bin/printf/printf.c b/usr.bin/printf/printf.c
index f135f569fdf6..df65f5a886af 100644
--- a/usr.bin/printf/printf.c
+++ b/usr.bin/printf/printf.c
@@ -86,7 +86,7 @@ static void escape __P((char *));
static int getchr __P((void));
static double getdouble __P((void));
static int getint __P((int *));
-static int getlong __P((long *));
+static int getquad __P((quad_t *));
static char *getstr __P((void));
static char *mklong __P((char *, int));
static void usage __P((void));
@@ -214,12 +214,12 @@ next: for (start = fmt;; ++fmt) {
break;
}
case 'd': case 'i': case 'o': case 'u': case 'x': case 'X': {
- long p;
+ quad_t p;
char *f;
if ((f = mklong(start, convch)) == NULL)
return (1);
- if (getlong(&p))
+ if (getquad(&p))
return (1);
PF(f, p);
break;
@@ -249,8 +249,11 @@ mklong(str, ch)
int len;
len = strlen(str) + 2;
+ if (len > sizeof copy)
+ return NULL;
+
memmove(copy, str, len - 3);
- copy[len - 3] = 'l';
+ copy[len - 3] = 'q';
copy[len - 2] = ch;
copy[len - 1] = '\0';
return (copy);
@@ -338,23 +341,23 @@ static int
getint(ip)
int *ip;
{
- long val;
+ quad_t val;
- if (getlong(&val))
+ if (getquad(&val))
return (1);
- if (val > INT_MAX) {
+ if (val < INT_MIN || val > INT_MAX) {
warnx3("%s: %s", *gargv, strerror(ERANGE));
return (1);
}
- *ip = val;
+ *ip = (int)val;
return (0);
}
static int
-getlong(lp)
- long *lp;
+getquad(lp)
+ quad_t *lp;
{
- long val;
+ quad_t val;
char *ep;
if (!*gargv) {
@@ -363,17 +366,17 @@ getlong(lp)
}
if (strchr(Number, **gargv)) {
errno = 0;
- val = strtol(*gargv, &ep, 0);
+ val = strtoq(*gargv, &ep, 0);
if (*ep != '\0') {
warnx2("%s: illegal number", *gargv, NULL);
return (1);
}
if (errno == ERANGE)
- if (val == LONG_MAX) {
+ if (val == QUAD_MAX) {
warnx3("%s: %s", *gargv, strerror(ERANGE));
return (1);
}
- if (val == LONG_MIN) {
+ if (val == QUAD_MIN) {
warnx3("%s: %s", *gargv, strerror(ERANGE));
return (1);
}