共用体のデータ型は、整数、文字へのポインタ (文字列)、gnumbers 構造体のどれかとします。また、共用体と現在の型は構造体で宣言されているとします。宣言は次のようになります。
enum utype {INTEGER=1, STRING=2, GNUMBERS=3};
struct u_tag {
enum utype utype; /* 共用体の要素識別子 */
union {
int ival;
char *pval;
struct gnumbers gn;
} uval;
};
例 A-12 では、合成データと XDR 手続きで、識別型共用体のシリアライズ (またはデシリアライズ) を行います。
struct xdr_discrim u_tag_arms[4] = {
{INTEGER, xdr_int},
{GNUMBERS, xdr_gnumbers}
{STRING, xdr_wrapstring},
{__dontcare__, NULL}
/* アームの最後は常に NULL の xdr_proc */
}
bool_t
xdr_u_tag(xdrs, utp)
XDR *xdrs;
struct u_tag *utp;
{
return(xdr_union(xdrs, &utp->utype, &utp->uval,
u_tag_arms, NULL));
}
xdr_gnumbers() については「XDR ライブラリ」の節で説明し、xdr_wrapstring() はサンプルプログラム C に示しました。この例では、xdr_union()のデフォルトの arm 引数 (最後の引数) には NULLを渡しています。したがって、共用体の要素識別子の値は、u_tag_arms 配列にリストした値のどれかでなければなりません。また、この例から、arm 配列の要素はソートされていなくてもよいことがわかります。
要素識別子は、この例では連続した値を取っていますが、連続しなくてもよいことを指摘しておく必要があります。要素識別子の型の各要素に、明示的に整数値を割り当てておくのはよい習慣です。こうすると、要素識別子の外部表現のドキュメントにもなりますし、異なる C コンパイラでも要素識別子が同じ値で出力されることが保証されます。