diff --git a/[refs] b/[refs] index 9d384886f8e6..dfc5bd35a800 100644 --- a/[refs] +++ b/[refs] @@ -1,2 +1,2 @@ --- -refs/heads/master: 64396accc2831fcbdc7d793edc25481a5ebc75b2 +refs/heads/master: 8cf32ac6578a70025be1103466da9d1d6141429e diff --git a/trunk/Documentation/lguest/lguest.txt b/trunk/Documentation/lguest/lguest.txt index 722d4e7fbebe..7885ab2d5f53 100644 --- a/trunk/Documentation/lguest/lguest.txt +++ b/trunk/Documentation/lguest/lguest.txt @@ -109,6 +109,10 @@ Running Lguest: See http://linux-net.osdl.org/index.php/Bridge for general information on how to get bridging working. +- You can also create an inter-guest network using + "--sharenet=": any two guests using the same file are on + the same network. This file is created if it does not exist. + There is a helpful mailing list at http://ozlabs.org/mailman/listinfo/lguest Good luck! diff --git a/trunk/Documentation/sysctl/vm.txt b/trunk/Documentation/sysctl/vm.txt index 6f31f0a247d0..b89570c30434 100644 --- a/trunk/Documentation/sysctl/vm.txt +++ b/trunk/Documentation/sysctl/vm.txt @@ -34,8 +34,6 @@ Currently, these files are in /proc/sys/vm: - oom_kill_allocating_task - mmap_min_address - numa_zonelist_order -- nr_hugepages -- nr_overcommit_hugepages ============================================================== @@ -307,20 +305,3 @@ will select "node" order in following case. Otherwise, "zone" order will be selected. Default order is recommended unless this is causing problems for your system/application. - -============================================================== - -nr_hugepages - -Change the minimum size of the hugepage pool. - -See Documentation/vm/hugetlbpage.txt - -============================================================== - -nr_overcommit_hugepages - -Change the maximum size of the hugepage pool. The maximum is -nr_hugepages + nr_overcommit_hugepages. - -See Documentation/vm/hugetlbpage.txt diff --git a/trunk/Documentation/vm/hugetlbpage.txt b/trunk/Documentation/vm/hugetlbpage.txt index f962d01bea2a..51ccc48aa763 100644 --- a/trunk/Documentation/vm/hugetlbpage.txt +++ b/trunk/Documentation/vm/hugetlbpage.txt @@ -30,10 +30,9 @@ alignment and size of the arguments to the above system calls. The output of "cat /proc/meminfo" will have lines like: ..... -HugePages_Total: vvv -HugePages_Free: www -HugePages_Rsvd: xxx -HugePages_Surp: yyy +HugePages_Total: xxx +HugePages_Free: yyy +HugePages_Rsvd: www Hugepagesize: zzz kB where: @@ -43,10 +42,6 @@ allocated. HugePages_Rsvd is short for "reserved," and is the number of hugepages for which a commitment to allocate from the pool has been made, but no allocation has yet been made. It's vaguely analogous to overcommit. -HugePages_Surp is short for "surplus," and is the number of hugepages in -the pool above the value in /proc/sys/vm/nr_hugepages. The maximum -number of surplus hugepages is controlled by -/proc/sys/vm/nr_overcommit_hugepages. /proc/filesystems should also show a filesystem of type "hugetlbfs" configured in the kernel. @@ -76,25 +71,7 @@ or failure of allocation depends on the amount of physically contiguous memory that is preset in system at this time. System administrators may want to put this command in one of the local rc init files. This will enable the kernel to request huge pages early in the boot process (when the possibility -of getting physical contiguous pages is still very high). In either -case, adminstrators will want to verify the number of hugepages actually -allocated by checking the sysctl or meminfo. - -/proc/sys/vm/nr_overcommit_hugepages indicates how large the pool of -hugepages can grow, if more hugepages than /proc/sys/vm/nr_hugepages are -requested by applications. echo'ing any non-zero value into this file -indicates that the hugetlb subsystem is allowed to try to obtain -hugepages from the buddy allocator, if the normal pool is exhausted. As -these surplus hugepages go out of use, they are freed back to the buddy -allocator. - -Caveat: Shrinking the pool via nr_hugepages while a surplus is in effect -will allow the number of surplus huge pages to exceed the overcommit -value, as the pool hugepages (which must have been in use for a surplus -hugepages to be allocated) will become surplus hugepages. As long as -this condition holds, however, no more surplus huge pages will be -allowed on the system until one of the two sysctls are increased -sufficiently, or the surplus huge pages go out of use and are freed. +of getting physical contiguous pages is still very high). If the user applications are going to request hugepages using mmap system call, then it is required that system administrator mount a file system of @@ -117,8 +94,8 @@ provided on command line then no limits are set. For size and nr_inodes options, you can use [G|g]/[M|m]/[K|k] to represent giga/mega/kilo. For example, size=2K has the same meaning as size=2048. -While read system calls are supported on files that reside on hugetlb -file systems, write system calls are not. +read and write system calls are not supported on files that reside on hugetlb +file systems. Regular chown, chgrp, and chmod commands (with right permissions) could be used to change the file attributes on hugetlbfs. diff --git a/trunk/arch/alpha/Makefile b/trunk/arch/alpha/Makefile index 4e1a8e2c4541..63104ebd1806 100644 --- a/trunk/arch/alpha/Makefile +++ b/trunk/arch/alpha/Makefile @@ -14,13 +14,13 @@ LDFLAGS_vmlinux := -static -N #-relax CHECKFLAGS += -D__alpha__ -m64 cflags-y := -pipe -mno-fp-regs -ffixed-8 -msmall-data -cpuflags-$(CONFIG_ALPHA_EV4) := -mcpu=ev4 -cpuflags-$(CONFIG_ALPHA_EV5) := -mcpu=ev5 -cpuflags-$(CONFIG_ALPHA_EV56) := -mcpu=ev56 +cpuflags-$(CONFIG_ALPHA_EV67) := -mcpu=ev67 +cpuflags-$(CONFIG_ALPHA_EV6) := -mcpu=ev6 cpuflags-$(CONFIG_ALPHA_POLARIS) := -mcpu=pca56 cpuflags-$(CONFIG_ALPHA_SX164) := -mcpu=pca56 -cpuflags-$(CONFIG_ALPHA_EV6) := -mcpu=ev6 -cpuflags-$(CONFIG_ALPHA_EV67) := -mcpu=ev67 +cpuflags-$(CONFIG_ALPHA_EV56) := -mcpu=ev56 +cpuflags-$(CONFIG_ALPHA_EV5) := -mcpu=ev5 +cpuflags-$(CONFIG_ALPHA_EV4) := -mcpu=ev4 # If GENERIC, make sure to turn off any instruction set extensions that # the host compiler might have on by default. Given that EV4 and EV5 # have the same instruction set, prefer EV5 because an EV5 schedule is diff --git a/trunk/arch/alpha/kernel/err_ev7.c b/trunk/arch/alpha/kernel/err_ev7.c index 68cd493f54c5..bc799f72d8c1 100644 --- a/trunk/arch/alpha/kernel/err_ev7.c +++ b/trunk/arch/alpha/kernel/err_ev7.c @@ -273,7 +273,7 @@ ev7_process_pal_subpacket(struct el_subpacket *header) struct el_subpacket_handler ev7_pal_subpacket_handler = SUBPACKET_HANDLER_INIT(EL_CLASS__PAL, ev7_process_pal_subpacket); -void __init +void ev7_register_error_handlers(void) { int i; diff --git a/trunk/arch/alpha/kernel/err_marvel.c b/trunk/arch/alpha/kernel/err_marvel.c index 413bf37eb094..497877bf2012 100644 --- a/trunk/arch/alpha/kernel/err_marvel.c +++ b/trunk/arch/alpha/kernel/err_marvel.c @@ -1152,7 +1152,7 @@ marvel_machine_check(u64 vector, u64 la_ptr) mb(); } -void __init +void marvel_register_error_handlers(void) { ev7_register_error_handlers(); diff --git a/trunk/arch/alpha/kernel/err_titan.c b/trunk/arch/alpha/kernel/err_titan.c index 257449ed15ef..6f3867877d9e 100644 --- a/trunk/arch/alpha/kernel/err_titan.c +++ b/trunk/arch/alpha/kernel/err_titan.c @@ -564,7 +564,7 @@ static struct el_subpacket_handler titan_subpacket_handler = SUBPACKET_HANDLER_INIT(EL_CLASS__REGATTA_FAMILY, el_process_regatta_subpacket); -void __init +void titan_register_error_handlers(void) { size_t i; diff --git a/trunk/arch/alpha/kernel/machvec_impl.h b/trunk/arch/alpha/kernel/machvec_impl.h index 466c9dff8181..0caa45aa128d 100644 --- a/trunk/arch/alpha/kernel/machvec_impl.h +++ b/trunk/arch/alpha/kernel/machvec_impl.h @@ -134,7 +134,7 @@ #define __initmv __initdata #define ALIAS_MV(x) #else -#define __initmv __initdata_refok +#define __initmv /* GCC actually has a syntax for defining aliases, but is under some delusion that you shouldn't be able to declare it extern somewhere diff --git a/trunk/arch/alpha/lib/ev6-stxncpy.S b/trunk/arch/alpha/lib/ev6-stxncpy.S index 1aa6e97e04b5..b581a7af2456 100644 --- a/trunk/arch/alpha/lib/ev6-stxncpy.S +++ b/trunk/arch/alpha/lib/ev6-stxncpy.S @@ -362,10 +362,10 @@ $unaligned: extql t2, a1, t2 # U : cmpbge zero, t1, t8 # E : is there a zero? - andnot t2, t6, t2 # E : dest mask for a single word copy + andnot t2, t6, t12 # E : dest mask for a single word copy or t8, t10, t5 # E : test for end-of-count too - cmpbge zero, t2, t3 # E : + cmpbge zero, t12, t3 # E : cmoveq a2, t5, t8 # E : Latency=2, extra map slot nop # E : keep with cmoveq andnot t8, t3, t8 # E : (stall) @@ -379,13 +379,13 @@ $unaligned: negq t8, t6 # E : build bitmask of bytes <= zero mskqh t1, t4, t1 # U : - and t6, t8, t12 # E : - subq t12, 1, t6 # E : (stall) - or t6, t12, t8 # E : (stall) - zapnot t2, t8, t2 # U : prepare source word; mirror changes (stall) + and t6, t8, t2 # E : + subq t2, 1, t6 # E : (stall) + or t6, t2, t8 # E : (stall) + zapnot t12, t8, t12 # U : prepare source word; mirror changes (stall) zapnot t1, t8, t1 # U : to source validity mask - andnot t0, t2, t0 # E : zero place for source to reside + andnot t0, t12, t0 # E : zero place for source to reside or t0, t1, t0 # E : and put it there (stall both t0, t1) stq_u t0, 0(a0) # L : (stall) diff --git a/trunk/arch/alpha/lib/strncpy.S b/trunk/arch/alpha/lib/strncpy.S index a46f7f3ad8c7..bbdef1be5f95 100644 --- a/trunk/arch/alpha/lib/strncpy.S +++ b/trunk/arch/alpha/lib/strncpy.S @@ -35,7 +35,7 @@ strncpy: or $3, $24, $3 # clear the bits between the last or $4, $27, $4 # written byte and the last byte in COUNT - andnot $3, $4, $4 + andnot $4, $3, $4 zap $1, $4, $1 stq_u $1, 0($16) diff --git a/trunk/arch/alpha/lib/stxncpy.S b/trunk/arch/alpha/lib/stxncpy.S index 3dece25283a3..da1a72740d29 100644 --- a/trunk/arch/alpha/lib/stxncpy.S +++ b/trunk/arch/alpha/lib/stxncpy.S @@ -315,9 +315,9 @@ $unaligned: extql t2, a1, t2 # e0 : cmpbge zero, t1, t8 # .. e1 : is there a zero? - andnot t2, t6, t2 # e0 : dest mask for a single word copy + andnot t2, t6, t12 # e0 : dest mask for a single word copy or t8, t10, t5 # .. e1 : test for end-of-count too - cmpbge zero, t2, t3 # e0 : + cmpbge zero, t12, t3 # e0 : cmoveq a2, t5, t8 # .. e1 : andnot t8, t3, t8 # e0 : beq t8, $u_head # .. e1 (zdb) @@ -330,14 +330,14 @@ $unaligned: ldq_u t0, 0(a0) # e0 : negq t8, t6 # .. e1 : build bitmask of bytes <= zero mskqh t1, t4, t1 # e0 : - and t6, t8, t12 # .. e1 : - subq t12, 1, t6 # e0 : - or t6, t12, t8 # e1 : + and t6, t8, t2 # .. e1 : + subq t2, 1, t6 # e0 : + or t6, t2, t8 # e1 : - zapnot t2, t8, t2 # e0 : prepare source word; mirror changes + zapnot t12, t8, t12 # e0 : prepare source word; mirror changes zapnot t1, t8, t1 # .. e1 : to source validity mask - andnot t0, t2, t0 # e0 : zero place for source to reside + andnot t0, t12, t0 # e0 : zero place for source to reside or t0, t1, t0 # e1 : and put it there stq_u t0, 0(a0) # e0 : ret (t9) # .. e1 : diff --git a/trunk/arch/um/drivers/net_user.c b/trunk/arch/um/drivers/net_user.c index 29185cad9fff..90d7f2e8ead8 100644 --- a/trunk/arch/um/drivers/net_user.c +++ b/trunk/arch/um/drivers/net_user.c @@ -201,7 +201,7 @@ static int change_tramp(char **argv, char *output, int output_len) close(fds[1]); if (pid > 0) - helper_wait(pid, 0, "change_tramp"); + CATCH_EINTR(err = waitpid(pid, NULL, 0)); return pid; } diff --git a/trunk/arch/um/drivers/slip_user.c b/trunk/arch/um/drivers/slip_user.c index b8711e50da80..5f06204d6871 100644 --- a/trunk/arch/um/drivers/slip_user.c +++ b/trunk/arch/um/drivers/slip_user.c @@ -77,7 +77,7 @@ static int slip_tramp(char **argv, int fd) { struct slip_pre_exec_data pe_data; char *output; - int pid, fds[2], err, output_len; + int status, pid, fds[2], err, output_len; err = os_pipe(fds, 1, 0); if (err < 0) { @@ -109,7 +109,15 @@ static int slip_tramp(char **argv, int fd) read_output(fds[0], output, output_len); printk("%s", output); - err = helper_wait(pid, 0, argv[0]); + CATCH_EINTR(err = waitpid(pid, &status, 0)); + if (err < 0) + err = errno; + else if (!WIFEXITED(status) || (WEXITSTATUS(status) != 0)) { + printk(UM_KERN_ERR "'%s' didn't exit with status 0\n", argv[0]); + err = -EINVAL; + } + else err = 0; + close(fds[0]); out_free: diff --git a/trunk/arch/um/drivers/slirp_user.c b/trunk/arch/um/drivers/slirp_user.c index 89c1be225fda..1865089ff41a 100644 --- a/trunk/arch/um/drivers/slirp_user.c +++ b/trunk/arch/um/drivers/slirp_user.c @@ -79,7 +79,7 @@ static int slirp_open(void *data) static void slirp_close(int fd, void *data) { struct slirp_data *pri = data; - int err; + int status,err; close(fd); close(pri->slave); @@ -98,9 +98,18 @@ static void slirp_close(int fd, void *data) "(%d)\n", pri->pid, errno); } #endif - err = helper_wait(pri->pid, 1, "slirp_close"); - if (err < 0) + + CATCH_EINTR(err = waitpid(pri->pid, &status, WNOHANG)); + if (err < 0) { + printk(UM_KERN_ERR "slirp_close: waitpid returned %d\n", errno); + return; + } + + if (err == 0) { + printk(UM_KERN_ERR "slirp_close: process %d has not exited\n", + pri->pid); return; + } pri->pid = -1; } diff --git a/trunk/arch/um/drivers/ubd_user.c b/trunk/arch/um/drivers/ubd_user.c index 48fc7452bc1d..41d254bd38df 100644 --- a/trunk/arch/um/drivers/ubd_user.c +++ b/trunk/arch/um/drivers/ubd_user.c @@ -49,7 +49,8 @@ int start_io_thread(unsigned long sp, int *fd_out) goto out_close; } - pid = clone(io_thread, (void *) sp, CLONE_FILES | CLONE_VM, NULL); + pid = clone(io_thread, (void *) sp, CLONE_FILES | CLONE_VM | SIGCHLD, + NULL); if(pid < 0){ err = -errno; printk("start_io_thread - clone failed : errno = %d\n", errno); diff --git a/trunk/arch/um/include/os.h b/trunk/arch/um/include/os.h index 6f0d1c741bca..fbf0a87c6eaa 100644 --- a/trunk/arch/um/include/os.h +++ b/trunk/arch/um/include/os.h @@ -214,7 +214,7 @@ extern int execvp_noalloc(char *buf, const char *file, char *const argv[]); extern int run_helper(void (*pre_exec)(void *), void *pre_data, char **argv); extern int run_helper_thread(int (*proc)(void *), void *arg, unsigned int flags, unsigned long *stack_out); -extern int helper_wait(int pid, int nohang, char *pname); +extern int helper_wait(int pid); /* tls.c */ diff --git a/trunk/arch/um/os-Linux/aio.c b/trunk/arch/um/os-Linux/aio.c index 93dc0c80ebaf..4158118c4a56 100644 --- a/trunk/arch/um/os-Linux/aio.c +++ b/trunk/arch/um/os-Linux/aio.c @@ -218,7 +218,7 @@ static int init_aio_24(void) goto out_close_pipe; err = run_helper_thread(not_aio_thread, NULL, - CLONE_FILES | CLONE_VM, &aio_stack); + CLONE_FILES | CLONE_VM | SIGCHLD, &aio_stack); if (err < 0) goto out_close_pipe; @@ -254,7 +254,7 @@ static int init_aio_26(void) } err = run_helper_thread(aio_thread, NULL, - CLONE_FILES | CLONE_VM, &aio_stack); + CLONE_FILES | CLONE_VM | SIGCHLD, &aio_stack); if (err < 0) return err; diff --git a/trunk/arch/um/os-Linux/drivers/ethertap_user.c b/trunk/arch/um/os-Linux/drivers/ethertap_user.c index 07ca0cb472ac..4ff553603449 100644 --- a/trunk/arch/um/os-Linux/drivers/ethertap_user.c +++ b/trunk/arch/um/os-Linux/drivers/ethertap_user.c @@ -94,7 +94,7 @@ static int etap_tramp(char *dev, char *gate, int control_me, int control_remote, int data_me, int data_remote) { struct etap_pre_exec_data pe_data; - int pid, err, n; + int pid, status, err, n; char version_buf[sizeof("nnnnn\0")]; char data_fd_buf[sizeof("nnnnnn\0")]; char gate_buf[sizeof("nnn.nnn.nnn.nnn\0")]; @@ -131,7 +131,13 @@ static int etap_tramp(char *dev, char *gate, int control_me, } if (c != 1) { printk(UM_KERN_ERR "etap_tramp : uml_net failed\n"); - err = helper_wait(pid, 0, "uml_net"); + err = -EINVAL; + CATCH_EINTR(n = waitpid(pid, &status, 0)); + if (n < 0) + err = -errno; + else if (!WIFEXITED(status) || (WEXITSTATUS(status) != 1)) + printk(UM_KERN_ERR "uml_net didn't exit with " + "status 1\n"); } return err; } diff --git a/trunk/arch/um/os-Linux/drivers/tuntap_user.c b/trunk/arch/um/os-Linux/drivers/tuntap_user.c index 1037a3b6386e..6c55d3c8ead8 100644 --- a/trunk/arch/um/os-Linux/drivers/tuntap_user.c +++ b/trunk/arch/um/os-Linux/drivers/tuntap_user.c @@ -107,7 +107,7 @@ static int tuntap_open_tramp(char *gate, int *fd_out, int me, int remote, "errno = %d\n", errno); return err; } - helper_wait(pid, 0, "tuntap_open_tramp"); + CATCH_EINTR(waitpid(pid, NULL, 0)); cmsg = CMSG_FIRSTHDR(&msg); if (cmsg == NULL) { diff --git a/trunk/arch/um/os-Linux/helper.c b/trunk/arch/um/os-Linux/helper.c index fba3f0fefeef..7a72dbb61b0d 100644 --- a/trunk/arch/um/os-Linux/helper.c +++ b/trunk/arch/um/os-Linux/helper.c @@ -76,7 +76,7 @@ int run_helper(void (*pre_exec)(void *), void *pre_data, char **argv) data.fd = fds[1]; data.buf = __cant_sleep() ? kmalloc(PATH_MAX, UM_GFP_ATOMIC) : kmalloc(PATH_MAX, UM_GFP_KERNEL); - pid = clone(helper_child, (void *) sp, CLONE_VM, &data); + pid = clone(helper_child, (void *) sp, CLONE_VM | SIGCHLD, &data); if (pid < 0) { ret = -errno; printk("run_helper : clone failed, errno = %d\n", errno); @@ -101,7 +101,7 @@ int run_helper(void (*pre_exec)(void *), void *pre_data, char **argv) ret = n; kill(pid, SIGKILL); } - CATCH_EINTR(waitpid(pid, NULL, __WCLONE)); + CATCH_EINTR(waitpid(pid, NULL, 0)); } out_free2: @@ -126,7 +126,7 @@ int run_helper_thread(int (*proc)(void *), void *arg, unsigned int flags, return -ENOMEM; sp = stack + UM_KERN_PAGE_SIZE - sizeof(void *); - pid = clone(proc, (void *) sp, flags, arg); + pid = clone(proc, (void *) sp, flags | SIGCHLD, arg); if (pid < 0) { err = -errno; printk("run_helper_thread : clone failed, errno = %d\n", @@ -134,7 +134,7 @@ int run_helper_thread(int (*proc)(void *), void *arg, unsigned int flags, return err; } if (stack_out == NULL) { - CATCH_EINTR(pid = waitpid(pid, &status, __WCLONE)); + CATCH_EINTR(pid = waitpid(pid, &status, 0)); if (pid < 0) { err = -errno; printk("run_helper_thread - wait failed, errno = %d\n", @@ -150,30 +150,14 @@ int run_helper_thread(int (*proc)(void *), void *arg, unsigned int flags, return pid; } -int helper_wait(int pid, int nohang, char *pname) +int helper_wait(int pid) { - int ret, status; - int wflags = __WCLONE; + int ret; - if (nohang) - wflags |= WNOHANG; - - if (!pname) - pname = "helper_wait"; - - CATCH_EINTR(ret = waitpid(pid, &status, wflags)); + CATCH_EINTR(ret = waitpid(pid, NULL, WNOHANG)); if (ret < 0) { - printk(UM_KERN_ERR "%s : waitpid process %d failed, " - "errno = %d\n", pname, pid, errno); - return -errno; - } else if (nohang && ret == 0) { - printk(UM_KERN_ERR "%s : process %d has not exited\n", - pname, pid); - return -ECHILD; - } else if (!WIFEXITED(status) || WEXITSTATUS(status) != 0) { - printk(UM_KERN_ERR "%s : process %d didn't exit with " - "status 0\n", pname, pid); - return -ECHILD; - } else - return 0; + ret = -errno; + printk("helper_wait : waitpid failed, errno = %d\n", errno); + } + return ret; } diff --git a/trunk/arch/um/os-Linux/process.c b/trunk/arch/um/os-Linux/process.c index bda5c3150d6c..37781db4ceca 100644 --- a/trunk/arch/um/os-Linux/process.c +++ b/trunk/arch/um/os-Linux/process.c @@ -101,7 +101,7 @@ void os_kill_process(int pid, int reap_child) { kill(pid, SIGKILL); if (reap_child) - CATCH_EINTR(waitpid(pid, NULL, __WALL)); + CATCH_EINTR(waitpid(pid, NULL, 0)); } /* This is here uniquely to have access to the userspace errno, i.e. the one @@ -130,7 +130,7 @@ void os_kill_ptraced_process(int pid, int reap_child) ptrace(PTRACE_KILL, pid); ptrace(PTRACE_CONT, pid); if (reap_child) - CATCH_EINTR(waitpid(pid, NULL, __WALL)); + CATCH_EINTR(waitpid(pid, NULL, 0)); } /* Don't use the glibc version, which caches the result in TLS. It misses some diff --git a/trunk/arch/um/os-Linux/skas/process.c b/trunk/arch/um/os-Linux/skas/process.c index e8b7a97e83d3..d77c81d7068a 100644 --- a/trunk/arch/um/os-Linux/skas/process.c +++ b/trunk/arch/um/os-Linux/skas/process.c @@ -64,7 +64,7 @@ void wait_stub_done(int pid) int n, status, err; while (1) { - CATCH_EINTR(n = waitpid(pid, &status, WUNTRACED | __WALL)); + CATCH_EINTR(n = waitpid(pid, &status, WUNTRACED)); if ((n < 0) || !WIFSTOPPED(status)) goto bad_wait; @@ -153,7 +153,7 @@ static void handle_trap(int pid, struct uml_pt_regs *regs, panic("handle_trap - continuing to end of syscall " "failed, errno = %d\n", errno); - CATCH_EINTR(err = waitpid(pid, &status, WUNTRACED | __WALL)); + CATCH_EINTR(err = waitpid(pid, &status, WUNTRACED)); if ((err < 0) || !WIFSTOPPED(status) || (WSTOPSIG(status) != SIGTRAP + 0x80)) { err = ptrace_dump_regs(pid); @@ -255,18 +255,16 @@ int start_userspace(unsigned long stub_stack) panic("start_userspace : mmap failed, errno = %d", errno); sp = (unsigned long) stack + UM_KERN_PAGE_SIZE - sizeof(void *); - flags = CLONE_FILES; + flags = CLONE_FILES | SIGCHLD; if (proc_mm) flags |= CLONE_VM; - else - flags |= SIGCHLD; pid = clone(userspace_tramp, (void *) sp, flags, (void *) stub_stack); if (pid < 0) panic("start_userspace : clone failed, errno = %d", errno); do { - CATCH_EINTR(n = waitpid(pid, &status, WUNTRACED | __WALL)); + CATCH_EINTR(n = waitpid(pid, &status, WUNTRACED)); if (n < 0) panic("start_userspace : wait failed, errno = %d", errno); @@ -316,7 +314,7 @@ void userspace(struct uml_pt_regs *regs) "pid=%d, ptrace operation = %d, errno = %d\n", pid, op, errno); - CATCH_EINTR(err = waitpid(pid, &status, WUNTRACED | __WALL)); + CATCH_EINTR(err = waitpid(pid, &status, WUNTRACED)); if (err < 0) panic("userspace - waitpid failed, errno = %d\n", errno); diff --git a/trunk/arch/um/os-Linux/util.c b/trunk/arch/um/os-Linux/util.c index 3e058ce9ffb6..ef095436a78c 100644 --- a/trunk/arch/um/os-Linux/util.c +++ b/trunk/arch/um/os-Linux/util.c @@ -141,7 +141,7 @@ void os_dump_core(void) * nothing reasonable to do if that fails. */ - while ((pid = waitpid(-1, NULL, WNOHANG | __WALL)) > 0) + while ((pid = waitpid(-1, NULL, WNOHANG)) > 0) os_kill_ptraced_process(pid, 0); abort(); diff --git a/trunk/arch/x86/kernel/suspend_64.c b/trunk/arch/x86/kernel/suspend_64.c index 2e5efaaf8800..db284ef44d53 100644 --- a/trunk/arch/x86/kernel/suspend_64.c +++ b/trunk/arch/x86/kernel/suspend_64.c @@ -192,25 +192,42 @@ static int res_phys_pud_init(pud_t *pud, unsigned long address, unsigned long en return 0; } +static int res_kernel_text_pud_init(pud_t *pud, unsigned long start) +{ + pmd_t *pmd; + unsigned long paddr; + + pmd = (pmd_t *)get_safe_page(GFP_ATOMIC); + if (!pmd) + return -ENOMEM; + set_pud(pud + pud_index(start), __pud(__pa(pmd) | _KERNPG_TABLE)); + for (paddr = 0; paddr < KERNEL_TEXT_SIZE; pmd++, paddr += PMD_SIZE) { + unsigned long pe; + + pe = __PAGE_KERNEL_LARGE_EXEC | _PAGE_GLOBAL | paddr; + pe &= __supported_pte_mask; + set_pmd(pmd, __pmd(pe)); + } + + return 0; +} + static int set_up_temporary_mappings(void) { unsigned long start, end, next; + pud_t *pud; int error; temp_level4_pgt = (pgd_t *)get_safe_page(GFP_ATOMIC); if (!temp_level4_pgt) return -ENOMEM; - /* It is safe to reuse the original kernel mapping */ - set_pgd(temp_level4_pgt + pgd_index(__START_KERNEL_map), - init_level4_pgt[pgd_index(__START_KERNEL_map)]); - /* Set up the direct mapping from scratch */ start = (unsigned long)pfn_to_kaddr(0); end = (unsigned long)pfn_to_kaddr(end_pfn); for (; start < end; start = next) { - pud_t *pud = (pud_t *)get_safe_page(GFP_ATOMIC); + pud = (pud_t *)get_safe_page(GFP_ATOMIC); if (!pud) return -ENOMEM; next = start + PGDIR_SIZE; @@ -221,7 +238,17 @@ static int set_up_temporary_mappings(void) set_pgd(temp_level4_pgt + pgd_index(start), mk_kernel_pgd(__pa(pud))); } - return 0; + + /* Set up the kernel text mapping from scratch */ + pud = (pud_t *)get_safe_page(GFP_ATOMIC); + if (!pud) + return -ENOMEM; + error = res_kernel_text_pud_init(pud, __START_KERNEL_map); + if (!error) + set_pgd(temp_level4_pgt + pgd_index(__START_KERNEL_map), + __pgd(__pa(pud) | _PAGE_TABLE)); + + return error; } int swsusp_arch_resume(void) diff --git a/trunk/drivers/ata/sata_sil.c b/trunk/drivers/ata/sata_sil.c index 4e6e381279cc..025622b14efb 100644 --- a/trunk/drivers/ata/sata_sil.c +++ b/trunk/drivers/ata/sata_sil.c @@ -390,23 +390,28 @@ static void sil_host_intr(struct ata_port *ap, u32 bmdma2) sil_scr_read(ap, SCR_ERROR, &serror); sil_scr_write(ap, SCR_ERROR, serror); - /* Trigger hotplug and accumulate SError only if the - * port isn't already frozen. Otherwise, PHY events - * during hardreset makes controllers with broken SIEN - * repeat probing needlessly. + /* Sometimes spurious interrupts occur, double check + * it's PHYRDY CHG. */ - if (!(ap->pflags & ATA_PFLAG_FROZEN)) { - ata_ehi_hotplugged(&ap->link.eh_info); - ap->link.eh_info.serror |= serror; + if (serror & SERR_PHYRDY_CHG) { + /* Trigger hotplug and accumulate SError only + * if the port isn't already frozen. + * Otherwise, PHY events during hardreset + * makes controllers with broken SIEN repeat + * probing needlessly. + */ + if (!(ap->pflags & ATA_PFLAG_FROZEN)) { + ata_ehi_hotplugged(&ap->link.eh_info); + ap->link.eh_info.serror |= serror; + } + goto freeze; } - goto freeze; + if (!(bmdma2 & SIL_DMA_COMPLETE)) + return; } - if (unlikely(!qc)) - goto freeze; - - if (unlikely(qc->tf.flags & ATA_TFLAG_POLLING)) { + if (unlikely(!qc || (qc->tf.flags & ATA_TFLAG_POLLING))) { /* this sometimes happens, just clear IRQ */ ata_chk_status(ap); return; diff --git a/trunk/drivers/block/pktcdvd.c b/trunk/drivers/block/pktcdvd.c index 3535ef896677..a5ee21319d37 100644 --- a/trunk/drivers/block/pktcdvd.c +++ b/trunk/drivers/block/pktcdvd.c @@ -117,10 +117,8 @@ static struct pktcdvd_kobj* pkt_kobj_create(struct pktcdvd_device *pd, p->kobj.parent = parent; p->kobj.ktype = ktype; p->pd = pd; - if (kobject_register(&p->kobj) != 0) { - kobject_put(&p->kobj); + if (kobject_register(&p->kobj) != 0) return NULL; - } return p; } /* diff --git a/trunk/drivers/cpufreq/cpufreq.c b/trunk/drivers/cpufreq/cpufreq.c index 79581fab82d6..5e626b12b97e 100644 --- a/trunk/drivers/cpufreq/cpufreq.c +++ b/trunk/drivers/cpufreq/cpufreq.c @@ -841,25 +841,19 @@ static int cpufreq_add_dev (struct sys_device * sys_dev) drv_attr = cpufreq_driver->attr; while ((drv_attr) && (*drv_attr)) { ret = sysfs_create_file(&policy->kobj, &((*drv_attr)->attr)); - if (ret) { - unlock_policy_rwsem_write(cpu); + if (ret) goto err_out_driver_exit; - } drv_attr++; } if (cpufreq_driver->get){ ret = sysfs_create_file(&policy->kobj, &cpuinfo_cur_freq.attr); - if (ret) { - unlock_policy_rwsem_write(cpu); + if (ret) goto err_out_driver_exit; - } } if (cpufreq_driver->target){ ret = sysfs_create_file(&policy->kobj, &scaling_cur_freq.attr); - if (ret) { - unlock_policy_rwsem_write(cpu); + if (ret) goto err_out_driver_exit; - } } spin_lock_irqsave(&cpufreq_driver_lock, flags); diff --git a/trunk/drivers/cpufreq/cpufreq_stats.c b/trunk/drivers/cpufreq/cpufreq_stats.c index 1b8312b02006..8a45d0f93e26 100644 --- a/trunk/drivers/cpufreq/cpufreq_stats.c +++ b/trunk/drivers/cpufreq/cpufreq_stats.c @@ -164,7 +164,7 @@ freq_table_get_index(struct cpufreq_stats *stat, unsigned int freq) return -1; } -static void cpufreq_stats_free_table(unsigned int cpu) +static void __cpuexit cpufreq_stats_free_table(unsigned int cpu) { struct cpufreq_stats *stat = cpufreq_stats_table[cpu]; struct cpufreq_policy *policy = cpufreq_cpu_get(cpu); diff --git a/trunk/drivers/dma/ioat_dma.c b/trunk/drivers/dma/ioat_dma.c index 45e7b4666c7b..c1c2dcc6fc2e 100644 --- a/trunk/drivers/dma/ioat_dma.c +++ b/trunk/drivers/dma/ioat_dma.c @@ -173,47 +173,10 @@ static void ioat_set_dest(dma_addr_t addr, tx_to_ioat_desc(tx)->dst = addr; } -/** - * ioat_dma_memcpy_issue_pending - push potentially unrecognized appended - * descriptors to hw - * @chan: DMA channel handle - */ static inline void __ioat1_dma_memcpy_issue_pending( - struct ioat_dma_chan *ioat_chan) -{ - ioat_chan->pending = 0; - writeb(IOAT_CHANCMD_APPEND, ioat_chan->reg_base + IOAT1_CHANCMD_OFFSET); -} - -static void ioat1_dma_memcpy_issue_pending(struct dma_chan *chan) -{ - struct ioat_dma_chan *ioat_chan = to_ioat_chan(chan); - - if (ioat_chan->pending != 0) { - spin_lock_bh(&ioat_chan->desc_lock); - __ioat1_dma_memcpy_issue_pending(ioat_chan); - spin_unlock_bh(&ioat_chan->desc_lock); - } -} - + struct ioat_dma_chan *ioat_chan); static inline void __ioat2_dma_memcpy_issue_pending( - struct ioat_dma_chan *ioat_chan) -{ - ioat_chan->pending = 0; - writew(ioat_chan->dmacount, - ioat_chan->reg_base + IOAT_CHAN_DMACOUNT_OFFSET); -} - -static void ioat2_dma_memcpy_issue_pending(struct dma_chan *chan) -{ - struct ioat_dma_chan *ioat_chan = to_ioat_chan(chan); - - if (ioat_chan->pending != 0) { - spin_lock_bh(&ioat_chan->desc_lock); - __ioat2_dma_memcpy_issue_pending(ioat_chan); - spin_unlock_bh(&ioat_chan->desc_lock); - } -} + struct ioat_dma_chan *ioat_chan); static dma_cookie_t ioat1_tx_submit(struct dma_async_tx_descriptor *tx) { @@ -240,7 +203,7 @@ static dma_cookie_t ioat1_tx_submit(struct dma_async_tx_descriptor *tx) prev = to_ioat_desc(ioat_chan->used_desc.prev); prefetch(prev->hw); do { - copy = min_t(size_t, len, ioat_chan->xfercap); + copy = min((u32) len, ioat_chan->xfercap); new->async_tx.ack = 1; @@ -328,12 +291,10 @@ static dma_cookie_t ioat2_tx_submit(struct dma_async_tx_descriptor *tx) orig_ack = first->async_tx.ack; new = first; - /* - * ioat_chan->desc_lock is still in force in version 2 path - * it gets unlocked at end of this function - */ + /* ioat_chan->desc_lock is still in force in version 2 path */ + do { - copy = min_t(size_t, len, ioat_chan->xfercap); + copy = min((u32) len, ioat_chan->xfercap); new->async_tx.ack = 1; @@ -471,7 +432,7 @@ static void ioat2_dma_massage_chan_desc(struct ioat_dma_chan *ioat_chan) static int ioat_dma_alloc_chan_resources(struct dma_chan *chan) { struct ioat_dma_chan *ioat_chan = to_ioat_chan(chan); - struct ioat_desc_sw *desc; + struct ioat_desc_sw *desc = NULL; u16 chanctrl; u32 chanerr; int i; @@ -614,7 +575,7 @@ static void ioat_dma_free_chan_resources(struct dma_chan *chan) static struct ioat_desc_sw * ioat1_dma_get_next_descriptor(struct ioat_dma_chan *ioat_chan) { - struct ioat_desc_sw *new; + struct ioat_desc_sw *new = NULL; if (!list_empty(&ioat_chan->free_desc)) { new = to_ioat_desc(ioat_chan->free_desc.next); @@ -622,11 +583,9 @@ ioat1_dma_get_next_descriptor(struct ioat_dma_chan *ioat_chan) } else { /* try to get another desc */ new = ioat_dma_alloc_descriptor(ioat_chan, GFP_ATOMIC); - if (!new) { - dev_err(&ioat_chan->device->pdev->dev, - "alloc failed\n"); - return NULL; - } + /* will this ever happen? */ + /* TODO add upper limit on these */ + BUG_ON(!new); } prefetch(new->hw); @@ -636,7 +595,7 @@ ioat1_dma_get_next_descriptor(struct ioat_dma_chan *ioat_chan) static struct ioat_desc_sw * ioat2_dma_get_next_descriptor(struct ioat_dma_chan *ioat_chan) { - struct ioat_desc_sw *new; + struct ioat_desc_sw *new = NULL; /* * used.prev points to where to start processing @@ -650,8 +609,8 @@ ioat2_dma_get_next_descriptor(struct ioat_dma_chan *ioat_chan) if (ioat_chan->used_desc.prev && ioat_chan->used_desc.next == ioat_chan->used_desc.prev->prev) { - struct ioat_desc_sw *desc; - struct ioat_desc_sw *noop_desc; + struct ioat_desc_sw *desc = NULL; + struct ioat_desc_sw *noop_desc = NULL; int i; /* set up the noop descriptor */ @@ -665,14 +624,10 @@ ioat2_dma_get_next_descriptor(struct ioat_dma_chan *ioat_chan) ioat_chan->pending++; ioat_chan->dmacount++; - /* try to get a few more descriptors */ + /* get a few more descriptors */ for (i = 16; i; i--) { desc = ioat_dma_alloc_descriptor(ioat_chan, GFP_ATOMIC); - if (!desc) { - dev_err(&ioat_chan->device->pdev->dev, - "alloc failed\n"); - break; - } + BUG_ON(!desc); list_add_tail(&desc->node, ioat_chan->used_desc.next); desc->hw->next @@ -722,13 +677,10 @@ static struct dma_async_tx_descriptor *ioat1_dma_prep_memcpy( spin_lock_bh(&ioat_chan->desc_lock); new = ioat_dma_get_next_descriptor(ioat_chan); + new->len = len; spin_unlock_bh(&ioat_chan->desc_lock); - if (new) { - new->len = len; - return &new->async_tx; - } else - return NULL; + return new ? &new->async_tx : NULL; } static struct dma_async_tx_descriptor *ioat2_dma_prep_memcpy( @@ -741,17 +693,53 @@ static struct dma_async_tx_descriptor *ioat2_dma_prep_memcpy( spin_lock_bh(&ioat_chan->desc_lock); new = ioat2_dma_get_next_descriptor(ioat_chan); + new->len = len; - /* - * leave ioat_chan->desc_lock set in ioat 2 path - * it will get unlocked at end of tx_submit - */ + /* leave ioat_chan->desc_lock set in version 2 path */ + return new ? &new->async_tx : NULL; +} - if (new) { - new->len = len; - return &new->async_tx; - } else - return NULL; + +/** + * ioat_dma_memcpy_issue_pending - push potentially unrecognized appended + * descriptors to hw + * @chan: DMA channel handle + */ +static inline void __ioat1_dma_memcpy_issue_pending( + struct ioat_dma_chan *ioat_chan) +{ + ioat_chan->pending = 0; + writeb(IOAT_CHANCMD_APPEND, ioat_chan->reg_base + IOAT1_CHANCMD_OFFSET); +} + +static void ioat1_dma_memcpy_issue_pending(struct dma_chan *chan) +{ + struct ioat_dma_chan *ioat_chan = to_ioat_chan(chan); + + if (ioat_chan->pending != 0) { + spin_lock_bh(&ioat_chan->desc_lock); + __ioat1_dma_memcpy_issue_pending(ioat_chan); + spin_unlock_bh(&ioat_chan->desc_lock); + } +} + +static inline void __ioat2_dma_memcpy_issue_pending( + struct ioat_dma_chan *ioat_chan) +{ + ioat_chan->pending = 0; + writew(ioat_chan->dmacount, + ioat_chan->reg_base + IOAT_CHAN_DMACOUNT_OFFSET); +} + +static void ioat2_dma_memcpy_issue_pending(struct dma_chan *chan) +{ + struct ioat_dma_chan *ioat_chan = to_ioat_chan(chan); + + if (ioat_chan->pending != 0) { + spin_lock_bh(&ioat_chan->desc_lock); + __ioat2_dma_memcpy_issue_pending(ioat_chan); + spin_unlock_bh(&ioat_chan->desc_lock); + } } static void ioat_dma_cleanup_tasklet(unsigned long data) @@ -1031,7 +1019,7 @@ static void ioat_dma_start_null_desc(struct ioat_dma_chan *ioat_chan) static void ioat_dma_test_callback(void *dma_async_param) { printk(KERN_ERR "ioatdma: ioat_dma_test_callback(%p)\n", - dma_async_param); + dma_async_param); } /** @@ -1044,7 +1032,7 @@ static int ioat_dma_self_test(struct ioatdma_device *device) u8 *src; u8 *dest; struct dma_chan *dma_chan; - struct dma_async_tx_descriptor *tx; + struct dma_async_tx_descriptor *tx = NULL; dma_addr_t addr; dma_cookie_t cookie; int err = 0; @@ -1363,7 +1351,7 @@ struct ioatdma_device *ioat_dma_probe(struct pci_dev *pdev, err_dma_pool: kfree(device); err_kzalloc: - dev_err(&pdev->dev, + dev_err(&device->pdev->dev, "Intel(R) I/OAT DMA Engine initialization failed\n"); return NULL; } diff --git a/trunk/drivers/dma/ioatdma.h b/trunk/drivers/dma/ioatdma.h index f2c7fedbf009..b668234ef654 100644 --- a/trunk/drivers/dma/ioatdma.h +++ b/trunk/drivers/dma/ioatdma.h @@ -76,7 +76,7 @@ struct ioat_dma_chan { dma_cookie_t completed_cookie; unsigned long last_completion; - size_t xfercap; /* XFERCAP register value expanded out */ + u32 xfercap; /* XFERCAP register value expanded out */ spinlock_t cleanup_lock; spinlock_t desc_lock; diff --git a/trunk/drivers/macintosh/via-pmu.c b/trunk/drivers/macintosh/via-pmu.c index 6123c70153d3..dc741d3a4531 100644 --- a/trunk/drivers/macintosh/via-pmu.c +++ b/trunk/drivers/macintosh/via-pmu.c @@ -2336,7 +2336,6 @@ powerbook_sleep_3400(void) ret = pmac_suspend_devices(); if (ret) { pbook_free_pci_save(); - iounmap(mem_ctrl); printk(KERN_ERR "Sleep rejected by devices\n"); return ret; } diff --git a/trunk/drivers/parport/procfs.c b/trunk/drivers/parport/procfs.c index d950fc34320a..ed82e41210d1 100644 --- a/trunk/drivers/parport/procfs.c +++ b/trunk/drivers/parport/procfs.c @@ -384,7 +384,7 @@ parport_device_sysctl_template = { { .procname = "timeslice", .data = NULL, - .maxlen = sizeof(unsigned long), + .maxlen = sizeof(int), .mode = 0644, .proc_handler = &proc_doulongvec_ms_jiffies_minmax, .extra1 = (void*) &parport_min_timeslice_value, diff --git a/trunk/drivers/rtc/rtc-at32ap700x.c b/trunk/drivers/rtc/rtc-at32ap700x.c index d3b9b14267ab..2999214ca534 100644 --- a/trunk/drivers/rtc/rtc-at32ap700x.c +++ b/trunk/drivers/rtc/rtc-at32ap700x.c @@ -225,12 +225,18 @@ static int __init at32_rtc_probe(struct platform_device *pdev) goto out; } + ret = request_irq(irq, at32_rtc_interrupt, IRQF_SHARED, "rtc", rtc); + if (ret) { + dev_dbg(&pdev->dev, "could not request irq %d\n", irq); + goto out; + } + rtc->irq = irq; rtc->regs = ioremap(regs->start, regs->end - regs->start + 1); if (!rtc->regs) { ret = -ENOMEM; dev_dbg(&pdev->dev, "could not map I/O memory\n"); - goto out; + goto out_free_irq; } spin_lock_init(&rtc->lock); @@ -247,18 +253,12 @@ static int __init at32_rtc_probe(struct platform_device *pdev) | RTC_BIT(CTRL_EN)); } - ret = request_irq(irq, at32_rtc_interrupt, IRQF_SHARED, "rtc", rtc); - if (ret) { - dev_dbg(&pdev->dev, "could not request irq %d\n", irq); - goto out_iounmap; - } - rtc->rtc = rtc_device_register(pdev->name, &pdev->dev, &at32_rtc_ops, THIS_MODULE); if (IS_ERR(rtc->rtc)) { dev_dbg(&pdev->dev, "could not register rtc device\n"); ret = PTR_ERR(rtc->rtc); - goto out_free_irq; + goto out_iounmap; } platform_set_drvdata(pdev, rtc); @@ -268,10 +268,10 @@ static int __init at32_rtc_probe(struct platform_device *pdev) return 0; -out_free_irq: - free_irq(irq, rtc); out_iounmap: iounmap(rtc->regs); +out_free_irq: + free_irq(irq, rtc); out: kfree(rtc); return ret; diff --git a/trunk/fs/Kconfig b/trunk/fs/Kconfig index 487236c65837..635f3e286ad8 100644 --- a/trunk/fs/Kconfig +++ b/trunk/fs/Kconfig @@ -1305,7 +1305,7 @@ config JFFS2_COMPRESSION_OPTIONS help Enabling this option allows you to explicitly choose which compression modules, if any, are enabled in JFFS2. Removing - compressors can mean you cannot read existing file systems, + compressors and mean you cannot read existing file systems, and enabling experimental compressors can mean that you write a file system which cannot be read by a standard kernel. diff --git a/trunk/fs/dquot.c b/trunk/fs/dquot.c index 686ab63a7c6c..2809768d9c41 100644 --- a/trunk/fs/dquot.c +++ b/trunk/fs/dquot.c @@ -965,7 +965,7 @@ static void send_warning(const struct dquot *dquot, const char warntype) } #endif -static inline void flush_warnings(struct dquot * const *dquots, char *warntype) +static inline void flush_warnings(struct dquot **dquots, char *warntype) { int i; @@ -1216,7 +1216,7 @@ int dquot_alloc_inode(const struct inode *inode, unsigned long number) for (cnt = 0; cnt < MAXQUOTAS; cnt++) if (inode->i_dquot[cnt]) mark_dquot_dirty(inode->i_dquot[cnt]); - flush_warnings(inode->i_dquot, warntype); + flush_warnings((struct dquot **)inode->i_dquot, warntype); up_read(&sb_dqopt(inode->i_sb)->dqptr_sem); return ret; } diff --git a/trunk/fs/ecryptfs/keystore.c b/trunk/fs/ecryptfs/keystore.c index f458c1f35565..263fed88c0ca 100644 --- a/trunk/fs/ecryptfs/keystore.c +++ b/trunk/fs/ecryptfs/keystore.c @@ -1860,7 +1860,7 @@ ecryptfs_add_global_auth_tok(struct ecryptfs_mount_crypt_stat *mount_crypt_stat, struct ecryptfs_global_auth_tok *new_auth_tok; int rc = 0; - new_auth_tok = kmem_cache_zalloc(ecryptfs_global_auth_tok_cache, + new_auth_tok = kmem_cache_alloc(ecryptfs_global_auth_tok_cache, GFP_KERNEL); if (!new_auth_tok) { rc = -ENOMEM; diff --git a/trunk/fs/ecryptfs/main.c b/trunk/fs/ecryptfs/main.c index a277754da171..b83a512b7e08 100644 --- a/trunk/fs/ecryptfs/main.c +++ b/trunk/fs/ecryptfs/main.c @@ -523,7 +523,6 @@ static int ecryptfs_read_super(struct super_block *sb, const char *dev_name) lower_mnt = nd.mnt; ecryptfs_set_superblock_lower(sb, lower_root->d_sb); sb->s_maxbytes = lower_root->d_sb->s_maxbytes; - sb->s_blocksize = lower_root->d_sb->s_blocksize; ecryptfs_set_dentry_lower(sb->s_root, lower_root); ecryptfs_set_dentry_lower_mnt(sb->s_root, lower_mnt); rc = ecryptfs_interpose(lower_root, sb->s_root, sb, 0); diff --git a/trunk/fs/ecryptfs/mmap.c b/trunk/fs/ecryptfs/mmap.c index 32c5711d79a3..16a7a555f392 100644 --- a/trunk/fs/ecryptfs/mmap.c +++ b/trunk/fs/ecryptfs/mmap.c @@ -263,13 +263,14 @@ static int fill_zeros_to_end_of_page(struct page *page, unsigned int to) return 0; } -/* This function must zero any hole we create */ static int ecryptfs_prepare_write(struct file *file, struct page *page, unsigned from, unsigned to) { int rc = 0; - loff_t prev_page_end_size; + if (from == 0 && to == PAGE_CACHE_SIZE) + goto out; /* If we are writing a full page, it will be + up to date. */ if (!PageUptodate(page)) { rc = ecryptfs_read_lower_page_segment(page, page->index, 0, PAGE_CACHE_SIZE, @@ -282,32 +283,22 @@ static int ecryptfs_prepare_write(struct file *file, struct page *page, } else SetPageUptodate(page); } - - prev_page_end_size = ((loff_t)page->index << PAGE_CACHE_SHIFT); - - /* - * If creating a page or more of holes, zero them out via truncate. - * Note, this will increase i_size. - */ if (page->index != 0) { - if (prev_page_end_size > i_size_read(page->mapping->host)) { + loff_t end_of_prev_pg_pos = + (((loff_t)page->index << PAGE_CACHE_SHIFT) - 1); + + if (end_of_prev_pg_pos > i_size_read(page->mapping->host)) { rc = ecryptfs_truncate(file->f_path.dentry, - prev_page_end_size); + end_of_prev_pg_pos); if (rc) { printk(KERN_ERR "Error on attempt to " "truncate to (higher) offset [%lld];" - " rc = [%d]\n", prev_page_end_size, rc); + " rc = [%d]\n", end_of_prev_pg_pos, rc); goto out; } } - } - /* - * Writing to a new page, and creating a small hole from start of page? - * Zero it out. - */ - if ((i_size_read(page->mapping->host) == prev_page_end_size) && - (from != 0)) { - zero_user_page(page, 0, PAGE_CACHE_SIZE, KM_USER0); + if (end_of_prev_pg_pos + 1 > i_size_read(page->mapping->host)) + zero_user_page(page, 0, PAGE_CACHE_SIZE, KM_USER0); } out: return rc; diff --git a/trunk/fs/ecryptfs/read_write.c b/trunk/fs/ecryptfs/read_write.c index 948f57624c05..6b7474a4336a 100644 --- a/trunk/fs/ecryptfs/read_write.c +++ b/trunk/fs/ecryptfs/read_write.c @@ -124,10 +124,6 @@ int ecryptfs_write(struct file *ecryptfs_file, char *data, loff_t offset, loff_t pos; int rc = 0; - /* - * if we are writing beyond current size, then start pos - * at the current size - we'll fill in zeros from there. - */ if (offset > ecryptfs_file_size) pos = ecryptfs_file_size; else @@ -141,7 +137,6 @@ int ecryptfs_write(struct file *ecryptfs_file, char *data, loff_t offset, if (num_bytes > total_remaining_bytes) num_bytes = total_remaining_bytes; if (pos < offset) { - /* remaining zeros to write, up to destination offset */ size_t total_remaining_zeros = (offset - pos); if (num_bytes > total_remaining_zeros) @@ -172,27 +167,17 @@ int ecryptfs_write(struct file *ecryptfs_file, char *data, loff_t offset, } } ecryptfs_page_virt = kmap_atomic(ecryptfs_page, KM_USER0); - - /* - * pos: where we're now writing, offset: where the request was - * If current pos is before request, we are filling zeros - * If we are at or beyond request, we are writing the *data* - * If we're in a fresh page beyond eof, zero it in either case - */ - if (pos < offset || !start_offset_in_page) { - /* We are extending past the previous end of the file. - * Fill in zero values to the end of the page */ - memset(((char *)ecryptfs_page_virt - + start_offset_in_page), 0, - PAGE_CACHE_SIZE - start_offset_in_page); - } - - /* pos >= offset, we are now writing the data request */ if (pos >= offset) { memcpy(((char *)ecryptfs_page_virt + start_offset_in_page), (data + data_offset), num_bytes); data_offset += num_bytes; + } else { + /* We are extending past the previous end of the file. + * Fill in zero values up to the start of where we + * will be writing data. */ + memset(((char *)ecryptfs_page_virt + + start_offset_in_page), 0, num_bytes); } kunmap_atomic(ecryptfs_page_virt, KM_USER0); flush_dcache_page(ecryptfs_page); diff --git a/trunk/fs/ext3/super.c b/trunk/fs/ext3/super.c index cb14de1502c3..de55da9e28ba 100644 --- a/trunk/fs/ext3/super.c +++ b/trunk/fs/ext3/super.c @@ -1676,7 +1676,7 @@ static int ext3_fill_super (struct super_block *sb, void *data, int silent) sbi->s_blocks_per_group = le32_to_cpu(es->s_blocks_per_group); sbi->s_frags_per_group = le32_to_cpu(es->s_frags_per_group); sbi->s_inodes_per_group = le32_to_cpu(es->s_inodes_per_group); - if (EXT3_INODE_SIZE(sb) == 0 || EXT3_INODES_PER_GROUP(sb) == 0) + if (EXT3_INODE_SIZE(sb) == 0) goto cantfind_ext3; sbi->s_inodes_per_block = blocksize / EXT3_INODE_SIZE(sb); if (sbi->s_inodes_per_block == 0) diff --git a/trunk/fs/ext4/super.c b/trunk/fs/ext4/super.c index 1ca0f546c466..8031dc0e24e5 100644 --- a/trunk/fs/ext4/super.c +++ b/trunk/fs/ext4/super.c @@ -1797,7 +1797,7 @@ static int ext4_fill_super (struct super_block *sb, void *data, int silent) sbi->s_desc_size = EXT4_MIN_DESC_SIZE; sbi->s_blocks_per_group = le32_to_cpu(es->s_blocks_per_group); sbi->s_inodes_per_group = le32_to_cpu(es->s_inodes_per_group); - if (EXT4_INODE_SIZE(sb) == 0 || EXT4_INODES_PER_GROUP(sb) == 0) + if (EXT4_INODE_SIZE(sb) == 0) goto cantfind_ext4; sbi->s_inodes_per_block = blocksize / EXT4_INODE_SIZE(sb); if (sbi->s_inodes_per_block == 0) diff --git a/trunk/include/asm-alpha/io_trivial.h b/trunk/include/asm-alpha/io_trivial.h index 1c77f10b4b36..b10d1aa4cdd1 100644 --- a/trunk/include/asm-alpha/io_trivial.h +++ b/trunk/include/asm-alpha/io_trivial.h @@ -72,29 +72,25 @@ IO_CONCAT(__IO_PREFIX,writew)(u16 b, volatile void __iomem *a) __EXTERN_INLINE u8 IO_CONCAT(__IO_PREFIX,readb)(const volatile void __iomem *a) { - void __iomem *addr = (void __iomem *)a; - return IO_CONCAT(__IO_PREFIX,ioread8)(addr); + return IO_CONCAT(__IO_PREFIX,ioread8)((void __iomem *)a); } __EXTERN_INLINE u16 IO_CONCAT(__IO_PREFIX,readw)(const volatile void __iomem *a) { - void __iomem *addr = (void __iomem *)a; - return IO_CONCAT(__IO_PREFIX,ioread16)(addr); + return IO_CONCAT(__IO_PREFIX,ioread16)((void __iomem *)a); } __EXTERN_INLINE void IO_CONCAT(__IO_PREFIX,writeb)(u8 b, volatile void __iomem *a) { - void __iomem *addr = (void __iomem *)a; - IO_CONCAT(__IO_PREFIX,iowrite8)(b, addr); + IO_CONCAT(__IO_PREFIX,iowrite8)(b, (void __iomem *)a); } __EXTERN_INLINE void IO_CONCAT(__IO_PREFIX,writew)(u16 b, volatile void __iomem *a) { - void __iomem *addr = (void __iomem *)a; - IO_CONCAT(__IO_PREFIX,iowrite16)(b, addr); + IO_CONCAT(__IO_PREFIX,iowrite16)(b, (void __iomem *)a); } #endif diff --git a/trunk/include/asm-generic/tlb.h b/trunk/include/asm-generic/tlb.h index 799307eea40f..f490e43a90b9 100644 --- a/trunk/include/asm-generic/tlb.h +++ b/trunk/include/asm-generic/tlb.h @@ -14,7 +14,6 @@ #define _ASM_GENERIC__TLB_H #include -#include #include #include @@ -86,9 +85,6 @@ tlb_flush_mmu(struct mmu_gather *tlb, unsigned long start, unsigned long end) static inline void tlb_finish_mmu(struct mmu_gather *tlb, unsigned long start, unsigned long end) { -#ifdef CONFIG_QUICKLIST - tlb->need_flush += &__get_cpu_var(quicklist)[0].nr_pages != 0; -#endif tlb_flush_mmu(tlb, start, end); /* keep the page table cache within bounds */ diff --git a/trunk/include/linux/Kbuild b/trunk/include/linux/Kbuild index 9abf5a806c15..37bfa19d8064 100644 --- a/trunk/include/linux/Kbuild +++ b/trunk/include/linux/Kbuild @@ -145,6 +145,7 @@ header-y += sound.h header-y += taskstats.h header-y += telephony.h header-y += termios.h +header-y += ticable.h header-y += times.h header-y += tiocl.h header-y += tipc.h diff --git a/trunk/include/linux/apm_bios.h b/trunk/include/linux/apm_bios.h index 01a6244c9bc9..9754baa14921 100644 --- a/trunk/include/linux/apm_bios.h +++ b/trunk/include/linux/apm_bios.h @@ -18,9 +18,6 @@ #include -typedef unsigned short apm_event_t; -typedef unsigned short apm_eventinfo_t; - struct apm_bios_info { __u16 version; __u16 cseg; @@ -35,6 +32,9 @@ struct apm_bios_info { #ifdef __KERNEL__ +typedef unsigned short apm_event_t; +typedef unsigned short apm_eventinfo_t; + #define APM_CS (GDT_ENTRY_APMBIOS_BASE * 8) #define APM_CS_16 (APM_CS + 8) #define APM_DS (APM_CS_16 + 8) diff --git a/trunk/include/linux/hugetlb.h b/trunk/include/linux/hugetlb.h index 30d606afcafe..24968790bc3e 100644 --- a/trunk/include/linux/hugetlb.h +++ b/trunk/include/linux/hugetlb.h @@ -33,7 +33,7 @@ void hugetlb_unreserve_pages(struct inode *inode, long offset, long freed); extern unsigned long max_huge_pages; extern unsigned long hugepages_treat_as_movable; -extern unsigned long nr_overcommit_huge_pages; +extern int hugetlb_dynamic_pool; extern const unsigned long hugetlb_zero, hugetlb_infinity; extern int sysctl_hugetlb_shm_group; diff --git a/trunk/kernel/sysctl.c b/trunk/kernel/sysctl.c index 1135de730872..8ac51714b08c 100644 --- a/trunk/kernel/sysctl.c +++ b/trunk/kernel/sysctl.c @@ -906,11 +906,11 @@ static struct ctl_table vm_table[] = { }, { .ctl_name = CTL_UNNUMBERED, - .procname = "nr_overcommit_hugepages", - .data = &nr_overcommit_huge_pages, - .maxlen = sizeof(nr_overcommit_huge_pages), + .procname = "hugetlb_dynamic_pool", + .data = &hugetlb_dynamic_pool, + .maxlen = sizeof(hugetlb_dynamic_pool), .mode = 0644, - .proc_handler = &proc_doulongvec_minmax, + .proc_handler = &proc_dointvec, }, #endif { diff --git a/trunk/kernel/sysctl_check.c b/trunk/kernel/sysctl_check.c index a68425a5cc1d..bed939f82c31 100644 --- a/trunk/kernel/sysctl_check.c +++ b/trunk/kernel/sysctl_check.c @@ -428,7 +428,7 @@ static struct trans_ctl_table trans_net_netrom_table[] = { {} }; -static struct trans_ctl_table trans_net_ax25_param_table[] = { +static struct trans_ctl_table trans_net_ax25_table[] = { { NET_AX25_IP_DEFAULT_MODE, "ip_default_mode" }, { NET_AX25_DEFAULT_MODE, "ax25_default_mode" }, { NET_AX25_BACKOFF_TYPE, "backoff_type" }, @@ -446,11 +446,6 @@ static struct trans_ctl_table trans_net_ax25_param_table[] = { {} }; -static struct trans_ctl_table trans_net_ax25_table[] = { - { 0, NULL, trans_net_ax25_param_table }, - {} -}; - static struct trans_ctl_table trans_net_bridge_table[] = { { NET_BRIDGE_NF_CALL_ARPTABLES, "bridge-nf-call-arptables" }, { NET_BRIDGE_NF_CALL_IPTABLES, "bridge-nf-call-iptables" }, diff --git a/trunk/mm/Kconfig b/trunk/mm/Kconfig index 9ef97417a0b9..c070ec0c15bf 100644 --- a/trunk/mm/Kconfig +++ b/trunk/mm/Kconfig @@ -112,17 +112,18 @@ config SPARSEMEM_EXTREME def_bool y depends on SPARSEMEM && !SPARSEMEM_STATIC +# +# SPARSEMEM_VMEMMAP uses a virtually mapped mem_map to optimise pfn_to_page +# and page_to_pfn. The most efficient option where kernel virtual space is +# not under pressure. +# config SPARSEMEM_VMEMMAP_ENABLE def_bool n config SPARSEMEM_VMEMMAP - bool "Sparse Memory virtual memmap" - depends on SPARSEMEM && SPARSEMEM_VMEMMAP_ENABLE - default y - help - SPARSEMEM_VMEMMAP uses a virtually mapped memmap to optimise - pfn_to_page and page_to_pfn operations. This is the most - efficient option when sufficient kernel resources are available. + bool + depends on SPARSEMEM + default y if (SPARSEMEM_VMEMMAP_ENABLE) # eventually, we can have this option just 'select SPARSEMEM' config MEMORY_HOTPLUG diff --git a/trunk/mm/hugetlb.c b/trunk/mm/hugetlb.c index 7224a4f07106..6f978218c2c8 100644 --- a/trunk/mm/hugetlb.c +++ b/trunk/mm/hugetlb.c @@ -31,7 +31,7 @@ static unsigned int free_huge_pages_node[MAX_NUMNODES]; static unsigned int surplus_huge_pages_node[MAX_NUMNODES]; static gfp_t htlb_alloc_mask = GFP_HIGHUSER; unsigned long hugepages_treat_as_movable; -unsigned long nr_overcommit_huge_pages; +int hugetlb_dynamic_pool; static int hugetlb_next_nid; /* @@ -227,58 +227,22 @@ static struct page *alloc_buddy_huge_page(struct vm_area_struct *vma, unsigned long address) { struct page *page; - unsigned int nid; - /* - * Assume we will successfully allocate the surplus page to - * prevent racing processes from causing the surplus to exceed - * overcommit - * - * This however introduces a different race, where a process B - * tries to grow the static hugepage pool while alloc_pages() is - * called by process A. B will only examine the per-node - * counters in determining if surplus huge pages can be - * converted to normal huge pages in adjust_pool_surplus(). A - * won't be able to increment the per-node counter, until the - * lock is dropped by B, but B doesn't drop hugetlb_lock until - * no more huge pages can be converted from surplus to normal - * state (and doesn't try to convert again). Thus, we have a - * case where a surplus huge page exists, the pool is grown, and - * the surplus huge page still exists after, even though it - * should just have been converted to a normal huge page. This - * does not leak memory, though, as the hugepage will be freed - * once it is out of use. It also does not allow the counters to - * go out of whack in adjust_pool_surplus() as we don't modify - * the node values until we've gotten the hugepage and only the - * per-node value is checked there. - */ - spin_lock(&hugetlb_lock); - if (surplus_huge_pages >= nr_overcommit_huge_pages) { - spin_unlock(&hugetlb_lock); + /* Check if the dynamic pool is enabled */ + if (!hugetlb_dynamic_pool) return NULL; - } else { - nr_huge_pages++; - surplus_huge_pages++; - } - spin_unlock(&hugetlb_lock); page = alloc_pages(htlb_alloc_mask|__GFP_COMP|__GFP_NOWARN, HUGETLB_PAGE_ORDER); - - spin_lock(&hugetlb_lock); if (page) { - nid = page_to_nid(page); set_compound_page_dtor(page, free_huge_page); - /* - * We incremented the global counters already - */ - nr_huge_pages_node[nid]++; - surplus_huge_pages_node[nid]++; - } else { - nr_huge_pages--; - surplus_huge_pages--; + spin_lock(&hugetlb_lock); + nr_huge_pages++; + nr_huge_pages_node[page_to_nid(page)]++; + surplus_huge_pages++; + surplus_huge_pages_node[page_to_nid(page)]++; + spin_unlock(&hugetlb_lock); } - spin_unlock(&hugetlb_lock); return page; } @@ -517,12 +481,6 @@ static unsigned long set_max_huge_pages(unsigned long count) * Increase the pool size * First take pages out of surplus state. Then make up the * remaining difference by allocating fresh huge pages. - * - * We might race with alloc_buddy_huge_page() here and be unable - * to convert a surplus huge page to a normal huge page. That is - * not critical, though, it just means the overall size of the - * pool might be one hugepage larger than it needs to be, but - * within all the constraints specified by the sysctls. */ spin_lock(&hugetlb_lock); while (surplus_huge_pages && count > persistent_huge_pages) { @@ -551,14 +509,6 @@ static unsigned long set_max_huge_pages(unsigned long count) * to keep enough around to satisfy reservations). Then place * pages into surplus state as needed so the pool will shrink * to the desired size as pages become free. - * - * By placing pages into the surplus state independent of the - * overcommit value, we are allowing the surplus pool size to - * exceed overcommit. There are few sane options here. Since - * alloc_buddy_huge_page() is checking the global counter, - * though, we'll note that we're not allowed to exceed surplus - * and won't grow the pool anywhere else. Not until one of the - * sysctls are changed, or the surplus pages go out of use. */ min_count = resv_huge_pages + nr_huge_pages - free_huge_pages; min_count = max(count, min_count); diff --git a/trunk/mm/page_alloc.c b/trunk/mm/page_alloc.c index d73bfad1c32f..b5a58d476c1a 100644 --- a/trunk/mm/page_alloc.c +++ b/trunk/mm/page_alloc.c @@ -847,19 +847,8 @@ static int rmqueue_bulk(struct zone *zone, unsigned int order, struct page *page = __rmqueue(zone, order, migratetype); if (unlikely(page == NULL)) break; - - /* - * Split buddy pages returned by expand() are received here - * in physical page order. The page is added to the callers and - * list and the list head then moves forward. From the callers - * perspective, the linked list is ordered by page number in - * some conditions. This is useful for IO devices that can - * merge IO requests if the physical pages are ordered - * properly. - */ list_add(&page->lru, list); set_page_private(page, migratetype); - list = &page->lru; } spin_unlock(&zone->lock); return i; diff --git a/trunk/mm/slub.c b/trunk/mm/slub.c index b9f37cb0f2e6..9c1d9f3b364f 100644 --- a/trunk/mm/slub.c +++ b/trunk/mm/slub.c @@ -1468,6 +1468,9 @@ static void *__slab_alloc(struct kmem_cache *s, void **object; struct page *new; + /* We handle __GFP_ZERO in the caller */ + gfpflags &= ~__GFP_ZERO; + if (!c->page) goto new_slab; diff --git a/trunk/mm/sparse.c b/trunk/mm/sparse.c index a2183cb5d524..e06f514fe04f 100644 --- a/trunk/mm/sparse.c +++ b/trunk/mm/sparse.c @@ -83,8 +83,6 @@ static int __meminit sparse_index_init(unsigned long section_nr, int nid) return -EEXIST; section = sparse_index_alloc(nid); - if (!section) - return -ENOMEM; /* * This lock keeps two different sections from * reallocating for the same index @@ -391,17 +389,9 @@ int sparse_add_one_section(struct zone *zone, unsigned long start_pfn, * no locking for this, because it does its own * plus, it does a kmalloc */ - ret = sparse_index_init(section_nr, pgdat->node_id); - if (ret < 0 && ret != -EEXIST) - return ret; + sparse_index_init(section_nr, pgdat->node_id); memmap = kmalloc_section_memmap(section_nr, pgdat->node_id, nr_pages); - if (!memmap) - return -ENOMEM; usemap = __kmalloc_section_usemap(); - if (!usemap) { - __kfree_section_memmap(memmap, nr_pages); - return -ENOMEM; - } pgdat_resize_lock(pgdat, &flags); @@ -411,16 +401,18 @@ int sparse_add_one_section(struct zone *zone, unsigned long start_pfn, goto out; } + if (!usemap) { + ret = -ENOMEM; + goto out; + } ms->section_mem_map |= SECTION_MARKED_PRESENT; ret = sparse_init_one_section(ms, section_nr, memmap, usemap); out: pgdat_resize_unlock(pgdat, &flags); - if (ret <= 0) { - kfree(usemap); + if (ret <= 0) __kfree_section_memmap(memmap, nr_pages); - } return ret; } #endif diff --git a/trunk/scripts/bloat-o-meter b/trunk/scripts/bloat-o-meter index 6501a50e17f0..ce59fc2d8de4 100755 --- a/trunk/scripts/bloat-o-meter +++ b/trunk/scripts/bloat-o-meter @@ -18,8 +18,7 @@ def getsizes(file): for l in os.popen("nm --size-sort " + file).readlines(): size, type, name = l[:-1].split() if type in "tTdDbB": - # function names begin with '.' on 64-bit powerpc - if "." in name[1:]: name = "static." + name.split(".")[0] + if "." in name: name = "static." + name.split(".")[0] sym[name] = sym.get(name, 0) + int(size, 16) return sym