I don't think this is sufficient according to ANSI, I can run it by a
standards-cop if we want. I think you have to take the approach I gave
for maximum portability. The sign extension occurs naturally as part of
the va_arg() primitive, and we're calling va_arg() incorrectly.
Dean
On Thu, 6 Feb 1997, Rodent of Unusual Size wrote:
> >From the fingers of Rodent of Unusual Size flowed the following:
> >
> >>From the fingers of Marc Slemko flowed the following:
> >>
> >>> >From the fingers of Marc Slemko flowed the following:
> >>> >
> >>> >ap_snprintf(foo, "%d", (int)-1) should give (2^32)-1 on the Alpha, since
> >>> >even though it is 64 bit ints are still 32-bit. It gives (2^64)-1.
> >>
> >>Sorry, mean unsigned int. something like %u and (unsigned int)...
> >
> > Ah, now I see. Looking at the code, I have no idea why it would be
> > doing that ...
>
> A little closer research shows why.. u_wide_int is typedef'd as
> "unsigned long". By default, a long on Alpha is 64 bits, so
> "magnitude" gets a whacking 64 bits of -1.
>
> > If it's safe to assume that a WIDE_INT (namely, a long) is always 32
> > bits, the [tested] patch below will fix this.
>
> Probably not a safe assumption, eh? Replace the previous patch with
> the following, and it should be portable. The only time the code
> fragment is entered is when we're processing a '%u' directive -
> which (as was mentioned before) takes an int, not a long.
>
> What's this called? Sign unextending? Sign destending? <g>
>
> Bear in mind that the only UNIX boxes I *have* are Alphas, so I can't
> test on any other platforms.
>
> #ken :-P}
>
> Index: util_snprintf.c
> ===================================================================
> RCS file: /usr/users/coar/myApache/repository/apache/src/util_snprintf.c,v
> retrieving revision 1.4
> diff -c -r1.4 util_snprintf.c
> *** 1.4 1997/01/20 23:55:11
> --- util_snprintf.c 1997/02/06 16:05:33
> ***************
> *** 360,366 ****
> register u_wide_int magnitude;
>
> if (is_unsigned) {
> ! magnitude = (u_wide_int) num;
> *is_negative = FALSE;
> }
> else {
> --- 360,366 ----
> register u_wide_int magnitude;
>
> if (is_unsigned) {
> ! magnitude = (u_wide_int) num & (unsigned int) -1;
> *is_negative = FALSE;
> }
> else {
>
|