mirror of
https://github.com/BobTheBlinker/android_kernel_motorola_sm6375.git
synced 2026-10-29 11:11:45 -04:00
Merge branch 'akpm' (patches from Andrew)
Merge misc updates from Andrew Morton: - kasan updates - procfs - lib/bitmap updates - other lib/ updates - checkpatch tweaks - rapidio - ubsan - pipe fixes and cleanups - lots of other misc bits * emailed patches from Andrew Morton <[email protected]>: (114 commits) Documentation/sysctl/user.txt: fix typo MAINTAINERS: update ARM/QUALCOMM SUPPORT patterns MAINTAINERS: update various PALM patterns MAINTAINERS: update "ARM/OXNAS platform support" patterns MAINTAINERS: update Cortina/Gemini patterns MAINTAINERS: remove ARM/CLKDEV SUPPORT file pattern MAINTAINERS: remove ANDROID ION pattern mm: docs: add blank lines to silence sphinx "Unexpected indentation" errors mm: docs: fix parameter names mismatch mm: docs: fixup punctuation pipe: read buffer limits atomically pipe: simplify round_pipe_size() pipe: reject F_SETPIPE_SZ with size over UINT_MAX pipe: fix off-by-one error when checking buffer limits pipe: actually allow root to exceed the pipe buffer limits pipe, sysctl: remove pipe_proc_fn() pipe, sysctl: drop 'min' parameter from pipe-max-size converter kasan: rework Kconfig settings crash_dump: is_kdump_kernel can be boolean kernel/mutex: mutex_is_locked can be boolean ...
This commit is contained in:
commit
a2e5790d84
134 changed files with 1422 additions and 1075 deletions
|
|
@ -410,7 +410,7 @@ void __init free_bootmem_node(pg_data_t *pgdat, unsigned long physaddr,
|
|||
|
||||
/**
|
||||
* free_bootmem - mark a page range as usable
|
||||
* @addr: starting physical address of the range
|
||||
* @physaddr: starting physical address of the range
|
||||
* @size: size of the range in bytes
|
||||
*
|
||||
* Partial pages will be considered reserved and left as they are.
|
||||
|
|
|
|||
108
mm/kasan/kasan.c
108
mm/kasan/kasan.c
|
|
@ -5,7 +5,7 @@
|
|||
* Author: Andrey Ryabinin <ryabinin.a.a@gmail.com>
|
||||
*
|
||||
* Some code borrowed from https://github.com/xairy/kasan-prototype by
|
||||
* Andrey Konovalov <adech.fo@gmail.com>
|
||||
* Andrey Konovalov <andreyknvl@gmail.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 2 as
|
||||
|
|
@ -489,21 +489,17 @@ void kasan_slab_alloc(struct kmem_cache *cache, void *object, gfp_t flags)
|
|||
kasan_kmalloc(cache, object, cache->object_size, flags);
|
||||
}
|
||||
|
||||
static void kasan_poison_slab_free(struct kmem_cache *cache, void *object)
|
||||
{
|
||||
unsigned long size = cache->object_size;
|
||||
unsigned long rounded_up_size = round_up(size, KASAN_SHADOW_SCALE_SIZE);
|
||||
|
||||
/* RCU slabs could be legally used after free within the RCU period */
|
||||
if (unlikely(cache->flags & SLAB_TYPESAFE_BY_RCU))
|
||||
return;
|
||||
|
||||
kasan_poison_shadow(object, rounded_up_size, KASAN_KMALLOC_FREE);
|
||||
}
|
||||
|
||||
bool kasan_slab_free(struct kmem_cache *cache, void *object)
|
||||
static bool __kasan_slab_free(struct kmem_cache *cache, void *object,
|
||||
unsigned long ip, bool quarantine)
|
||||
{
|
||||
s8 shadow_byte;
|
||||
unsigned long rounded_up_size;
|
||||
|
||||
if (unlikely(nearest_obj(cache, virt_to_head_page(object), object) !=
|
||||
object)) {
|
||||
kasan_report_invalid_free(object, ip);
|
||||
return true;
|
||||
}
|
||||
|
||||
/* RCU slabs could be legally used after free within the RCU period */
|
||||
if (unlikely(cache->flags & SLAB_TYPESAFE_BY_RCU))
|
||||
|
|
@ -511,14 +507,14 @@ bool kasan_slab_free(struct kmem_cache *cache, void *object)
|
|||
|
||||
shadow_byte = READ_ONCE(*(s8 *)kasan_mem_to_shadow(object));
|
||||
if (shadow_byte < 0 || shadow_byte >= KASAN_SHADOW_SCALE_SIZE) {
|
||||
kasan_report_double_free(cache, object,
|
||||
__builtin_return_address(1));
|
||||
kasan_report_invalid_free(object, ip);
|
||||
return true;
|
||||
}
|
||||
|
||||
kasan_poison_slab_free(cache, object);
|
||||
rounded_up_size = round_up(cache->object_size, KASAN_SHADOW_SCALE_SIZE);
|
||||
kasan_poison_shadow(object, rounded_up_size, KASAN_KMALLOC_FREE);
|
||||
|
||||
if (unlikely(!(cache->flags & SLAB_KASAN)))
|
||||
if (!quarantine || unlikely(!(cache->flags & SLAB_KASAN)))
|
||||
return false;
|
||||
|
||||
set_track(&get_alloc_info(cache, object)->free_track, GFP_NOWAIT);
|
||||
|
|
@ -526,6 +522,11 @@ bool kasan_slab_free(struct kmem_cache *cache, void *object)
|
|||
return true;
|
||||
}
|
||||
|
||||
bool kasan_slab_free(struct kmem_cache *cache, void *object, unsigned long ip)
|
||||
{
|
||||
return __kasan_slab_free(cache, object, ip, true);
|
||||
}
|
||||
|
||||
void kasan_kmalloc(struct kmem_cache *cache, const void *object, size_t size,
|
||||
gfp_t flags)
|
||||
{
|
||||
|
|
@ -589,25 +590,29 @@ void kasan_krealloc(const void *object, size_t size, gfp_t flags)
|
|||
kasan_kmalloc(page->slab_cache, object, size, flags);
|
||||
}
|
||||
|
||||
void kasan_poison_kfree(void *ptr)
|
||||
void kasan_poison_kfree(void *ptr, unsigned long ip)
|
||||
{
|
||||
struct page *page;
|
||||
|
||||
page = virt_to_head_page(ptr);
|
||||
|
||||
if (unlikely(!PageSlab(page)))
|
||||
if (unlikely(!PageSlab(page))) {
|
||||
if (ptr != page_address(page)) {
|
||||
kasan_report_invalid_free(ptr, ip);
|
||||
return;
|
||||
}
|
||||
kasan_poison_shadow(ptr, PAGE_SIZE << compound_order(page),
|
||||
KASAN_FREE_PAGE);
|
||||
else
|
||||
kasan_poison_slab_free(page->slab_cache, ptr);
|
||||
} else {
|
||||
__kasan_slab_free(page->slab_cache, ptr, ip, false);
|
||||
}
|
||||
}
|
||||
|
||||
void kasan_kfree_large(const void *ptr)
|
||||
void kasan_kfree_large(void *ptr, unsigned long ip)
|
||||
{
|
||||
struct page *page = virt_to_page(ptr);
|
||||
|
||||
kasan_poison_shadow(ptr, PAGE_SIZE << compound_order(page),
|
||||
KASAN_FREE_PAGE);
|
||||
if (ptr != page_address(virt_to_head_page(ptr)))
|
||||
kasan_report_invalid_free(ptr, ip);
|
||||
/* The object will be poisoned by page_alloc. */
|
||||
}
|
||||
|
||||
int kasan_module_alloc(void *addr, size_t size)
|
||||
|
|
@ -736,6 +741,55 @@ void __asan_unpoison_stack_memory(const void *addr, size_t size)
|
|||
}
|
||||
EXPORT_SYMBOL(__asan_unpoison_stack_memory);
|
||||
|
||||
/* Emitted by compiler to poison alloca()ed objects. */
|
||||
void __asan_alloca_poison(unsigned long addr, size_t size)
|
||||
{
|
||||
size_t rounded_up_size = round_up(size, KASAN_SHADOW_SCALE_SIZE);
|
||||
size_t padding_size = round_up(size, KASAN_ALLOCA_REDZONE_SIZE) -
|
||||
rounded_up_size;
|
||||
size_t rounded_down_size = round_down(size, KASAN_SHADOW_SCALE_SIZE);
|
||||
|
||||
const void *left_redzone = (const void *)(addr -
|
||||
KASAN_ALLOCA_REDZONE_SIZE);
|
||||
const void *right_redzone = (const void *)(addr + rounded_up_size);
|
||||
|
||||
WARN_ON(!IS_ALIGNED(addr, KASAN_ALLOCA_REDZONE_SIZE));
|
||||
|
||||
kasan_unpoison_shadow((const void *)(addr + rounded_down_size),
|
||||
size - rounded_down_size);
|
||||
kasan_poison_shadow(left_redzone, KASAN_ALLOCA_REDZONE_SIZE,
|
||||
KASAN_ALLOCA_LEFT);
|
||||
kasan_poison_shadow(right_redzone,
|
||||
padding_size + KASAN_ALLOCA_REDZONE_SIZE,
|
||||
KASAN_ALLOCA_RIGHT);
|
||||
}
|
||||
EXPORT_SYMBOL(__asan_alloca_poison);
|
||||
|
||||
/* Emitted by compiler to unpoison alloca()ed areas when the stack unwinds. */
|
||||
void __asan_allocas_unpoison(const void *stack_top, const void *stack_bottom)
|
||||
{
|
||||
if (unlikely(!stack_top || stack_top > stack_bottom))
|
||||
return;
|
||||
|
||||
kasan_unpoison_shadow(stack_top, stack_bottom - stack_top);
|
||||
}
|
||||
EXPORT_SYMBOL(__asan_allocas_unpoison);
|
||||
|
||||
/* Emitted by the compiler to [un]poison local variables. */
|
||||
#define DEFINE_ASAN_SET_SHADOW(byte) \
|
||||
void __asan_set_shadow_##byte(const void *addr, size_t size) \
|
||||
{ \
|
||||
__memset((void *)addr, 0x##byte, size); \
|
||||
} \
|
||||
EXPORT_SYMBOL(__asan_set_shadow_##byte)
|
||||
|
||||
DEFINE_ASAN_SET_SHADOW(00);
|
||||
DEFINE_ASAN_SET_SHADOW(f1);
|
||||
DEFINE_ASAN_SET_SHADOW(f2);
|
||||
DEFINE_ASAN_SET_SHADOW(f3);
|
||||
DEFINE_ASAN_SET_SHADOW(f5);
|
||||
DEFINE_ASAN_SET_SHADOW(f8);
|
||||
|
||||
#ifdef CONFIG_MEMORY_HOTPLUG
|
||||
static int __meminit kasan_mem_notifier(struct notifier_block *nb,
|
||||
unsigned long action, void *data)
|
||||
|
|
|
|||
|
|
@ -24,6 +24,14 @@
|
|||
#define KASAN_STACK_PARTIAL 0xF4
|
||||
#define KASAN_USE_AFTER_SCOPE 0xF8
|
||||
|
||||
/*
|
||||
* alloca redzone shadow values
|
||||
*/
|
||||
#define KASAN_ALLOCA_LEFT 0xCA
|
||||
#define KASAN_ALLOCA_RIGHT 0xCB
|
||||
|
||||
#define KASAN_ALLOCA_REDZONE_SIZE 32
|
||||
|
||||
/* Don't break randconfig/all*config builds */
|
||||
#ifndef KASAN_ABI_VERSION
|
||||
#define KASAN_ABI_VERSION 1
|
||||
|
|
@ -99,8 +107,7 @@ static inline const void *kasan_shadow_to_mem(const void *shadow_addr)
|
|||
|
||||
void kasan_report(unsigned long addr, size_t size,
|
||||
bool is_write, unsigned long ip);
|
||||
void kasan_report_double_free(struct kmem_cache *cache, void *object,
|
||||
void *ip);
|
||||
void kasan_report_invalid_free(void *object, unsigned long ip);
|
||||
|
||||
#if defined(CONFIG_SLAB) || defined(CONFIG_SLUB)
|
||||
void quarantine_put(struct kasan_free_meta *info, struct kmem_cache *cache);
|
||||
|
|
@ -113,4 +120,48 @@ static inline void quarantine_reduce(void) { }
|
|||
static inline void quarantine_remove_cache(struct kmem_cache *cache) { }
|
||||
#endif
|
||||
|
||||
/*
|
||||
* Exported functions for interfaces called from assembly or from generated
|
||||
* code. Declarations here to avoid warning about missing declarations.
|
||||
*/
|
||||
asmlinkage void kasan_unpoison_task_stack_below(const void *watermark);
|
||||
void __asan_register_globals(struct kasan_global *globals, size_t size);
|
||||
void __asan_unregister_globals(struct kasan_global *globals, size_t size);
|
||||
void __asan_loadN(unsigned long addr, size_t size);
|
||||
void __asan_storeN(unsigned long addr, size_t size);
|
||||
void __asan_handle_no_return(void);
|
||||
void __asan_poison_stack_memory(const void *addr, size_t size);
|
||||
void __asan_unpoison_stack_memory(const void *addr, size_t size);
|
||||
void __asan_alloca_poison(unsigned long addr, size_t size);
|
||||
void __asan_allocas_unpoison(const void *stack_top, const void *stack_bottom);
|
||||
|
||||
void __asan_load1(unsigned long addr);
|
||||
void __asan_store1(unsigned long addr);
|
||||
void __asan_load2(unsigned long addr);
|
||||
void __asan_store2(unsigned long addr);
|
||||
void __asan_load4(unsigned long addr);
|
||||
void __asan_store4(unsigned long addr);
|
||||
void __asan_load8(unsigned long addr);
|
||||
void __asan_store8(unsigned long addr);
|
||||
void __asan_load16(unsigned long addr);
|
||||
void __asan_store16(unsigned long addr);
|
||||
|
||||
void __asan_load1_noabort(unsigned long addr);
|
||||
void __asan_store1_noabort(unsigned long addr);
|
||||
void __asan_load2_noabort(unsigned long addr);
|
||||
void __asan_store2_noabort(unsigned long addr);
|
||||
void __asan_load4_noabort(unsigned long addr);
|
||||
void __asan_store4_noabort(unsigned long addr);
|
||||
void __asan_load8_noabort(unsigned long addr);
|
||||
void __asan_store8_noabort(unsigned long addr);
|
||||
void __asan_load16_noabort(unsigned long addr);
|
||||
void __asan_store16_noabort(unsigned long addr);
|
||||
|
||||
void __asan_set_shadow_00(const void *addr, size_t size);
|
||||
void __asan_set_shadow_f1(const void *addr, size_t size);
|
||||
void __asan_set_shadow_f2(const void *addr, size_t size);
|
||||
void __asan_set_shadow_f3(const void *addr, size_t size);
|
||||
void __asan_set_shadow_f5(const void *addr, size_t size);
|
||||
void __asan_set_shadow_f8(const void *addr, size_t size);
|
||||
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -5,7 +5,7 @@
|
|||
* Author: Andrey Ryabinin <ryabinin.a.a@gmail.com>
|
||||
*
|
||||
* Some code borrowed from https://github.com/xairy/kasan-prototype by
|
||||
* Andrey Konovalov <adech.fo@gmail.com>
|
||||
* Andrey Konovalov <andreyknvl@gmail.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 2 as
|
||||
|
|
@ -102,6 +102,10 @@ static const char *get_shadow_bug_type(struct kasan_access_info *info)
|
|||
case KASAN_USE_AFTER_SCOPE:
|
||||
bug_type = "use-after-scope";
|
||||
break;
|
||||
case KASAN_ALLOCA_LEFT:
|
||||
case KASAN_ALLOCA_RIGHT:
|
||||
bug_type = "alloca-out-of-bounds";
|
||||
break;
|
||||
}
|
||||
|
||||
return bug_type;
|
||||
|
|
@ -322,13 +326,12 @@ static void print_shadow_for_address(const void *addr)
|
|||
}
|
||||
}
|
||||
|
||||
void kasan_report_double_free(struct kmem_cache *cache, void *object,
|
||||
void *ip)
|
||||
void kasan_report_invalid_free(void *object, unsigned long ip)
|
||||
{
|
||||
unsigned long flags;
|
||||
|
||||
kasan_start_report(&flags);
|
||||
pr_err("BUG: KASAN: double-free or invalid-free in %pS\n", ip);
|
||||
pr_err("BUG: KASAN: double-free or invalid-free in %pS\n", (void *)ip);
|
||||
pr_err("\n");
|
||||
print_address_description(object);
|
||||
pr_err("\n");
|
||||
|
|
|
|||
2
mm/ksm.c
2
mm/ksm.c
|
|
@ -2302,7 +2302,7 @@ next_mm:
|
|||
|
||||
/**
|
||||
* ksm_do_scan - the ksm scanner main worker function.
|
||||
* @scan_npages - number of pages we want to scan before we return.
|
||||
* @scan_npages: number of pages we want to scan before we return.
|
||||
*/
|
||||
static void ksm_do_scan(unsigned int scan_npages)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -70,7 +70,7 @@ EXPORT_SYMBOL_GPL(probe_kernel_write);
|
|||
* strncpy_from_unsafe: - Copy a NUL terminated string from unsafe address.
|
||||
* @dst: Destination address, in kernel space. This buffer must be at
|
||||
* least @count bytes long.
|
||||
* @src: Unsafe address.
|
||||
* @unsafe_addr: Unsafe address.
|
||||
* @count: Maximum number of bytes to copy, including the trailing NUL.
|
||||
*
|
||||
* Copies a NUL-terminated string from unsafe address to kernel buffer.
|
||||
|
|
|
|||
|
|
@ -1654,7 +1654,7 @@ bool __init_memblock memblock_is_memory(phys_addr_t addr)
|
|||
return memblock_search(&memblock.memory, addr) != -1;
|
||||
}
|
||||
|
||||
int __init_memblock memblock_is_map_memory(phys_addr_t addr)
|
||||
bool __init_memblock memblock_is_map_memory(phys_addr_t addr)
|
||||
{
|
||||
int i = memblock_search(&memblock.memory, addr);
|
||||
|
||||
|
|
@ -1690,13 +1690,13 @@ int __init_memblock memblock_search_pfn_nid(unsigned long pfn,
|
|||
* RETURNS:
|
||||
* 0 if false, non-zero if true
|
||||
*/
|
||||
int __init_memblock memblock_is_region_memory(phys_addr_t base, phys_addr_t size)
|
||||
bool __init_memblock memblock_is_region_memory(phys_addr_t base, phys_addr_t size)
|
||||
{
|
||||
int idx = memblock_search(&memblock.memory, base);
|
||||
phys_addr_t end = base + memblock_cap_size(base, &size);
|
||||
|
||||
if (idx == -1)
|
||||
return 0;
|
||||
return false;
|
||||
return (memblock.memory.regions[idx].base +
|
||||
memblock.memory.regions[idx].size) >= end;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -917,7 +917,7 @@ int mem_cgroup_scan_tasks(struct mem_cgroup *memcg,
|
|||
/**
|
||||
* mem_cgroup_page_lruvec - return lruvec for isolating/putting an LRU page
|
||||
* @page: the page
|
||||
* @zone: zone of the page
|
||||
* @pgdat: pgdat of the page
|
||||
*
|
||||
* This function is only safe when following the LRU page isolation
|
||||
* and putback protocol: the LRU lock must be held, and the page must
|
||||
|
|
@ -5818,8 +5818,8 @@ bool mem_cgroup_charge_skmem(struct mem_cgroup *memcg, unsigned int nr_pages)
|
|||
|
||||
/**
|
||||
* mem_cgroup_uncharge_skmem - uncharge socket memory
|
||||
* @memcg - memcg to uncharge
|
||||
* @nr_pages - number of pages to uncharge
|
||||
* @memcg: memcg to uncharge
|
||||
* @nr_pages: number of pages to uncharge
|
||||
*/
|
||||
void mem_cgroup_uncharge_skmem(struct mem_cgroup *memcg, unsigned int nr_pages)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -59,7 +59,6 @@
|
|||
#include <linux/writeback.h>
|
||||
#include <linux/memcontrol.h>
|
||||
#include <linux/mmu_notifier.h>
|
||||
#include <linux/kallsyms.h>
|
||||
#include <linux/swapops.h>
|
||||
#include <linux/elf.h>
|
||||
#include <linux/gfp.h>
|
||||
|
|
@ -767,9 +766,6 @@ static void print_bad_pte(struct vm_area_struct *vma, unsigned long addr,
|
|||
dump_page(page, "bad pte");
|
||||
pr_alert("addr:%p vm_flags:%08lx anon_vma:%p mapping:%p index:%lx\n",
|
||||
(void *)addr, vma->vm_flags, vma->anon_vma, mapping, index);
|
||||
/*
|
||||
* Choose text because data symbols depend on CONFIG_KALLSYMS_ALL=y
|
||||
*/
|
||||
pr_alert("file:%pD fault:%pf mmap:%pf readpage:%pf\n",
|
||||
vma->vm_file,
|
||||
vma->vm_ops ? vma->vm_ops->fault : NULL,
|
||||
|
|
|
|||
|
|
@ -103,10 +103,10 @@ static inline void poison_element(mempool_t *pool, void *element)
|
|||
}
|
||||
#endif /* CONFIG_DEBUG_SLAB || CONFIG_SLUB_DEBUG_ON */
|
||||
|
||||
static void kasan_poison_element(mempool_t *pool, void *element)
|
||||
static __always_inline void kasan_poison_element(mempool_t *pool, void *element)
|
||||
{
|
||||
if (pool->alloc == mempool_alloc_slab || pool->alloc == mempool_kmalloc)
|
||||
kasan_poison_kfree(element);
|
||||
kasan_poison_kfree(element, _RET_IP_);
|
||||
if (pool->alloc == mempool_alloc_pages)
|
||||
kasan_free_pages(element, (unsigned long)pool->pool_data);
|
||||
}
|
||||
|
|
@ -119,7 +119,7 @@ static void kasan_unpoison_element(mempool_t *pool, void *element, gfp_t flags)
|
|||
kasan_alloc_pages(element, (unsigned long)pool->pool_data);
|
||||
}
|
||||
|
||||
static void add_element(mempool_t *pool, void *element)
|
||||
static __always_inline void add_element(mempool_t *pool, void *element)
|
||||
{
|
||||
BUG_ON(pool->curr_nr >= pool->min_nr);
|
||||
poison_element(pool, element);
|
||||
|
|
|
|||
|
|
@ -157,7 +157,7 @@ static void __munlock_isolation_failed(struct page *page)
|
|||
|
||||
/**
|
||||
* munlock_vma_page - munlock a vma page
|
||||
* @page - page to be unlocked, either a normal page or THP page head
|
||||
* @page: page to be unlocked, either a normal page or THP page head
|
||||
*
|
||||
* returns the size of the page as a page mask (0 for normal page,
|
||||
* HPAGE_PMD_NR - 1 for THP head page)
|
||||
|
|
|
|||
|
|
@ -1836,7 +1836,7 @@ int __access_remote_vm(struct task_struct *tsk, struct mm_struct *mm,
|
|||
}
|
||||
|
||||
/**
|
||||
* @access_remote_vm - access another process' address space
|
||||
* access_remote_vm - access another process' address space
|
||||
* @mm: the mm_struct of the target address space
|
||||
* @addr: start address to access
|
||||
* @buf: source or destination buffer
|
||||
|
|
|
|||
|
|
@ -265,6 +265,7 @@ static int __walk_page_range(unsigned long start, unsigned long end,
|
|||
* pte_entry(), and/or hugetlb_entry(). If you don't set up for some of these
|
||||
* callbacks, the associated entries/pages are just ignored.
|
||||
* The return values of these callbacks are commonly defined like below:
|
||||
*
|
||||
* - 0 : succeeded to handle the current entry, and if you don't reach the
|
||||
* end address yet, continue to walk.
|
||||
* - >0 : succeeded to handle the current entry, and return to the caller
|
||||
|
|
|
|||
|
|
@ -25,7 +25,7 @@
|
|||
/**
|
||||
* process_vm_rw_pages - read/write pages from task specified
|
||||
* @pages: array of pointers to pages we want to copy
|
||||
* @start_offset: offset in page to start copying from/to
|
||||
* @offset: offset in page to start copying from/to
|
||||
* @len: number of bytes to copy
|
||||
* @iter: where to copy to/from locally
|
||||
* @vm_write: 0 means copy from, 1 means copy to
|
||||
|
|
@ -147,6 +147,7 @@ static int process_vm_rw_single_vec(unsigned long addr,
|
|||
* @riovcnt: size of rvec array
|
||||
* @flags: currently unused
|
||||
* @vm_write: 0 if reading from other process, 1 if writing to other process
|
||||
*
|
||||
* Returns the number of bytes read/written or error code. May
|
||||
* return less bytes than expected if an error occurs during the copying
|
||||
* process.
|
||||
|
|
@ -197,11 +198,7 @@ static ssize_t process_vm_rw_core(pid_t pid, struct iov_iter *iter,
|
|||
}
|
||||
|
||||
/* Get process information */
|
||||
rcu_read_lock();
|
||||
task = find_task_by_vpid(pid);
|
||||
if (task)
|
||||
get_task_struct(task);
|
||||
rcu_read_unlock();
|
||||
task = find_get_task_by_vpid(pid);
|
||||
if (!task) {
|
||||
rc = -ESRCH;
|
||||
goto free_proc_pages;
|
||||
|
|
@ -253,6 +250,7 @@ free_proc_pages:
|
|||
* @riovcnt: size of rvec array
|
||||
* @flags: currently unused
|
||||
* @vm_write: 0 if reading from other process, 1 if writing to other process
|
||||
*
|
||||
* Returns the number of bytes read/written or error code. May
|
||||
* return less bytes than expected if an error occurs during the copying
|
||||
* process.
|
||||
|
|
|
|||
|
|
@ -3478,11 +3478,11 @@ free_done:
|
|||
* Release an obj back to its cache. If the obj has a constructed state, it must
|
||||
* be in this state _before_ it is released. Called with disabled ints.
|
||||
*/
|
||||
static inline void __cache_free(struct kmem_cache *cachep, void *objp,
|
||||
unsigned long caller)
|
||||
static __always_inline void __cache_free(struct kmem_cache *cachep, void *objp,
|
||||
unsigned long caller)
|
||||
{
|
||||
/* Put the object into the quarantine, don't touch it for now. */
|
||||
if (kasan_slab_free(cachep, objp))
|
||||
if (kasan_slab_free(cachep, objp, _RET_IP_))
|
||||
return;
|
||||
|
||||
___cache_free(cachep, objp, caller);
|
||||
|
|
|
|||
10
mm/slub.c
10
mm/slub.c
|
|
@ -1356,13 +1356,13 @@ static inline void kmalloc_large_node_hook(void *ptr, size_t size, gfp_t flags)
|
|||
kasan_kmalloc_large(ptr, size, flags);
|
||||
}
|
||||
|
||||
static inline void kfree_hook(const void *x)
|
||||
static __always_inline void kfree_hook(void *x)
|
||||
{
|
||||
kmemleak_free(x);
|
||||
kasan_kfree_large(x);
|
||||
kasan_kfree_large(x, _RET_IP_);
|
||||
}
|
||||
|
||||
static inline void *slab_free_hook(struct kmem_cache *s, void *x)
|
||||
static __always_inline void *slab_free_hook(struct kmem_cache *s, void *x)
|
||||
{
|
||||
void *freeptr;
|
||||
|
||||
|
|
@ -1390,7 +1390,7 @@ static inline void *slab_free_hook(struct kmem_cache *s, void *x)
|
|||
* kasan_slab_free() may put x into memory quarantine, delaying its
|
||||
* reuse. In this case the object's freelist pointer is changed.
|
||||
*/
|
||||
kasan_slab_free(s, x);
|
||||
kasan_slab_free(s, x, _RET_IP_);
|
||||
return freeptr;
|
||||
}
|
||||
|
||||
|
|
@ -3910,7 +3910,7 @@ void kfree(const void *x)
|
|||
page = virt_to_head_page(x);
|
||||
if (unlikely(!PageSlab(page))) {
|
||||
BUG_ON(!PageCompound(page));
|
||||
kfree_hook(x);
|
||||
kfree_hook(object);
|
||||
__free_pages(page, compound_order(page));
|
||||
return;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -913,11 +913,11 @@ EXPORT_SYMBOL(__pagevec_lru_add);
|
|||
* @pvec: Where the resulting entries are placed
|
||||
* @mapping: The address_space to search
|
||||
* @start: The starting entry index
|
||||
* @nr_entries: The maximum number of entries
|
||||
* @nr_pages: The maximum number of pages
|
||||
* @indices: The cache indices corresponding to the entries in @pvec
|
||||
*
|
||||
* pagevec_lookup_entries() will search for and return a group of up
|
||||
* to @nr_entries pages and shadow entries in the mapping. All
|
||||
* to @nr_pages pages and shadow entries in the mapping. All
|
||||
* entries are placed in @pvec. pagevec_lookup_entries() takes a
|
||||
* reference against actual pages in @pvec.
|
||||
*
|
||||
|
|
|
|||
|
|
@ -16,7 +16,6 @@
|
|||
#include <linux/userfaultfd_k.h>
|
||||
#include <linux/mmu_notifier.h>
|
||||
#include <linux/hugetlb.h>
|
||||
#include <linux/pagemap.h>
|
||||
#include <linux/shmem_fs.h>
|
||||
#include <asm/tlbflush.h>
|
||||
#include "internal.h"
|
||||
|
|
|
|||
|
|
@ -1595,6 +1595,7 @@ static unsigned long isolate_lru_pages(unsigned long nr_to_scan,
|
|||
* found will be decremented.
|
||||
*
|
||||
* Restrictions:
|
||||
*
|
||||
* (1) Must be called with an elevated refcount on the page. This is a
|
||||
* fundamentnal difference from isolate_lru_pages (which is called
|
||||
* without a stable reference).
|
||||
|
|
|
|||
|
|
@ -769,7 +769,7 @@ static void z3fold_free(struct z3fold_pool *pool, unsigned long handle)
|
|||
/**
|
||||
* z3fold_reclaim_page() - evicts allocations from a pool page and frees it
|
||||
* @pool: pool from which a page will attempt to be evicted
|
||||
* @retires: number of pages on the LRU list for which eviction will
|
||||
* @retries: number of pages on the LRU list for which eviction will
|
||||
* be attempted before failing
|
||||
*
|
||||
* z3fold reclaim is different from normal system reclaim in that it is done
|
||||
|
|
@ -779,7 +779,7 @@ static void z3fold_free(struct z3fold_pool *pool, unsigned long handle)
|
|||
* z3fold and the user, however.
|
||||
*
|
||||
* To avoid these, this is how z3fold_reclaim_page() should be called:
|
||||
|
||||
*
|
||||
* The user detects a page should be reclaimed and calls z3fold_reclaim_page().
|
||||
* z3fold_reclaim_page() will remove a z3fold page from the pool LRU list and
|
||||
* call the user-defined eviction handler with the pool and handle as
|
||||
|
|
|
|||
|
|
@ -466,7 +466,7 @@ void zbud_free(struct zbud_pool *pool, unsigned long handle)
|
|||
/**
|
||||
* zbud_reclaim_page() - evicts allocations from a pool page and frees it
|
||||
* @pool: pool from which a page will attempt to be evicted
|
||||
* @retires: number of pages on the LRU list for which eviction will
|
||||
* @retries: number of pages on the LRU list for which eviction will
|
||||
* be attempted before failing
|
||||
*
|
||||
* zbud reclaim is different from normal system reclaim in that the reclaim is
|
||||
|
|
@ -476,7 +476,7 @@ void zbud_free(struct zbud_pool *pool, unsigned long handle)
|
|||
* the user, however.
|
||||
*
|
||||
* To avoid these, this is how zbud_reclaim_page() should be called:
|
||||
|
||||
*
|
||||
* The user detects a page should be reclaimed and calls zbud_reclaim_page().
|
||||
* zbud_reclaim_page() will remove a zbud page from the pool LRU list and call
|
||||
* the user-defined eviction handler with the pool and handle as arguments.
|
||||
|
|
|
|||
46
mm/zpool.c
46
mm/zpool.c
|
|
@ -101,7 +101,7 @@ static void zpool_put_driver(struct zpool_driver *driver)
|
|||
|
||||
/**
|
||||
* zpool_has_pool() - Check if the pool driver is available
|
||||
* @type The type of the zpool to check (e.g. zbud, zsmalloc)
|
||||
* @type: The type of the zpool to check (e.g. zbud, zsmalloc)
|
||||
*
|
||||
* This checks if the @type pool driver is available. This will try to load
|
||||
* the requested module, if needed, but there is no guarantee the module will
|
||||
|
|
@ -136,10 +136,10 @@ EXPORT_SYMBOL(zpool_has_pool);
|
|||
|
||||
/**
|
||||
* zpool_create_pool() - Create a new zpool
|
||||
* @type The type of the zpool to create (e.g. zbud, zsmalloc)
|
||||
* @name The name of the zpool (e.g. zram0, zswap)
|
||||
* @gfp The GFP flags to use when allocating the pool.
|
||||
* @ops The optional ops callback.
|
||||
* @type: The type of the zpool to create (e.g. zbud, zsmalloc)
|
||||
* @name: The name of the zpool (e.g. zram0, zswap)
|
||||
* @gfp: The GFP flags to use when allocating the pool.
|
||||
* @ops: The optional ops callback.
|
||||
*
|
||||
* This creates a new zpool of the specified type. The gfp flags will be
|
||||
* used when allocating memory, if the implementation supports it. If the
|
||||
|
|
@ -201,7 +201,7 @@ struct zpool *zpool_create_pool(const char *type, const char *name, gfp_t gfp,
|
|||
|
||||
/**
|
||||
* zpool_destroy_pool() - Destroy a zpool
|
||||
* @pool The zpool to destroy.
|
||||
* @zpool: The zpool to destroy.
|
||||
*
|
||||
* Implementations must guarantee this to be thread-safe,
|
||||
* however only when destroying different pools. The same
|
||||
|
|
@ -224,7 +224,7 @@ void zpool_destroy_pool(struct zpool *zpool)
|
|||
|
||||
/**
|
||||
* zpool_get_type() - Get the type of the zpool
|
||||
* @pool The zpool to check
|
||||
* @zpool: The zpool to check
|
||||
*
|
||||
* This returns the type of the pool.
|
||||
*
|
||||
|
|
@ -239,10 +239,10 @@ const char *zpool_get_type(struct zpool *zpool)
|
|||
|
||||
/**
|
||||
* zpool_malloc() - Allocate memory
|
||||
* @pool The zpool to allocate from.
|
||||
* @size The amount of memory to allocate.
|
||||
* @gfp The GFP flags to use when allocating memory.
|
||||
* @handle Pointer to the handle to set
|
||||
* @zpool: The zpool to allocate from.
|
||||
* @size: The amount of memory to allocate.
|
||||
* @gfp: The GFP flags to use when allocating memory.
|
||||
* @handle: Pointer to the handle to set
|
||||
*
|
||||
* This allocates the requested amount of memory from the pool.
|
||||
* The gfp flags will be used when allocating memory, if the
|
||||
|
|
@ -261,8 +261,8 @@ int zpool_malloc(struct zpool *zpool, size_t size, gfp_t gfp,
|
|||
|
||||
/**
|
||||
* zpool_free() - Free previously allocated memory
|
||||
* @pool The zpool that allocated the memory.
|
||||
* @handle The handle to the memory to free.
|
||||
* @zpool: The zpool that allocated the memory.
|
||||
* @handle: The handle to the memory to free.
|
||||
*
|
||||
* This frees previously allocated memory. This does not guarantee
|
||||
* that the pool will actually free memory, only that the memory
|
||||
|
|
@ -280,9 +280,9 @@ void zpool_free(struct zpool *zpool, unsigned long handle)
|
|||
|
||||
/**
|
||||
* zpool_shrink() - Shrink the pool size
|
||||
* @pool The zpool to shrink.
|
||||
* @pages The number of pages to shrink the pool.
|
||||
* @reclaimed The number of pages successfully evicted.
|
||||
* @zpool: The zpool to shrink.
|
||||
* @pages: The number of pages to shrink the pool.
|
||||
* @reclaimed: The number of pages successfully evicted.
|
||||
*
|
||||
* This attempts to shrink the actual memory size of the pool
|
||||
* by evicting currently used handle(s). If the pool was
|
||||
|
|
@ -304,11 +304,11 @@ int zpool_shrink(struct zpool *zpool, unsigned int pages,
|
|||
|
||||
/**
|
||||
* zpool_map_handle() - Map a previously allocated handle into memory
|
||||
* @pool The zpool that the handle was allocated from
|
||||
* @handle The handle to map
|
||||
* @mm How the memory should be mapped
|
||||
* @zpool: The zpool that the handle was allocated from
|
||||
* @handle: The handle to map
|
||||
* @mapmode: How the memory should be mapped
|
||||
*
|
||||
* This maps a previously allocated handle into memory. The @mm
|
||||
* This maps a previously allocated handle into memory. The @mapmode
|
||||
* param indicates to the implementation how the memory will be
|
||||
* used, i.e. read-only, write-only, read-write. If the
|
||||
* implementation does not support it, the memory will be treated
|
||||
|
|
@ -332,8 +332,8 @@ void *zpool_map_handle(struct zpool *zpool, unsigned long handle,
|
|||
|
||||
/**
|
||||
* zpool_unmap_handle() - Unmap a previously mapped handle
|
||||
* @pool The zpool that the handle was allocated from
|
||||
* @handle The handle to unmap
|
||||
* @zpool: The zpool that the handle was allocated from
|
||||
* @handle: The handle to unmap
|
||||
*
|
||||
* This unmaps a previously mapped handle. Any locks or other
|
||||
* actions that the implementation took in zpool_map_handle()
|
||||
|
|
@ -347,7 +347,7 @@ void zpool_unmap_handle(struct zpool *zpool, unsigned long handle)
|
|||
|
||||
/**
|
||||
* zpool_get_total_size() - The total size of the pool
|
||||
* @pool The zpool to check
|
||||
* @zpool: The zpool to check
|
||||
*
|
||||
* This returns the total size in bytes of the pool.
|
||||
*
|
||||
|
|
|
|||
Loading…
Reference in a new issue