mm/execmem, arch: convert remaining overrides of module_alloc to execmem
[linux-block.git] / arch / powerpc / kernel / module.c
index f6d6ae0a1692396a6b65458e9731cbb61ea443a6..ac80559015a306889adcd076cabea8de80f49e98 100644 (file)
@@ -10,6 +10,7 @@
 #include <linux/vmalloc.h>
 #include <linux/mm.h>
 #include <linux/bug.h>
+#include <linux/execmem.h>
 #include <asm/module.h>
 #include <linux/uaccess.h>
 #include <asm/firmware.h>
@@ -89,39 +90,56 @@ int module_finalize(const Elf_Ehdr *hdr,
        return 0;
 }
 
-static __always_inline void *
-__module_alloc(unsigned long size, unsigned long start, unsigned long end, bool nowarn)
+static struct execmem_info execmem_info __ro_after_init;
+
+struct execmem_info __init *execmem_arch_setup(void)
 {
        pgprot_t prot = strict_module_rwx_enabled() ? PAGE_KERNEL : PAGE_KERNEL_EXEC;
-       gfp_t gfp = GFP_KERNEL | (nowarn ? __GFP_NOWARN : 0);
+       unsigned long fallback_start = 0, fallback_end = 0;
+       unsigned long start, end;
 
        /*
-        * Don't do huge page allocations for modules yet until more testing
-        * is done. STRICT_MODULE_RWX may require extra work to support this
-        * too.
+        * BOOK3S_32 and 8xx define MODULES_VADDR for text allocations and
+        * allow allocating data in the entire vmalloc space
         */
-       return __vmalloc_node_range(size, 1, start, end, gfp, prot,
-                                   VM_FLUSH_RESET_PERMS,
-                                   NUMA_NO_NODE, __builtin_return_address(0));
-}
-
-void *module_alloc(unsigned long size)
-{
 #ifdef MODULES_VADDR
        unsigned long limit = (unsigned long)_etext - SZ_32M;
-       void *ptr = NULL;
 
        BUILD_BUG_ON(TASK_SIZE > MODULES_VADDR);
 
        /* First try within 32M limit from _etext to avoid branch trampolines */
-       if (MODULES_VADDR < PAGE_OFFSET && MODULES_END > limit)
-               ptr = __module_alloc(size, limit, MODULES_END, true);
-
-       if (!ptr)
-               ptr = __module_alloc(size, MODULES_VADDR, MODULES_END, false);
+       if (MODULES_VADDR < PAGE_OFFSET && MODULES_END > limit) {
+               start = limit;
+               fallback_start = MODULES_VADDR;
+               fallback_end = MODULES_END;
+       } else {
+               start = MODULES_VADDR;
+       }
 
-       return ptr;
+       end = MODULES_END;
 #else
-       return __module_alloc(size, VMALLOC_START, VMALLOC_END, false);
+       start = VMALLOC_START;
+       end = VMALLOC_END;
 #endif
+
+       execmem_info = (struct execmem_info){
+               .ranges = {
+                       [EXECMEM_DEFAULT] = {
+                               .start  = start,
+                               .end    = end,
+                               .pgprot = prot,
+                               .alignment = 1,
+                               .fallback_start = fallback_start,
+                               .fallback_end   = fallback_end,
+                       },
+                       [EXECMEM_MODULE_DATA] = {
+                               .start  = VMALLOC_START,
+                               .end    = VMALLOC_END,
+                               .pgprot = PAGE_KERNEL,
+                               .alignment = 1,
+                       },
+               },
+       };
+
+       return &execmem_info;
 }