diff -r 567da1a48940 drivers/xen/privcmd/compat_privcmd.c --- a/drivers/xen/privcmd/compat_privcmd.c Fri Oct 19 10:27:45 2007 +0100 +++ b/drivers/xen/privcmd/compat_privcmd.c Mon Oct 22 16:45:06 2007 +0100 @@ -33,8 +33,8 @@ int privcmd_ioctl_32(int fd, unsigned in switch (cmd) { case IOCTL_PRIVCMD_MMAP_32: { - struct privcmd_mmap *p; - struct privcmd_mmap_32 *p32; + struct privcmd_mmap __user *p; + struct privcmd_mmap_32 __user *p32; struct privcmd_mmap_32 n32; p32 = compat_ptr(arg); @@ -49,20 +49,51 @@ int privcmd_ioctl_32(int fd, unsigned in } break; case IOCTL_PRIVCMD_MMAPBATCH_32: { - struct privcmd_mmapbatch *p; - struct privcmd_mmapbatch_32 *p32; + struct privcmd_mmapbatch __user*p; struct privcmd_mmapbatch_32 n32; + xen_pfn_t pfn64; + xen_pfn_t __user *upfn64; + u32 pfn32; + u32 __user *upfn32; + int i; - p32 = compat_ptr(arg); - p = compat_alloc_user_space(sizeof(*p)); - if (copy_from_user(&n32, p32, sizeof(n32)) || - put_user(n32.num, &p->num) || - put_user(n32.dom, &p->dom) || - put_user(n32.addr, &p->addr) || - put_user(compat_ptr(n32.arr), &p->arr)) + if (copy_from_user(&n32, compat_ptr(arg), sizeof(n32))) return -EFAULT; - + + p = compat_alloc_user_space(sizeof(*p) + sizeof(*upfn64) * n32.num); + upfn64 = (xen_pfn_t __user *)(p + 1); + + if (put_user(n32.num, &p->num)) + return -EFAULT; + if (put_user(n32.dom, &p->dom)) + return -EFAULT; + if (put_user(n32.addr, &p->addr)) + return -EFAULT; + + upfn32 = compat_ptr(n32.arr); + for (i=0; iarr)) + return -EFAULT; + ret = sys_ioctl(fd, IOCTL_PRIVCMD_MMAPBATCH, (unsigned long)p); + + for (i=0; i