Commit 5cf750c4 authored by Charlie Jacobsen's avatar Charlie Jacobsen Committed by Vikram Narayanan

More extensive test of cap.

parent 1f10f73b
......@@ -27,6 +27,36 @@ static inline int test_rm_cspace(struct cspace *cspace, int ret_val)
return ret_val;
}
static inline void test_check_cnode(struct cspace *cspace, cptr_t cptr,
void *object, enum lcd_cap_type t,
int rights)
{
struct cnode *cnode;
lcd_cap_lock();
if (lcd_cnode_lookup(cspace, cptr, &cnode)) {
LCD_ERR("looking up object at %p in cspace at %p at cptr %d",
object, cspace, cptr);
goto unlock;
}
if (__lcd_cnode_type(cnode) != t) {
LCD_ERR("cnode has type %d, expected %d",
__lcd_cnode_type(cnode), t);
goto unlock;
}
if (__lcd_cnode_rights(cnode) != rights) {
LCD_ERR("cnode has rights %d, expected %d",
__lcd_cnode_rights(cnode), rights);
goto unlock;
}
if (__lcd_cnode_object(cnode) != object) {
LCD_ERR("cnode has object %p, expected %p",
__lcd_cnode_object(cnode), object);
goto unlock;
}
unlock:
lcd_cap_unlock();
}
static int test01(void)
{
struct cspace *cspace;
......@@ -172,126 +202,202 @@ fail:
return test_rm_cspace(cspace, -1);
}
#if 0
static int test03(void)
{
struct cspace *cspace;
struct cnode *cnode;
cptr_t cptr;
int i;
int x;
if (lcd_mk_cspace(&cspace))
LCD_FAIL("mk cspace");
if (lcd_cnode_alloc(cspace, &cptr)) {
LCD_ERR("alloc");
goto fail;
}
/*
* Insert object
*/
x = 517;
if (lcd_cnode_insert(cspace, cptr, &x, LCD_CAP_TYPE_SYNC_EP,
LCD_CAP_RIGHT_WRITE)) {
LCD_ERR("insert");
goto fail;
}
for (i = 0; i < 5; i++) {
if (lcd_cap_alloc(cspace, &cptr)) {
lcd_rm_cspace(cspace);
LCD_FAIL("cap alloc");
}
if (cptr != i) {
lcd_rm_cspace(cspace);
LCD_FAIL("i = %d, cptr = %lld", i, cptr);
}
}
if (cspace->free_slot != 5) {
lcd_rm_cspace(cspace);
LCD_FAIL("free slot is %d", cspace->free_slot);
}
lcd_rm_cspace(cspace);
LCD_PASS();
/*
* LOCK cap
*/
lcd_cap_lock();
if (__lcd_cnode_lookup(cspace, cptr, &cnode)) {
LCD_ERR("lookup");
goto fail_unlock;
}
if (!__lcd_cnode_is_sync_ep(cnode)) {
LCD_ERR("cnode not sync ep");
goto fail_unlock;
}
if (__lcd_cnode_rights(cnode) != LCD_CAP_RIGHT_WRITE) {
LCD_ERR("cnode rights not write");
goto fail_unlock;
}
if (__lcd_cnode_object(cnode) != &x) {
LCD_ERR("cnode bad object");
goto fail_unlock;
}
__lcd_rm_cspace(&cspace);
/*
* UNLOCK cap
*/
lcd_cap_unlock();
return 0;
fail_unlock:
/*
* UNLOCK cap
*/
lcd_cap_unlock();
fail:
return test_rm_cspace(cspace, -1);
}
static int test04(void)
{
struct cspace *cspace;
cptr_t cptr;
int i;
struct cspace *cspace1;
struct cspace *cspace2;
struct cspace *cspace3;
cptr_t cptr1;
cptr_t cptr2;
cptr_t cptr3;
int x;
struct cnode *cnode;
if (lcd_mk_cspace(&cspace))
LCD_FAIL("mk cspace");
for (i = 0; i < 5; i++) {
if (lcd_cap_alloc(cspace, &cptr)) {
lcd_rm_cspace(cspace);
LCD_FAIL("cap alloc");
}
/*
* MAKE CSPACES
*/
if (lcd_mk_cspace(&cspace1))
LCD_FAIL("mk cspace1");
if (lcd_mk_cspace(&cspace2)) {
LCD_ERR("mk cspace2");
goto fail1;
}
/* cptr = 4 */
x = 517;
if (lcd_cap_insert(cspace, cptr, &x, LCD_CAP_TYPE_SYNC_EP)) {
lcd_rm_cspace(cspace);
LCD_FAIL("insert");
if (lcd_mk_cspace(&cspace3)) {
LCD_ERR("mk cspace3");
goto fail2;
}
if (lcd_cnode_lookup(cspace, cptr, &cnode)) {
lcd_rm_cspace(cspace);
LCD_FAIL("lookup");
/*
* ALLOC SLOTS IN EACH FOR CAP
*/
if (lcd_cap_alloc(cspace1, &cptr1)) {
LCD_ERR("alloc cptr1");
goto fail3;
}
if (cnode->type != LCD_CAP_TYPE_SYNC_EP ||
cnode->object != &x) {
lcd_rm_cspace(cspace);
LCD_FAIL("cnode type = %d, object addr = %p",
cnode->type, cnode->object);
if (lcd_cap_alloc(cspace2, &cptr2)) {
LCD_ERR("alloc cptr2");
goto fail3;
}
if (lcd_cap_alloc(cspace3, &cptr3)) {
LCD_ERR("alloc cptr3");
goto fail3;
}
/*
* INSERT OBJECT INTO CSPACE 1
*/
x = 519;
if (lcd_cnode_insert(cspace1, cptr1, &x, LCD_CAP_TYPE_SYNC_EP,
LCD_CAP_RIGHT_ALL)) {
LCD_ERR("insert cspace1");
goto fail3;
}
lcd_rm_cspace(cspace);
LCD_PASS();
}
static int test05(void)
{
struct cspace *src_cspace;
struct cspace *dest_cspace;
cptr_t src_cptr, dest_cptr;
int i;
int x;
struct cnode *cnode;
/*
* GRANT RIGHTS
*/
if (lcd_mk_cspace(&src_cspace))
LCD_FAIL("mk src cspace");
if (lcd_mk_cspace(&dest_cspace))
LCD_FAIL("mk dest cspace");
for (i = 0; i < 5; i++) {
if (lcd_cap_alloc(src_cspace, &src_cptr)) {
lcd_rm_cspace(src_cspace);
lcd_rm_cspace(dest_cspace);
LCD_FAIL("src cap alloc");
}
}
for (i = 0; i < 3; i++) {
if (lcd_cap_alloc(dest_cspace, &dest_cptr)) {
lcd_rm_cspace(src_cspace);
lcd_rm_cspace(dest_cspace);
LCD_FAIL("dest cap alloc");
}
}
/* src_cptr = 4, dest_ctpr = 2 */
x = 517;
if (lcd_cap_insert(src_cspace, src_cptr, &x, LCD_CAP_TYPE_SYNC_EP)) {
lcd_rm_cspace(src_cspace);
lcd_rm_cspace(dest_cspace);
LCD_FAIL("insert");
}
if (lcd_cap_grant(src_cspace, dest_cspace, src_cptr, dest_cptr)) {
lcd_rm_cspace(src_cspace);
lcd_rm_cspace(dest_cspace);
LCD_FAIL("grant");
}
if (lcd_cnode_lookup(dest_cspace, dest_cptr, &cnode)) {
lcd_rm_cspace(src_cspace);
lcd_rm_cspace(dest_cspace);
LCD_FAIL("lookup");
}
if (cnode->type != LCD_CAP_TYPE_SYNC_EP ||
cnode->object != &x) {
lcd_rm_cspace(src_cspace);
lcd_rm_cspace(dest_cspace);
LCD_FAIL("cnode type = %d, object addr = %p",
cnode->type, cnode->object);
}
lcd_rm_cspace(src_cspace);
lcd_rm_cspace(dest_cspace);
/*
* Grant write and read to cspace 2
*/
if (lcd_cnode_grant(cspace1, cspace2, cptr1, cptr2,
LCD_CAP_RIGHT_WRITE | LCD_CAP_RIGHT_READ)) {
LCD_ERR("grant 1 to 2");
goto fail3;
}
/*
* Grant read to cspace 3
*/
if (lcd_cnode_grant(cspace2, cspace3, cptr2, cptr3,
LCD_CAP_RIGHT_READ)) {
LCD_ERR("grant 2 to 3");
goto fail3;
}
/*
* Check
*/
test_check_cnode(cspace1, cptr1, &x, LCD_CAP_TYPE_SYNC_EP,
LCD_CAP_RIGHT_ALL);
test_check_cnode(cspace2, cptr2, &x, LCD_CAP_TYPE_SYNC_EP,
LCD_CAP_RIGHT_WRITE | LCD_CAP_RIGHT_READ);
test_check_cnode(cspace3, cptr3, &x, LCD_CAP_TYPE_SYNC_EP,
LCD_CAP_RIGHT_READ);
/*
* Revoke read
*/
if (lcd_cnode_revoke(cspace1, cptr1, LCD_CAP_RIGHT_READ)) {
LCD_ERR("revoke read");
goto fail3;
}
/*
* Check
*/
test_check_cnode(cspace1, cptr1, &x, LCD_CAP_TYPE_SYNC_EP,
LCD_CAP_RIGHT_ALL);
test_check_cnode(cspace2, cptr2, &x, LCD_CAP_TYPE_SYNC_EP,
LCD_CAP_RIGHT_WRITE);
test_check_cnode(cspace3, cptr3, &x, LCD_CAP_TYPE_SYNC_EP, 0);
/*
* Free cap
*/
lcd_cap_lock();
if (lcd_cnode_lookup(cspace1, cptr1, &cnode)) {
LCD_ERR("cspace1 cnode lookup");
goto fail3_unlock;
}
__lcd_cnode_free(cnode);
lcd_cap_unlock();
/*
* Check
*/
test_check_cnode(cspace1, cptr1, &x, LCD_CAP_TYPE_FREE, 0);
test_check_cnode(cspace2, cptr2, &x, LCD_CAP_TYPE_FREE, 0);
test_check_cnode(cspace3, cptr3, &x, LCD_CAP_TYPE_FREE, 0);
/*
* rm cspaces
*/
test_rm_cspace(cspace1, 0);
test_rm_cspace(cspace2, 0);
test_rm_cspace(cspace3, 0);
LCD_PASS();
}
#endif
fail3_unlock:
lcd_cap_unlock();
fail3:
test_rm_cspace(cspace3, -1);
fail2:
test_rm_cspace(cspace2, -1);
fail1:
return test_rm_cspace(cspace1, -1);
}
int api_tests(void)
{
......@@ -301,10 +407,8 @@ int api_tests(void)
return -1;
if (test03())
return -1;
/* if (test04()) */
/* return -1; */
/* if (test05()) */
/* return -1; */
if (test04())
return -1;
LCD_MSG("all api tests passed!");
return 0;
}
......@@ -286,9 +286,10 @@ static void __lcd_cnode_do_free(struct cnode *parent)
list_del_init(&child->child_list);
}
/*
* Mark parent as free
* Mark parent as free, and remove all rights
*/
__lcd_cnode_set_type(parent, LCD_CAP_TYPE_FREE);
__lcd_cnode_set_rights(parent, LCD_CAP_RIGHT_NONE);
/*
* Add to containing cspace free list
*/
......
......@@ -92,6 +92,7 @@ enum lcd_cap_right {
LCD_CAP_RIGHT_OWNER = (1 << 3),
};
#define LCD_CAP_RIGHT_ALL ((1 << 4) - 1)
#define LCD_CAP_RIGHT_NONE 0
struct cspace;
......@@ -211,6 +212,23 @@ static inline int __lcd_cnode_rights(struct cnode *cnode)
{
return cnode->rights;
}
static inline void __lcd_cnode_set_rights(struct cnode *cnode, int rights)
{
cnode->rights = rights;
}
static inline int __lcd_cnode_type(struct cnode *cnode)
{
return cnode->type;
}
static inline void __lcd_cnode_set_type(struct cnode *cnode,
enum lcd_cap_type t)
{
cnode->type = t;
}
static inline void * __lcd_cnode_object(struct cnode *cnode)
{
return cnode->object;
}
static inline int __lcd_cnode_can_read(struct cnode *cnode)
{
return cnode->rights & LCD_CAP_RIGHT_READ;
......@@ -243,15 +261,6 @@ static inline int __lcd_cnode_is_sync_ep(struct cnode *cnode)
{
return cnode->type == LCD_CAP_TYPE_SYNC_EP;
}
static inline void __lcd_cnode_set_type(struct cnode *cnode,
enum lcd_cap_type t)
{
cnode->type = t;
}
static inline void * __lcd_cnode_object(struct cnode *cnode)
{
return cnode->object;
}
/* IPC -------------------------------------------------- */
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment