Commit 78c58e54 authored by Pankaj Kumar's avatar Pankaj Kumar

Ported capability stuff to userspace

parent 8d710ddb
############################
## ##
## liblcd ##
## ##
############################
ccflags-y += -Werror
lib-y += $(addprefix src/, cap.o grant_cap.o cptr_cache.c)
#ifndef LCD_DOMAINS_INTERNAL_H
#define LCD_DOMAINS_INTERNAL_H
#include <stdint.h>
#include "types.h"
#include "list.h"
#include <pthread.h>
#include <stdlib.h>
#include <stdarg.h>
/* There is a lot of LCD code which is not required.
* I will be removing the unnecessary stuff.
*/
#include <linux/module.h>
#include <linux/sched.h>
#include <linux/types.h>
#include <linux/spinlock.h>
#include <asm/lcd-domains/lcd-domains.h>
#include <lcd-domains/types.h>
#include <lcd-domains/utcb.h>
#include <lcd-domains/syscall.h>
typedef uint64_t u64;
typedef struct {
int counter;
} atomic_t;
/* --------------------------------------------------
* DEBUG
* --------------------------------------------------
......@@ -22,27 +26,51 @@
static inline void __lcd_err(char *file, int lineno, char *fmt, ...)
{
va_list args;
#ifdef KERNEL
printk(KERN_ERR "lcd-domains: %s:%d: error: ", file, lineno);
#else
printf("lcd-domains: %s:%d: error: ", file, lineno);
#endif
va_start(args, fmt);
#ifdef KERNEL
vprintk(fmt, args);
#else
printf(fmt, args);
#endif
va_end(args);
}
#define LCD_MSG(msg...) __lcd_msg(__FILE__, __LINE__, msg)
static inline void __lcd_msg(char *file, int lineno, char *fmt, ...)
{
va_list args;
#ifdef KERNEL
printk(KERN_ERR "lcd-domains: %s:%d: note: ", file, lineno);
#else
printf("lcd-domains: %s:%d: note: ", file, lineno);
#endif
va_start(args, fmt);
#ifdef KERNEL
vprintk(fmt, args);
#else
printf(fmt, args);
#endif
va_end(args);
}
#define LCD_WARN(msg...) __lcd_warn(__FILE__, __LINE__, msg)
static inline void __lcd_warn(char *file, int lineno, char *fmt, ...)
{
va_list args;
#ifdef KERNEL
printk(KERN_ERR "lcd-domains: %s:%d: warning: ", file, lineno);
#else
printf("lcd-domains: %s:%d: warning: ", file, lineno);
#endif
va_start(args, fmt);
#ifdef KERNEL
vprintk(fmt, args);
#else
printf(fmt, args);
#endif
va_end(args);
}
......@@ -58,9 +86,17 @@ static inline void __lcd_warn(char *file, int lineno, char *fmt, ...)
static inline void __lcd_debug(char *file, int lineno, char *fmt, ...)
{
va_list args;
#ifdef KERNEL
printk(KERN_ERR "lcd-domains: %s:%d: debug: ", file, lineno);
#else
printf("lcd-domains: %s:%d: debug: ", file, lineno);
#endif
va_start(args, fmt);
#ifdef KERNEL
vprintk(fmt, args);
#else
printf(fmt, args);
#endif
va_end(args);
}
......@@ -101,14 +137,22 @@ enum allocation_state {
struct cnode;
struct cdt_root_node {
#ifdef KERNEL
struct mutex lock;
#else
pthread_mutex_t lock;
#endif
struct cnode *cnode;
enum allocation_state state;
};
struct cspace;
struct cnode {
#ifdef KERNEL
struct mutex lock;
#else
pthread_mutex_t lock;
#endif
/*
* cnode data
*/
......@@ -142,10 +186,18 @@ struct cnode_table {
};
struct cspace {
#ifdef KERNEL
struct mutex lock;
#else
pthread_mutex_t lock;
#endif
enum allocation_state state;
struct cnode_table *cnode_table;
#ifdef KERNEL
struct kmem_cache *cnode_table_cache;
#else
void * cnode_table_cache;
#endif
struct list_head table_list;
};
......@@ -244,7 +296,11 @@ struct lcd {
*
* (Pray for me that I will not get deadlocks)
*/
#ifdef KERNEL
struct mutex lock;
#else
pthread_mutex_t lock;
#endif
/*
* Status
*/
......@@ -338,7 +394,11 @@ struct lcd {
struct lcd_sync_endpoint {
struct list_head senders;
struct list_head receivers;
#ifdef KERNEL
struct mutex lock;
#else
pthread_mutex_t lock;
#endif
};
/* KLCD STUFF -------------------------------------------------- */
......@@ -384,9 +444,13 @@ int __lcd_reply(struct lcd *caller);
* destroy routine below.
*/
void __lcd_sync_endpoint_check(struct lcd *lcd, struct lcd_sync_endpoint *e);
void __lcd_page_check(struct lcd *lcd, struct page *p, int is_mapped,
/*void __lcd_page_check(struct lcd *lcd, struct page *p, int is_mapped,
gpa_t where_mapped);*/
void __lcd_page_check(struct lcd *lcd, void *p, int is_mapped,
gpa_t where_mapped);
void __lcd_kpage_check(struct lcd *lcd, struct page *p, int is_mapped,
/*void __lcd_kpage_check(struct lcd *lcd, struct page *p, int is_mapped,
gpa_t where_mapped);*/
void __lcd_kpage_check(struct lcd *lcd, void *p, int is_mapped,
gpa_t where_mapped);
void __lcd_check(struct lcd *owning_lcd, struct lcd *owned_lcd);
......@@ -395,8 +459,10 @@ void __lcd_check(struct lcd *owning_lcd, struct lcd *owned_lcd);
* away.
*/
void __lcd_sync_endpoint_destroy(struct lcd_sync_endpoint *e);
void __lcd_page_destroy(struct page *p);
void __lcd_kpage_destroy(struct page *p);
//void __lcd_page_destroy(struct page *p);
void __lcd_page_destroy(void *p);
//void __lcd_kpage_destroy(struct page *p);
void __lcd_kpage_destroy(void *p);
void __lcd_destroy(struct lcd *owned_lcd);
void __lcd_destroy__(struct lcd *owned_lcd);
......
......@@ -12,8 +12,6 @@
#ifndef LCD_DOMAINS_KLIBLCD_H
#define LCD_DOMAINS_KLIBLCD_H
#include <lcd-domains/types.h>
#include <lcd-domains/utcb.h>
#include <linux/sched.h>
/* KLIBLCD INTERNALS -------------------------------------------------- */
......
This diff is collapsed.
......@@ -9,7 +9,6 @@
#define LCD_DOMAINS_TYPES_H
#include <linux/kernel.h>
#include <asm/page.h>
/* CPTRs -------------------------------------------------- */
......@@ -233,6 +232,9 @@ struct lcd_boot_info_for_page {
* Hack for now to make boot easier, used in liblcd/lcd/cap.c for cptr
* cache.
*/
#define DIV_ROUND_UP(n,d) (((n) + (d) - 1) / (d))
#define BITS_PER_BYTE 8
#define BITS_TO_LONGS(nr) DIV_ROUND_UP(nr, BITS_PER_BYTE * sizeof(long))
#define LCD_BMAP0_SIZE (1 << (LCD_CPTR_SLOT_BITS + 0 * LCD_CPTR_FANOUT_BITS))
#define LCD_BMAP1_SIZE (1 << (LCD_CPTR_SLOT_BITS + 1 * LCD_CPTR_FANOUT_BITS))
......
This diff is collapsed.
......@@ -3,16 +3,79 @@
*
* Authors:
* Charlie Jacobsen <charlesj@cs.utah.edu>
* Pankaj Kumar <pankajk@cs.utah.edu>
*/
#include <linux/slab.h>
#include <lcd-domains/kliblcd.h>
#include <lcd-domains/utcb.h>
#include <lcd-domains/types.h>
#include <linux/mutex.h>
#include "../internal.h"
#include "../include/internal.h"
#include "../include/types.h"
#include "../include/list.h"
#define ENOMEM 1
static int cptr_cache_init(struct cptr_cache **out)
#ifndef __WORDSIZE
#define __WORDSIZE (sizeof(long) * 8)
#endif
#define BITS_PER_LONG __WORDSIZE
#define BIT_MASK(nr) (1UL << ((nr) % BITS_PER_LONG))
#define BIT_WORD(nr) ((nr) / BITS_PER_LONG)
#define BITS_PER_BYTE 8
/*#define BITS_TO_LONGS(nr) DIV_ROUND_UP(nr, BITS_PER_BYTE * sizeof(long))
#define BITS_TO_U64(nr) DIV_ROUND_UP(nr, BITS_PER_BYTE * sizeof(u64))
#define BITS_TO_U32(nr) DIV_ROUND_UP(nr, BITS_PER_BYTE * sizeof(u32))
#define BITS_TO_BYTES(nr) DIV_ROUND_UP(nr, BITS_PER_BYTE)
*/
#ifndef min
#define min(x, y) ({ \
typeof(x) _min1 = (x); \
typeof(y) _min2 = (y); \
(void) (&_min1 == &_min2); \
_min1 < _min2 ? _min1 : _min2; })
#endif
static inline void set_bit(int nr, volatile unsigned long *addr)
{
unsigned long mask = BIT_MASK(nr);
unsigned long *p = ((unsigned long *)addr) + BIT_WORD(nr);
unsigned long flags;
// _atomic_spin_lock_irqsave(p, flags); Need to find counter parts!!
*p |= mask;
// _atomic_spin_unlock_irqrestore(p, flags);
}
static inline void clear_bit(int nr, volatile unsigned long *addr)
{
unsigned long mask = BIT_MASK(nr);
unsigned long *p = ((unsigned long *)addr) + BIT_WORD(nr);
unsigned long flags;
// _atomic_spin_lock_irqsave(p, flags);
*p &= ~mask;
// _atomic_spin_unlock_irqrestore(p, flags);
}
static inline unsigned long ffz(unsigned long word)
{
asm("rep; bsf %1,%0"
: "=r" (word)
: "r" (~word));
return word;
}
unsigned long find_first_zero_bit(const unsigned long *addr, unsigned long size)
{
unsigned long idx;
for (idx = 0; idx * BITS_PER_LONG < size; idx++) {
if (addr[idx] != ~0UL)
return min(idx * BITS_PER_LONG + ffz(addr[idx]), size);
}
return size;
}
int cptr_cache_init(struct cptr_cache **out)
{
struct cptr_cache *cache;
int ret;
......@@ -21,9 +84,15 @@ static int cptr_cache_init(struct cptr_cache **out)
/*
* Allocate the container
*/
#ifdef KERNEL
cache = kzalloc(sizeof(*cache), GFP_KERNEL);
#else
//cache = (struct cptr_cache *) malloc(1 * sizeof(struct cptr_cache));
cache = (struct cptr_cache *) malloc(1 * sizeof(*cache));
#endif
if (!cache) {
ret = -ENOMEM;
//ret = -ENOMEM;
ret = -1;
goto fail1;
}
/*
......@@ -40,9 +109,14 @@ static int cptr_cache_init(struct cptr_cache **out)
/*
* Alloc bitmap
*/
#ifdef KERNEL
cache->bmaps[i] = kzalloc(sizeof(unsigned long) *
BITS_TO_LONGS(nbits),
GFP_KERNEL);
#else
cache->bmaps[i] = malloc(sizeof(unsigned long) *
BITS_TO_LONGS(nbits));
#endif
if (!cache->bmaps[i]) {
ret = -ENOMEM;
goto fail2; /* i = level we failed at */
......@@ -61,8 +135,13 @@ static int cptr_cache_init(struct cptr_cache **out)
fail2:
for (j = 0; j < i; j++)
#ifdef KERNEL
kfree(cache->bmaps[j]);
kfree(cache);
#else
free(cache->bmaps[j]);
free(cache);
#endif
fail1:
return ret;
}
......@@ -74,14 +153,19 @@ static void cptr_cache_destroy(struct cptr_cache *cache)
* Free bitmaps
*/
for (i = 0; i < (1 << LCD_CPTR_DEPTH_BITS); i++)
#ifdef KERNEL
kfree(cache->bmaps[i]);
/*
* Free container
*/
kfree(cache);
#else
free(cache->bmaps[i]);
free(cache);
#endif
}
static int __lcd_alloc_cptr_from_bmap(unsigned long *bmap, int size,
int __lcd_alloc_cptr_from_bmap(unsigned long *bmap, int size,
unsigned long *out)
{
unsigned long idx;
......@@ -167,12 +251,17 @@ void __klcd_free_cptr(struct cptr_cache *cptr_cache, cptr_t c)
int klcd_alloc_cptr(cptr_t *free_slot)
{
return __lcd_alloc_cptr(current->cptr_cache, free_slot);
struct cptr_cache *cache;
//return __lcd_alloc_cptr(current->cptr_cache, free_slot);
//return __lcd_alloc_cptr(cache, free_slot);
return 0;
}
void klcd_free_cptr(cptr_t c)
{
__lcd_free_cptr(current->cptr_cache, c);
struct cptr_cache *cache;
//__lcd_free_cptr(current->cptr_cache, c);
//__lcd_free_cptr(cache, c);
}
int klcd_init_cptr(struct cptr_cache **c_out)
......@@ -184,10 +273,3 @@ void klcd_destroy_cptr(struct cptr_cache *c)
{
cptr_cache_destroy(c);
}
/* EXPORTS -------------------------------------------------- */
EXPORT_SYMBOL(__klcd_alloc_cptr);
EXPORT_SYMBOL(__klcd_free_cptr);
EXPORT_SYMBOL(klcd_alloc_cptr);
EXPORT_SYMBOL(klcd_free_cptr);
#include <lcd-domains/types.h>
#include "../internal.h"
#include "../include/types.h"
#include "../include/internal.h"
/*
* Regular grant.
......@@ -14,20 +14,23 @@
*
* 1. Resolve process A to cspace A
* 2. Resolve process B to cspace B
* 3. Invoke grant function in the library (libcap):
* 3. Invoke grant function in the library (libcap).
*
* This entire functionality has te be tested yet!!
* I am testing it and will add the testing results.
*/
static int libcap_grant_capability(void *s_cspace, void *d_cspace,
unsigned long s_cptr, unsigned long d_cptr)
cptr_t s_cptr, cptr_t d_cptr)
{
int ret;
struct cspace *src_cspace = (struct cspace *) s_cspace;
struct cspace *dest_cspace = (struct cspace *) d_cspace;
cptr_c src_cptr = (cptr_c) s_cptr;
cptr_c dest_cptr = (cptr_c) d_cptr;
cptr_t src_cptr = s_cptr;
cptr_t dest_cptr = d_cptr;
if (cptr_is_null(c_src) || cptr_is_null(c_dst)) {
if (cptr_is_null(src_cptr) || cptr_is_null(dest_cptr)) {
LCD_ERR("trying to grant with a null cptr");
return -EINVAL;
return -1;
}
......
CC = cc
libdir = ../lib
flags = -lpthread -lcap -L $(libdir)
all:
$(CC) -g -o test-cap cap-stuff.c $(flags)
#include <stdio.h>
#include "../include/internal.h"
#include "../include/types.h"
#include <string.h>
#define ENOMEM 1
/*
* A testcase to check:
* 1. Cspace initialization
* 2. cptr cache initialization (User's stuff)
* 3. Capability insertion in scpace
* 4. Lookup after insertion
* 5. Capability deletion (Here i am getting a locking issue)
* 6. Capability Grant (Todo)
*
* For quick testing, I have embedded the code in one function.
* I will subsequently break down the code in different functions.
*
*/
int testcase1()
{
int ret;
struct cspace * csp;
struct cnode *cnode;
cptr_t slot_out, slot_out_orig;
struct cptr_cache *cache;
char *p;
struct cnode *check;
struct cnode *check1;
/* Initialize a cspace */
csp = malloc(1 * sizeof(*csp));
__lcd_cap_init_cspace(csp);
printf("Initialized cspace Address:%p\n", csp);
/* cptr cache intialization. This is totally users stuff */
cache = malloc (1 * sizeof(*cache));
ret = cptr_cache_init(&cache);
ret = __klcd_alloc_cptr(cache, &slot_out);
p = malloc(sizeof(char) * 4);
if (!p) {
LCD_ERR("alloc failed");
ret = -ENOMEM;
goto fail;
}
memset(p, 0, 4);
/* Insert capability in cspace */
ret = __lcd_cap_insert(csp, slot_out, p, LCD_CAP_TYPE_PAGE);
if (ret) {
LCD_ERR("set up cspace");
goto fail;
}
/* Verification if capability is properly inserted in the cspace. */
ret = __lcd_cnode_get(csp, slot_out, &check);
if (ret < 0) {
LCD_ERR("Lookup failed");
goto fail;
} else {
if (check->object == p)
printf("Capability Lookup Passed\n");
else
printf("Capability lookup failed!!!\n");
}
/* Capability deletion from cspace.
* Presently, I am getting an issue in this functionality.
* Some locking issue. I am working on it.
* For now, I am commenting the code.
*/
/*
slot_out_orig = slot_out;
__lcd_cap_delete(csp, slot_out);
printf("Old=%p New=%p\n", slot_out_orig, slot_out);
//Lookup
ret = __lcd_cnode_get(csp, slot_out, &check1);
if (ret < 0) {
LCD_ERR("Lookup failed");
goto fail;
} else {
if (check->object == p)
printf("Screwed!!!\n");
else
printf("Yippiee!!!\n");
}
*/
fail:
/* Free memory stuff. */
return ret;
}
int main()
{
int ret;
ret = testcase1();
}
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