X-Git-Url: https://git.saurik.com/apple/security.git/blobdiff_plain/80e2389990082500d76eb566d4946be3e786c3ef..d8f41ccd20de16f8ebe2ccc84d47bf1cb2b26bbb:/libsecurityd/lib/sec_xdr.c?ds=inline diff --git a/libsecurityd/lib/sec_xdr.c b/libsecurityd/lib/sec_xdr.c deleted file mode 100644 index e82f6374..00000000 --- a/libsecurityd/lib/sec_xdr.c +++ /dev/null @@ -1,293 +0,0 @@ -/* - * Copyright (c) 2006 Apple Computer, Inc. All Rights Reserved. - * - * @APPLE_LICENSE_HEADER_START@ - * - * This file contains Original Code and/or Modifications of Original Code - * as defined in and that are subject to the Apple Public Source License - * Version 2.0 (the 'License'). You may not use this file except in - * compliance with the License. Please obtain a copy of the License at - * http://www.opensource.apple.com/apsl/ and read it before using this - * file. - * - * The Original Code and all software distributed under the License are - * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER - * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES, - * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT. - * Please see the License for the specific language governing rights and - * limitations under the License. - * - * @APPLE_LICENSE_HEADER_END@ - */ - -#include -#include -#include - -#include "sec_xdr.h" - -#define ALIGNMENT sizeof(void*) -#define ALIGNUP(LEN) (((LEN - 1) & ~(ALIGNMENT - 1)) + ALIGNMENT) - -/* - * XDR counted bytes - * *cpp is a pointer to the bytes, *sizep is the count. - * If *cpp is NULL maxsize bytes are allocated - */ -bool_t sec_xdr_bytes(XDR *xdrs, uint8_t **cpp, u_int *sizep, u_int maxsize) -{ - uint8_t *sp = cpp ? *cpp : NULL; /* sp is the actual string pointer */ - u_int nodesize = sizep ? *sizep : 0; - - /* - * first deal with the length since xdr bytes are counted - */ - if (! xdr_u_int(xdrs, &nodesize)) - return (FALSE); - - if ((nodesize > maxsize) && (xdrs->x_op != XDR_FREE)) - return (FALSE); - - if (sizep && (xdrs->x_op == XDR_DECODE)) - *sizep = nodesize; - - bool_t sizeof_alloc = sec_xdr_arena_size_allocator(xdrs); - - /* - * now deal with the actual bytes - */ - switch (xdrs->x_op) { - case XDR_DECODE: - if (nodesize == 0) - return (TRUE); - if (!sp) { - if (!sec_mem_alloc(xdrs, nodesize, &sp)) - return (FALSE); - if (!sizeof_alloc) - *cpp = sp; /* sp can be NULL when counting required space */ - } - /* FALLTHROUGH */ - case XDR_ENCODE: - return (xdr_opaque(xdrs, (char *)sp, nodesize)); - - case XDR_FREE: - if (sp != NULL) { - sec_mem_free(xdrs, sp, nodesize); - *cpp = NULL; - } - return (TRUE); - } - /* NOTREACHED */ - return (FALSE); -} - -bool_t sec_xdr_charp(XDR *xdrs, char **cpp, u_int maxsize) -{ - char *sp = cpp ? *cpp : NULL; /* sp is the actual string pointer */ - u_int size = 0; - - switch (xdrs->x_op) { - case XDR_FREE: - if (sp == NULL) return(TRUE); /* already free */ - sec_mem_free(xdrs, sp, size); - *cpp = NULL; - return (TRUE); - case XDR_ENCODE: - if (sp) size = (u_int)(strlen(sp) + 1); - /* FALLTHROUGH */ - case XDR_DECODE: - return sec_xdr_bytes(xdrs, (uint8_t**)cpp, &size, maxsize); - } - /* NOTREACHED */ - return (FALSE); -} - -bool_t sec_mem_alloc(XDR *xdr, u_int bsize, uint8_t **data) -{ - if (!xdr || !data) - return (FALSE); - - assert(xdr->x_op == XDR_DECODE); - - sec_xdr_arena_allocator_t *allocator = sec_xdr_arena_allocator(xdr); - if (allocator) { - if (*data != NULL) - return (TRUE); // no allocation needed - size_t bytes_left; - switch(allocator->magic) { - case xdr_arena_magic: - bytes_left = allocator->end - allocator->offset; - if (bsize > bytes_left) - return (FALSE); - else { - uint8_t *temp = allocator->offset; - allocator->offset += bsize; - *data = temp; - return (TRUE); - } - case xdr_size_magic: - allocator->offset = (uint8_t*)((size_t)allocator->offset + bsize); - return (TRUE); - } - } - - void *alloc = calloc(1, bsize); - if (!alloc) - return (FALSE); - - *data = alloc; - return (TRUE); -} - -void sec_mem_free(XDR *xdr, void *ptr, u_int bsize) -{ - if (sec_xdr_arena_allocator(xdr)) - return; - - return free(ptr); -} - -static const sec_xdr_arena_allocator_t size_alloc = { xdr_size_magic, 0, 0, 0 }; -void sec_xdr_arena_init_size_alloc(sec_xdr_arena_allocator_t *arena, XDR *xdr) -{ - memcpy(arena, &size_alloc, sizeof(size_alloc)); - xdr->x_public = (char *)arena; -} - -bool_t sec_xdr_arena_init(sec_xdr_arena_allocator_t *arena, XDR *xdr, - size_t in_length, uint8_t *in_data) -{ - if (!xdr) - return FALSE; - uint8_t *data = in_data ? in_data : calloc(1, ALIGNUP(in_length)); - if (!data) - return FALSE; - arena->magic = xdr_arena_magic; - arena->offset = data; - arena->data = data; - arena->end = data + in_length; - xdr->x_public = (void*)arena; - return TRUE; -} - -void sec_xdr_arena_free(sec_xdr_arena_allocator_t *arena, - void *ptr, size_t bsize) -{ - assert(arena->magic == xdr_arena_magic); - free(arena->data); -} - -void *sec_xdr_arena_data(sec_xdr_arena_allocator_t *arena) -{ - if (arena) - return arena->data; - - return NULL; -} - -sec_xdr_arena_allocator_t *sec_xdr_arena_allocator(XDR *xdr) -{ - sec_xdr_arena_allocator_t *allocator = xdr ? (sec_xdr_arena_allocator_t *)xdr->x_public : NULL; - - if (allocator && - (allocator->magic == xdr_arena_magic || - allocator->magic == xdr_size_magic)) - return allocator; - - return NULL; -} - -bool_t sec_xdr_arena_size_allocator(XDR *xdr) -{ - sec_xdr_arena_allocator_t *allocator = xdr ? (sec_xdr_arena_allocator_t *)xdr->x_public : NULL; - if (allocator && (allocator->magic == xdr_size_magic)) - return TRUE; - - return FALSE; -} - - -bool_t copyin(void *data, xdrproc_t proc, void** copy, u_int *size) -{ - if (!copy) - return (FALSE); - - // xdr_sizeof is illbehaved - u_int length = sec_xdr_sizeof_in(proc, data); - uint8_t *xdr_data = malloc(length); - if (!xdr_data) - return (FALSE); - - XDR xdr; - sec_xdrmem_create(&xdr, (char *)xdr_data, length, XDR_ENCODE); - - // cast to void* - function can go both ways (xdr->x_op) - if (proc(&xdr, data, 0)) { - *copy = xdr_data; - if (size) *size = length; - return (TRUE); - } - - free(xdr_data); - return (FALSE); -} - -// Unmarshall xdr data and return pointer to single allocation containing data -// Generally use *_PTR for xdrproc_t taking an objp that matches data's type -// ie. xdr_CSSM_POSSIBLY_KEY_IN_DATA_PTR(XDR *xdrs, CSSM_DATA_PTR *objp) -// with data matching objp -// If you pass in length pointing to a non-zero value, data will be assumed -// to have pre-allocated space for use by copyout in that amount. -// If *data is not NULL it will be assumed to be allocated already. -bool_t copyout(const void *copy, u_int size, xdrproc_t proc, void **data, u_int *length) -{ - - if (!data || (size > ~(u_int)0)) - return (FALSE); - - XDR xdr; - sec_xdrmem_create(&xdr, (void *)copy, size, XDR_DECODE); - - u_int length_required = sec_xdr_sizeof_out(copy, size, proc, data); - u_int length_out = length ? *length : 0; - - if (length_out && (length_required > length_out)) - return (FALSE); - - bool_t passed_in_data = (*data && length_out); - sec_xdr_arena_allocator_t arena; - // set up arena with memory passed in (length_out > 0) or ask to allocate - if (!sec_xdr_arena_init(&arena, &xdr, length_out ? length_out : length_required, length_out ? *data : NULL)) - return (FALSE); - - if (proc(&xdr, data, 0)) - { - *length = length_required; - return (TRUE); - } - - if (!passed_in_data) - sec_xdr_arena_free(sec_xdr_arena_allocator(&xdr), NULL, 0); - return (FALSE); -} - -// unmarshall xdr data and return pointer to individual allocations containing data -// only use *_PTR for xdrproc_ts and pointers for data -bool_t copyout_chunked(const void *copy, u_int size, xdrproc_t proc, void **data) -{ - if (!data || (size > ~(u_int)0)) - return (FALSE); - - XDR xdr; - sec_xdrmem_create(&xdr, (void *)copy, size, XDR_DECODE); - - void *data_out = NULL; - - if (proc(&xdr, &data_out, 0)) - { - *data = data_out; - return (TRUE); - } - return (FALSE); -}