[parisc-linux-cvs] mmap2 syscall
Matthew Wilcox
willy@ldl.fc.hp.com
Sun, 04 Mar 2001 20:26:05 -0700
Add an mmap2 syscall. It allows 32-bit applications to mmap a chunk of
files up to 44-bits (16TB) long. It's part of the LFS, and most of the
other ports have it. Probably requires glibc to be rebuilt to use it.
Index: arch/parisc/kernel/sys_parisc.c
===================================================================
RCS file: /home/cvs/parisc/linux/arch/parisc/kernel/sys_parisc.c,v
retrieving revision 1.8
diff -u -p -r1.8 sys_parisc.c
--- sys_parisc.c 2001/03/04 04:48:53 1.8
+++ sys_parisc.c 2001/03/05 03:15:37
@@ -1,7 +1,7 @@
/*
* linux/arch/parisc/kernel/sys_parisc.c
*
- * this implements the missing syscalls.
+ * this implements syscalls which are handled per-arch.
*/
#include <asm/uaccess.h>
@@ -10,6 +10,7 @@
#include <linux/linkage.h>
#include <linux/mm.h>
#include <linux/mman.h>
+#include <linux/shm.h>
#include <linux/smp_lock.h>
int sys_pipe(int *fildes)
@@ -32,22 +33,22 @@ int sys_pause(void)
return -ERESTARTNOHAND;
}
-int sys_mmap(unsigned long addr, unsigned long len,
- unsigned long prot, unsigned long flags, unsigned long fd,
- unsigned long offset)
+static unsigned long do_mmap2(unsigned long addr, unsigned long len,
+ unsigned long prot, unsigned long flags, unsigned long fd,
+ unsigned long pgoff)
{
struct file * file = NULL;
- int error = -EBADF;
-
+ unsigned long error = -EBADF;
if (!(flags & MAP_ANONYMOUS)) {
file = fget(fd);
if (!file)
goto out;
}
+
flags &= ~(MAP_EXECUTABLE | MAP_DENYWRITE);
down(¤t->mm->mmap_sem);
- error = do_mmap(file, addr, len, prot, flags, offset);
+ error = do_mmap_pgoff(file, addr, len, prot, flags, pgoff);
up(¤t->mm->mmap_sem);
if (file != NULL)
@@ -55,11 +56,29 @@ int sys_mmap(unsigned long addr, unsigne
out:
return error;
}
+
+asmlinkage unsigned long sys_mmap2(unsigned long addr, unsigned long len,
+ unsigned long prot, unsigned long flags, unsigned long fd,
+ unsigned long pgoff)
+{
+ /* Make sure the shift for mmap2 is constant (12), no matter what PAGE_SIZE
+ we have. */
+ return do_mmap2(addr, len, prot, flags, fd, pgoff >> (PAGE_SHIFT - 12));
+}
+
+asmlinkage unsigned long sys_mmap(unsigned long addr, unsigned long len,
+ unsigned long prot, unsigned long flags, unsigned long fd,
+ unsigned long offset)
+{
+ if (!(offset & ~PAGE_MASK)) {
+ return do_mmap2(addr, len, prot, flags, fd, offset >> PAGE_SHIFT);
+ } else {
+ return -EINVAL;
+ }
+}
-long sys_shmat_wrapper(int shmid, void *shmaddr, int shmflag)
+long sys_shmat_wrapper(int shmid, char *shmaddr, int shmflag)
{
- extern int sys_shmat(int shmid, char *shmaddr, int shmflg,
- unsigned long * raddr);
unsigned long raddr;
int r;
Index: arch/parisc/kernel/syscall.S
===================================================================
RCS file: /home/cvs/parisc/linux/arch/parisc/kernel/syscall.S,v
retrieving revision 1.58
diff -u -p -r1.58 syscall.S
--- syscall.S 2001/03/01 17:07:10 1.58
+++ syscall.S 2001/03/05 03:15:37
@@ -418,8 +418,7 @@ sys_call_table:
ENTRY_UHOH(uselib)
ENTRY_SAME(swapon)
ENTRY_SAME(reboot)
- ENTRY_SAME(ni_syscall)
- /* I'm not certain about off_t... */
+ ENTRY_SAME(mmap2)
ENTRY_SAME(mmap) /* 90 */
ENTRY_SAME(munmap)
ENTRY_SAME(truncate)
Index: include/asm-parisc/unistd.h
===================================================================
RCS file: /home/cvs/parisc/linux/include/asm-parisc/unistd.h,v
retrieving revision 1.18
diff -u -p -r1.18 unistd.h
--- unistd.h 2001/03/04 04:48:54 1.18
+++ unistd.h 2001/03/05 03:15:37
@@ -579,7 +579,7 @@
#define __NR_uselib (__NR_Linux + 86)
#define __NR_swapon (__NR_Linux + 87)
#define __NR_reboot (__NR_Linux + 88)
-/* #define __NR_readdir (__NR_Linux + 89) */
+#define __NR_mmap2 (__NR_Linux + 89)
#define __NR_mmap (__NR_Linux + 90)
#define __NR_munmap (__NR_Linux + 91)
#define __NR_truncate (__NR_Linux + 92)
@@ -795,7 +795,7 @@ type name(type1 arg1, type2 arg2, type3
}
-/* mmap takes 6 arguments */
+/* mmap & mmap2 take 6 arguments */
#define _syscall6(type,name,type1,arg1,type2,arg2,type3,arg3,type4,arg4,type5,arg5,type6,arg6) \
type name(type1 arg1, type2 arg2, type3 arg3, type4 arg4, type5 arg5, type6 arg6) \