mm: Revert PID optimizations

Change-Id: I61da569fb17d5a5ac5e814bcbeed8013c6e5a7a2
Signed-off-by: Richard Raya <rdxzv.dev@gmail.com>
This commit is contained in:
Richard Raya 2024-04-18 10:02:27 -03:00
parent 304813b888
commit fec6892d1c
9 changed files with 46 additions and 417 deletions

View File

@ -95,5 +95,3 @@ obj-$(CONFIG_OKL4_LINK_SHBUF) += okl4-link-shbuf.o
obj-$(CONFIG_AW8624_HAPTIC) += aw8624_haptic/
obj-$(CONFIG_DRV2624_HAPTIC) += drv2624_haptic/
obj-$(CONFIG_LDO_WL2866D) += wl2866d.o
obj-y += lyb_taskmmu.o

View File

@ -1,30 +0,0 @@
// SPDX-License-Identifier: GPL-2.0
#include <linux/init.h>
#include <linux/module.h>
#include <linux/kernel.h>
#include <misc/lyb_taskmmu.h>
MODULE_LICENSE("GPL");
MODULE_AUTHOR("lybxlpsv");
MODULE_DESCRIPTION("lyb taskmmu");
MODULE_VERSION("0.0.2");
bool lyb_sultan_pid = false;
module_param(lyb_sultan_pid, bool, 0644);
bool lyb_sultan_pid_shrink = false;
module_param(lyb_sultan_pid_shrink, bool, 0644);
static int __init lyb_driver_init(void) {
printk(KERN_INFO "lyb taskmmu initialized");
lyb_sultan_pid = false;
lyb_sultan_pid_shrink = false;
return 0;
}
static void __exit lyb_driver_exit(void) {
printk(KERN_INFO "lyb taskmmu exit");
}
module_init(lyb_driver_init);
module_exit(lyb_driver_exit);

View File

