1*4bff34e3Sthurlow /* 2*4bff34e3Sthurlow * Copyright (c) 2000, Boris Popov 3*4bff34e3Sthurlow * All rights reserved. 4*4bff34e3Sthurlow * 5*4bff34e3Sthurlow * Redistribution and use in source and binary forms, with or without 6*4bff34e3Sthurlow * modification, are permitted provided that the following conditions 7*4bff34e3Sthurlow * are met: 8*4bff34e3Sthurlow * 1. Redistributions of source code must retain the above copyright 9*4bff34e3Sthurlow * notice, this list of conditions and the following disclaimer. 10*4bff34e3Sthurlow * 2. Redistributions in binary form must reproduce the above copyright 11*4bff34e3Sthurlow * notice, this list of conditions and the following disclaimer in the 12*4bff34e3Sthurlow * documentation and/or other materials provided with the distribution. 13*4bff34e3Sthurlow * 3. All advertising materials mentioning features or use of this software 14*4bff34e3Sthurlow * must display the following acknowledgement: 15*4bff34e3Sthurlow * This product includes software developed by Boris Popov. 16*4bff34e3Sthurlow * 4. Neither the name of the author nor the names of any co-contributors 17*4bff34e3Sthurlow * may be used to endorse or promote products derived from this software 18*4bff34e3Sthurlow * without specific prior written permission. 19*4bff34e3Sthurlow * 20*4bff34e3Sthurlow * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 21*4bff34e3Sthurlow * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 22*4bff34e3Sthurlow * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 23*4bff34e3Sthurlow * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 24*4bff34e3Sthurlow * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 25*4bff34e3Sthurlow * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 26*4bff34e3Sthurlow * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 27*4bff34e3Sthurlow * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 28*4bff34e3Sthurlow * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 29*4bff34e3Sthurlow * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 30*4bff34e3Sthurlow * SUCH DAMAGE. 31*4bff34e3Sthurlow * 32*4bff34e3Sthurlow * $Id: mbuf.c,v 1.3 2004/12/13 00:25:22 lindak Exp $ 33*4bff34e3Sthurlow */ 34*4bff34e3Sthurlow 35*4bff34e3Sthurlow #pragma ident "%Z%%M% %I% %E% SMI" 36*4bff34e3Sthurlow 37*4bff34e3Sthurlow #include <sys/types.h> 38*4bff34e3Sthurlow #include <ctype.h> 39*4bff34e3Sthurlow #include <errno.h> 40*4bff34e3Sthurlow #include <stdio.h> 41*4bff34e3Sthurlow #include <stdlib.h> 42*4bff34e3Sthurlow #include <string.h> 43*4bff34e3Sthurlow #include <strings.h> 44*4bff34e3Sthurlow #include <libintl.h> 45*4bff34e3Sthurlow 46*4bff34e3Sthurlow #include <netsmb/smb.h> 47*4bff34e3Sthurlow #include <netsmb/smb_lib.h> 48*4bff34e3Sthurlow #include <netsmb/mchain.h> 49*4bff34e3Sthurlow 50*4bff34e3Sthurlow #ifdef APPLE 51*4bff34e3Sthurlow #define __func__ "" 52*4bff34e3Sthurlow #define MBERROR(format, args...) \ 53*4bff34e3Sthurlow printf("%s(%d): "format, __func__, __LINE__, ## args) 54*4bff34e3Sthurlow #endif 55*4bff34e3Sthurlow 56*4bff34e3Sthurlow static int 57*4bff34e3Sthurlow m_get(size_t len, struct mbuf **mpp) 58*4bff34e3Sthurlow { 59*4bff34e3Sthurlow struct mbuf *m; 60*4bff34e3Sthurlow 61*4bff34e3Sthurlow len = M_ALIGN(len); 62*4bff34e3Sthurlow if (len < M_MINSIZE) 63*4bff34e3Sthurlow len = M_MINSIZE; 64*4bff34e3Sthurlow m = malloc(M_BASESIZE + len); 65*4bff34e3Sthurlow if (m == NULL) 66*4bff34e3Sthurlow return (ENOMEM); 67*4bff34e3Sthurlow bzero(m, M_BASESIZE + len); 68*4bff34e3Sthurlow m->m_maxlen = len; 69*4bff34e3Sthurlow m->m_data = M_TOP(m); 70*4bff34e3Sthurlow *mpp = m; 71*4bff34e3Sthurlow return (0); 72*4bff34e3Sthurlow } 73*4bff34e3Sthurlow 74*4bff34e3Sthurlow static void 75*4bff34e3Sthurlow m_free(struct mbuf *m) 76*4bff34e3Sthurlow { 77*4bff34e3Sthurlow free(m); 78*4bff34e3Sthurlow } 79*4bff34e3Sthurlow 80*4bff34e3Sthurlow static void 81*4bff34e3Sthurlow m_freem(struct mbuf *m0) 82*4bff34e3Sthurlow { 83*4bff34e3Sthurlow struct mbuf *m; 84*4bff34e3Sthurlow 85*4bff34e3Sthurlow while (m0) { 86*4bff34e3Sthurlow m = m0->m_next; 87*4bff34e3Sthurlow m_free(m0); 88*4bff34e3Sthurlow m0 = m; 89*4bff34e3Sthurlow } 90*4bff34e3Sthurlow } 91*4bff34e3Sthurlow 92*4bff34e3Sthurlow static size_t 93*4bff34e3Sthurlow m_totlen(struct mbuf *m0) 94*4bff34e3Sthurlow { 95*4bff34e3Sthurlow struct mbuf *m = m0; 96*4bff34e3Sthurlow int len = 0; 97*4bff34e3Sthurlow 98*4bff34e3Sthurlow while (m) { 99*4bff34e3Sthurlow len += m->m_len; 100*4bff34e3Sthurlow m = m->m_next; 101*4bff34e3Sthurlow } 102*4bff34e3Sthurlow return (len); 103*4bff34e3Sthurlow } 104*4bff34e3Sthurlow 105*4bff34e3Sthurlow int 106*4bff34e3Sthurlow m_lineup(struct mbuf *m0, struct mbuf **mpp) 107*4bff34e3Sthurlow { 108*4bff34e3Sthurlow struct mbuf *nm, *m; 109*4bff34e3Sthurlow char *dp; 110*4bff34e3Sthurlow size_t len; 111*4bff34e3Sthurlow int error; 112*4bff34e3Sthurlow 113*4bff34e3Sthurlow if (m0->m_next == NULL) { 114*4bff34e3Sthurlow *mpp = m0; 115*4bff34e3Sthurlow return (0); 116*4bff34e3Sthurlow } 117*4bff34e3Sthurlow if ((error = m_get(m_totlen(m0), &nm)) != 0) 118*4bff34e3Sthurlow return (error); 119*4bff34e3Sthurlow dp = mtod(nm, char *); 120*4bff34e3Sthurlow while (m0) { 121*4bff34e3Sthurlow len = m0->m_len; 122*4bff34e3Sthurlow bcopy(m0->m_data, dp, len); 123*4bff34e3Sthurlow dp += len; 124*4bff34e3Sthurlow m = m0->m_next; 125*4bff34e3Sthurlow m_free(m0); 126*4bff34e3Sthurlow m0 = m; 127*4bff34e3Sthurlow } 128*4bff34e3Sthurlow *mpp = nm; 129*4bff34e3Sthurlow return (0); 130*4bff34e3Sthurlow } 131*4bff34e3Sthurlow 132*4bff34e3Sthurlow int 133*4bff34e3Sthurlow mb_init(struct mbdata *mbp, size_t size) 134*4bff34e3Sthurlow { 135*4bff34e3Sthurlow struct mbuf *m; 136*4bff34e3Sthurlow int error; 137*4bff34e3Sthurlow 138*4bff34e3Sthurlow if ((error = m_get(size, &m)) != 0) 139*4bff34e3Sthurlow return (error); 140*4bff34e3Sthurlow return (mb_initm(mbp, m)); 141*4bff34e3Sthurlow } 142*4bff34e3Sthurlow 143*4bff34e3Sthurlow int 144*4bff34e3Sthurlow mb_initm(struct mbdata *mbp, struct mbuf *m) 145*4bff34e3Sthurlow { 146*4bff34e3Sthurlow bzero(mbp, sizeof (*mbp)); 147*4bff34e3Sthurlow mbp->mb_top = mbp->mb_cur = m; 148*4bff34e3Sthurlow mbp->mb_pos = mtod(m, char *); 149*4bff34e3Sthurlow return (0); 150*4bff34e3Sthurlow } 151*4bff34e3Sthurlow 152*4bff34e3Sthurlow int 153*4bff34e3Sthurlow mb_done(struct mbdata *mbp) 154*4bff34e3Sthurlow { 155*4bff34e3Sthurlow if (mbp->mb_top) { 156*4bff34e3Sthurlow m_freem(mbp->mb_top); 157*4bff34e3Sthurlow mbp->mb_top = NULL; 158*4bff34e3Sthurlow } 159*4bff34e3Sthurlow return (0); 160*4bff34e3Sthurlow } 161*4bff34e3Sthurlow 162*4bff34e3Sthurlow int 163*4bff34e3Sthurlow m_getm(struct mbuf *top, size_t len, struct mbuf **mpp) 164*4bff34e3Sthurlow { 165*4bff34e3Sthurlow struct mbuf *m, *mp; 166*4bff34e3Sthurlow int error; 167*4bff34e3Sthurlow 168*4bff34e3Sthurlow for (mp = top; ; mp = mp->m_next) { 169*4bff34e3Sthurlow len -= M_TRAILINGSPACE(mp); 170*4bff34e3Sthurlow if (mp->m_next == NULL) 171*4bff34e3Sthurlow break; 172*4bff34e3Sthurlow 173*4bff34e3Sthurlow } 174*4bff34e3Sthurlow if (len > 0) { 175*4bff34e3Sthurlow if ((error = m_get(len, &m)) != 0) 176*4bff34e3Sthurlow return (error); 177*4bff34e3Sthurlow mp->m_next = m; 178*4bff34e3Sthurlow } 179*4bff34e3Sthurlow *mpp = top; 180*4bff34e3Sthurlow return (0); 181*4bff34e3Sthurlow } 182*4bff34e3Sthurlow 183*4bff34e3Sthurlow /* 184*4bff34e3Sthurlow * Routines to put data in a buffer 185*4bff34e3Sthurlow */ 186*4bff34e3Sthurlow #define MB_PUT(t) int error; t *p; \ 187*4bff34e3Sthurlow if ((error = mb_fit(mbp, sizeof (t), (char **)&p)) != 0) \ 188*4bff34e3Sthurlow return (error) 189*4bff34e3Sthurlow 190*4bff34e3Sthurlow /* 191*4bff34e3Sthurlow * Check if object of size 'size' fit to the current position and 192*4bff34e3Sthurlow * allocate new mbuf if not. Advance pointers and increase length of mbuf(s). 193*4bff34e3Sthurlow * Return pointer to the object placeholder or NULL if any error occured. 194*4bff34e3Sthurlow */ 195*4bff34e3Sthurlow int 196*4bff34e3Sthurlow mb_fit(struct mbdata *mbp, size_t size, char **pp) 197*4bff34e3Sthurlow { 198*4bff34e3Sthurlow struct mbuf *m, *mn; 199*4bff34e3Sthurlow int error; 200*4bff34e3Sthurlow 201*4bff34e3Sthurlow m = mbp->mb_cur; 202*4bff34e3Sthurlow if (M_TRAILINGSPACE(m) < (int)size) { 203*4bff34e3Sthurlow if ((error = m_get(size, &mn)) != 0) 204*4bff34e3Sthurlow return (error); 205*4bff34e3Sthurlow mbp->mb_pos = mtod(mn, char *); 206*4bff34e3Sthurlow mbp->mb_cur = m->m_next = mn; 207*4bff34e3Sthurlow m = mn; 208*4bff34e3Sthurlow } 209*4bff34e3Sthurlow m->m_len += size; 210*4bff34e3Sthurlow *pp = mbp->mb_pos; 211*4bff34e3Sthurlow mbp->mb_pos += size; 212*4bff34e3Sthurlow mbp->mb_count += size; 213*4bff34e3Sthurlow return (0); 214*4bff34e3Sthurlow } 215*4bff34e3Sthurlow 216*4bff34e3Sthurlow int 217*4bff34e3Sthurlow mb_put_uint8(struct mbdata *mbp, uint8_t x) 218*4bff34e3Sthurlow { 219*4bff34e3Sthurlow MB_PUT(uint8_t); 220*4bff34e3Sthurlow *p = x; 221*4bff34e3Sthurlow return (0); 222*4bff34e3Sthurlow } 223*4bff34e3Sthurlow 224*4bff34e3Sthurlow int 225*4bff34e3Sthurlow mb_put_uint16be(struct mbdata *mbp, uint16_t x) 226*4bff34e3Sthurlow { 227*4bff34e3Sthurlow MB_PUT(uint16_t); 228*4bff34e3Sthurlow /* LINTED */ 229*4bff34e3Sthurlow setwbe(p, 0, x); 230*4bff34e3Sthurlow return (0); 231*4bff34e3Sthurlow } 232*4bff34e3Sthurlow 233*4bff34e3Sthurlow int 234*4bff34e3Sthurlow mb_put_uint16le(struct mbdata *mbp, uint16_t x) 235*4bff34e3Sthurlow { 236*4bff34e3Sthurlow MB_PUT(uint16_t); 237*4bff34e3Sthurlow /* LINTED */ 238*4bff34e3Sthurlow setwle(p, 0, x); 239*4bff34e3Sthurlow return (0); 240*4bff34e3Sthurlow } 241*4bff34e3Sthurlow 242*4bff34e3Sthurlow int 243*4bff34e3Sthurlow mb_put_uint32be(struct mbdata *mbp, uint32_t x) 244*4bff34e3Sthurlow { 245*4bff34e3Sthurlow MB_PUT(uint32_t); 246*4bff34e3Sthurlow /* LINTED */ 247*4bff34e3Sthurlow setdbe(p, 0, x); 248*4bff34e3Sthurlow return (0); 249*4bff34e3Sthurlow } 250*4bff34e3Sthurlow 251*4bff34e3Sthurlow int 252*4bff34e3Sthurlow mb_put_uint32le(struct mbdata *mbp, uint32_t x) 253*4bff34e3Sthurlow { 254*4bff34e3Sthurlow MB_PUT(uint32_t); 255*4bff34e3Sthurlow /* LINTED */ 256*4bff34e3Sthurlow setdle(p, 0, x); 257*4bff34e3Sthurlow return (0); 258*4bff34e3Sthurlow } 259*4bff34e3Sthurlow 260*4bff34e3Sthurlow int 261*4bff34e3Sthurlow mb_put_uint64be(struct mbdata *mbp, uint64_t x) 262*4bff34e3Sthurlow { 263*4bff34e3Sthurlow MB_PUT(uint64_t); 264*4bff34e3Sthurlow *p = htobeq(x); 265*4bff34e3Sthurlow return (0); 266*4bff34e3Sthurlow } 267*4bff34e3Sthurlow 268*4bff34e3Sthurlow int 269*4bff34e3Sthurlow mb_put_uint64le(struct mbdata *mbp, uint64_t x) 270*4bff34e3Sthurlow { 271*4bff34e3Sthurlow MB_PUT(uint64_t); 272*4bff34e3Sthurlow *p = htoleq(x); 273*4bff34e3Sthurlow return (0); 274*4bff34e3Sthurlow } 275*4bff34e3Sthurlow 276*4bff34e3Sthurlow int 277*4bff34e3Sthurlow mb_put_mem(struct mbdata *mbp, const char *source, size_t size) 278*4bff34e3Sthurlow { 279*4bff34e3Sthurlow struct mbuf *m; 280*4bff34e3Sthurlow char *dst; 281*4bff34e3Sthurlow size_t cplen; 282*4bff34e3Sthurlow int error; 283*4bff34e3Sthurlow 284*4bff34e3Sthurlow if (size == 0) 285*4bff34e3Sthurlow return (0); 286*4bff34e3Sthurlow m = mbp->mb_cur; 287*4bff34e3Sthurlow if ((error = m_getm(m, size, &m)) != 0) 288*4bff34e3Sthurlow return (error); 289*4bff34e3Sthurlow while (size > 0) { 290*4bff34e3Sthurlow cplen = M_TRAILINGSPACE(m); 291*4bff34e3Sthurlow if (cplen == 0) { 292*4bff34e3Sthurlow m = m->m_next; 293*4bff34e3Sthurlow continue; 294*4bff34e3Sthurlow } 295*4bff34e3Sthurlow if (cplen > size) 296*4bff34e3Sthurlow cplen = size; 297*4bff34e3Sthurlow dst = mtod(m, char *) + m->m_len; 298*4bff34e3Sthurlow if (source) { 299*4bff34e3Sthurlow bcopy(source, dst, cplen); 300*4bff34e3Sthurlow source += cplen; 301*4bff34e3Sthurlow } else 302*4bff34e3Sthurlow bzero(dst, cplen); 303*4bff34e3Sthurlow size -= cplen; 304*4bff34e3Sthurlow m->m_len += cplen; 305*4bff34e3Sthurlow mbp->mb_count += cplen; 306*4bff34e3Sthurlow } 307*4bff34e3Sthurlow mbp->mb_pos = mtod(m, char *) + m->m_len; 308*4bff34e3Sthurlow mbp->mb_cur = m; 309*4bff34e3Sthurlow return (0); 310*4bff34e3Sthurlow } 311*4bff34e3Sthurlow 312*4bff34e3Sthurlow int 313*4bff34e3Sthurlow mb_put_mbuf(struct mbdata *mbp, struct mbuf *m) 314*4bff34e3Sthurlow { 315*4bff34e3Sthurlow mbp->mb_cur->m_next = m; 316*4bff34e3Sthurlow while (m) { 317*4bff34e3Sthurlow mbp->mb_count += m->m_len; 318*4bff34e3Sthurlow if (m->m_next == NULL) 319*4bff34e3Sthurlow break; 320*4bff34e3Sthurlow m = m->m_next; 321*4bff34e3Sthurlow } 322*4bff34e3Sthurlow mbp->mb_pos = mtod(m, char *) + m->m_len; 323*4bff34e3Sthurlow mbp->mb_cur = m; 324*4bff34e3Sthurlow return (0); 325*4bff34e3Sthurlow } 326*4bff34e3Sthurlow 327*4bff34e3Sthurlow int 328*4bff34e3Sthurlow mb_put_pstring(struct mbdata *mbp, const char *s) 329*4bff34e3Sthurlow { 330*4bff34e3Sthurlow int error, len = strlen(s); 331*4bff34e3Sthurlow 332*4bff34e3Sthurlow if (len > 255) { 333*4bff34e3Sthurlow len = 255; 334*4bff34e3Sthurlow } 335*4bff34e3Sthurlow if ((error = mb_put_uint8(mbp, len)) != 0) 336*4bff34e3Sthurlow return (error); 337*4bff34e3Sthurlow return (mb_put_mem(mbp, s, len)); 338*4bff34e3Sthurlow } 339*4bff34e3Sthurlow 340*4bff34e3Sthurlow /* 341*4bff34e3Sthurlow * Routines for fetching data from an mbuf chain 342*4bff34e3Sthurlow */ 343*4bff34e3Sthurlow #define mb_left(m, p) (mtod(m, char *) + (m)->m_len - (p)) 344*4bff34e3Sthurlow 345*4bff34e3Sthurlow int 346*4bff34e3Sthurlow mb_get_uint8(struct mbdata *mbp, uint8_t *x) 347*4bff34e3Sthurlow { 348*4bff34e3Sthurlow return (mb_get_mem(mbp, (char *)x, 1)); 349*4bff34e3Sthurlow } 350*4bff34e3Sthurlow 351*4bff34e3Sthurlow int 352*4bff34e3Sthurlow mb_get_uint16(struct mbdata *mbp, uint16_t *x) 353*4bff34e3Sthurlow { 354*4bff34e3Sthurlow return (mb_get_mem(mbp, (char *)x, 2)); 355*4bff34e3Sthurlow } 356*4bff34e3Sthurlow 357*4bff34e3Sthurlow int 358*4bff34e3Sthurlow mb_get_uint16le(struct mbdata *mbp, uint16_t *x) 359*4bff34e3Sthurlow { 360*4bff34e3Sthurlow uint16_t v; 361*4bff34e3Sthurlow int error = mb_get_uint16(mbp, &v); 362*4bff34e3Sthurlow 363*4bff34e3Sthurlow if (x != NULL) 364*4bff34e3Sthurlow *x = letohs(v); 365*4bff34e3Sthurlow return (error); 366*4bff34e3Sthurlow } 367*4bff34e3Sthurlow 368*4bff34e3Sthurlow int 369*4bff34e3Sthurlow mb_get_uint16be(struct mbdata *mbp, uint16_t *x) { 370*4bff34e3Sthurlow uint16_t v; 371*4bff34e3Sthurlow int error = mb_get_uint16(mbp, &v); 372*4bff34e3Sthurlow 373*4bff34e3Sthurlow if (x != NULL) 374*4bff34e3Sthurlow *x = betohs(v); 375*4bff34e3Sthurlow return (error); 376*4bff34e3Sthurlow } 377*4bff34e3Sthurlow 378*4bff34e3Sthurlow int 379*4bff34e3Sthurlow mb_get_uint32(struct mbdata *mbp, uint32_t *x) 380*4bff34e3Sthurlow { 381*4bff34e3Sthurlow return (mb_get_mem(mbp, (char *)x, 4)); 382*4bff34e3Sthurlow } 383*4bff34e3Sthurlow 384*4bff34e3Sthurlow int 385*4bff34e3Sthurlow mb_get_uint32be(struct mbdata *mbp, uint32_t *x) 386*4bff34e3Sthurlow { 387*4bff34e3Sthurlow uint32_t v; 388*4bff34e3Sthurlow int error; 389*4bff34e3Sthurlow 390*4bff34e3Sthurlow error = mb_get_uint32(mbp, &v); 391*4bff34e3Sthurlow if (x != NULL) 392*4bff34e3Sthurlow *x = betohl(v); 393*4bff34e3Sthurlow return (error); 394*4bff34e3Sthurlow } 395*4bff34e3Sthurlow 396*4bff34e3Sthurlow int 397*4bff34e3Sthurlow mb_get_uint32le(struct mbdata *mbp, uint32_t *x) 398*4bff34e3Sthurlow { 399*4bff34e3Sthurlow uint32_t v; 400*4bff34e3Sthurlow int error; 401*4bff34e3Sthurlow 402*4bff34e3Sthurlow error = mb_get_uint32(mbp, &v); 403*4bff34e3Sthurlow if (x != NULL) 404*4bff34e3Sthurlow *x = letohl(v); 405*4bff34e3Sthurlow return (error); 406*4bff34e3Sthurlow } 407*4bff34e3Sthurlow 408*4bff34e3Sthurlow int 409*4bff34e3Sthurlow mb_get_uint64(struct mbdata *mbp, uint64_t *x) 410*4bff34e3Sthurlow { 411*4bff34e3Sthurlow return (mb_get_mem(mbp, (char *)x, 8)); 412*4bff34e3Sthurlow } 413*4bff34e3Sthurlow 414*4bff34e3Sthurlow int 415*4bff34e3Sthurlow mb_get_uint64be(struct mbdata *mbp, uint64_t *x) 416*4bff34e3Sthurlow { 417*4bff34e3Sthurlow uint64_t v; 418*4bff34e3Sthurlow int error; 419*4bff34e3Sthurlow 420*4bff34e3Sthurlow error = mb_get_uint64(mbp, &v); 421*4bff34e3Sthurlow if (x != NULL) 422*4bff34e3Sthurlow *x = betohq(v); 423*4bff34e3Sthurlow return (error); 424*4bff34e3Sthurlow } 425*4bff34e3Sthurlow 426*4bff34e3Sthurlow int 427*4bff34e3Sthurlow mb_get_uint64le(struct mbdata *mbp, uint64_t *x) 428*4bff34e3Sthurlow { 429*4bff34e3Sthurlow uint64_t v; 430*4bff34e3Sthurlow int error; 431*4bff34e3Sthurlow 432*4bff34e3Sthurlow error = mb_get_uint64(mbp, &v); 433*4bff34e3Sthurlow if (x != NULL) 434*4bff34e3Sthurlow *x = letohq(v); 435*4bff34e3Sthurlow return (error); 436*4bff34e3Sthurlow } 437*4bff34e3Sthurlow 438*4bff34e3Sthurlow int 439*4bff34e3Sthurlow mb_get_mem(struct mbdata *mbp, char *target, size_t size) 440*4bff34e3Sthurlow { 441*4bff34e3Sthurlow struct mbuf *m = mbp->mb_cur; 442*4bff34e3Sthurlow uint_t count; 443*4bff34e3Sthurlow 444*4bff34e3Sthurlow while (size > 0) { 445*4bff34e3Sthurlow if (m == NULL) { 446*4bff34e3Sthurlow #ifdef DEBUG 447*4bff34e3Sthurlow printf( 448*4bff34e3Sthurlow dgettext(TEXT_DOMAIN, "incomplete copy\n")); 449*4bff34e3Sthurlow #endif 450*4bff34e3Sthurlow #ifdef APPLE 451*4bff34e3Sthurlow MBERROR("incomplete copy\n"); 452*4bff34e3Sthurlow #endif 453*4bff34e3Sthurlow return (EBADRPC); 454*4bff34e3Sthurlow } 455*4bff34e3Sthurlow count = mb_left(m, mbp->mb_pos); 456*4bff34e3Sthurlow if (count == 0) { 457*4bff34e3Sthurlow mbp->mb_cur = m = m->m_next; 458*4bff34e3Sthurlow if (m) 459*4bff34e3Sthurlow mbp->mb_pos = mtod(m, char *); 460*4bff34e3Sthurlow continue; 461*4bff34e3Sthurlow } 462*4bff34e3Sthurlow if (count > size) 463*4bff34e3Sthurlow count = size; 464*4bff34e3Sthurlow size -= count; 465*4bff34e3Sthurlow if (target) { 466*4bff34e3Sthurlow if (count == 1) { 467*4bff34e3Sthurlow *target++ = *mbp->mb_pos; 468*4bff34e3Sthurlow } else { 469*4bff34e3Sthurlow bcopy(mbp->mb_pos, target, count); 470*4bff34e3Sthurlow target += count; 471*4bff34e3Sthurlow } 472*4bff34e3Sthurlow } 473*4bff34e3Sthurlow mbp->mb_pos += count; 474*4bff34e3Sthurlow } 475*4bff34e3Sthurlow return (0); 476*4bff34e3Sthurlow } 477