jim 99/12/13 05:36:17
Modified:src/lib/apr/lib apr_snprintf.c
Log:
Fold in the snprintf() changes
Revision ChangesPath
1.5 +202 -44 apache-2.0/src/lib/apr/lib/apr_snprintf.c
Index: apr_snprintf.c
===
RCS file: /export/home/cvs/apache-2.0/src/lib/apr/lib/apr_snprintf.c,v
retrieving revision 1.4
retrieving revision 1.5
diff -u -r1.4 -r1.5
--- apr_snprintf.c1999/12/09 21:00:44 1.4
+++ apr_snprintf.c1999/12/13 13:36:16 1.5
@@ -54,7 +54,7 @@
* project, please see http://www.apache.org/.
*
* This code is based on, and used with the permission of, the
- * SIO stdiocntxteplacement strx_* functions by Panos Tsirigotis
+ * SIO stdio-replacement strx_* functions by Panos Tsirigotis
* [EMAIL PROTECTED] for xinetd.
*/
@@ -90,12 +90,22 @@
#ifndef TRUE
#define TRUE 1
#endif
+#ifndef AP_LONGEST_LONG
+#define AP_LONGEST_LONG long
+#endif
#define NUL '\0'
-#define INT_NULL ((int *)0)
#define WIDE_INT long
+#define WIDEST_INT AP_LONGEST_LONG
typedef WIDE_INT wide_int;
typedef unsigned WIDE_INT u_wide_int;
+typedef WIDEST_INT widest_int;
+#ifdef __TANDEM
+/* Although Tandem supports long long there is no unsigned variant. */
+typedef unsigned long u_widest_int;
+#else
+typedef unsigned WIDEST_INT u_widest_int;
+#endif
typedef int bool_int;
#define S_NULL (null)
@@ -131,7 +141,7 @@
register int r2;
double fi, fj;
register char *p, *p1;
-
+
if (ndigits = NDIG - 1)
ndigits = NDIG - 2;
r2 = 0;
@@ -350,6 +360,10 @@
* The caller provides a buffer for the string: that is the buf_end argument
* which is a pointer to the END of the buffer + 1 (i.e. if the buffer
* is declared as buf[ 100 ], buf_end should be buf[ 100 ])
+ *
+ * Note: we have 2 versions. One is used when we need to use quads
+ * (conv_10_quad), the other when we don't (conv_10). We're assuming the
+ * latter is faster.
*/
static char *conv_10(register wide_int num, register bool_int is_unsigned,
register bool_int *is_negative, char *buf_end,
@@ -398,6 +412,62 @@
return (p);
}
+static char *conv_10_quad(widest_int num, register bool_int is_unsigned,
+ register bool_int *is_negative, char *buf_end,
+ register int *len)
+{
+register char *p = buf_end;
+u_widest_int magnitude;
+
+/*
+ * We see if we can use the faster non-quad version by checking the
+ * number against the largest long value it can be. If =, we
+ * punt to the quicker version.
+ */
+if ((num = ULONG_MAX is_unsigned) || (num = LONG_MAX
!is_unsigned))
+ return(conv_10( (wide_int)num, is_unsigned, is_negative,
+buf_end, len));
+
+if (is_unsigned) {
+ magnitude = (u_widest_int) num;
+ *is_negative = FALSE;
+}
+else {
+ *is_negative = (num 0);
+
+ /*
+ * On a 2's complement machine, negating the most negative integer
+ * results in a number that cannot be represented as a signed integer.
+ * Here is what we do to obtain the number's magnitude:
+ * a. add 1 to the number
+ * b. negate it (becomes positive)
+ * c. convert it to unsigned
+ * d. add 1
+ */
+ if (*is_negative) {
+ widest_int t = num + 1;
+
+ magnitude = ((u_widest_int) -t) + 1;
+ }
+ else
+ magnitude = (u_widest_int) num;
+}
+
+/*
+ * We use a do-while loop so that we write at least 1 digit
+ */
+do {
+ u_widest_int new_magnitude = magnitude / 10;
+
+ *--p = (char) (magnitude - new_magnitude * 10 + '0');
+ magnitude = new_magnitude;
+}
+while (magnitude);
+
+*len = buf_end - p;
+return (p);
+}
+
static char *conv_in_addr(struct in_addr *ia, char *buf_end, int *len)
@@ -537,6 +607,9 @@
* The caller provides a buffer for the string: that is the buf_end argument
* which is a pointer to the END of the buffer + 1 (i.e. if the buffer
* is declared as buf[ 100 ], buf_end should be buf[ 100 ])
+ *
+ * As with conv_10, we have a faster version which is used when
+ * the number isn't quad size.
*/
static char *conv_p2(register u_wide_int num, register int nbits,
char format, char *buf_end, register int *len)
@@ -557,12 +630,34 @@
return (p);
}
+static char *conv_p2_quad(u_widest_int num, register int nbits,
+ char format, char *buf_end, register int *len)
+{
+register int mask = (1 nbits) - 1;
+register char *p = buf_end;
+static