174462Salfred/* $NetBSD: xdr_mem.c,v 1.15 2000/01/22 22:19:18 mycroft Exp $ */ 274462Salfred 3272850Shrs/*- 4272850Shrs * Copyright (c) 2010, Oracle America, Inc. 58870Srgrimes * 6272850Shrs * Redistribution and use in source and binary forms, with or without 7272850Shrs * modification, are permitted provided that the following conditions are 8272850Shrs * met: 98870Srgrimes * 10272850Shrs * * Redistributions of source code must retain the above copyright 11272850Shrs * notice, this list of conditions and the following disclaimer. 12272850Shrs * * Redistributions in binary form must reproduce the above 13272850Shrs * copyright notice, this list of conditions and the following 14272850Shrs * disclaimer in the documentation and/or other materials 15272850Shrs * provided with the distribution. 16272850Shrs * * Neither the name of the "Oracle America, Inc." nor the names of its 17272850Shrs * contributors may be used to endorse or promote products derived 18272850Shrs * from this software without specific prior written permission. 198870Srgrimes * 20272850Shrs * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 21272850Shrs * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 22272850Shrs * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS 23272850Shrs * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE 24272850Shrs * COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, 25272850Shrs * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 26272850Shrs * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE 27272850Shrs * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 28272850Shrs * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 29272850Shrs * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 30272850Shrs * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 31272850Shrs * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 321902Swollman */ 331902Swollman 341902Swollman#if defined(LIBC_SCCS) && !defined(lint) 35136582Sobrienstatic char *sccsid2 = "@(#)xdr_mem.c 1.19 87/08/11 Copyr 1984 Sun Micro"; 3692986Sobrienstatic char *sccsid = "@(#)xdr_mem.c 2.1 88/07/29 4.0 RPCSRC"; 371902Swollman#endif 3892986Sobrien#include <sys/cdefs.h> 3992986Sobrien__FBSDID("$FreeBSD: stable/10/lib/libc/xdr/xdr_mem.c 309485 2016-12-03 17:17:42Z ngie $"); 401902Swollman 411902Swollman/* 421902Swollman * xdr_mem.h, XDR implementation using memory buffers. 431902Swollman * 441902Swollman * If you have some data to be interpreted as external data representation 451902Swollman * or to be converted to external data representation in a memory buffer, 461902Swollman * then this is the package for you. 471902Swollman * 481902Swollman */ 491902Swollman 5074462Salfred#include "namespace.h" 5174462Salfred#include <sys/types.h> 5274462Salfred 5374462Salfred#include <netinet/in.h> 5474462Salfred 5511669Sphk#include <string.h> 5674462Salfred 571902Swollman#include <rpc/types.h> 581902Swollman#include <rpc/xdr.h> 5974462Salfred#include "un-namespace.h" 601902Swollman 6192905Sobrienstatic void xdrmem_destroy(XDR *); 6292905Sobrienstatic bool_t xdrmem_getlong_aligned(XDR *, long *); 6392905Sobrienstatic bool_t xdrmem_putlong_aligned(XDR *, const long *); 6492905Sobrienstatic bool_t xdrmem_getlong_unaligned(XDR *, long *); 6592905Sobrienstatic bool_t xdrmem_putlong_unaligned(XDR *, const long *); 6692905Sobrienstatic bool_t xdrmem_getbytes(XDR *, char *, u_int); 6792905Sobrienstatic bool_t xdrmem_putbytes(XDR *, const char *, u_int); 6874462Salfred/* XXX: w/64-bit pointers, u_int not enough! */ 6992905Sobrienstatic u_int xdrmem_getpos(XDR *); 7092905Sobrienstatic bool_t xdrmem_setpos(XDR *, u_int); 7192905Sobrienstatic int32_t *xdrmem_inline_aligned(XDR *, u_int); 7292905Sobrienstatic int32_t *xdrmem_inline_unaligned(XDR *, u_int); 731902Swollman 7474462Salfredstatic const struct xdr_ops xdrmem_ops_aligned = { 7521062Speter xdrmem_getlong_aligned, 7621062Speter xdrmem_putlong_aligned, 771902Swollman xdrmem_getbytes, 781902Swollman xdrmem_putbytes, 791902Swollman xdrmem_getpos, 801902Swollman xdrmem_setpos, 8121062Speter xdrmem_inline_aligned, 821902Swollman xdrmem_destroy 831902Swollman}; 841902Swollman 8574462Salfredstatic const struct xdr_ops xdrmem_ops_unaligned = { 8621062Speter xdrmem_getlong_unaligned, 8721062Speter xdrmem_putlong_unaligned, 8821062Speter xdrmem_getbytes, 8921062Speter xdrmem_putbytes, 9021062Speter xdrmem_getpos, 9121062Speter xdrmem_setpos, 9221062Speter xdrmem_inline_unaligned, 9321062Speter xdrmem_destroy 9421062Speter}; 9521062Speter 961902Swollman/* 971902Swollman * The procedure xdrmem_create initializes a stream descriptor for a 988870Srgrimes * memory buffer. 991902Swollman */ 1001902Swollmanvoid 1011902Swollmanxdrmem_create(xdrs, addr, size, op) 10274462Salfred XDR *xdrs; 10374462Salfred char *addr; 1041902Swollman u_int size; 1051902Swollman enum xdr_op op; 1061902Swollman{ 1071902Swollman 1081902Swollman xdrs->x_op = op; 10974462Salfred xdrs->x_ops = ((unsigned long)addr & (sizeof(int32_t) - 1)) 11074462Salfred ? &xdrmem_ops_unaligned : &xdrmem_ops_aligned; 1111902Swollman xdrs->x_private = xdrs->x_base = addr; 1121902Swollman xdrs->x_handy = size; 1131902Swollman} 1141902Swollman 11574462Salfred/*ARGSUSED*/ 1161902Swollmanstatic void 11774462Salfredxdrmem_destroy(xdrs) 11874462Salfred XDR *xdrs; 1191902Swollman{ 12021062Speter 1211902Swollman} 1221902Swollman 1231902Swollmanstatic bool_t 12421062Speterxdrmem_getlong_aligned(xdrs, lp) 12574462Salfred XDR *xdrs; 1261902Swollman long *lp; 1271902Swollman{ 1281902Swollman 129111962Snectar if (xdrs->x_handy < sizeof(int32_t)) 1301902Swollman return (FALSE); 131111962Snectar xdrs->x_handy -= sizeof(int32_t); 13274462Salfred *lp = ntohl(*(u_int32_t *)xdrs->x_private); 13374462Salfred xdrs->x_private = (char *)xdrs->x_private + sizeof(int32_t); 1341902Swollman return (TRUE); 1351902Swollman} 1361902Swollman 1371902Swollmanstatic bool_t 13821062Speterxdrmem_putlong_aligned(xdrs, lp) 13974462Salfred XDR *xdrs; 14074462Salfred const long *lp; 1411902Swollman{ 1421902Swollman 143111962Snectar if (xdrs->x_handy < sizeof(int32_t)) 1441902Swollman return (FALSE); 145111962Snectar xdrs->x_handy -= sizeof(int32_t); 14674462Salfred *(u_int32_t *)xdrs->x_private = htonl((u_int32_t)*lp); 14774462Salfred xdrs->x_private = (char *)xdrs->x_private + sizeof(int32_t); 1481902Swollman return (TRUE); 1491902Swollman} 1501902Swollman 1511902Swollmanstatic bool_t 15221062Speterxdrmem_getlong_unaligned(xdrs, lp) 15374462Salfred XDR *xdrs; 15421062Speter long *lp; 15521062Speter{ 15674462Salfred u_int32_t l; 15721062Speter 158111962Snectar if (xdrs->x_handy < sizeof(int32_t)) 15921062Speter return (FALSE); 160111962Snectar xdrs->x_handy -= sizeof(int32_t); 16174462Salfred memmove(&l, xdrs->x_private, sizeof(int32_t)); 16221062Speter *lp = ntohl(l); 16374462Salfred xdrs->x_private = (char *)xdrs->x_private + sizeof(int32_t); 16421062Speter return (TRUE); 16521062Speter} 16621062Speter 16721062Speterstatic bool_t 16821062Speterxdrmem_putlong_unaligned(xdrs, lp) 16974462Salfred XDR *xdrs; 17074462Salfred const long *lp; 17121062Speter{ 17274462Salfred u_int32_t l; 17321062Speter 174111962Snectar if (xdrs->x_handy < sizeof(int32_t)) 17521062Speter return (FALSE); 176111962Snectar xdrs->x_handy -= sizeof(int32_t); 17774462Salfred l = htonl((u_int32_t)*lp); 17874462Salfred memmove(xdrs->x_private, &l, sizeof(int32_t)); 17974462Salfred xdrs->x_private = (char *)xdrs->x_private + sizeof(int32_t); 18021062Speter return (TRUE); 18121062Speter} 18221062Speter 18321062Speterstatic bool_t 1841902Swollmanxdrmem_getbytes(xdrs, addr, len) 18574462Salfred XDR *xdrs; 18674462Salfred char *addr; 18774462Salfred u_int len; 1881902Swollman{ 1891902Swollman 190111962Snectar if (xdrs->x_handy < len) 1911902Swollman return (FALSE); 192111962Snectar xdrs->x_handy -= len; 19374462Salfred memmove(addr, xdrs->x_private, len); 19474462Salfred xdrs->x_private = (char *)xdrs->x_private + len; 1951902Swollman return (TRUE); 1961902Swollman} 1971902Swollman 1981902Swollmanstatic bool_t 1991902Swollmanxdrmem_putbytes(xdrs, addr, len) 20074462Salfred XDR *xdrs; 20174462Salfred const char *addr; 20274462Salfred u_int len; 2031902Swollman{ 2041902Swollman 205111962Snectar if (xdrs->x_handy < len) 2061902Swollman return (FALSE); 207111962Snectar xdrs->x_handy -= len; 20874462Salfred memmove(xdrs->x_private, addr, len); 20974462Salfred xdrs->x_private = (char *)xdrs->x_private + len; 2101902Swollman return (TRUE); 2111902Swollman} 2121902Swollman 2131902Swollmanstatic u_int 2141902Swollmanxdrmem_getpos(xdrs) 21574462Salfred XDR *xdrs; 2161902Swollman{ 2171902Swollman 21821062Speter /* XXX w/64-bit pointers, u_int not enough! */ 21974462Salfred return (u_int)((u_long)xdrs->x_private - (u_long)xdrs->x_base); 2201902Swollman} 2211902Swollman 2221902Swollmanstatic bool_t 2231902Swollmanxdrmem_setpos(xdrs, pos) 22474462Salfred XDR *xdrs; 2251902Swollman u_int pos; 2261902Swollman{ 22774462Salfred char *newaddr = xdrs->x_base + pos; 22874462Salfred char *lastaddr = (char *)xdrs->x_private + xdrs->x_handy; 2291902Swollman 230111962Snectar if (newaddr > lastaddr) 2311902Swollman return (FALSE); 2321902Swollman xdrs->x_private = newaddr; 233111962Snectar xdrs->x_handy = (u_int)(lastaddr - newaddr); /* XXX sizeof(u_int) <? sizeof(ptrdiff_t) */ 2341902Swollman return (TRUE); 2351902Swollman} 2361902Swollman 23721062Speterstatic int32_t * 23821062Speterxdrmem_inline_aligned(xdrs, len) 23974462Salfred XDR *xdrs; 24074462Salfred u_int len; 2411902Swollman{ 242309485Sngie int32_t *buf = NULL; 2431902Swollman 2441902Swollman if (xdrs->x_handy >= len) { 2451902Swollman xdrs->x_handy -= len; 24674462Salfred buf = (int32_t *)xdrs->x_private; 24774462Salfred xdrs->x_private = (char *)xdrs->x_private + len; 2481902Swollman } 2491902Swollman return (buf); 2501902Swollman} 25121062Speter 25274462Salfred/* ARGSUSED */ 25321062Speterstatic int32_t * 25421062Speterxdrmem_inline_unaligned(xdrs, len) 25574462Salfred XDR *xdrs; 25674462Salfred u_int len; 25721062Speter{ 25874462Salfred 25921062Speter return (0); 26021062Speter} 261