diff -u --recursive --new-file pre3/linux/arch/i386/kernel/entry.S linux/arch/i386/kernel/entry.S --- pre3/linux/arch/i386/kernel/entry.S Mon Oct 8 10:39:58 2001 +++ linux/arch/i386/kernel/entry.S Wed Oct 17 10:02:39 2001 @@ -621,6 +621,7 @@ .long SYMBOL_NAME(sys_ni_syscall) /* reserved for TUX */ .long SYMBOL_NAME(sys_ni_syscall) /* Reserved for Security */ .long SYMBOL_NAME(sys_gettid) + .long SYMBOL_NAME(sys_readahead) /* 225 */ .rept NR_syscalls-(.-sys_call_table)/4 .long SYMBOL_NAME(sys_ni_syscall) diff -u --recursive --new-file pre3/linux/include/asm-i386/unistd.h linux/include/asm-i386/unistd.h --- pre3/linux/include/asm-i386/unistd.h Mon Oct 8 10:40:16 2001 +++ linux/include/asm-i386/unistd.h Wed Oct 17 10:03:03 2001 @@ -229,6 +229,7 @@ #define __NR_fcntl64 221 #define __NR_security 223 /* syscall for security modules */ #define __NR_gettid 224 +#define __NR_readahead 225 /* user-visible error numbers are in the range -1 - -124: see */ diff -u --recursive --new-file pre3/linux/mm/filemap.c linux/mm/filemap.c --- pre3/linux/mm/filemap.c Mon Oct 15 16:17:40 2001 +++ linux/mm/filemap.c Wed Oct 17 10:21:37 2001 @@ -1520,6 +1520,53 @@ return retval; } +static ssize_t do_readahead(struct file *file, unsigned long index, unsigned long nr) +{ + struct address_space *mapping = file->f_dentry->d_inode->i_mapping; + unsigned long max; + + if (!mapping || !mapping->a_ops || !mapping->a_ops->readpage) + return -EINVAL; + + /* Limit it to the size of the file.. */ + max = (mapping->host->i_size + ~PAGE_CACHE_MASK) >> PAGE_CACHE_SHIFT; + if (index > max) + return 0; + max -= index; + if (nr > max) + nr = max; + + /* And limit it to a sane percentage of the inactive list.. */ + max = nr_inactive_pages / 2; + if (nr > max) + nr = max; + + while (nr) { + page_cache_read(file, index); + index++; + nr--; + } + return 0; +} + +asmlinkage ssize_t sys_readahead(int fd, loff_t offset, size_t count) +{ + ssize_t ret; + struct file *file; + + ret = -EBADF; + file = fget(fd); + if (file) { + if (file->f_mode & FMODE_READ) { + unsigned long start = offset >> PAGE_CACHE_SHIFT; + unsigned long len = (count + ((long)offset & ~PAGE_CACHE_MASK)) >> PAGE_CACHE_SHIFT; + ret = do_readahead(file, start, len); + } + fput(file); + } + return ret; +} + /* * Read-ahead and flush behind for MADV_SEQUENTIAL areas. Since we are * sure this is sequential access, we don't need a flexible read-ahead