How about this? If this is agreement i can write up a draft.
enum ippack { IPv4=1, IPv6Bytes=2, IPv6Shorts=3, IPV6Ints=4 };
struct rx_addr {
enum ippack ippack; /* the union's discriminant */
union {
afs_uint32 ip4_addr;
unsigned char ip6_addr8[16];
afs_uint16 ip6_addr16[8];
afs_uint32 ip6_addr32[4];
} ipN_addr;
};
Serialize and deserialize the discriminated union:
struct xdr_discrim rx_addr_arms[5] = {
{ IPv4, xdr_int },
{ IPv6Bytes, xdr_ip6_addr8 }
{ IPv6Shorts, xdr_ip6_addr16 },
{ IPv6Ints, xdr_ip6_addr32 },
{ 0, NULL }
}
bool_t
xdr_rx_addr(xdrs, utp)
XDR *xdrs;
struct u_tag *utp;
{
return(xdr_union(xdrs, &utp->ippack, &utp->ipNaddr,
rx_addr_arms, NULL));
}
Defining the obvious xdr types for the ipv6 address subtypes.
On Mon, Feb 7, 2011 at 11:34 AM, Steve Simmons <[email protected]> wrote:
>
> On Feb 5, 2011, at 11:12 AM, Hartmut Reuter wrote:
>
>> Derrick Brashear wrote:
>>> On Sat, Feb 5, 2011 at 4:09 AM, Jeffrey Hutzelman<[email protected]> wrote:
>>>> --On Friday, February 04, 2011 10:14:23 AM -0600 Andrew Deason
>>>> <[email protected]> wrote:
>>>>
>>>>> On Fri, 4 Feb 2011 09:32:53 -0500
>>>>> Derrick Brashear<[email protected]> wrote:
>>>>>
>>>>>> struct UbikInterfaceInfo {
>>>>>> afsUUID uuid;
>>>>>> struct sockaddr_storage hostAddr[UBIK_MAX_INTERFACE_ADDR];
>>>>>> };
>>>>>
>>>>> I thought struct sockaddr_storage can be different on different
>>>>> implementations, and isn't guaranteed to store ~everything, just the
>>>>> representations that host supports. This is something I've been a little
>>>>> unclear about, actually; is there any existing standard for transmitting
>>>>> generalized network addresses across platforms? Or does everyone just
>>>>> come up with their own?
>>>>
>>>> Indeed, sockaddr_storage is an API artifact, and certainly not suitable for
>>>> use in an Rx RPC signature. The appropriate thing here is some kind of
>>>> discriminated union. We should probably define such a type as an extension
>>>> to the "standard" types supported by Rx, rather than doing it in Ubik and
>>>> again in VL and again in RXAFSCB and so on and so on.
>>>
>>> to that end, may i propose that rx define a type e.g.
>>> typedef struct
>>> {
>>> /* The discriminator for the union below. */
>>> rx_addrtype_t addr_type;
>>> union
>>> {
>>> /* IPv4 address, in network byte order. */
>>> struct in_addr ipv4;
>>>
>>> /* IPv6 address, in network byte order. */
>>> struct in6_addr ipv6;
>>> } addr;
>>> } rxaddr_t;
>>
>>
>> This will not work because in6_addr is a union and xdr cannot handle unions
>> unless you have a switch variable which says which branch of the union
>> should be used. 16 bytes are not the same as 4 int32 if you have different
>> endianess!
>
> This is kind of ugly, but might be representable in xdr (which I'm moderately
> ignorant of):
>
> typedef struct
> {
> /* The discriminator for the union below. */
> rx_addrtype_t addr_type;
> addr char addr_buf[ sizeof(struct in6_addr) ];
> } rxaddr_t;
>
>> typedef enum
>> {
>> /* IPv4 address */
>> RX_IPV4 = 0x1,
>> /* IPv6 address */
>> RX_IPV6 = 0x2
>> } rx_addrtype_t;
>
>
> It would clearly need a couple of helper functions so we could do things like
>
> struct rxaddr_t address;
> struct in_addr ipv4addr;
> struct in6_addr ipv6addr;
>
> switch ( address.addr_type) {
> case RX_IPV4:
> addrbuf2ipv4( address, &ipv4addr );
> break;
> case RX_IPV6:
> addrbuf2ipv6( address, &ipv6addr );
> break;
> default:
> whoops();
> }
>
> and matching ipv{4,6}addr2addrbuf() functions. In the best of all worlds,
> these would be mostly simple calls to memcpy().
>
> Steve_______________________________________________
> AFS3-standardization mailing list
> [email protected]
> http://lists.openafs.org/mailman/listinfo/afs3-standardization
>
--
Derrick
_______________________________________________
AFS3-standardization mailing list
[email protected]
http://lists.openafs.org/mailman/listinfo/afs3-standardization