@ -3101,7 +3101,12 @@ static int prepend_name(char **buffer, int *buflen, const struct qstr *name)
return -ENAMETOOLONG;
p = *buffer -= dlen + 1;
*p++ = '/';
memcpy(p, dname, dlen);
while (dlen--) {
char c = *dname++;
if (!c)
break;
*p++ = c;
}
return 0;
}
@ -3304,9 +3309,9 @@ static void get_fs_root_rcu(struct fs_struct *fs, struct path *root)
*
* "buflen" should be positive.
*/
char *d_path_outlen(const struct path *path, char *buf, int *buflen)
char *d_path(const struct path *path, char *buf, int buflen)
{
char *res = buf + *buflen;
char *res = buf + buflen;
struct path root;
int error;
@ -3323,22 +3328,17 @@ char *d_path_outlen(const struct path *path, char *buf, int *buflen)
*/
if (path->dentry->d_op && path->dentry->d_op->d_dname &&
(!IS_ROOT(path->dentry) || path->dentry != path->mnt->mnt_root))
return path->dentry->d_op->d_dname(path->dentry, buf, *buflen);
return path->dentry->d_op->d_dname(path->dentry, buf, buflen);
rcu_read_lock();
get_fs_root_rcu(current->fs, &root);
error = path_with_deleted(path, &root, &res, buflen);
error = path_with_deleted(path, &root, &res, &buflen);
rcu_read_unlock();
if (error < 0)
res = ERR_PTR(error);
return res;
}
char *d_path(const struct path *path, char *buf, int buflen)
{
return d_path_outlen(path, buf, &buflen);
}
EXPORT_SYMBOL(d_path);
/*

View File

@ -798,8 +798,6 @@ int setup_arg_pages(struct linux_binprm *bprm,
ret = expand_stack(vma, stack_base);
if (ret)
ret = -EFAULT;
else
current->mm->stack_vma = vma;
out_unlock:
up_write(&mm->mmap_sem);

View File

@ -24,7 +24,6 @@
#include <asm/elf.h>
#include <asm/tlb.h>
#include <asm/tlbflush.h>
#include <misc/lyb_taskmmu.h>
#include "internal.h"
void task_mem(struct seq_file *m, struct mm_struct *mm)
@ -148,7 +147,7 @@ static void seq_print_vma_name(struct seq_file *m, struct vm_area_struct *vma)
page_offset = (unsigned long)name - page_start_vaddr;
num_pages = DIV_ROUND_UP(page_offset + max_len, PAGE_SIZE);
seq_write(m, "[anon:", 6);
seq_puts(m, "[anon:");
for (i = 0; i < num_pages; i++) {
int len;
@ -160,7 +159,7 @@ static void seq_print_vma_name(struct seq_file *m, struct vm_area_struct *vma)
pages_pinned = get_user_pages_remote(current, mm,
page_start_vaddr, 1, 0, &page, NULL, NULL);
if (pages_pinned < 1) {
seq_write(m, "<fault>]\n", 9);
seq_puts(m, "<fault>]");
return;
}
@ -180,7 +179,7 @@ static void seq_print_vma_name(struct seq_file *m, struct vm_area_struct *vma)
page_start_vaddr += PAGE_SIZE;
}
seq_write(m, "]\n", 2);
seq_putc(m, ']');
}
static void vma_stop(struct proc_maps_private *priv)
@ -339,272 +338,21 @@ static int is_stack(struct vm_area_struct *vma)
vma->vm_end >= vma->vm_mm->start_stack;
}
#define print_vma_hex10(out, val, clz_fn) \
({ \
const typeof(val) __val = val; \
char *const __out = out; \
size_t __len; \
\
if (__val) { \
__len = (sizeof(__val) * 8 - clz_fn(__val) + 3) / 4; \
switch (__len) { \
case 10: \
__out[9] = hex_asc[(__val >> 0) & 0xf]; \
__out[8] = hex_asc[(__val >> 4) & 0xf]; \
__out[7] = hex_asc[(__val >> 8) & 0xf]; \
__out[6] = hex_asc[(__val >> 12) & 0xf]; \
__out[5] = hex_asc[(__val >> 16) & 0xf]; \
__out[4] = hex_asc[(__val >> 20) & 0xf]; \
__out[3] = hex_asc[(__val >> 24) & 0xf]; \
__out[2] = hex_asc[(__val >> 28) & 0xf]; \
__out[1] = hex_asc[(__val >> 32) & 0xf]; \
__out[0] = hex_asc[(__val >> 36) & 0xf]; \
break; \
case 9: \
__out[8] = hex_asc[(__val >> 0) & 0xf]; \
__out[7] = hex_asc[(__val >> 4) & 0xf]; \
__out[6] = hex_asc[(__val >> 8) & 0xf]; \
__out[5] = hex_asc[(__val >> 12) & 0xf]; \
__out[4] = hex_asc[(__val >> 16) & 0xf]; \
__out[3] = hex_asc[(__val >> 20) & 0xf]; \
__out[2] = hex_asc[(__val >> 24) & 0xf]; \
__out[1] = hex_asc[(__val >> 28) & 0xf]; \
__out[0] = hex_asc[(__val >> 32) & 0xf]; \
break; \
default: \
__out[7] = hex_asc[(__val >> 0) & 0xf]; \
__out[6] = hex_asc[(__val >> 4) & 0xf]; \
__out[5] = hex_asc[(__val >> 8) & 0xf]; \
__out[4] = hex_asc[(__val >> 12) & 0xf]; \
__out[3] = hex_asc[(__val >> 16) & 0xf]; \
__out[2] = hex_asc[(__val >> 20) & 0xf]; \
__out[1] = hex_asc[(__val >> 24) & 0xf]; \
__out[0] = hex_asc[(__val >> 28) & 0xf]; \
__len = 8; \
break; \
} \
} else { \
*(u64 *)__out = U64_C(0x3030303030303030); \
__len = 8; \
} \
\
__len; \
})
#define print_vma_hex2(out, val) \
({ \
const typeof(val) __val = val; \
char *const __out = out; \
\
__out[1] = hex_asc[(__val >> 0) & 0xf]; \
__out[0] = hex_asc[(__val >> 4) & 0xf]; \
\
2; \
})
#define print_vma_hex10_shrink(out, val, clz_fn) \
({ \
const typeof(val) __val = val; \
char *const __out = out; \
size_t __len; \
\
if (__val) { \
__len = (sizeof(__val) * 8 - clz_fn(__val) + 3) / 4; \
switch (__len) { \
case 10: \
__out[9] = hex_asc[(__val >> 0) & 0xf]; \
__out[8] = hex_asc[(__val >> 4) & 0xf]; \
__out[7] = hex_asc[(__val >> 8) & 0xf]; \
__out[6] = hex_asc[(__val >> 12) & 0xf]; \
__out[5] = hex_asc[(__val >> 16) & 0xf]; \
__out[4] = hex_asc[(__val >> 20) & 0xf]; \
__out[3] = hex_asc[(__val >> 24) & 0xf]; \
__out[2] = hex_asc[(__val >> 28) & 0xf]; \
__out[1] = hex_asc[(__val >> 32) & 0xf]; \
__out[0] = hex_asc[(__val >> 36) & 0xf]; \
break; \
case 9: \
__out[8] = hex_asc[(__val >> 0) & 0xf]; \
__out[7] = hex_asc[(__val >> 4) & 0xf]; \
__out[6] = hex_asc[(__val >> 8) & 0xf]; \
__out[5] = hex_asc[(__val >> 12) & 0xf]; \
__out[4] = hex_asc[(__val >> 16) & 0xf]; \
__out[3] = hex_asc[(__val >> 20) & 0xf]; \
__out[2] = hex_asc[(__val >> 24) & 0xf]; \
__out[1] = hex_asc[(__val >> 28) & 0xf]; \
__out[0] = hex_asc[(__val >> 32) & 0xf]; \
break; \
case 8: \
__out[7] = hex_asc[(__val >> 0) & 0xf]; \
__out[6] = hex_asc[(__val >> 4) & 0xf]; \
__out[5] = hex_asc[(__val >> 8) & 0xf]; \
__out[4] = hex_asc[(__val >> 12) & 0xf]; \
__out[3] = hex_asc[(__val >> 16) & 0xf]; \
__out[2] = hex_asc[(__val >> 20) & 0xf]; \
__out[1] = hex_asc[(__val >> 24) & 0xf]; \
__out[0] = hex_asc[(__val >> 28) & 0xf]; \
break; \
case 7: \
__out[6] = hex_asc[(__val >> 0) & 0xf]; \
__out[5] = hex_asc[(__val >> 4) & 0xf]; \
__out[4] = hex_asc[(__val >> 8) & 0xf]; \
__out[3] = hex_asc[(__val >> 12) & 0xf]; \
__out[2] = hex_asc[(__val >> 16) & 0xf]; \
__out[1] = hex_asc[(__val >> 20) & 0xf]; \
__out[0] = hex_asc[(__val >> 24) & 0xf]; \
break; \
case 6: \
__out[5] = hex_asc[(__val >> 0) & 0xf]; \
__out[4] = hex_asc[(__val >> 4) & 0xf]; \
__out[3] = hex_asc[(__val >> 8) & 0xf]; \
__out[2] = hex_asc[(__val >> 12) & 0xf]; \
__out[1] = hex_asc[(__val >> 16) & 0xf]; \
__out[0] = hex_asc[(__val >> 20) & 0xf]; \
break; \
case 5: \
__out[4] = hex_asc[(__val >> 0) & 0xf]; \
__out[3] = hex_asc[(__val >> 4) & 0xf]; \
__out[2] = hex_asc[(__val >> 8) & 0xf]; \
__out[1] = hex_asc[(__val >> 12) & 0xf]; \
__out[0] = hex_asc[(__val >> 16) & 0xf]; \
break; \
case 4: \
__out[3] = hex_asc[(__val >> 0) & 0xf]; \
__out[2] = hex_asc[(__val >> 4) & 0xf]; \
__out[1] = hex_asc[(__val >> 8) & 0xf]; \
__out[0] = hex_asc[(__val >> 12) & 0xf]; \
break; \
case 3: \
__out[2] = hex_asc[(__val >> 0) & 0xf]; \
__out[1] = hex_asc[(__val >> 4) & 0xf]; \
__out[0] = hex_asc[(__val >> 8) & 0xf]; \
break; \
case 2: \
__out[1] = hex_asc[(__val >> 0) & 0xf]; \
__out[0] = hex_asc[(__val >> 4) & 0xf]; \
break; \
case 1: \
__out[0] = hex_asc[(__val >> 0) & 0xf]; \
break; \
} \
} else { \
__len = 1; \
__out[0] = '0'; \
} \
\
__len; \
})
#define print_vma_hex2_shrink(out, val, clz_fn) \
({ \
const typeof(val) __val = val; \
char *const __out = out; \
size_t __len; \
\
if (__val) { \
__len = (sizeof(__val) * 8 - clz_fn(__val) + 3) / 4; \
switch (__len) { \
case 2: \
__out[1] = hex_asc[(__val >> 0) & 0xf]; \
__out[0] = hex_asc[(__val >> 4) & 0xf]; \
break; \
case 1: \
__out[0] = hex_asc[(__val >> 0) & 0xf]; \
break; \
} \
} else { \
__len = 1; \
__out[0] = '0'; \
} \
\
__len; \
})
static int show_vma_header_prefix(struct seq_file *m, unsigned long start,
unsigned long end, vm_flags_t flags,
unsigned long long pgoff, dev_t dev,
unsigned long ino)
static void show_vma_header_prefix(struct seq_file *m,
unsigned long start, unsigned long end,
vm_flags_t flags, unsigned long long pgoff,
dev_t dev, unsigned long ino)
{
size_t len;
char *out;
/* Set the overflow status to get more memory if there's no space */
if (seq_get_buf(m, &out) < 65) {
seq_commit(m, -1);
return -ENOMEM;
}
/* Supports printing up to 40 bits per virtual address */
BUILD_BUG_ON(CONFIG_ARM64_VA_BITS > 40);
if (lyb_sultan_pid_shrink)
{
/*
* shrinks the PID map output to be as small as
* possible by omitting non-significant leading zeros from
* hex output.
*/
len = print_vma_hex10_shrink(out, start, __builtin_clzl);
out[len++] = '-';
len += print_vma_hex10_shrink(out + len, end, __builtin_clzl);
out[len++] = ' ';
out[len++] = "-r"[!!(flags & VM_READ)];
out[len++] = "-w"[!!(flags & VM_WRITE)];
out[len++] = "-x"[!!(flags & VM_EXEC)];
out[len++] = "ps"[!!(flags & VM_MAYSHARE)];
out[len++] = ' ';
len += print_vma_hex10_shrink(out + len, pgoff, __builtin_clzll);
out[len++] = ' ';
len += print_vma_hex2_shrink(out + len, MAJOR(dev), __builtin_clz);
out[len++] = ':';
len += print_vma_hex2_shrink(out + len, MINOR(dev), __builtin_clz);
out[len++] = ' ';
} else {
/*
* retains insignificant leading zeros from printed hex values
* to maintain the current output format.
*/
len = print_vma_hex10(out, start, __builtin_clzl);
out[len++] = '-';
len += print_vma_hex10(out + len, end, __builtin_clzl);
out[len++] = ' ';
out[len++] = "-r"[!!(flags & VM_READ)];
out[len++] = "-w"[!!(flags & VM_WRITE)];
out[len++] = "-x"[!!(flags & VM_EXEC)];
out[len++] = "ps"[!!(flags & VM_MAYSHARE)];
out[len++] = ' ';
len += print_vma_hex10(out + len, pgoff, __builtin_clzll);
out[len++] = ' ';
len += print_vma_hex2(out + len, MAJOR(dev));
out[len++] = ':';
len += print_vma_hex2(out + len, MINOR(dev));
out[len++] = ' ';
}
len += num_to_str(&out[len], 20, ino);
out[len++] = ' ';
m->count += len;
return 0;
seq_setwidth(m, 25 + sizeof(void *) * 6 - 1);
seq_printf(m, "%08lx-%08lx %c%c%c%c %08llx %02x:%02x %lu ",
start,
end,
flags & VM_READ ? 'r' : '-',
flags & VM_WRITE ? 'w' : '-',
flags & VM_EXEC ? 'x' : '-',
flags & VM_MAYSHARE ? 's' : 'p',
pgoff,
MAJOR(dev), MINOR(dev), ino);
}
static void
@ -628,44 +376,16 @@ show_map_vma(struct seq_file *m, struct vm_area_struct *vma, int is_pid)
start = vma->vm_start;
end = vma->vm_end;
if (show_vma_header_prefix(m, start, end, flags, pgoff, dev, ino))
return;
show_vma_header_prefix(m, start, end, flags, pgoff, dev, ino);
/*
* Print the dentry name for named mappings, and a
* special [heap] marker for the heap:
*/
if (file) {
char *buf;
size_t size = seq_get_buf(m, &buf);
/*
* This won't escape newline characters from the path. If a
* program uses newlines in its paths then it can kick rocks.
*/
if (size > 1) {
const int inlen = size - 1;
int outlen = inlen;
char *p;
p = d_path_outlen(&file->f_path, buf, &outlen);
if (!IS_ERR(p)) {
size_t len;
if (outlen != inlen)
len = inlen - outlen - 1;
else
len = strlen(p);
memmove(buf, p, len);
buf[len] = '\n';
seq_commit(m, len + 1);
return;
}
}
/* Set the overflow status to get more memory */
seq_commit(m, -1);
return;
seq_pad(m, ' ');
seq_file_path(m, file, "\n");
goto done;
}
if (vma->vm_ops && vma->vm_ops->name) {
@ -677,30 +397,32 @@ show_map_vma(struct seq_file *m, struct vm_area_struct *vma, int is_pid)
name = arch_vma_name(vma);
if (!name) {
if (!mm) {
seq_write(m, "[vdso]\n", 7);
return;
name = "[vdso]";
goto done;
}
if (vma->vm_start <= mm->brk &&
vma->vm_end >= mm->start_brk) {
seq_write(m, "[heap]\n", 7);
return;
name = "[heap]";
goto done;
}
if (is_stack(vma)) {
seq_write(m, "[stack]\n", 8);
return;
name = "[stack]";
goto done;
}
if (vma_get_anon_name(vma)) {
seq_pad(m, ' ');
seq_print_vma_name(m, vma);
return;
}
}
done:
if (name)
if (name) {
seq_pad(m, ' ');
seq_puts(m, name);
}
seq_putc(m, '\n');
}
@ -721,50 +443,6 @@ static int show_tid_map(struct seq_file *m, void *v)
return show_map(m, v, 0);
}
static void *m_start_pid(struct seq_file *m, loff_t *ppos)
{
struct vm_area_struct *vma = m_start(m, ppos);
/*
* Android only cares about the stack mapping, so we can optimize this
* to only return the stack mapping. Processes that have several
* thousands of mappings waste a lot of time in here when Android only
* cares about finding the stack mapping. Android does this in Bionic to
* determine the size of a process' stack when pthreads are used.
*/
if (vma) {
struct mm_struct *mm = vma->vm_mm;
struct vm_area_struct *tmp;
/* Optimistically check if the cached stack mapping is valid */
tmp = READ_ONCE(mm->stack_vma);
if (tmp && is_stack(tmp))
return tmp;
/* Look for the current stack mapping and update the cache */
tmp = vma;
do {
if (is_stack(tmp)) {
WRITE_ONCE(mm->stack_vma, vma);
return tmp;
}
tmp = tmp->vm_next;
} while (tmp);
}
return NULL;
}
static void *m_next_pid(struct seq_file *m, void *v, loff_t *pos)
{
struct proc_maps_private *priv = m->private;
/* Terminate since the stack mapping has been printed */
vma_stop(priv);
(*pos)++;
return NULL;
}
static const struct seq_operations proc_pid_maps_op = {
.start = m_start,
.next = m_next,
@ -772,13 +450,6 @@ static const struct seq_operations proc_pid_maps_op = {
.show = show_pid_map
};
static const struct seq_operations proc_pid_maps_op_sultanpid = {
.start = m_start_pid,
.next = m_next_pid,
.stop = m_stop,
.show = show_pid_map
};
static const struct seq_operations proc_tid_maps_op = {
.start = m_start,
.next = m_next,
@ -788,9 +459,7 @@ static const struct seq_operations proc_tid_maps_op = {
static int pid_maps_open(struct inode *inode, struct file *file)
{
if (lyb_sultan_pid)
return do_maps_open(inode, file, &proc_pid_maps_op_sultanpid);
else return do_maps_open(inode, file, &proc_pid_maps_op);
return do_maps_open(inode, file, &proc_pid_maps_op);
}
static int tid_maps_open(struct inode *inode, struct file *file)
@ -1204,10 +873,12 @@ static int show_smap(struct seq_file *m, void *v, int is_pid)
if (vma_get_anon_name(vma)) {
seq_puts(m, "Name: ");
seq_print_vma_name(m, vma);
seq_putc(m, '\n');
}
} else if (last_vma) {
show_vma_header_prefix(
m, mss->first_vma_start, vma->vm_end, 0, 0, 0, 0);
seq_pad(m, ' ');
seq_puts(m, "[rollup]\n");
} else {
ret = SEQ_SKIP;
@ -1216,6 +887,7 @@ static int show_smap(struct seq_file *m, void *v, int is_pid)
if (vma_get_anon_name(vma)) {
seq_puts(m, "Name: ");
seq_print_vma_name(m, vma);
seq_putc(m, '\n');
}
if (!rollup_mode)

View File

@ -305,7 +305,6 @@ extern char *simple_dname(struct dentry *, char *, int);
extern char *__d_path(const struct path *, const struct path *, char *, int);
extern char *d_absolute_path(const struct path *, char *, int);
extern char *d_path(const struct path *, char *, int);
extern char *d_path_outlen(const struct path *, char *, int *);
extern char *dentry_path_raw(struct dentry *, char *, int);
extern char *dentry_path(struct dentry *, char *, int);

View File

@ -374,7 +374,7 @@ struct core_state {
struct kioctx_table;
struct mm_struct {
struct vm_area_struct *mmap, *stack_vma; /* list of VMAs */
struct vm_area_struct *mmap; /* list of VMAs */
struct rb_root mm_rb;
#ifdef CONFIG_SPECULATIVE_PAGE_FAULT
rwlock_t mm_rb_lock;

View File

@ -1,4 +0,0 @@
// SPDX-License-Identifier: GPL-2.0
extern bool lyb_sultan_pid;
extern bool lyb_sultan_pid_shrink;

View File

@ -184,8 +184,6 @@ static struct vm_area_struct *remove_vma(struct vm_area_struct *vma)
struct vm_area_struct *next = vma->vm_next;
might_sleep();
if (vma == vma->vm_mm->stack_vma)
vma->vm_mm->stack_vma = NULL;
if (vma->vm_ops && vma->vm_ops->close)
vma->vm_ops->close(vma);
put_vma(vma);
@ -966,8 +964,6 @@ again:
mm->map_count--;
vm_raw_write_end(next);
put_vma(next);
if (next == mm->stack_vma)
mm->stack_vma = NULL;
/*
* In mprotect's case 6 (see comments on vma_merge),
* we must remove another next too. It would clutter