ANDROID: vendor_hooks: Add hooks to extend struct swap_slots_cache

Three vendor hooks are provided to extend struct swap_slots_cache.
The extended data are used to record the information of the
specified reclaimed swap location:
1) android_vh_alloc_swap_slot_cache, replace the function
alloc_swap_slot_cache adding allocation of the extension
of struct swap_slots_cache;
2) android_vh_drain_slots_cache_cpu, replace the function
drain_slots_cache_cpu adding the initialization of the
extension of struct swap_slots_cache;
3) android_vh_get_swap_page, replace the function get_swap_page,
according to the reclaimed location information of the page,
get the the swap page from the specified swap location;

Bug: 234214858
Signed-off-by: Bing Han <bing.han@transsion.com>
Change-Id: I3bce6e8cf255df1d879b7c4022d54981cce7c273
This commit is contained in:
Bing Han
2022-05-30 16:28:05 +08:00
committed by Treehugger Robot
parent 4506bcbba5
commit d4eef93a9d
3 changed files with 32 additions and 1 deletions

View File

@@ -416,7 +416,10 @@ EXPORT_TRACEPOINT_SYMBOL_GPL(android_vh_page_referenced_one_end);
EXPORT_TRACEPOINT_SYMBOL_GPL(android_vh_count_pswpin);
EXPORT_TRACEPOINT_SYMBOL_GPL(android_vh_count_pswpout);
EXPORT_TRACEPOINT_SYMBOL_GPL(android_vh_count_swpout_vm_event);
EXPORT_TRACEPOINT_SYMBOL_GPL(android_vh_drain_slots_cache_cpu);
EXPORT_TRACEPOINT_SYMBOL_GPL(android_vh_alloc_swap_slot_cache);
EXPORT_TRACEPOINT_SYMBOL_GPL(android_vh_free_swap_slot);
EXPORT_TRACEPOINT_SYMBOL_GPL(android_vh_get_swap_page);
EXPORT_TRACEPOINT_SYMBOL_GPL(android_vh_page_isolated_for_reclaim);
EXPORT_TRACEPOINT_SYMBOL_GPL(android_vh_inactive_is_low);
EXPORT_TRACEPOINT_SYMBOL_GPL(android_vh_snapshot_refaults);

View File

@@ -33,6 +33,7 @@ struct readahead_control;
#include <linux/pagemap.h>
#endif /* __GENKSYMS__ */
struct cma;
struct swap_slots_cache;
DECLARE_RESTRICTED_HOOK(android_rvh_set_skip_swapcache_flags,
TP_PROTO(gfp_t *flags),
@@ -176,9 +177,20 @@ DECLARE_HOOK(android_vh_count_pswpout,
DECLARE_HOOK(android_vh_count_swpout_vm_event,
TP_PROTO(struct swap_info_struct *sis, struct page *page, bool *skip),
TP_ARGS(sis, page, skip));
DECLARE_HOOK(android_vh_drain_slots_cache_cpu,
TP_PROTO(struct swap_slots_cache *cache, unsigned int type,
bool free_slots, bool *skip),
TP_ARGS(cache, type, free_slots, skip));
DECLARE_HOOK(android_vh_alloc_swap_slot_cache,
TP_PROTO(struct swap_slots_cache *cache, int *ret, bool *skip),
TP_ARGS(cache, ret, skip));
DECLARE_HOOK(android_vh_free_swap_slot,
TP_PROTO(swp_entry_t entry, struct swap_slots_cache *cache, bool *skip),
TP_ARGS(entry, cache, skip));
DECLARE_HOOK(android_vh_get_swap_page,
TP_PROTO(struct page *page, swp_entry_t *entry,
struct swap_slots_cache *cache, bool *found),
TP_ARGS(page, entry, cache, found));
DECLARE_HOOK(android_vh_page_isolated_for_reclaim,
TP_PROTO(struct mm_struct *mm, struct page *page),
TP_ARGS(mm, page));

View File

@@ -33,6 +33,7 @@
#include <linux/vmalloc.h>
#include <linux/mutex.h>
#include <linux/mm.h>
#include <trace/hooks/mm.h>
static DEFINE_PER_CPU(struct swap_slots_cache, swp_slots);
static bool swap_slot_cache_active;
@@ -115,12 +116,18 @@ static int alloc_swap_slot_cache(unsigned int cpu)
{
struct swap_slots_cache *cache;
swp_entry_t *slots, *slots_ret;
bool skip = false;
int ret = 0;
/*
* Do allocation outside swap_slots_cache_mutex
* as kvzalloc could trigger reclaim and get_swap_page,
* which can lock swap_slots_cache_mutex.
*/
trace_android_vh_alloc_swap_slot_cache(&per_cpu(swp_slots, cpu),
&ret, &skip);
if (skip)
return ret;
slots = kvcalloc(SWAP_SLOTS_CACHE_SIZE, sizeof(swp_entry_t),
GFP_KERNEL);
if (!slots)
@@ -171,8 +178,13 @@ static void drain_slots_cache_cpu(unsigned int cpu, unsigned int type,
{
struct swap_slots_cache *cache;
swp_entry_t *slots = NULL;
bool skip = false;
cache = &per_cpu(swp_slots, cpu);
trace_android_vh_drain_slots_cache_cpu(cache, type,
free_slots, &skip);
if (skip)
return;
if ((type & SLOTS_CACHE) && cache->slots) {
mutex_lock(&cache->alloc_lock);
swapcache_free_entries(cache->slots + cache->cur, cache->nr);
@@ -311,9 +323,13 @@ swp_entry_t get_swap_page(struct page *page)
{
swp_entry_t entry;
struct swap_slots_cache *cache;
bool found = false;
entry.val = 0;
trace_android_vh_get_swap_page(page, &entry, raw_cpu_ptr(&swp_slots), &found);
if (found)
goto out;
if (PageTransHuge(page)) {
if (IS_ENABLED(CONFIG_THP_SWAP))
get_swap_pages(1, &entry, HPAGE_PMD_NR);