Unverified Commit 11b9cc9a authored by openeuler-ci-bot's avatar openeuler-ci-bot Committed by Gitee
Browse files

!13122 fs: 6.6 performance improve patches

Merge Pull Request from: @ci-robot 
 
PR sync from: Jinjie Ruan <ruanjinjie@huawei.com>
https://mailweb.openeuler.org/hyperkitty/list/kernel@openeuler.org/message/PEALMR3OJQPGX65G2EAMFZKTKJ7I7CK7/ 
6.6 performance improve patches, with mm和fs , Unixbench Process create
improve 1 ~ 3%,lmbench exec/shell/fork improve 1.4 ~ 1.9%,
0.7 ~ 2.2%, 2 ~ 3.8% respectively. libmicro fork10/exec/sys improves
1.5%, 3.9 ~ 5.8%, 3.7 ~ 5.3%.

Christian Brauner (4):
  fs: move audit parent inode
  fs: pull up trailing slashes check for O_CREAT
  fs: remove audit dummy context check
  fs: rearrange general fastpath check now that O_CREAT uses it

David Hildenbrand (1):
  mm/rmap: minimize folio->_nr_pages_mapped updates when batching PTE
    (un)mapping

Jeff Layton (1):
  fs: try an opportunistic lookup for O_CREAT opens too

Liam R. Howlett (1):
  maple_tree: remove rcu_read_lock() from mt_validate()

Mateusz Guzik (1):
  mm: batch unlink_file_vma calls in free_pgd_range

Yu Ma (2):
  fs/file.c: add fast path in find_next_fd()
  fs/file.c: remove sanity_check and add likely/unlikely in alloc_fd()

 
https://gitee.com/src-openeuler/kernel/issues/IB1S01 
 
Link:https://gitee.com/openeuler/kernel/pulls/13122

 

Reviewed-by: default avatarKefeng Wang <wangkefeng.wang@huawei.com>
Reviewed-by: default avatarzhangyi (F) <yi.zhang@huawei.com>
Signed-off-by: default avatarZhang Peng <zhangpeng362@huawei.com>
parents b656f813 314c1caa
Loading
Loading
Loading
Loading
+24 −19
Original line number Diff line number Diff line
@@ -482,6 +482,15 @@ static unsigned int find_next_fd(struct fdtable *fdt, unsigned int start)
	unsigned int maxfd = fdt->max_fds; /* always multiple of BITS_PER_LONG */
	unsigned int maxbit = maxfd / BITS_PER_LONG;
	unsigned int bitbit = start / BITS_PER_LONG;
	unsigned int bit;

	/*
	 * Try to avoid looking at the second level bitmap
	 */
	bit = find_next_zero_bit(&fdt->open_fds[bitbit], BITS_PER_LONG,
				 start & (BITS_PER_LONG - 1));
	if (bit < BITS_PER_LONG)
		return bit + bitbit * BITS_PER_LONG;

	bitbit = find_next_zero_bit(fdt->full_fds_bits, maxbit, bitbit) * BITS_PER_LONG;
	if (bitbit >= maxfd)
@@ -508,7 +517,7 @@ static int alloc_fd(unsigned start, unsigned end, unsigned flags)
	if (fd < files->next_fd)
		fd = files->next_fd;

	if (fd < fdt->max_fds)
	if (likely(fd < fdt->max_fds))
		fd = find_next_fd(fdt, fd);

	/*
@@ -516,9 +525,10 @@ static int alloc_fd(unsigned start, unsigned end, unsigned flags)
	 * will limit the total number of files that can be opened.
	 */
	error = -EMFILE;
	if (fd >= end)
	if (unlikely(fd >= end))
		goto out;

	if (unlikely(fd >= fdt->max_fds)) {
		error = expand_files(files, fd);
		if (error < 0)
			goto out;
@@ -529,6 +539,8 @@ static int alloc_fd(unsigned start, unsigned end, unsigned flags)
		 */
		if (error)
			goto repeat;
	}

	if (files_cg_alloc_fd(files, 1)) {
		error = -EMFILE;
		goto out;
@@ -543,13 +555,6 @@ static int alloc_fd(unsigned start, unsigned end, unsigned flags)
	else
		__clear_close_on_exec(fd, fdt);
	error = fd;
#if 1
	/* Sanity check */
	if (rcu_access_pointer(fdt->fd[fd]) != NULL) {
		printk(KERN_WARNING "alloc_fd: slot %d not NULL!\n", fd);
		rcu_assign_pointer(fdt->fd[fd], NULL);
	}
#endif

out:
	spin_unlock(&files->file_lock);
@@ -614,7 +619,7 @@ void fd_install(unsigned int fd, struct file *file)
		rcu_read_unlock_sched();
		spin_lock(&files->file_lock);
		fdt = files_fdtable(files);
		BUG_ON(fdt->fd[fd] != NULL);
		WARN_ON(fdt->fd[fd] != NULL);
		rcu_assign_pointer(fdt->fd[fd], file);
		spin_unlock(&files->file_lock);
		return;
+47 −14
Original line number Diff line number Diff line
@@ -3433,6 +3433,9 @@ static struct dentry *lookup_open(struct nameidata *nd, struct file *file,
		return dentry;
	}

	if (open_flag & O_CREAT)
		audit_inode(nd->name, dir, AUDIT_INODE_PARENT);

	/*
	 * Checking write permission is tricky, bacuse we don't know if we are
	 * going to actually need it: O_CREAT opens should work as long as the
@@ -3503,6 +3506,42 @@ static struct dentry *lookup_open(struct nameidata *nd, struct file *file,
	return ERR_PTR(error);
}

static inline bool trailing_slashes(struct nameidata *nd)
{
	return (bool)nd->last.name[nd->last.len];
}

static struct dentry *lookup_fast_for_open(struct nameidata *nd, int open_flag)
{
	struct dentry *dentry;

	if (open_flag & O_CREAT) {
		if (trailing_slashes(nd))
			return ERR_PTR(-EISDIR);

		/* Don't bother on an O_EXCL create */
		if (open_flag & O_EXCL)
			return NULL;
	}

	if (trailing_slashes(nd))
		nd->flags |= LOOKUP_FOLLOW | LOOKUP_DIRECTORY;

	dentry = lookup_fast(nd);
	if (IS_ERR_OR_NULL(dentry))
		return dentry;

	if (open_flag & O_CREAT) {
		/* Discard negative dentries. Need inode_lock to do the create */
		if (!dentry->d_inode) {
			if (!(nd->flags & LOOKUP_RCU))
				dput(dentry);
			dentry = NULL;
		}
	}
	return dentry;
}

