x86/smpboot: Init apic mapping before usage
[cascardo/linux.git] / fs / select.c
index 8ed9da5..3d4f85d 100644 (file)
@@ -29,6 +29,7 @@
 #include <linux/sched/rt.h>
 #include <linux/freezer.h>
 #include <net/busy_poll.h>
+#include <linux/vmalloc.h>
 
 #include <asm/uaccess.h>
 
@@ -554,7 +555,7 @@ int core_sys_select(int n, fd_set __user *inp, fd_set __user *outp,
        fd_set_bits fds;
        void *bits;
        int ret, max_fds;
-       unsigned int size;
+       size_t size, alloc_size;
        struct fdtable *fdt;
        /* Allocate small arguments on the stack to save memory and be faster */
        long stack_fds[SELECT_STACK_ALLOC/sizeof(long)];
@@ -581,7 +582,14 @@ int core_sys_select(int n, fd_set __user *inp, fd_set __user *outp,
        if (size > sizeof(stack_fds) / 6) {
                /* Not enough space in on-stack array; must use kmalloc */
                ret = -ENOMEM;
-               bits = kmalloc(6 * size, GFP_KERNEL);
+               if (size > (SIZE_MAX / 6))
+                       goto out_nofds;
+
+               alloc_size = 6 * size;
+               bits = kmalloc(alloc_size, GFP_KERNEL|__GFP_NOWARN);
+               if (!bits && alloc_size > PAGE_SIZE)
+                       bits = vmalloc(alloc_size);
+
                if (!bits)
                        goto out_nofds;
        }
@@ -618,7 +626,7 @@ int core_sys_select(int n, fd_set __user *inp, fd_set __user *outp,
 
 out:
        if (bits != stack_fds)
-               kfree(bits);
+               kvfree(bits);
 out_nofds:
        return ret;
 }