ia64/xen-unstable

changeset 2668:0c8e3e76fd4f

bitkeeper revision 1.1159.1.246 (41769031EO0QYVfh-w1e1Xv25hBTiA)

Make balloon driver work with 2.6 and with the control interface.
author mwilli2@equilibrium.research
date Wed Oct 20 16:20:01 2004 +0000 (2004-10-20)
parents 77b6b9acf383
children 081dd58e4d58
files linux-2.6.8.1-xen-sparse/drivers/xen/Makefile linux-2.6.8.1-xen-sparse/drivers/xen/balloon/balloon.c
line diff
     1.1 --- a/linux-2.6.8.1-xen-sparse/drivers/xen/Makefile	Wed Oct 20 16:18:05 2004 +0000
     1.2 +++ b/linux-2.6.8.1-xen-sparse/drivers/xen/Makefile	Wed Oct 20 16:20:01 2004 +0000
     1.3 @@ -3,6 +3,7 @@
     1.4  obj-y	+= console/
     1.5  obj-y	+= evtchn/
     1.6  obj-y	+= privcmd/
     1.7 +obj-y   += balloon/
     1.8  
     1.9  obj-$(CONFIG_XEN_BLKDEV_BACKEND)	+= blkback/
    1.10  obj-$(CONFIG_XEN_NETDEV_BACKEND)	+= netback/
     2.1 --- a/linux-2.6.8.1-xen-sparse/drivers/xen/balloon/balloon.c	Wed Oct 20 16:18:05 2004 +0000
     2.2 +++ b/linux-2.6.8.1-xen-sparse/drivers/xen/balloon/balloon.c	Wed Oct 20 16:20:01 2004 +0000
     2.3 @@ -11,7 +11,7 @@
     2.4  #include <linux/kernel.h>
     2.5  #include <linux/sched.h>
     2.6  #include <linux/errno.h>
     2.7 -#include <asm/xen_proc.h>
     2.8 +#include <asm-xen/xen_proc.h>
     2.9  
    2.10  #include <linux/mm.h>
    2.11  #include <linux/mman.h>
    2.12 @@ -21,7 +21,8 @@
    2.13  #include <linux/highmem.h>
    2.14  #include <linux/vmalloc.h>
    2.15  
    2.16 -#include <asm/hypervisor.h>
    2.17 +#include <asm-xen/hypervisor.h>
    2.18 +#include <asm-xen/ctrl_if.h>
    2.19  #include <asm/pgalloc.h>
    2.20  #include <asm/pgtable.h>
    2.21  #include <asm/uaccess.h>
    2.22 @@ -37,6 +38,7 @@ typedef struct user_balloon_op {
    2.23  /* END OF USER DEFINE */
    2.24  
    2.25  static struct proc_dir_entry *balloon_pde;
    2.26 +
    2.27  unsigned long credit;
    2.28  static unsigned long current_pages, most_seen_pages;
    2.29  
    2.30 @@ -56,7 +58,7 @@ static inline pte_t *get_ptep(unsigned l
    2.31      pmd = pmd_offset(pgd, addr);
    2.32      if ( pmd_none(*pmd) || pmd_bad(*pmd) ) BUG();
    2.33  
    2.34 -    ptep = pte_offset(pmd, addr);
    2.35 +    ptep = pte_offset_kernel(pmd, addr);
    2.36  
    2.37      return ptep;
    2.38  }
    2.39 @@ -256,7 +258,7 @@ static void pagetable_extend (int cur_lo
    2.40      end = (unsigned long)__va(low_pfn*PAGE_SIZE);
    2.41  
    2.42      pgd_base = init_mm.pgd;
    2.43 -    i = __pgd_offset(PAGE_OFFSET);
    2.44 +    i = pgd_index(PAGE_OFFSET);
    2.45      pgd = pgd_base + i;
    2.46  
    2.47      for (; i < PTRS_PER_PGD; pgd++, i++) {
    2.48 @@ -279,11 +281,11 @@ static void pagetable_extend (int cur_lo
    2.49                  vaddr = i*PGDIR_SIZE + j*PMD_SIZE + k*PAGE_SIZE;
    2.50                  if (end && (vaddr >= end))
    2.51                      break;
    2.52 -                *pte = mk_pte_phys(__pa(vaddr), PAGE_KERNEL);
    2.53 +                *pte = mk_pte(virt_to_page(vaddr), PAGE_KERNEL);
    2.54              }
    2.55              kpgd = pgd_offset_k((unsigned long)pte_base);
    2.56              kpmd = pmd_offset(kpgd, (unsigned long)pte_base);
    2.57 -            kpte = pte_offset(kpmd, (unsigned long)pte_base);
    2.58 +            kpte = pte_offset_kernel(kpmd, (unsigned long)pte_base);
    2.59              queue_l1_entry_update(kpte,
    2.60                                    (*(unsigned long *)kpte)&~_PAGE_RW);
    2.61              set_pmd(pmd, __pmd(_KERNPG_TABLE + __pa(pte_base)));
    2.62 @@ -313,7 +315,7 @@ claim_new_pages(unsigned long num_pages)
    2.63  
    2.64      if (most_seen_pages+num_pages> max_pfn)
    2.65          num_pages = max_pfn-most_seen_pages;
    2.66 -    if (num_pages==0) return 0;
    2.67 +    if (num_pages==0) return -EINVAL;
    2.68  
    2.69      parray = (unsigned long *)vmalloc(num_pages * sizeof(unsigned long));
    2.70      if ( parray == NULL )
    2.71 @@ -383,8 +385,76 @@ claim_new_pages(unsigned long num_pages)
    2.72      return new_page_cnt;
    2.73  }
    2.74  
    2.75 +
    2.76 +static int balloon_try_target(int target)
    2.77 +{
    2.78 +    if ( target < current_pages )
    2.79 +    {
    2.80 +        int change = inflate_balloon(current_pages-target);
    2.81 +        if ( change <= 0 )
    2.82 +            return change;
    2.83 +
    2.84 +        current_pages -= change;
    2.85 +        printk(KERN_INFO "Relinquish %dMB to xen. Domain now has %luMB\n",
    2.86 +            change>>PAGE_TO_MB_SHIFT, current_pages>>PAGE_TO_MB_SHIFT);
    2.87 +    }
    2.88 +    else if ( target > current_pages )
    2.89 +    {
    2.90 +        int change, reclaim = min(target,most_seen_pages) - current_pages;
    2.91 +
    2.92 +        if ( reclaim )
    2.93 +        {
    2.94 +            change = deflate_balloon( reclaim );
    2.95 +            if ( change <= 0 )
    2.96 +                return change;
    2.97 +            current_pages += change;
    2.98 +            printk(KERN_INFO "Reclaim %dMB from xen. Domain now has %luMB\n",
    2.99 +                change>>PAGE_TO_MB_SHIFT, current_pages>>PAGE_TO_MB_SHIFT);
   2.100 +        }
   2.101 +
   2.102 +        if ( most_seen_pages < target )
   2.103 +        {
   2.104 +            int growth = claim_new_pages(target-most_seen_pages);
   2.105 +            if ( growth <= 0 )
   2.106 +                return growth;
   2.107 +            most_seen_pages += growth;
   2.108 +            current_pages += growth;
   2.109 +            printk(KERN_INFO "Granted %dMB new mem. Dom now has %luMB\n",
   2.110 +                growth>>PAGE_TO_MB_SHIFT, current_pages>>PAGE_TO_MB_SHIFT);
   2.111 +        }
   2.112 +    }
   2.113 +
   2.114 +    return 1;
   2.115 +}
   2.116 +
   2.117 +
   2.118 +static void balloon_ctrlif_rx(ctrl_msg_t *msg, unsigned long id)
   2.119 +{
   2.120 +    switch ( msg->subtype )
   2.121 +    {
   2.122 +    case CMSG_MEM_REQUEST_SET:
   2.123 +        if ( msg->length != sizeof(mem_request_t) )
   2.124 +            goto parse_error;
   2.125 +        {
   2.126 +            mem_request_t *req = (mem_request_t *)&msg->msg[0];
   2.127 +            req->status = balloon_try_target(req->target);
   2.128 +        }
   2.129 +        break;        
   2.130 +    default:
   2.131 +        goto parse_error;
   2.132 +    }
   2.133 +
   2.134 +    ctrl_if_send_response(msg);
   2.135 +    return;
   2.136 +
   2.137 + parse_error:
   2.138 +    msg->length = 0;
   2.139 +    ctrl_if_send_response(msg);
   2.140 +}
   2.141 +
   2.142 +
   2.143  static int balloon_write(struct file *file, const char *buffer,
   2.144 -                         u_long count, void *data)
   2.145 +                         size_t count, loff_t *offp)
   2.146  {
   2.147      char memstring[64], *endchar;
   2.148      int len, i;
   2.149 @@ -414,100 +484,82 @@ static int balloon_write(struct file *fi
   2.150      targetbytes = memparse(memstring,&endchar);
   2.151      target = targetbytes >> PAGE_SHIFT;
   2.152  
   2.153 -    if ( target < current_pages )
   2.154 -    {
   2.155 -        int change = inflate_balloon(current_pages-target);
   2.156 -        if ( change <= 0 )
   2.157 -            return change;
   2.158 -
   2.159 -        current_pages -= change;
   2.160 -        printk(KERN_INFO "Relinquish %dMB to xen. Domain now has %luMB\n",
   2.161 -            change>>PAGE_TO_MB_SHIFT, current_pages>>PAGE_TO_MB_SHIFT);
   2.162 -    }
   2.163 -    else if ( target > current_pages )
   2.164 -    {
   2.165 -        int change, reclaim = min(target,most_seen_pages) - current_pages;
   2.166 +    i = balloon_try_target(target);
   2.167  
   2.168 -        if ( reclaim )
   2.169 -        {
   2.170 -            change = deflate_balloon( reclaim);
   2.171 -            if ( change <= 0 )
   2.172 -                return change;
   2.173 -            current_pages += change;
   2.174 -            printk(KERN_INFO "Reclaim %dMB from xen. Domain now has %luMB\n",
   2.175 -                change>>PAGE_TO_MB_SHIFT, current_pages>>PAGE_TO_MB_SHIFT);
   2.176 -        }
   2.177 +    if ( i <= 0 ) return i;
   2.178  
   2.179 -        if ( most_seen_pages < target )
   2.180 -        {
   2.181 -            int growth = claim_new_pages(target-most_seen_pages);
   2.182 -            if ( growth <= 0 )
   2.183 -                return growth;
   2.184 -            most_seen_pages += growth;
   2.185 -            current_pages += growth;
   2.186 -            printk(KERN_INFO "Granted %dMB new mem. Dom now has %luMB\n",
   2.187 -                growth>>PAGE_TO_MB_SHIFT, current_pages>>PAGE_TO_MB_SHIFT);
   2.188 -        }
   2.189 -    }
   2.190 -
   2.191 -
   2.192 +    *offp += len;
   2.193      return len;
   2.194  }
   2.195  
   2.196  
   2.197 -static int balloon_read(char *page, char **start, off_t off,
   2.198 -      int count, int *eof, void *data)
   2.199 +static int balloon_read(struct file *filp, char *buffer,
   2.200 +                        size_t count, loff_t *offp)
   2.201  {
   2.202 +    static char priv_buf[32];
   2.203 +    char *priv_bufp = priv_buf;
   2.204      int len;
   2.205 -    len = sprintf(page,"%lu\n",current_pages<<PAGE_SHIFT);
   2.206 +    len = sprintf(priv_buf,"%lu\n",current_pages<<PAGE_SHIFT);
   2.207  
   2.208 -    if (len <= off+count) *eof = 1;
   2.209 -    *start = page + off;
   2.210 -    len -= off;
   2.211 +    len -= *offp;
   2.212 +    priv_bufp += *offp;
   2.213      if (len>count) len = count;
   2.214      if (len<0) len = 0;
   2.215 +
   2.216 +    copy_to_user(buffer, priv_bufp, len);
   2.217 +
   2.218 +    *offp += len;
   2.219      return len;
   2.220  }
   2.221  
   2.222 -static int __init init_module(void)
   2.223 +static struct file_operations balloon_fops = {
   2.224 +    .read  = balloon_read,
   2.225 +    .write = balloon_write
   2.226 +};
   2.227 +
   2.228 +static int __init balloon_init(void)
   2.229  {
   2.230      printk(KERN_ALERT "Starting Xen Balloon driver\n");
   2.231  
   2.232 -    most_seen_pages = current_pages = min(xen_start_info.nr_pages,max_pfn);
   2.233 +    most_seen_pages = current_pages = min(start_info.nr_pages,max_pfn);
   2.234      if ( (balloon_pde = create_xen_proc_entry("memory_target", 0644)) == NULL )
   2.235      {
   2.236          printk(KERN_ALERT "Unable to create balloon driver proc entry!");
   2.237          return -1;
   2.238      }
   2.239  
   2.240 -    balloon_pde->write_proc = balloon_write;
   2.241 -    balloon_pde->read_proc = balloon_read;
   2.242 +    balloon_pde->owner     = THIS_MODULE;
   2.243 +    balloon_pde->nlink     = 1;
   2.244 +    balloon_pde->proc_fops = &balloon_fops;
   2.245 +
   2.246 +    (void)ctrl_if_register_receiver(CMSG_MEM_REQUEST, balloon_ctrlif_rx,
   2.247 +                                    CALLBACK_IN_BLOCKING_CONTEXT);
   2.248  
   2.249      /* 
   2.250 -     * make a new phys map if mem= says xen can give us memory  to grow
   2.251 +     * make_module a new phys map if mem= says xen can give us memory  to grow
   2.252       */
   2.253 -    if ( max_pfn > xen_start_info.nr_pages )
   2.254 +    if ( max_pfn > start_info.nr_pages )
   2.255      {
   2.256          extern unsigned long *phys_to_machine_mapping;
   2.257          unsigned long *newmap;
   2.258          newmap = (unsigned long *)vmalloc(max_pfn * sizeof(unsigned long));
   2.259          memset(newmap, ~0, max_pfn * sizeof(unsigned long));
   2.260          memcpy(newmap, phys_to_machine_mapping,
   2.261 -               xen_start_info.nr_pages * sizeof(unsigned long));
   2.262 +               start_info.nr_pages * sizeof(unsigned long));
   2.263          phys_to_machine_mapping = newmap;
   2.264      }
   2.265  
   2.266      return 0;
   2.267  }
   2.268  
   2.269 -static void __exit cleanup_module(void)
   2.270 +static void __exit balloon_cleanup(void)
   2.271  {
   2.272      if ( balloon_pde != NULL )
   2.273      {
   2.274 -        remove_xen_proc_entry("balloon");
   2.275 +        remove_xen_proc_entry("memory_target");
   2.276          balloon_pde = NULL;
   2.277      }
   2.278  }
   2.279  
   2.280 -module_init(init_module);
   2.281 -module_exit(cleanup_module);
   2.282 +module_init(balloon_init);
   2.283 +module_exit(balloon_cleanup);