static const char *open_last_lookups(struct nameidata *nd,
		   struct file *file, const struct open_flags *op)
{
@@ -3520,27 +3559,21 @@ static const char *open_last_lookups(struct nameidata *nd,
		return handle_dots(nd, nd->last_type);
	}

	if (!(open_flag & O_CREAT)) {
		if (nd->last.name[nd->last.len])
			nd->flags |= LOOKUP_FOLLOW | LOOKUP_DIRECTORY;
		/* we _can_ be in RCU mode here */
		dentry = lookup_fast(nd);
	/* We _can_ be in RCU mode here */
	dentry = lookup_fast_for_open(nd, open_flag);
	if (IS_ERR(dentry))
		return ERR_CAST(dentry);

	if (likely(dentry))
		goto finish_lookup;

	if (!(open_flag & O_CREAT)) {
		BUG_ON(nd->flags & LOOKUP_RCU);
	} else {
		/* create side of things */
		if (nd->flags & LOOKUP_RCU) {
			if (!try_to_unlazy(nd))
				return ERR_PTR(-ECHILD);
		}
		audit_inode(nd->name, dir, AUDIT_INODE_PARENT);
		/* trailing slashes? */
		if (unlikely(nd->last.name[nd->last.len]))
			return ERR_PTR(-EISDIR);
	}

	if (open_flag & (O_CREAT | O_TRUNC | O_WRONLY | O_RDWR)) {
+2 −5
Original line number Diff line number Diff line
@@ -7618,14 +7618,14 @@ static void mt_validate_nulls(struct maple_tree *mt)
 * 2. The gap is correctly set in the parents
 */
void mt_validate(struct maple_tree *mt)
	__must_hold(mas->tree->ma_lock)
{
	unsigned char end;

	MA_STATE(mas, mt, 0, 0);
	rcu_read_lock();
	mas_start(&mas);
	if (!mas_is_active(&mas))
		goto done;
		return;

	while (!mte_is_leaf(mas.node))
		mas_descend(&mas);
@@ -7646,9 +7646,6 @@ void mt_validate(struct maple_tree *mt)
		mas_dfs_postorder(&mas, ULONG_MAX);
	}
	mt_validate_nulls(mt);
done:
	rcu_read_unlock();

}
EXPORT_SYMBOL_GPL(mt_validate);

+10 −0
Original line number Diff line number Diff line
@@ -1446,4 +1446,14 @@ void __meminit __init_single_page(struct page *page, unsigned long pfn,
#ifdef CONFIG_PAGE_CACHE_LIMIT
unsigned long shrink_memory(unsigned long nr_to_reclaim, bool may_swap);
#endif /* CONFIG_PAGE_CACHE_LIMIT */

struct unlink_vma_file_batch {
	int count;
	struct vm_area_struct *vmas[8];
};

void unlink_file_vma_batch_init(struct unlink_vma_file_batch *);
void unlink_file_vma_batch_add(struct unlink_vma_file_batch *, struct vm_area_struct *);
void unlink_file_vma_batch_final(struct unlink_vma_file_batch *);

#endif	/* __MM_INTERNAL_H */
+8 −2
Original line number Diff line number Diff line
@@ -368,6 +368,8 @@ void free_pgtables(struct mmu_gather *tlb, struct ma_state *mas,
		   struct vm_area_struct *vma, unsigned long floor,
		   unsigned long ceiling, bool mm_wr_locked)
{
	struct unlink_vma_file_batch vb;

	do {
		unsigned long addr = vma->vm_start;
		struct vm_area_struct *next;
@@ -387,12 +389,15 @@ void free_pgtables(struct mmu_gather *tlb, struct ma_state *mas,
		if (mm_wr_locked)
			vma_start_write(vma);
		unlink_anon_vmas(vma);
		unlink_file_vma(vma);

		if (is_vm_hugetlb_page(vma)) {
			unlink_file_vma(vma);
			hugetlb_free_pgd_range(tlb, addr, vma->vm_end,
				floor, next ? next->vm_start : ceiling);
		} else {
			unlink_file_vma_batch_init(&vb);
			unlink_file_vma_batch_add(&vb, vma);

			/*
			 * Optimization: gather nearby vmas into one call down
			 */
@@ -405,8 +410,9 @@ void free_pgtables(struct mmu_gather *tlb, struct ma_state *mas,
				if (mm_wr_locked)
					vma_start_write(vma);
				unlink_anon_vmas(vma);
				unlink_file_vma(vma);
				unlink_file_vma_batch_add(&vb, vma);
			}
			unlink_file_vma_batch_final(&vb);
			free_pgd_range(tlb, addr, vma->vm_end,
				floor, next ? next->vm_start : ceiling);
		}
Loading