[Xen-devel] [PATCH 6/9] libxc: add hypercall buffer arrays

Don Slutz dslutz at verizon.com
Thu Nov 7 15:46:43 EST 2013


For what it is worth.

Reviewed-by: Don Slutz <dslutz at verizon.com>
     -Don Slutz

On 11/06/13 09:49, David Vrabel wrote:
> From: David Vrabel <david.vrabel at citrix.com>
>
> Hypercall buffer arrays are used when a hypercall takes a variable
> length array of buffers.
>
> Signed-off-by: David Vrabel <david.vrabel at citrix.com>
> Acked-by: Ian Campbell <ian.campbell at citrix.com>
> Reviewed-by: Daniel Kiper <daniel.kiper at oracle.com>
> Tested-by: Daniel Kiper <daniel.kiper at oracle.com>
> Reviewed-by: Andrew Cooper <andrew.cooper3 at citrix.com>
> ---
>   tools/libxc/xc_hcall_buf.c |   73 ++++++++++++++++++++++++++++++++++++++++++++
>   tools/libxc/xenctrl.h      |   27 ++++++++++++++++
>   2 files changed, 100 insertions(+), 0 deletions(-)
>
> diff --git a/tools/libxc/xc_hcall_buf.c b/tools/libxc/xc_hcall_buf.c
> index c354677..e762a93 100644
> --- a/tools/libxc/xc_hcall_buf.c
> +++ b/tools/libxc/xc_hcall_buf.c
> @@ -228,6 +228,79 @@ void xc__hypercall_bounce_post(xc_interface *xch, xc_hypercall_buffer_t *b)
>       xc__hypercall_buffer_free(xch, b);
>   }
>   
> +struct xc_hypercall_buffer_array {
> +    unsigned max_bufs;
> +    xc_hypercall_buffer_t *bufs;
> +};
> +
> +xc_hypercall_buffer_array_t *xc_hypercall_buffer_array_create(xc_interface *xch,
> +                                                              unsigned n)
> +{
> +    xc_hypercall_buffer_array_t *array;
> +    xc_hypercall_buffer_t *bufs = NULL;
> +
> +    array = malloc(sizeof(*array));
> +    if ( array == NULL )
> +        goto error;
> +
> +    bufs = calloc(n, sizeof(*bufs));
> +    if ( bufs == NULL )
> +        goto error;
> +
> +    array->max_bufs = n;
> +    array->bufs     = bufs;
> +
> +    return array;
> +
> +error:
> +    free(bufs);
> +    free(array);
> +    return NULL;
> +}
> +
> +void *xc__hypercall_buffer_array_alloc(xc_interface *xch,
> +                                       xc_hypercall_buffer_array_t *array,
> +                                       unsigned index,
> +                                       xc_hypercall_buffer_t *hbuf,
> +                                       size_t size)
> +{
> +    void *buf;
> +
> +    if ( index >= array->max_bufs || array->bufs[index].hbuf )
> +        abort();
> +
> +    buf = xc__hypercall_buffer_alloc(xch, hbuf, size);
> +    if ( buf )
> +        array->bufs[index] = *hbuf;
> +    return buf;
> +}
> +
> +void *xc__hypercall_buffer_array_get(xc_interface *xch,
> +                                     xc_hypercall_buffer_array_t *array,
> +                                     unsigned index,
> +                                     xc_hypercall_buffer_t *hbuf)
> +{
> +    if ( index >= array->max_bufs || array->bufs[index].hbuf == NULL )
> +        abort();
> +
> +    *hbuf = array->bufs[index];
> +    return array->bufs[index].hbuf;
> +}
> +
> +void xc_hypercall_buffer_array_destroy(xc_interface *xc,
> +                                       xc_hypercall_buffer_array_t *array)
> +{
> +    unsigned i;
> +
> +    if ( array == NULL )
> +        return;
> +
> +    for (i = 0; i < array->max_bufs; i++ )
> +        xc__hypercall_buffer_free(xc, &array->bufs[i]);
> +    free(array->bufs);
> +    free(array);
> +}
> +
>   /*
>    * Local variables:
>    * mode: C
> diff --git a/tools/libxc/xenctrl.h b/tools/libxc/xenctrl.h
> index 8cf3f3b..a7e8c31 100644
> --- a/tools/libxc/xenctrl.h
> +++ b/tools/libxc/xenctrl.h
> @@ -321,6 +321,33 @@ void xc__hypercall_buffer_free_pages(xc_interface *xch, xc_hypercall_buffer_t *b
>   #define xc_hypercall_buffer_free_pages(_xch, _name, _nr) xc__hypercall_buffer_free_pages(_xch, HYPERCALL_BUFFER(_name), _nr)
>   
>   /*
> + * Array of hypercall buffers.
> + *
> + * Create an array with xc_hypercall_buffer_array_create() and
> + * populate it by declaring one hypercall buffer in a loop and
> + * allocating the buffer with xc_hypercall_buffer_array_alloc().
> + *
> + * To access a previously allocated buffers, declare a new hypercall
> + * buffer and call xc_hypercall_buffer_array_get().
> + *
> + * Destroy the array with xc_hypercall_buffer_array_destroy() to free
> + * the array and all its alocated hypercall buffers.
> + */
> +struct xc_hypercall_buffer_array;
> +typedef struct xc_hypercall_buffer_array xc_hypercall_buffer_array_t;
> +
> +xc_hypercall_buffer_array_t *xc_hypercall_buffer_array_create(xc_interface *xch, unsigned n);
> +void *xc__hypercall_buffer_array_alloc(xc_interface *xch, xc_hypercall_buffer_array_t *array,
> +                                       unsigned index, xc_hypercall_buffer_t *hbuf, size_t size);
> +#define xc_hypercall_buffer_array_alloc(_xch, _array, _index, _name, _size) \
> +    xc__hypercall_buffer_array_alloc(_xch, _array, _index, HYPERCALL_BUFFER(_name), _size)
> +void *xc__hypercall_buffer_array_get(xc_interface *xch, xc_hypercall_buffer_array_t *array,
> +                                     unsigned index, xc_hypercall_buffer_t *hbuf);
> +#define xc_hypercall_buffer_array_get(_xch, _array, _index, _name, _size) \
> +    xc__hypercall_buffer_array_get(_xch, _array, _index, HYPERCALL_BUFFER(_name))
> +void xc_hypercall_buffer_array_destroy(xc_interface *xc, xc_hypercall_buffer_array_t *array);
> +
> +/*
>    * CPUMAP handling
>    */
>   typedef uint8_t *xc_cpumap_t;




More information about the kexec mailing list