data8 sys_ni_syscall
data8 sys32_lseek
data8 sys_getpid /* 20 */
- data8 sys_mount
+ data8 compat_sys_mount
data8 sys_oldumount
data8 sys_setuid /* 16-bit version */
data8 sys_getuid /* 16-bit version */
#include <linux/slab.h>
#include <linux/uio.h>
#include <linux/nfs_fs.h>
-#include <linux/smb_fs.h>
-#include <linux/smb_mount.h>
-#include <linux/ncp_fs.h>
#include <linux/quota.h>
#include <linux/sunrpc/svc.h>
#include <linux/nfsd/nfsd.h>
#ifdef NOTYET /* UNTESTED FOR IA64 FROM HERE DOWN */
-struct ncp_mount_data32 {
- int version;
- unsigned int ncp_fd;
- compat_uid_t mounted_uid;
- int wdog_pid;
- unsigned char mounted_vol[NCP_VOLNAME_LEN + 1];
- unsigned int time_out;
- unsigned int retry_count;
- unsigned int flags;
- compat_uid_t uid;
- compat_gid_t gid;
- compat_mode_t file_mode;
- compat_mode_t dir_mode;
-};
-
-static void *
-do_ncp_super_data_conv(void *raw_data)
-{
- struct ncp_mount_data *n = (struct ncp_mount_data *)raw_data;
- struct ncp_mount_data32 *n32 = (struct ncp_mount_data32 *)raw_data;
-
- n->dir_mode = n32->dir_mode;
- n->file_mode = n32->file_mode;
- n->gid = n32->gid;
- n->uid = n32->uid;
- memmove (n->mounted_vol, n32->mounted_vol,
- (sizeof (n32->mounted_vol) + 3 * sizeof (unsigned int)));
- n->wdog_pid = n32->wdog_pid;
- n->mounted_uid = n32->mounted_uid;
- return raw_data;
-}
-
-struct smb_mount_data32 {
- int version;
- compat_uid_t mounted_uid;
- compat_uid_t uid;
- compat_gid_t gid;
- compat_mode_t file_mode;
- compat_mode_t dir_mode;
-};
-
-static void *
-do_smb_super_data_conv(void *raw_data)
-{
- struct smb_mount_data *s = (struct smb_mount_data *)raw_data;
- struct smb_mount_data32 *s32 = (struct smb_mount_data32 *)raw_data;
-
- if (s32->version != SMB_MOUNT_OLDVERSION)
- goto out;
- s->version = s32->version;
- s->mounted_uid = s32->mounted_uid;
- s->uid = s32->uid;
- s->gid = s32->gid;
- s->file_mode = s32->file_mode;
- s->dir_mode = s32->dir_mode;
-out:
- return raw_data;
-}
-
-static int
-copy_mount_stuff_to_kernel(const void *user, unsigned long *kernel)
-{
- int i;
- unsigned long page;
- struct vm_area_struct *vma;
-
- *kernel = 0;
- if(!user)
- return 0;
- vma = find_vma(current->mm, (unsigned long)user);
- if(!vma || (unsigned long)user < vma->vm_start)
- return -EFAULT;
- if(!(vma->vm_flags & VM_READ))
- return -EFAULT;
- i = vma->vm_end - (unsigned long) user;
- if(PAGE_SIZE <= (unsigned long) i)
- i = PAGE_SIZE - 1;
- if(!(page = __get_free_page(GFP_KERNEL)))
- return -ENOMEM;
- if(copy_from_user((void *) page, user, i)) {
- free_page(page);
- return -EFAULT;
- }
- *kernel = page;
- return 0;
-}
-
-#define SMBFS_NAME "smbfs"
-#define NCPFS_NAME "ncpfs"
-
-asmlinkage long
-sys32_mount(char *dev_name, char *dir_name, char *type,
- unsigned long new_flags, u32 data)
-{
- unsigned long type_page;
- int err, is_smb, is_ncp;
-
- if(!capable(CAP_SYS_ADMIN))
- return -EPERM;
- is_smb = is_ncp = 0;
- err = copy_mount_stuff_to_kernel((const void *)type, &type_page);
- if(err)
- return err;
- if(type_page) {
- is_smb = !strcmp((char *)type_page, SMBFS_NAME);
- is_ncp = !strcmp((char *)type_page, NCPFS_NAME);
- }
- if(!is_smb && !is_ncp) {
- if(type_page)
- free_page(type_page);
- return sys_mount(dev_name, dir_name, type, new_flags,
- (void *)AA(data));
- } else {
- unsigned long dev_page, dir_page, data_page;
-
- err = copy_mount_stuff_to_kernel((const void *)dev_name,
- &dev_page);
- if(err)
- goto out;
- err = copy_mount_stuff_to_kernel((const void *)dir_name,
- &dir_page);
- if(err)
- goto dev_out;
- err = copy_mount_stuff_to_kernel((const void *)AA(data),
- &data_page);
- if(err)
- goto dir_out;
- if(is_ncp)
- do_ncp_super_data_conv((void *)data_page);
- else if(is_smb)
- do_smb_super_data_conv((void *)data_page);
- else
- panic("The problem is here...");
- err = do_mount((char *)dev_page, (char *)dir_page,
- (char *)type_page, new_flags,
- (void *)data_page);
- if(data_page)
- free_page(data_page);
- dir_out:
- if(dir_page)
- free_page(dir_page);
- dev_out:
- if(dev_page)
- free_page(dev_page);
- out:
- if(type_page)
- free_page(type_page);
- return err;
- }
-}
-
asmlinkage long sys32_setreuid(compat_uid_t ruid, compat_uid_t euid)
{
uid_t sruid, seuid;
return error;
}
-static int copy_mount_stuff_to_kernel(const void *user, unsigned long *kernel)
-{
- int i;
- unsigned long page;
- struct vm_area_struct *vma;
-
- *kernel = 0;
- if(!user)
- return 0;
- vma = find_vma(current->mm, (unsigned long)user);
- if(!vma || (unsigned long)user < vma->vm_start)
- return -EFAULT;
- if(!(vma->vm_flags & VM_READ))
- return -EFAULT;
- i = vma->vm_end - (unsigned long) user;
- if(PAGE_SIZE <= (unsigned long) i)
- i = PAGE_SIZE - 1;
- if(!(page = __get_free_page(GFP_KERNEL)))
- return -ENOMEM;
- if(copy_from_user((void *) page, user, i)) {
- free_page(page);
- return -EFAULT;
- }
- *kernel = page;
- return 0;
-}
-
-#define SMBFS_NAME "smbfs"
-#define NCPFS_NAME "ncpfs"
-
-asmlinkage int sys32_mount(char *dev_name, char *dir_name, char *type, unsigned long new_flags, u32 data)
-{
- unsigned long type_page = 0;
- unsigned long data_page = 0;
- unsigned long dev_page = 0;
- unsigned long dir_page = 0;
- int err, is_smb, is_ncp;
-
- is_smb = is_ncp = 0;
-
- err = copy_mount_stuff_to_kernel((const void *)type, &type_page);
- if (err)
- goto out;
-
- if (!type_page) {
- err = -EINVAL;
- goto out;
- }
-
- is_smb = !strcmp((char *)type_page, SMBFS_NAME);
- is_ncp = !strcmp((char *)type_page, NCPFS_NAME);
-
- err = copy_mount_stuff_to_kernel((const void *)(unsigned long)data, &data_page);
- if (err)
- goto type_out;
-
- err = copy_mount_stuff_to_kernel(dev_name, &dev_page);
- if (err)
- goto data_out;
-
- err = copy_mount_stuff_to_kernel(dir_name, &dir_page);
- if (err)
- goto dev_out;
-
- if (!is_smb && !is_ncp) {
- lock_kernel();
- err = do_mount((char*)dev_page, (char*)dir_page,
- (char*)type_page, new_flags, (char*)data_page);
- unlock_kernel();
- } else {
- if (is_ncp)
- panic("NCP mounts not yet supported 32/64 parisc");
- /* do_ncp_super_data_conv((void *)data_page); */
- else {
- panic("SMB mounts not yet supported 32/64 parisc");
- /* do_smb_super_data_conv((void *)data_page); */
- }
-
- lock_kernel();
- err = do_mount((char*)dev_page, (char*)dir_page,
- (char*)type_page, new_flags, (char*)data_page);
- unlock_kernel();
- }
- free_page(dir_page);
-
-dev_out:
- free_page(dev_page);
-
-data_out:
- free_page(data_page);
-
-type_out:
- free_page(type_page);
-
-out:
- return err;
-}
-
-
/* readv/writev stolen from mips64 */
typedef ssize_t (*IO_fn_t)(struct file *, char *, size_t, loff_t *);
ENTRY_DIFF(lseek)
ENTRY_SAME(getpid) /* 20 */
/* the 'void * data' parameter may need re-packing in wide */
- ENTRY_DIFF(mount)
+ ENTRY_COMP(mount)
/* concerned about struct sockaddr in wide/narrow */
/* ---> I think sockaddr is OK unless the compiler packs the struct */
/* differently to align the char array */
.llong .sys_ni_syscall /* old stat syscall */
.llong .ppc32_lseek
.llong .sys_getpid /* 20 */
- .llong .sys32_mount
+ .llong .compat_sys_mount
.llong .sys_oldumount
.llong .sys_setuid
.llong .sys_getuid
#include <linux/uio.h>
#include <linux/aio.h>
#include <linux/nfs_fs.h>
-#include <linux/smb_fs.h>
-#include <linux/smb_mount.h>
-#include <linux/ncp_fs.h>
#include <linux/module.h>
#include <linux/sunrpc/svc.h>
#include <linux/nfsd/nfsd.h>
return ret;
}
-struct ncp_mount_data32_v3 {
- int version;
- unsigned int ncp_fd;
- compat_uid_t mounted_uid;
- compat_pid_t wdog_pid;
- unsigned char mounted_vol[NCP_VOLNAME_LEN + 1];
- unsigned int time_out;
- unsigned int retry_count;
- unsigned int flags;
- compat_uid_t uid;
- compat_gid_t gid;
- compat_mode_t file_mode;
- compat_mode_t dir_mode;
-};
-
-struct ncp_mount_data32_v4 {
- int version;
- /* all members below are "long" in ABI ... i.e. 32bit on sparc32, while 64bits on sparc64 */
- unsigned int flags;
- unsigned int mounted_uid;
- int wdog_pid;
-
- unsigned int ncp_fd;
- unsigned int time_out;
- unsigned int retry_count;
-
- unsigned int uid;
- unsigned int gid;
- unsigned int file_mode;
- unsigned int dir_mode;
-};
-
-static void *do_ncp_super_data_conv(void *raw_data)
-{
- switch (*(int*)raw_data) {
- case NCP_MOUNT_VERSION:
- {
- struct ncp_mount_data news, *n = &news;
- struct ncp_mount_data32_v3 *n32 = (struct ncp_mount_data32_v3 *)raw_data;
-
- n->version = n32->version;
- n->ncp_fd = n32->ncp_fd;
- n->mounted_uid = n32->mounted_uid;
- n->wdog_pid = n32->wdog_pid;
- memmove (n->mounted_vol, n32->mounted_vol, sizeof (n32->mounted_vol));
- n->time_out = n32->time_out;
- n->retry_count = n32->retry_count;
- n->flags = n32->flags;
- n->uid = n32->uid;
- n->gid = n32->gid;
- n->file_mode = n32->file_mode;
- n->dir_mode = n32->dir_mode;
- memcpy(raw_data, n, sizeof(*n));
- }
- break;
- case NCP_MOUNT_VERSION_V4:
- {
- struct ncp_mount_data_v4 news, *n = &news;
- struct ncp_mount_data32_v4 *n32 = (struct ncp_mount_data32_v4 *)raw_data;
-
- n->version = n32->version;
- n->flags = n32->flags;
- n->mounted_uid = n32->mounted_uid;
- n->wdog_pid = n32->wdog_pid;
- n->ncp_fd = n32->ncp_fd;
- n->time_out = n32->time_out;
- n->retry_count = n32->retry_count;
- n->uid = n32->uid;
- n->gid = n32->gid;
- n->file_mode = n32->file_mode;
- n->dir_mode = n32->dir_mode;
- memcpy(raw_data, n, sizeof(*n));
- }
- break;
- default:
- /* do not touch unknown structures */
- break;
- }
- return raw_data;
-}
-
-struct smb_mount_data32 {
- int version;
- compat_uid_t mounted_uid;
- compat_uid_t uid;
- compat_gid_t gid;
- compat_mode_t file_mode;
- compat_mode_t dir_mode;
-};
-
-static void *do_smb_super_data_conv(void *raw_data)
-{
- struct smb_mount_data news, *s = &news;
- struct smb_mount_data32 *s32 = (struct smb_mount_data32 *)raw_data;
-
- if (s32->version != SMB_MOUNT_OLDVERSION)
- goto out;
- s->version = s32->version;
- s->mounted_uid = s32->mounted_uid;
- s->uid = s32->uid;
- s->gid = s32->gid;
- s->file_mode = s32->file_mode;
- s->dir_mode = s32->dir_mode;
- memcpy(raw_data, s, sizeof(struct smb_mount_data));
-out:
- return raw_data;
-}
-
-static int copy_mount_stuff_to_kernel(const void *user, unsigned long *kernel)
-{
- int i;
- unsigned long page;
- struct vm_area_struct *vma;
-
- *kernel = 0;
- if(!user)
- return 0;
- vma = find_vma(current->mm, (unsigned long)user);
- if(!vma || (unsigned long)user < vma->vm_start)
- return -EFAULT;
- if(!(vma->vm_flags & VM_READ))
- return -EFAULT;
- i = vma->vm_end - (unsigned long) user;
- if(PAGE_SIZE <= (unsigned long) i)
- i = PAGE_SIZE - 1;
- if(!(page = __get_free_page(GFP_KERNEL)))
- return -ENOMEM;
- if(copy_from_user((void *) page, user, i)) {
- free_page(page);
- return -EFAULT;
- }
- *kernel = page;
- return 0;
-}
-
-#define SMBFS_NAME "smbfs"
-#define NCPFS_NAME "ncpfs"
-
-asmlinkage long sys32_mount(char *dev_name, char *dir_name, char *type, unsigned long new_flags, u32 data)
-{
- unsigned long type_page = 0;
- unsigned long data_page = 0;
- unsigned long dev_page = 0;
- unsigned long dir_page = 0;
- int err, is_smb, is_ncp;
-
- is_smb = is_ncp = 0;
-
- err = copy_mount_stuff_to_kernel((const void *)type, &type_page);
- if (err)
- goto out;
-
- if (!type_page) {
- err = -EINVAL;
- goto out;
- }
-
- is_smb = !strcmp((char *)type_page, SMBFS_NAME);
- is_ncp = !strcmp((char *)type_page, NCPFS_NAME);
-
- err = copy_mount_stuff_to_kernel((const void *)AA(data), &data_page);
- if (err)
- goto type_out;
-
- err = copy_mount_stuff_to_kernel(dev_name, &dev_page);
- if (err)
- goto data_out;
-
- err = copy_mount_stuff_to_kernel(dir_name, &dir_page);
- if (err)
- goto dev_out;
-
- if (!is_smb && !is_ncp) {
- lock_kernel();
- err = do_mount((char*)dev_page, (char*)dir_page,
- (char*)type_page, new_flags, (char*)data_page);
- unlock_kernel();
- } else {
- if (is_ncp)
- do_ncp_super_data_conv((void *)data_page);
- else
- do_smb_super_data_conv((void *)data_page);
-
- lock_kernel();
- err = do_mount((char*)dev_page, (char*)dir_page,
- (char*)type_page, new_flags, (char*)data_page);
- unlock_kernel();
- }
- free_page(dir_page);
-
-dev_out:
- free_page(dev_page);
-
-data_out:
- free_page(data_page);
-
-type_out:
- free_page(type_page);
-
-out:
- return err;
-}
-
/* readdir & getdents */
#define NAME_OFFSET(de) ((int) ((de)->d_name - (char *) (de)))
#define ROUND_UP(x) (((x)+sizeof(u32)-1) & ~(sizeof(u32)-1))
#include <linux/slab.h>
#include <linux/uio.h>
#include <linux/nfs_fs.h>
-#include <linux/smb_fs.h>
-#include <linux/smb_mount.h>
-#include <linux/ncp_fs.h>
#include <linux/quota.h>
#include <linux/module.h>
#include <linux/sunrpc/svc.h>
return err;
}
-struct ncp_mount_data32 {
- int version;
- unsigned int ncp_fd;
- compat_uid_t mounted_uid;
- compat_pid_t wdog_pid;
- unsigned char mounted_vol[NCP_VOLNAME_LEN + 1];
- unsigned int time_out;
- unsigned int retry_count;
- unsigned int flags;
- compat_uid_t uid;
- compat_gid_t gid;
- compat_mode_t file_mode;
- compat_mode_t dir_mode;
-};
-
-static void *do_ncp_super_data_conv(void *raw_data)
-{
- struct ncp_mount_data *n = (struct ncp_mount_data *)raw_data;
- struct ncp_mount_data32 *n32 = (struct ncp_mount_data32 *)raw_data;
-
- n->dir_mode = n32->dir_mode;
- n->file_mode = n32->file_mode;
- n->gid = low2highgid(n32->gid);
- n->uid = low2highuid(n32->uid);
- memmove (n->mounted_vol, n32->mounted_vol, (sizeof (n32->mounted_vol) + 3 * sizeof (unsigned int)));
- n->wdog_pid = n32->wdog_pid;
- n->mounted_uid = low2highuid(n32->mounted_uid);
- return raw_data;
-}
-
-struct smb_mount_data32 {
- int version;
- compat_uid_t mounted_uid;
- compat_uid_t uid;
- compat_gid_t gid;
- compat_mode_t file_mode;
- compat_mode_t dir_mode;
-};
-
-static void *do_smb_super_data_conv(void *raw_data)
-{
- struct smb_mount_data *s = (struct smb_mount_data *)raw_data;
- struct smb_mount_data32 *s32 = (struct smb_mount_data32 *)raw_data;
-
- if (s32->version != SMB_MOUNT_OLDVERSION)
- goto out;
- s->version = s32->version;
- s->mounted_uid = low2highuid(s32->mounted_uid);
- s->uid = low2highuid(s32->uid);
- s->gid = low2highgid(s32->gid);
- s->file_mode = s32->file_mode;
- s->dir_mode = s32->dir_mode;
-out:
- return raw_data;
-}
-
-static int copy_mount_stuff_to_kernel(const void *user, unsigned long *kernel)
-{
- int i;
- unsigned long page;
- struct vm_area_struct *vma;
-
- *kernel = 0;
- if(!user)
- return 0;
- vma = find_vma(current->mm, (unsigned long)user);
- if(!vma || (unsigned long)user < vma->vm_start)
- return -EFAULT;
- if(!(vma->vm_flags & VM_READ))
- return -EFAULT;
- i = vma->vm_end - (unsigned long) user;
- if(PAGE_SIZE <= (unsigned long) i)
- i = PAGE_SIZE - 1;
- if(!(page = __get_free_page(GFP_KERNEL)))
- return -ENOMEM;
- if(copy_from_user((void *) page, user, i)) {
- free_page(page);
- return -EFAULT;
- }
- *kernel = page;
- return 0;
-}
-
-#define SMBFS_NAME "smbfs"
-#define NCPFS_NAME "ncpfs"
-
-asmlinkage int sys32_mount(char *dev_name, char *dir_name, char *type, unsigned long new_flags, u32 data)
-{
- unsigned long type_page = 0;
- unsigned long data_page = 0;
- unsigned long dev_page = 0;
- unsigned long dir_page = 0;
- int err, is_smb, is_ncp;
-
- is_smb = is_ncp = 0;
-
- err = copy_mount_stuff_to_kernel((const void *)type, &type_page);
- if (err)
- goto out;
-
- if (!type_page) {
- err = -EINVAL;
- goto out;
- }
-
- is_smb = !strcmp((char *)type_page, SMBFS_NAME);
- is_ncp = !strcmp((char *)type_page, NCPFS_NAME);
-
- err = copy_mount_stuff_to_kernel((const void *)AA(data), &data_page);
- if (err)
- goto type_out;
-
- err = copy_mount_stuff_to_kernel(dev_name, &dev_page);
- if (err)
- goto data_out;
-
- err = copy_mount_stuff_to_kernel(dir_name, &dir_page);
- if (err)
- goto dev_out;
-
- if (!is_smb && !is_ncp) {
- lock_kernel();
- err = do_mount((char*)dev_page, (char*)dir_page,
- (char*)type_page, new_flags, (char*)data_page);
- unlock_kernel();
- } else {
- if (is_ncp)
- do_ncp_super_data_conv((void *)data_page);
- else
- do_smb_super_data_conv((void *)data_page);
-
- lock_kernel();
- err = do_mount((char*)dev_page, (char*)dir_page,
- (char*)type_page, new_flags, (char*)data_page);
- unlock_kernel();
- }
- free_page(dir_page);
-
-dev_out:
- free_page(dev_page);
-
-data_out:
- free_page(data_page);
-
-type_out:
- free_page(type_page);
-
-out:
- return err;
-}
-
struct sysinfo32 {
s32 uptime;
u32 loads[3];
llgtr %r4,%r4 # char *
llgfr %r5,%r5 # unsigned long
llgtr %r6,%r6 # void *
- jg sys32_mount # branch to system call
+ jg compat_sys_mount # branch to system call
.globl sys32_oldumount_wrapper
sys32_oldumount_wrapper:
#include <linux/slab.h>
#include <linux/uio.h>
#include <linux/nfs_fs.h>
-#include <linux/smb_fs.h>
-#include <linux/smb_mount.h>
-#include <linux/ncp_fs.h>
#include <linux/quota.h>
#include <linux/module.h>
#include <linux/sunrpc/svc.h>
return sys_sysfs(option, arg1, arg2);
}
-struct ncp_mount_data32_v3 {
- int version;
- unsigned int ncp_fd;
- compat_uid_t mounted_uid;
- compat_pid_t wdog_pid;
- unsigned char mounted_vol[NCP_VOLNAME_LEN + 1];
- unsigned int time_out;
- unsigned int retry_count;
- unsigned int flags;
- compat_uid_t uid;
- compat_gid_t gid;
- compat_mode_t file_mode;
- compat_mode_t dir_mode;
-};
-
-struct ncp_mount_data32_v4 {
- int version;
- /* all members below are "long" in ABI ... i.e. 32bit on sparc32, while 64bits on sparc64 */
- unsigned int flags;
- unsigned int mounted_uid;
- int wdog_pid;
-
- unsigned int ncp_fd;
- unsigned int time_out;
- unsigned int retry_count;
-
- unsigned int uid;
- unsigned int gid;
- unsigned int file_mode;
- unsigned int dir_mode;
-};
-
-static void *do_ncp_super_data_conv(void *raw_data)
-{
- switch (*(int*)raw_data) {
- case NCP_MOUNT_VERSION:
- {
- struct ncp_mount_data news, *n = &news;
- struct ncp_mount_data32_v3 *n32 = (struct ncp_mount_data32_v3 *)raw_data;
-
- n->version = n32->version;
- n->ncp_fd = n32->ncp_fd;
- n->mounted_uid = low2highuid(n32->mounted_uid);
- n->wdog_pid = n32->wdog_pid;
- memmove (n->mounted_vol, n32->mounted_vol, sizeof (n32->mounted_vol));
- n->time_out = n32->time_out;
- n->retry_count = n32->retry_count;
- n->flags = n32->flags;
- n->uid = low2highuid(n32->uid);
- n->gid = low2highgid(n32->gid);
- n->file_mode = n32->file_mode;
- n->dir_mode = n32->dir_mode;
- memcpy(raw_data, n, sizeof(*n));
- }
- break;
- case NCP_MOUNT_VERSION_V4:
- {
- struct ncp_mount_data_v4 news, *n = &news;
- struct ncp_mount_data32_v4 *n32 = (struct ncp_mount_data32_v4 *)raw_data;
-
- n->version = n32->version;
- n->flags = n32->flags;
- n->mounted_uid = n32->mounted_uid;
- n->wdog_pid = n32->wdog_pid;
- n->ncp_fd = n32->ncp_fd;
- n->time_out = n32->time_out;
- n->retry_count = n32->retry_count;
- n->uid = n32->uid;
- n->gid = n32->gid;
- n->file_mode = n32->file_mode;
- n->dir_mode = n32->dir_mode;
- memcpy(raw_data, n, sizeof(*n));
- }
- break;
- default:
- /* do not touch unknown structures */
- break;
- }
- return raw_data;
-}
-
-struct smb_mount_data32 {
- int version;
- compat_uid_t mounted_uid;
- compat_uid_t uid;
- compat_gid_t gid;
- compat_mode_t file_mode;
- compat_mode_t dir_mode;
-};
-
-static void *do_smb_super_data_conv(void *raw_data)
-{
- struct smb_mount_data news, *s = &news;
- struct smb_mount_data32 *s32 = (struct smb_mount_data32 *)raw_data;
-
- if (s32->version != SMB_MOUNT_OLDVERSION)
- goto out;
- s->version = s32->version;
- s->mounted_uid = low2highuid(s32->mounted_uid);
- s->uid = low2highuid(s32->uid);
- s->gid = low2highgid(s32->gid);
- s->file_mode = s32->file_mode;
- s->dir_mode = s32->dir_mode;
- memcpy(raw_data, s, sizeof(struct smb_mount_data));
-out:
- return raw_data;
-}
-
-static int copy_mount_stuff_to_kernel(const void *user, unsigned long *kernel)
-{
- int i;
- unsigned long page;
- struct vm_area_struct *vma;
-
- *kernel = 0;
- if(!user)
- return 0;
- vma = find_vma(current->mm, (unsigned long)user);
- if(!vma || (unsigned long)user < vma->vm_start)
- return -EFAULT;
- if(!(vma->vm_flags & VM_READ))
- return -EFAULT;
- i = vma->vm_end - (unsigned long) user;
- if(PAGE_SIZE <= (unsigned long) i)
- i = PAGE_SIZE - 1;
- if(!(page = __get_free_page(GFP_KERNEL)))
- return -ENOMEM;
- if(copy_from_user((void *) page, user, i)) {
- free_page(page);
- return -EFAULT;
- }
- *kernel = page;
- return 0;
-}
-
-#define SMBFS_NAME "smbfs"
-#define NCPFS_NAME "ncpfs"
-
-asmlinkage int sys32_mount(char *dev_name, char *dir_name, char *type, unsigned long new_flags, u32 data)
-{
- unsigned long type_page = 0;
- unsigned long data_page = 0;
- unsigned long dev_page = 0;
- unsigned long dir_page = 0;
- int err, is_smb, is_ncp;
-
- is_smb = is_ncp = 0;
-
- err = copy_mount_stuff_to_kernel((const void *)type, &type_page);
- if (err)
- goto out;
-
- if (!type_page) {
- err = -EINVAL;
- goto out;
- }
-
- is_smb = !strcmp((char *)type_page, SMBFS_NAME);
- is_ncp = !strcmp((char *)type_page, NCPFS_NAME);
-
- err = copy_mount_stuff_to_kernel((const void *)AA(data), &data_page);
- if (err)
- goto type_out;
-
- err = copy_mount_stuff_to_kernel(dev_name, &dev_page);
- if (err)
- goto data_out;
-
- err = copy_mount_stuff_to_kernel(dir_name, &dir_page);
- if (err)
- goto dev_out;
-
- if (!is_smb && !is_ncp) {
- lock_kernel();
- err = do_mount((char*)dev_page, (char*)dir_page,
- (char*)type_page, new_flags, (char*)data_page);
- unlock_kernel();
- } else {
- if (is_ncp)
- do_ncp_super_data_conv((void *)data_page);
- else
- do_smb_super_data_conv((void *)data_page);
-
- lock_kernel();
- err = do_mount((char*)dev_page, (char*)dir_page,
- (char*)type_page, new_flags, (char*)data_page);
- unlock_kernel();
- }
- free_page(dir_page);
-
-dev_out:
- free_page(dev_page);
-
-data_out:
- free_page(data_page);
-
-type_out:
- free_page(type_page);
-
-out:
- return err;
-}
-
struct sysinfo32 {
s32 uptime;
u32 loads[3];
/*150*/ .word sys_nis_syscall, sys_nis_syscall, sys_nis_syscall, sys_poll, sys_getdents64
.word compat_sys_fcntl64, sys_ni_syscall, compat_sys_statfs, compat_sys_fstatfs, sys_oldumount
/*160*/ .word compat_sys_sched_setaffinity, compat_sys_sched_getaffinity, sys_getdomainname, sys_setdomainname, sys_nis_syscall
- .word sys_quotactl, sys_set_tid_address, sys32_mount, sys_ustat, sys_setxattr
+ .word sys_quotactl, sys_set_tid_address, compat_sys_mount, sys_ustat, sys_setxattr
/*170*/ .word sys_lsetxattr, sys_fsetxattr, sys_getxattr, sys_lgetxattr, sys32_getdents
.word sys_setsid, sys_fchdir, sys_fgetxattr, sys_listxattr, sys_llistxattr
/*180*/ .word sys_flistxattr, sys_removexattr, sys_lremovexattr, compat_sys_sigpending, sys_ni_syscall
.quad sys_stat
.quad sys32_lseek
.quad sys_getpid /* 20 */
- .quad sys_mount /* mount */
+ .quad compat_sys_mount /* mount */
.quad sys_oldumount /* old_umount */
.quad sys_setuid16
.quad sys_getuid16
#include <linux/slab.h>
#include <linux/uio.h>
#include <linux/nfs_fs.h>
-#include <linux/smb_fs.h>
-#include <linux/smb_mount.h>
-#include <linux/ncp_fs.h>
#include <linux/quota.h>
#include <linux/module.h>
#include <linux/sunrpc/svc.h>
return sys_sysfs(option, arg1, arg2);
}
-static char *badfs[] = {
- "smbfs", "ncpfs", NULL
-};
-
-static int checktype(char *user_type)
-{
- int err = 0;
- char **s,*kernel_type = getname(user_type);
- if (!kernel_type || IS_ERR(kernel_type))
- return -EFAULT;
- for (s = badfs; *s; ++s)
- if (!strcmp(kernel_type, *s)) {
- printk(KERN_ERR "mount32: unsupported fs `%s' -- use 64bit mount\n", *s);
- err = -EINVAL;
- break;
- }
- putname(user_type);
- return err;
-}
-
-asmlinkage long
-sys32_mount(char *dev_name, char *dir_name, char *type,
- unsigned long new_flags, u32 data)
-{
- int err;
- if(!capable(CAP_SYS_ADMIN))
- return -EPERM;
- err = checktype(type);
- if (err)
- return err;
- return sys_mount(dev_name, dir_name, type, new_flags, (void *)AA(data));
-}
-
struct sysinfo32 {
s32 uptime;
u32 loads[3];
#include <linux/ioctl32.h>
#include <linux/init.h>
#include <linux/sockios.h> /* for SIOCDEVPRIVATE */
+#include <linux/smb.h>
+#include <linux/smb_mount.h>
+#include <linux/ncp_mount.h>
#include <linux/smp_lock.h>
#include <linux/syscalls.h>
#include <linux/ctype.h>
ret = sys_io_submit(ctx_id, nr, iocb64);
return ret;
}
+
+struct compat_ncp_mount_data {
+ compat_int_t version;
+ compat_uint_t ncp_fd;
+ compat_uid_t mounted_uid;
+ compat_pid_t wdog_pid;
+ unsigned char mounted_vol[NCP_VOLNAME_LEN + 1];
+ compat_uint_t time_out;
+ compat_uint_t retry_count;
+ compat_uint_t flags;
+ compat_uid_t uid;
+ compat_gid_t gid;
+ compat_mode_t file_mode;
+ compat_mode_t dir_mode;
+};
+
+struct compat_ncp_mount_data_v4 {
+ compat_int_t version;
+ compat_ulong_t flags;
+ compat_ulong_t mounted_uid;
+ compat_long_t wdog_pid;
+ compat_uint_t ncp_fd;
+ compat_uint_t time_out;
+ compat_uint_t retry_count;
+ compat_ulong_t uid;
+ compat_ulong_t gid;
+ compat_ulong_t file_mode;
+ compat_ulong_t dir_mode;
+};
+
+static void *do_ncp_super_data_conv(void *raw_data)
+{
+ int version = *(unsigned int *)raw_data;
+
+ if (version == 3) {
+ struct compat_ncp_mount_data *c_n = raw_data;
+ struct ncp_mount_data *n = raw_data;
+
+ n->dir_mode = c_n->dir_mode;
+ n->file_mode = c_n->file_mode;
+ n->gid = c_n->gid;
+ n->uid = c_n->uid;
+ memmove (n->mounted_vol, c_n->mounted_vol, (sizeof (c_n->mounted_vol) + 3 * sizeof (unsigned int)));
+ n->wdog_pid = c_n->wdog_pid;
+ n->mounted_uid = c_n->mounted_uid;
+ } else if (version == 4) {
+ struct compat_ncp_mount_data_v4 *c_n = raw_data;
+ struct ncp_mount_data_v4 *n = raw_data;
+
+ n->dir_mode = c_n->dir_mode;
+ n->file_mode = c_n->file_mode;
+ n->gid = c_n->gid;
+ n->uid = c_n->uid;
+ n->retry_count = c_n->retry_count;
+ n->time_out = c_n->time_out;
+ n->ncp_fd = c_n->ncp_fd;
+ n->wdog_pid = c_n->wdog_pid;
+ n->mounted_uid = c_n->mounted_uid;
+ n->flags = c_n->flags;
+ } else if (version != 5) {
+ return NULL;
+ }
+
+ return raw_data;
+}
+
+struct compat_smb_mount_data {
+ compat_int_t version;
+ compat_uid_t mounted_uid;
+ compat_uid_t uid;
+ compat_gid_t gid;
+ compat_mode_t file_mode;
+ compat_mode_t dir_mode;
+};
+
+static void *do_smb_super_data_conv(void *raw_data)
+{
+ struct smb_mount_data *s = raw_data;
+ struct compat_smb_mount_data *c_s = raw_data;
+
+ if (c_s->version != SMB_MOUNT_OLDVERSION)
+ goto out;
+ s->dir_mode = c_s->dir_mode;
+ s->file_mode = c_s->file_mode;
+ s->gid = c_s->gid;
+ s->uid = c_s->uid;
+ s->mounted_uid = c_s->mounted_uid;
+ out:
+ return raw_data;
+}
+
+extern int copy_mount_options (const void __user *, unsigned long *);
+
+#define SMBFS_NAME "smbfs"
+#define NCPFS_NAME "ncpfs"
+
+asmlinkage int compat_sys_mount(char __user * dev_name, char __user * dir_name,
+ char __user * type, unsigned long flags,
+ void __user * data)
+{
+ unsigned long type_page;
+ unsigned long data_page;
+ unsigned long dev_page;
+ char *dir_page;
+ int retval;
+
+ retval = copy_mount_options (type, &type_page);
+ if (retval < 0)
+ goto out;
+
+ dir_page = getname(dir_name);
+ retval = PTR_ERR(dir_page);
+ if (IS_ERR(dir_page))
+ goto out1;
+
+ retval = copy_mount_options (dev_name, &dev_page);
+ if (retval < 0)
+ goto out2;
+
+ retval = copy_mount_options (data, &data_page);
+ if (retval < 0)
+ goto out3;
+
+ retval = -EINVAL;
+
+ if (type_page) {
+ if (!strcmp((char *)type_page, SMBFS_NAME)) {
+ do_smb_super_data_conv((void *)data_page);
+ } else if (!strcmp((char *)type_page, NCPFS_NAME)) {
+ do_ncp_super_data_conv((void *)data_page);
+ }
+ }
+
+ lock_kernel();
+ retval = do_mount((char*)dev_page, dir_page, (char*)type_page,
+ flags, (void*)data_page);
+ unlock_kernel();
+
+ free_page(data_page);
+ out3:
+ free_page(dev_page);
+ out2:
+ putname(dir_page);
+ out1:
+ free_page(type_page);
+ out:
+ return retval;
+}
+
return err;
}
-static int copy_mount_options (const void __user *data, unsigned long *where)
+int copy_mount_options (const void __user *data, unsigned long *where)
{
int i;
unsigned long page;
#define __LINUX_NET_SCM_H
#include <linux/limits.h>
+#include <linux/net.h>
/* Well, we should have at least one descriptor open
* to accept passed FDs 8)