2 * Copyright 2000, International Business Machines Corporation and others.
5 * This software has been released under the terms of the IBM Public
6 * License. For details, see the LICENSE file in the top-level source
7 * directory or online at http://www.openafs.org/dl/license10.html
11 * xdr_rx.c. XDR using RX.
14 #include <afsconfig.h>
15 #include <afs/param.h>
18 # include "afs/sysincludes.h"
22 # ifdef AFS_LINUX20_ENV
23 # include "h/socket.h"
25 # include "rpc/types.h"
27 # ifdef AFS_LINUX22_ENV
29 # define quad_t __quad_t
30 # define u_quad_t __u_quad_t
33 # include "netinet/in.h"
34 # endif /* !UKERNEL */
42 /* Static prototypes */
43 static bool_t
xdrrx_getint32(XDR
*axdrs
, afs_int32
* lp
);
44 static bool_t
xdrrx_putint32(XDR
*axdrs
, afs_int32
* lp
);
45 static bool_t
xdrrx_getbytes(XDR
*axdrs
, caddr_t addr
,
47 static bool_t
xdrrx_putbytes(XDR
*axdrs
, caddr_t addr
,
49 static afs_int32
*xdrrx_inline(XDR
*axdrs
, u_int len
);
53 * Ops vector for stdio type XDR
55 static struct xdr_ops xdrrx_ops
= {
56 #ifndef HAVE_STRUCT_LABEL_SUPPORT
57 /* Windows does not support labeled assigments */
58 xdrrx_getint32
, /* deserialize an afs_int32 */
59 xdrrx_putint32
, /* serialize an afs_int32 */
60 xdrrx_getbytes
, /* deserialize counted bytes */
61 xdrrx_putbytes
, /* serialize counted bytes */
62 NULL
, /* get offset in the stream: not supported. */
63 NULL
, /* set offset in the stream: not supported. */
64 xdrrx_inline
, /* prime stream for inline macros */
65 NULL
, /* destroy stream */
67 .x_getint32
= xdrrx_getint32
, /* deserialize an afs_int32 */
68 .x_putint32
= xdrrx_putint32
, /* serialize an afs_int32 */
69 .x_getbytes
= xdrrx_getbytes
, /* deserialize counted bytes */
70 .x_putbytes
= xdrrx_putbytes
, /* serialize counted bytes */
71 .x_getpostn
= NULL
, /* get offset in the stream: not supported. */
72 .x_setpostn
= NULL
, /* set offset in the stream: not supported. */
73 .x_inline
= xdrrx_inline
, /* prime stream for inline macros */
74 .x_destroy
= NULL
, /* destroy stream */
79 * Initialize an rx xdr handle, for a given rx call. op must be XDR_ENCODE or XDR_DECODE.
80 * Call must have been returned by rx_MakeCall or rx_GetCall.
83 xdrrx_create(XDR
* xdrs
, struct rx_call
*call
,
87 xdrs
->x_ops
= &xdrrx_ops
;
88 xdrs
->x_private
= (caddr_t
) call
;
91 #if defined(KERNEL) && defined(AFS_AIX32_ENV)
92 #define STACK_TO_PIN 2*PAGESIZE /* 8K */
93 int rx_pin_failed
= 0;
97 xdrrx_getint32(XDR
*axdrs
, afs_int32
* lp
)
100 XDR
* xdrs
= (XDR
*)axdrs
;
101 struct rx_call
*call
= ((struct rx_call
*)(xdrs
)->x_private
);
102 #if defined(KERNEL) && defined(AFS_AIX32_ENV)
103 char *saddr
= (char *)&l
;
104 saddr
-= STACK_TO_PIN
;
106 * Hack of hacks: Aix3.2 only guarantees that the next 2K of stack in pinned. Under
107 * splnet (disables interrupts), which is set throughout rx, we can't swap in stack
108 * pages if we need so we panic. Since sometimes, under splnet, we'll use more than
109 * 2K stack we could try to bring the next few stack pages in here before we call the rx
110 * layer. Of course this doesn't guarantee that those stack pages won't be swapped
111 * out between here and calling splnet. So we now pin (and unpin) them instead to
112 * guarantee that they remain there.
114 if (pin(saddr
, STACK_TO_PIN
)) {
115 /* XXX There's little we can do by continue XXX */
120 if (rx_Read32(call
, &l
) == sizeof(l
)) {
122 #if defined(KERNEL) && defined(AFS_AIX32_ENV)
124 unpin(saddr
, STACK_TO_PIN
);
128 #if defined(KERNEL) && defined(AFS_AIX32_ENV)
130 unpin(saddr
, STACK_TO_PIN
);
136 xdrrx_putint32(XDR
*axdrs
, afs_int32
* lp
)
138 afs_int32 code
, l
= htonl(*lp
);
139 XDR
* xdrs
= (XDR
*)axdrs
;
140 struct rx_call
*call
= ((struct rx_call
*)(xdrs
)->x_private
);
141 #if defined(KERNEL) && defined(AFS_AIX32_ENV)
142 char *saddr
= (char *)&code
;
143 saddr
-= STACK_TO_PIN
;
145 * Hack of hacks: Aix3.2 only guarantees that the next 2K of stack in pinned. Under
146 * splnet (disables interrupts), which is set throughout rx, we can't swap in stack
147 * pages if we need so we panic. Since sometimes, under splnet, we'll use more than
148 * 2K stack we could try to bring the next few stack pages in here before we call the rx
149 * layer. Of course this doesn't guarantee that those stack pages won't be swapped
150 * out between here and calling splnet. So we now pin (and unpin) them instead to
151 * guarantee that they remain there.
153 if (pin(saddr
, STACK_TO_PIN
)) {
158 code
= (rx_Write32(call
, &l
) == sizeof(l
));
159 #if defined(KERNEL) && defined(AFS_AIX32_ENV)
161 unpin(saddr
, STACK_TO_PIN
);
167 xdrrx_getbytes(XDR
*axdrs
, caddr_t addr
, u_int len
)
170 XDR
* xdrs
= (XDR
*)axdrs
;
171 struct rx_call
*call
= ((struct rx_call
*)(xdrs
)->x_private
);
172 #if defined(KERNEL) && defined(AFS_AIX32_ENV)
173 char *saddr
= (char *)&code
;
174 saddr
-= STACK_TO_PIN
;
176 * Hack of hacks: Aix3.2 only guarantees that the next 2K of stack in pinned. Under
177 * splnet (disables interrupts), which is set throughout rx, we can't swap in stack
178 * pages if we need so we panic. Since sometimes, under splnet, we'll use more than
179 * 2K stack we could try to bring the next few stack pages in here before we call the rx
180 * layer. Of course this doesn't guarantee that those stack pages won't be swapped
181 * out between here and calling splnet. So we now pin (and unpin) them instead to
182 * guarantee that they remain there.
184 if (pin(saddr
, STACK_TO_PIN
)) {
185 /* XXX There's little we can do by continue XXX */
190 code
= (rx_Read(call
, addr
, len
) == len
);
191 #if defined(KERNEL) && defined(AFS_AIX32_ENV)
193 unpin(saddr
, STACK_TO_PIN
);
199 xdrrx_putbytes(XDR
*axdrs
, caddr_t addr
, u_int len
)
202 XDR
* xdrs
= (XDR
*)axdrs
;
203 struct rx_call
*call
= ((struct rx_call
*)(xdrs
)->x_private
);
204 #if defined(KERNEL) && defined(AFS_AIX32_ENV)
205 char *saddr
= (char *)&code
;
206 saddr
-= STACK_TO_PIN
;
208 * Hack of hacks: Aix3.2 only guarantees that the next 2K of stack in pinned. Under
209 * splnet (disables interrupts), which is set throughout rx, we can't swap in stack
210 * pages if we need so we panic. Since sometimes, under splnet, we'll use more than
211 * 2K stack we could try to bring the next few stack pages in here before we call the rx
212 * layer. Of course this doesn't guarantee that those stack pages won't be swapped
213 * out between here and calling splnet. So we now pin (and unpin) them instead to
214 * guarantee that they remain there.
216 if (pin(saddr
, STACK_TO_PIN
)) {
217 /* XXX There's little we can do by continue XXX */
222 code
= (rx_Write(call
, addr
, len
) == len
);
223 #if defined(KERNEL) && defined(AFS_AIX32_ENV)
225 unpin(saddr
, STACK_TO_PIN
);
230 #ifdef undef /* not used */
232 xdrrx_getpos(XDR
* xdrs
)
234 /* Not supported. What error code should we return? (It doesn't matter: it will never be called, anyway!) */
239 xdrrx_setpos(XDR
* xdrs
, u_int pos
)
247 xdrrx_inline(XDR
*axdrs
, u_int len
)
249 /* I don't know what this routine is supposed to do, but the stdio module returns null, so we will, too */