ISC dhcp server on NetBSD
dhcp.50.CHRIS94561 at spamgourmet.com
dhcp.50.CHRIS94561 at spamgourmet.com
Sun Apr 25 13:39:44 UTC 2004
From: dhcp.50.CHRIS94561 at spamgourmet.com
> I'd say that it is reasonable for ntohl to be unsigned, since a 32-bit
> quantity in non-native byte order shouldn't be treated as signed
> (which implies native byte order). time_t might become 64 bits in the
> future, too.
Problem is that time_t is a signed, not unsigned.
The code is converting between on-the-wire types, which are of course
a size fixed by the protocol, into host types. So a variable which is
the right type for the wire format (uint32_t, I'd argue) should be
used to hold the bits in wire format, and the assignment to a time_t
variable only done after the ntohl, and that probably should have an
explicit cast.
While that all may be true. Part of the question I'm asking is: Why does
the same code compile on Linux and not NetBSD? In both cases ntohl is
unsigned and time_t is signed. So why the discrepancy in the compiler
behavior?
On NetBSD/i386 1.6.2 (which I am guessing you are using), ntohl
expands to an inline function, which therefore does type checking:
static __inline u_int32_t
__byte_swap_long_variable(u_int32_t x)
{
__asm __volatile (
#if defined(_KERNEL) && !defined(_LKM) && !defined(I386_CPU)
"bswap %1"
#else
"rorw $8, %w1\n\trorl $16, %1\n\trorw $8, %w1"
#endif
: "=r" (x) : "0" (x));
return (x);
}
There is also a macro for doing this, used if __OPTIMIZE__ is not
defined or for constants, which won't do much type checking (but might
warn if the provided type is too small to hold 0xff000000):
#define __byte_swap_long_constant(x) \
((((x) & 0xff000000) >> 24) | \
(((x) & 0x00ff0000) >> 8) | \
(((x) & 0x0000ff00) << 8) | \
(((x) & 0x000000ff) << 24))
More information about the dhcp-hackers
mailing list