aboutsummaryrefslogtreecommitdiffstats
path: root/xenolinux-2.4.21-pre4-sparse
diff options
context:
space:
mode:
authorkaf24@labyrinth.cl.cam.ac.uk <kaf24@labyrinth.cl.cam.ac.uk>2003-03-03 15:43:22 +0000
committerkaf24@labyrinth.cl.cam.ac.uk <kaf24@labyrinth.cl.cam.ac.uk>2003-03-03 15:43:22 +0000
commitdfca2c82d597482bab554fd1256cdb13154efba7 (patch)
tree8c4c3d724d509a1e14015f139cdde1d8b51cb4d5 /xenolinux-2.4.21-pre4-sparse
parent4f13d2a61fc684ddbc11d482f91f8c6cc788fd9e (diff)
parentf456b7444e6fa5a931a76960606bf0b4bc9b26fa (diff)
downloadxen-dfca2c82d597482bab554fd1256cdb13154efba7.tar.gz
xen-dfca2c82d597482bab554fd1256cdb13154efba7.tar.bz2
xen-dfca2c82d597482bab554fd1256cdb13154efba7.zip
bitkeeper revision 1.105.1.8 (3e63781aEVDfQh1rIWk8m6mnaO7HtA)
Merge labyrinth.cl.cam.ac.uk:/usr/groups/xeno/BK/xeno.bk into labyrinth.cl.cam.ac.uk:/local/scratch/kaf24/bd-xeno
Diffstat (limited to 'xenolinux-2.4.21-pre4-sparse')
-rw-r--r--xenolinux-2.4.21-pre4-sparse/arch/xeno/Makefile5
-rw-r--r--xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/balloon/Makefile3
-rw-r--r--xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/balloon/balloon.c275
-rw-r--r--xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/balloon/dom_mem_ops.h32
-rw-r--r--xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/dom0/dom0_core.c2
-rw-r--r--xenolinux-2.4.21-pre4-sparse/include/asm-xeno/hypervisor.h11
-rw-r--r--xenolinux-2.4.21-pre4-sparse/include/asm-xeno/page.h4
7 files changed, 331 insertions, 1 deletions
diff --git a/xenolinux-2.4.21-pre4-sparse/arch/xeno/Makefile b/xenolinux-2.4.21-pre4-sparse/arch/xeno/Makefile
index 544af84605..557fe98217 100644
--- a/xenolinux-2.4.21-pre4-sparse/arch/xeno/Makefile
+++ b/xenolinux-2.4.21-pre4-sparse/arch/xeno/Makefile
@@ -47,12 +47,14 @@ HEAD := arch/xeno/kernel/head.o arch/xeno/kernel/init_task.o
SUBDIRS += arch/xeno/kernel arch/xeno/mm arch/xeno/lib
SUBDIRS += arch/xeno/drivers/console arch/xeno/drivers/network
SUBDIRS += arch/xeno/drivers/dom0 arch/xeno/drivers/block
+SUBDIRS += arch/xeno/drivers/balloon
CORE_FILES += arch/xeno/kernel/kernel.o arch/xeno/mm/mm.o
CORE_FILES += arch/xeno/drivers/console/con.o
CORE_FILES += arch/xeno/drivers/block/blk.o
CORE_FILES += arch/xeno/drivers/network/net.o
CORE_FILES += arch/xeno/drivers/dom0/dom0.o
+CORE_FILES += arch/xeno/drivers/balloon/balloon_driver.o
LIBS := $(TOPDIR)/arch/xeno/lib/lib.a $(LIBS) $(TOPDIR)/arch/xeno/lib/lib.a
arch/xeno/kernel: dummy
@@ -73,6 +75,9 @@ arch/xeno/drivers/block: dummy
arch/xeno/drivers/dom0: dummy
$(MAKE) linuxsubdirs SUBDIRS=arch/xeno/drivers/dom0
+arch/xeno/drivers/balloon: dummy
+ $(MAKE) linuxsubdirs SUBDIRS=arch/xeno/drivers/balloon
+
MAKEBOOT = $(MAKE) -C arch/$(ARCH)/boot
vmlinux: arch/xeno/vmlinux.lds
diff --git a/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/balloon/Makefile b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/balloon/Makefile
new file mode 100644
index 0000000000..f780a515e0
--- /dev/null
+++ b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/balloon/Makefile
@@ -0,0 +1,3 @@
+O_TARGET := balloon_driver.o
+obj-y := balloon.o
+include $(TOPDIR)/Rules.make
diff --git a/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/balloon/balloon.c b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/balloon/balloon.c
new file mode 100644
index 0000000000..abe5884800
--- /dev/null
+++ b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/balloon/balloon.c
@@ -0,0 +1,275 @@
+/******************************************************************************
+ * balloon.c
+ *
+ * Xeno balloon driver - enables returning/claiming memory to/from xen
+ *
+ * Copyright (c) 2003, B Dragovic
+ */
+
+#include <linux/config.h>
+#include <linux/module.h>
+#include <linux/kernel.h>
+#include <linux/sched.h>
+#include <linux/errno.h>
+#include <linux/proc_fs.h>
+
+#include <linux/mm.h>
+#include <linux/mman.h>
+#include <linux/smp_lock.h>
+#include <linux/pagemap.h>
+
+#include <asm/hypervisor.h>
+#include <asm/pgalloc.h>
+#include <asm/pgtable.h>
+#include <asm/uaccess.h>
+#include <asm/tlb.h>
+
+#include "dom_mem_ops.h"
+
+/* USER DEFINES -- THESE SHOULD BE COPIED TO USER-SPACE TOOLS */
+#define USER_INFLATE_BALLOON 1 /* return mem to hypervisor */
+#define USER_DEFLATE_BALLOON 2 /* claim mem from hypervisor */
+typedef struct user_balloon_op {
+ unsigned int op;
+ unsigned long size;
+} user_balloon_op_t;
+/* END OF USER DEFINE */
+
+/* Dead entry written into ballon-owned entries in the PMT. */
+#define DEAD 0xdeadbeef
+
+#define BALLOON_ENTRY "balloon"
+extern struct proc_dir_entry *xeno_base;
+
+static struct proc_dir_entry *balloon_pde;
+unsigned long credit;
+
+static inline unsigned long get_ppte(unsigned long addr)
+{
+ unsigned long ppte;
+ pgd_t *pgd; pmd_t *pmd; pte_t *ptep;
+ pgd = pgd_offset_k(addr);
+
+ if ( pgd_none(*pgd) || pgd_bad(*pgd) ) BUG();
+
+ pmd = pmd_offset(pgd, addr);
+ if ( pmd_none(*pmd) || pmd_bad(*pmd) ) BUG();
+
+ ptep = pte_offset(pmd, addr);
+ ppte = (unsigned long)__pa(ptep);
+
+ return ppte;
+}
+
+/* main function for relinquishing bit of memory */
+static unsigned long inflate_balloon(unsigned long num_pages)
+{
+ dom_mem_op_t dom_mem_op;
+ unsigned long *parray;
+ unsigned long *currp;
+ unsigned long ret = 0;
+ unsigned long vaddr;
+ unsigned long i, j;
+
+ parray = (unsigned long *)kmalloc(num_pages *
+ sizeof(unsigned long), GFP_KERNEL);
+ currp = parray;
+
+ for ( i = 0; i < num_pages; i++ )
+ {
+ /* try to obtain a free page, has to be done with GFP_ATOMIC
+ * as we do not want to sleep indefinately.
+ */
+ vaddr = __get_free_page(GFP_ATOMIC);
+
+ /* if allocation fails, free all reserved pages */
+ if(!vaddr){
+ printk("Unable to inflate balloon by %ld, only %ld pages free.",
+ num_pages, i);
+ currp = parray;
+ for(j = 0; j < i; j++){
+ free_page(*currp++);
+ }
+ goto cleanup;
+ }
+
+ *currp++ = vaddr;
+ }
+
+
+ currp = parray;
+ for ( i = 0; i < num_pages; i++ )
+ {
+ queue_l1_entry_update(get_ppte(*currp) | PGREQ_NORMAL, 0);
+ phys_to_machine_mapping[__pa(*currp) >> PAGE_SHIFT] = DEAD;
+ currp++;
+ }
+
+ XENO_flush_page_update_queue();
+
+ dom_mem_op.op = BALLOON_INFLATE_OP;
+ dom_mem_op.u.balloon_inflate.size = num_pages;
+ dom_mem_op.u.balloon_inflate.pages = parray;
+ if ( (ret = HYPERVISOR_dom_mem_op(&dom_mem_op)) != num_pages )
+ {
+ printk("Unable to deflate balloon, error %lx\n", ret);
+ goto cleanup;
+ }
+
+ credit += num_pages;
+ ret = num_pages;
+
+ cleanup:
+ kfree(parray);
+
+ return ret;
+}
+
+/* install new mem pages obtained by deflate_balloon. function walks
+ * phys->machine mapping table looking for DEAD entries and populates
+ * them.
+ */
+static unsigned long process_new_pages(unsigned long * parray,
+ unsigned long num)
+{
+ /* currently, this function is rather simplistic as
+ * it is assumed that domain reclaims only number of
+ * pages previously released. this is to change soon
+ * and the code to extend page tables etc. will be
+ * incorporated here.
+ */
+
+ unsigned long tot_pages = start_info.nr_pages;
+ unsigned long * curr = parray;
+ unsigned long num_installed;
+ unsigned long i;
+
+ num_installed = 0;
+ for ( i = 0; i < tot_pages; i++ )
+ {
+ if ( phys_to_machine_mapping[i] == DEAD )
+ {
+ phys_to_machine_mapping[i] = *curr;
+ queue_l1_entry_update((i << PAGE_SHIFT) | PGREQ_MPT_UPDATE, i);
+ queue_l1_entry_update(
+ get_ppte((unsigned long)__va(i << PAGE_SHIFT)) | PGREQ_NORMAL,
+ ((*curr) << PAGE_SHIFT) | L1_PROT);
+
+ *curr = (unsigned long)__va(i << PAGE_SHIFT);
+ curr++;
+ num_installed++;
+ }
+ }
+
+ /* now, this is tricky (and will also change for machine addrs that
+ * are mapped to not previously released addresses). we free pages
+ * that were allocated by get_free_page (the mappings are different
+ * now, of course).
+ */
+ curr = parray;
+ for ( i = 0; i < num_installed; i++ )
+ {
+ free_page(*curr);
+ curr++;
+ }
+
+ return num_installed;
+}
+
+static unsigned long deflate_balloon(unsigned long num_pages)
+{
+ dom_mem_op_t dom_mem_op;
+ unsigned long ret;
+ unsigned long * parray;
+
+ if ( num_pages > credit )
+ {
+ printk("Can not allocate more pages than previously released.\n");
+ return -EAGAIN;
+ }
+
+ parray = (unsigned long *)kmalloc(num_pages * sizeof(unsigned long),
+ GFP_KERNEL);
+
+ dom_mem_op.op = BALLOON_DEFLATE_OP;
+ dom_mem_op.u.balloon_deflate.size = num_pages;
+ dom_mem_op.u.balloon_deflate.pages = parray;
+ if((ret = HYPERVISOR_dom_mem_op(&dom_mem_op)) != num_pages){
+ printk("Unable to deflate balloon, error %lx\n", ret);
+ goto cleanup;
+ }
+
+ if((ret = process_new_pages(parray, num_pages)) < num_pages){
+ printk("Unable to deflate balloon by specified %lx pages, only %lx.\n",
+ num_pages, ret);
+ goto cleanup;
+ }
+
+ ret = num_pages;
+
+ cleanup:
+ kfree(parray);
+
+ return ret;
+}
+
+static int balloon_write(struct file *file, const char *buffer,
+ u_long count, void *data)
+{
+ user_balloon_op_t bop;
+
+ /* Only admin can play with the balloon :) */
+ if ( !capable(CAP_SYS_ADMIN) )
+ return -EPERM;
+
+ if ( copy_from_user(&bop, buffer, sizeof(bop)) )
+ return -EFAULT;
+
+ switch ( bop.op )
+ {
+ case USER_INFLATE_BALLOON:
+ if ( inflate_balloon(bop.size) < bop.size )
+ return -EAGAIN;
+ break;
+
+ case USER_DEFLATE_BALLOON:
+ deflate_balloon(bop.size);
+ break;
+
+ default:
+ printk("Unknown command to balloon driver.");
+ return -EFAULT;
+ }
+
+ return sizeof(bop);
+}
+
+/*
+ * main balloon driver initialization function.
+ */
+static int __init init_module(void)
+{
+ printk(KERN_ALERT "Starting Xeno Balloon driver\n");
+
+ credit = 0;
+
+ balloon_pde = create_proc_entry(BALLOON_ENTRY, 0600, xeno_base);
+ if ( balloon_pde == NULL )
+ {
+ printk(KERN_ALERT "Unable to create balloon driver proc entry!");
+ return -1;
+ }
+
+ balloon_pde->write_proc = balloon_write;
+
+ return 0;
+}
+
+static void __exit cleanup_module(void)
+{
+}
+
+module_init(init_module);
+module_exit(cleanup_module);
+
+
diff --git a/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/balloon/dom_mem_ops.h b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/balloon/dom_mem_ops.h
new file mode 100644
index 0000000000..c473f193e7
--- /dev/null
+++ b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/balloon/dom_mem_ops.h
@@ -0,0 +1,32 @@
+/******************************************************************************
+ * dom_mem_ops.h
+ *
+ * Header file supporting domain related memory operations. N.B. keep in sync
+ * with xen version.
+ *
+ * Copyright (c) 2003, B Dragovic
+ */
+
+#define L1_PROT (_PAGE_PRESENT|_PAGE_RW|_PAGE_USER|_PAGE_ACCESSED)
+#define BALLOON_DEFLATE_OP 0
+#define BALLOON_INFLATE_OP 1
+
+typedef struct balloon_deflate_op {
+ unsigned long size;
+ unsigned long * pages;
+} balloon_def_op_t;
+
+typedef struct balloon_inflate_op {
+ unsigned long size;
+ unsigned long * pages;
+} balloon_inf_op_t;
+
+typedef struct dom_mem_ops
+{
+ unsigned int op;
+ union
+ {
+ balloon_def_op_t balloon_deflate;
+ balloon_inf_op_t balloon_inflate;
+ }u;
+} dom_mem_op_t;
diff --git a/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/dom0/dom0_core.c b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/dom0/dom0_core.c
index f8af85358b..c36ab02e96 100644
--- a/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/dom0/dom0_core.c
+++ b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/dom0/dom0_core.c
@@ -53,7 +53,7 @@ typedef struct proc_mem_data {
#define MAP_DISCONT 1
-static struct proc_dir_entry *xeno_base;
+struct proc_dir_entry *xeno_base;
static struct proc_dir_entry *dom0_cmd_intf;
static struct proc_dir_entry *proc_ft;
diff --git a/xenolinux-2.4.21-pre4-sparse/include/asm-xeno/hypervisor.h b/xenolinux-2.4.21-pre4-sparse/include/asm-xeno/hypervisor.h
index df25598730..16f37cfe65 100644
--- a/xenolinux-2.4.21-pre4-sparse/include/asm-xeno/hypervisor.h
+++ b/xenolinux-2.4.21-pre4-sparse/include/asm-xeno/hypervisor.h
@@ -313,4 +313,15 @@ static inline int HYPERVISOR_set_fast_trap(int idx)
return ret;
}
+static inline int HYPERVISOR_dom_mem_op(void *dom_mem_op)
+{
+ int ret;
+ __asm__ __volatile__ (
+ TRAP_INSTR
+ : "=a" (ret) : "0" (__HYPERVISOR_dom_mem_op),
+ "b" (dom_mem_op) : "memory" );
+
+ return ret;
+}
+
#endif /* __HYPERVISOR_H__ */
diff --git a/xenolinux-2.4.21-pre4-sparse/include/asm-xeno/page.h b/xenolinux-2.4.21-pre4-sparse/include/asm-xeno/page.h
index e157a31a36..aad36820b7 100644
--- a/xenolinux-2.4.21-pre4-sparse/include/asm-xeno/page.h
+++ b/xenolinux-2.4.21-pre4-sparse/include/asm-xeno/page.h
@@ -173,6 +173,10 @@ static __inline__ int get_order(unsigned long size)
#define VM_DATA_DEFAULT_FLAGS (VM_READ | VM_WRITE | VM_EXEC | \
VM_MAYREAD | VM_MAYWRITE | VM_MAYEXEC)
+/* VIRT <-> MACHINE conversion */
+#define virt_to_machine(_a) (phys_to_machine(__pa(_a)))
+#define machine_to_virt(_m) (__va(machine_to_phys(_m)))
+
#endif /* __KERNEL__ */
#endif /* _I386_PAGE_H */