blob: 995de07de85f84efff1be15fa3a7b6b5c3e8977a [file] [log] [blame]
/*
* Copyright 2014, NICTA
*
* This software may be distributed and modified according to the terms of
* the BSD 2-Clause license. Note that NO WARRANTY is provided.
* See "LICENSE_BSD2.txt" for details.
*
* @TAG(NICTA_BSD)
*/
#ifndef _ALLOCMAN_UTSPACE_VKA_H_
#define _ALLOCMAN_UTSPACE_VKA_H_
#include <autoconf.h>
#include <sel4/types.h>
#include <allocman/utspace/utspace.h>
#include <vka/cspacepath_t.h>
#include <vka/vka.h>
#include <vka/kobject_t.h>
#include <assert.h>
/* This is an untyped manager that just proxies calls to a VKA interface.
* We also need to do some extra book keeping work */
typedef struct utspace_vka_cookie {
seL4_Word original_cookie;
seL4_Word type;
} utspace_vka_cookie_t;
static inline seL4_Word _utspace_vka_alloc(struct allocman *alloc, void *_vka, size_t size_bits, seL4_Word type, const cspacepath_t *slot, int *error)
{
vka_t *vka = (vka_t *)_vka;
size_t sel4_size_bits = get_sel4_object_size(type, size_bits);
utspace_vka_cookie_t *cookie = (utspace_vka_cookie_t*)malloc(sizeof(*cookie));
if (!cookie) {
SET_ERROR(error, 1);
return 0;
}
int _error = vka_utspace_alloc(vka, slot, type, sel4_size_bits, &cookie->original_cookie);
SET_ERROR(error, _error);
if (!_error) {
cookie->type = type;
} else {
free(cookie);
cookie = NULL;
}
return (seL4_Word)cookie;
}
static inline void _utspace_vka_free(struct allocman *alloc, void *_vka, seL4_Word _cookie, size_t size_bits)
{
vka_t *vka = (vka_t *)_vka;
utspace_vka_cookie_t *cookie = (utspace_vka_cookie_t*)_cookie;
vka_utspace_free(vka, cookie->original_cookie, cookie->type, get_sel4_object_size(cookie->type, size_bits));
}
static inline uintptr_t _utspace_vka_paddr(void *_vka, seL4_Word _cookie, size_t size_bits)
{
vka_t *vka = (vka_t *)_vka;
utspace_vka_cookie_t *cookie = (utspace_vka_cookie_t*)_cookie;
return vka_utspace_paddr(vka, cookie->original_cookie, cookie->type, get_sel4_object_size(cookie->type, size_bits));
}
static inline int _utspace_vka_add_uts(struct allocman *alloc, void *_trickle, size_t num, const cspacepath_t *uts, size_t *size_bits, uintptr_t *paddr)
{
assert(!"VKA interface does not support adding untypeds after creation");
return -1;
}
/**
* Make a utspace interface from a VKA. It is the responsibility of the caller to ensure
* that this pointer remains valid for as long as this cspace is used
*
* @param vka Allocator to proxy cspace calls to
* @return utspace_interface that can be given to allocman
*/
static inline struct utspace_interface utspace_vka_make_interface(vka_t *vka) {
return (struct utspace_interface) {
.alloc = _utspace_vka_alloc,
.free = _utspace_vka_free,
.add_uts = _utspace_vka_add_uts,
.paddr = _utspace_vka_paddr,
.properties = ALLOCMAN_DEFAULT_PROPERTIES,
.utspace = vka
};
}
#endif