All of lore.kernel.org
 help / color / mirror / Atom feed
From: Kirill Tkhai <ktkhai@virtuozzo.com>
To: Matthew Wilcox <willy@infradead.org>
Cc: viro@zeniv.linux.org.uk, hannes@cmpxchg.org, mhocko@kernel.org,
	vdavydov.dev@gmail.com, akpm@linux-foundation.org,
	tglx@linutronix.de, pombredanne@nexb.com,
	stummala@codeaurora.org, gregkh@linuxfoundation.org,
	sfr@canb.auug.org.au, guro@fb.com, mka@chromium.org,
	penguin-kernel@I-love.SAKURA.ne.jp, chris@chris-wilson.co.uk,
	longman@redhat.com, minchan@kernel.org, hillf.zj@alibaba-inc.com,
	ying.huang@intel.com, mgorman@techsingularity.net,
	shakeelb@google.com, jbacik@fb.com, linux@roeck-us.net,
	linux-kernel@vger.kernel.org, linux-mm@kvack.org
Subject: Re: [PATCH 03/10] mm: Assign memcg-aware shrinkers bitmap to memcg
Date: Thu, 22 Mar 2018 19:39:06 +0300	[thread overview]
Message-ID: <ef34c7c8-0ce7-f427-6743-2cbd8d844298@virtuozzo.com> (raw)
In-Reply-To: <20180321175453.GG4780@bombadil.infradead.org>

On 21.03.2018 20:54, Matthew Wilcox wrote:
> On Wed, Mar 21, 2018 at 07:42:38PM +0300, Kirill Tkhai wrote:
>> On 21.03.2018 19:20, Matthew Wilcox wrote:
>>>> Sound great, thanks for explaining this. The big problem I see is
>>>> that IDA/IDR add primitives allocate memory, while they will be used
>>>> in the places, where they mustn't fail. There is list_lru_add(), and
>>>> it's called unconditionally in current kernel code. The patchset makes
>>>> the bitmap be populated in this function. So, we can't use IDR there.
>>>
>>> Maybe we can use GFP_NOFAIL here.  They're small allocations, so we're
>>> only asking for single-page allocations to not fail, which shouldn't
>>> put too much strain on the VM.
>>  
>> Oh. I'm not sure about this. Even if each allocation is small, there is
>> theoretically possible a situation, when many lists will want to add first
>> element. list_lru_add() is called from iput() for example.
> 
> I see.  Maybe we could solve this with an IDA_NO_SHRINK flag and an
> ida_resize(ida, max); call.

But what will be the difference to bitmap, if we allocate maximal map anyway?

> You'll also want something like this:
> 
> 
> diff --git a/include/linux/idr.h b/include/linux/idr.h
> index 0f650b90ced0..ee7185354fb2 100644
> --- a/include/linux/idr.h
> +++ b/include/linux/idr.h
> @@ -273,6 +273,22 @@ static inline void ida_init(struct ida *ida)
>  			ida_alloc_range(ida, start, (end) - 1, gfp)
>  #define ida_simple_remove(ida, id)	ida_free(ida, id)
>  
> +int ida_find(struct ida *, unsigned int id);
> +
> +/**
> + * ida_for_each() - Iterate over all allocated IDs.
> + * @ida: IDA handle.
> + * @id: Loop cursor.
> + *
> + * For each iteration of this loop, @id will be set to an allocated ID.
> + * No locks are held across the body of the loop, so you can call ida_free()
> + * if you want or adjust @id to skip IDs or re-process earlier IDs.
> + *
> + * On successful loop exit, @id will be less than 0.
> + */
> +#define ida_for_each(ida, i)			\
> +	for (i = ida_find(ida, 0); i >= 0; i = ida_find(ida, i + 1))
> +
>  /**
>   * ida_get_new - allocate new ID
>   * @ida:	idr handle
> diff --git a/lib/idr.c b/lib/idr.c
> index fab3763e8c2a..ba9fae7eb2f5 100644
> --- a/lib/idr.c
> +++ b/lib/idr.c
> @@ -612,3 +612,54 @@ void ida_free(struct ida *ida, unsigned int id)
>  	spin_unlock_irqrestore(&simple_ida_lock, flags);
>  }
>  EXPORT_SYMBOL(ida_free);
> +
> +/**
> + * ida_find() - Find an allocated ID.
> + * @ida: IDA handle.
> + * @id: Minimum ID to return.
> + *
> + * Context: Any context.
> + * Return: An ID which is at least as large as @id or %-ENOSPC if @id is
> + * higher than any allocated ID.
> + */
> +int ida_find(struct ida *ida, unsigned int id)
> +{
> +	unsigned long flags;
> +	unsigned long index = id / IDA_BITMAP_BITS;
> +	unsigned bit = id % IDA_BITMAP_BITS;
> +	struct ida_bitmap *bitmap;
> +	struct radix_tree_iter iter;
> +	void __rcu **slot;
> +	int ret = -ENOSPC;
> +
> +	spin_lock_irqsave(&simple_ida_lock, flags);
> +advance:
> +	slot = radix_tree_iter_find(&ida->ida_rt, &iter, index);
> +	if (!slot)
> +		goto unlock;
> +	bitmap = rcu_dereference_raw(*slot);
> +	if (radix_tree_exception(bitmap)) {
> +		if (bit < (BITS_PER_LONG - RADIX_TREE_EXCEPTIONAL_SHIFT)) {
> +			unsigned long bits = (unsigned long)bitmap;
> +
> +			bits >>= bit + RADIX_TREE_EXCEPTIONAL_SHIFT;
> +			if (bits) {
> +				bit += __ffs(bits);
> +				goto found;
> +			}
> +		}
> +	} else {
> +		bit = find_next_bit(bitmap->bitmap, IDA_BITMAP_BITS, bit);
> +		if (bit < IDA_BITMAP_BITS)
> +			goto found;
> +	}
> +	bit = 0;
> +	index++;
> +	goto advance;
> +found:
> +	ret = iter.index * IDA_BITMAP_BITS + bit;
> +unlock:
> +	spin_unlock_irqrestore(&simple_ida_lock, flags);
> +	return ret;
> +}
> +EXPORT_SYMBOL(ida_find);
> diff --git a/tools/testing/radix-tree/idr-test.c b/tools/testing/radix-tree/idr-test.c
> index 6c645eb77d42..a9b5a33a4ef3 100644
> --- a/tools/testing/radix-tree/idr-test.c
> +++ b/tools/testing/radix-tree/idr-test.c
> @@ -358,8 +358,12 @@ void ida_check_conv(void)
>  		assert(ida_pre_get(&ida, GFP_KERNEL));
>  		assert(!ida_get_new_above(&ida, i + 1, &id));
>  		assert(id == i + 1);
> +		ida_for_each(&ida, id)
> +			BUG_ON(id != (i + 1));
>  		assert(!ida_get_new_above(&ida, i + BITS_PER_LONG, &id));
>  		assert(id == i + BITS_PER_LONG);
> +		ida_for_each(&ida, id)
> +			BUG_ON((id != (i + 1)) && (id != (i + BITS_PER_LONG)));
>  		ida_remove(&ida, i + 1);
>  		ida_remove(&ida, i + BITS_PER_LONG);
>  		assert(ida_is_empty(&ida));
> @@ -484,7 +488,7 @@ void ida_simple_get_remove_test(void)
>  void ida_checks(void)
>  {
>  	DEFINE_IDA(ida);
> -	int id;
> +	int id, id2;
>  	unsigned long i;
>  
>  	radix_tree_cpu_dead(1);
> @@ -496,8 +500,22 @@ void ida_checks(void)
>  		assert(id == i);
>  	}
>  
> +	id2 = 0;
> +	ida_for_each(&ida, id) {
> +		BUG_ON(id != id2++);
> +	}
> +	BUG_ON(id >= 0);
> +	BUG_ON(id2 != 10000);
> +
>  	ida_remove(&ida, 20);
>  	ida_remove(&ida, 21);
> +	id2 = 0;
> +	ida_for_each(&ida, id) {
> +		if (id != id2++) {
> +			BUG_ON(id != 22 || id2 != 21);
> +			id2 = 23;
> +		}
> +	}
>  	for (i = 0; i < 3; i++) {
>  		assert(ida_pre_get(&ida, GFP_KERNEL));
>  		assert(!ida_get_new(&ida, &id));
> 

  reply	other threads:[~2018-03-22 16:39 UTC|newest]

Thread overview: 57+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2018-03-21 13:21 [PATCH 00/10] Improve shrink_slab() scalability (old complexity was O(n^2), new is O(n)) Kirill Tkhai
2018-03-21 13:21 ` [PATCH 01/10] mm: Assign id to every memcg-aware shrinker Kirill Tkhai
2018-03-24 18:40   ` Vladimir Davydov
2018-03-26 15:09     ` Kirill Tkhai
2018-03-26 15:14       ` Matthew Wilcox
2018-03-26 15:38         ` Kirill Tkhai
2018-03-27  9:15       ` Vladimir Davydov
2018-03-27 15:09         ` Kirill Tkhai
2018-03-27 15:48           ` Vladimir Davydov
2018-03-28 10:30             ` Kirill Tkhai
2018-03-28 11:02               ` Vladimir Davydov
2018-03-21 13:21 ` [PATCH 02/10] mm: Maintain memcg-aware shrinkers in mcg_shrinkers array Kirill Tkhai
2018-03-24 18:45   ` Vladimir Davydov
2018-03-26 15:20     ` Kirill Tkhai
2018-03-26 15:34       ` Matthew Wilcox
2018-03-27  9:18       ` Vladimir Davydov
2018-03-27 15:30         ` Kirill Tkhai
2018-03-21 13:21 ` [PATCH 03/10] mm: Assign memcg-aware shrinkers bitmap to memcg Kirill Tkhai
2018-03-21 14:56   ` Matthew Wilcox
2018-03-21 15:12     ` Kirill Tkhai
2018-03-21 15:26       ` Matthew Wilcox
2018-03-21 15:43         ` Kirill Tkhai
2018-03-21 16:20           ` Matthew Wilcox
2018-03-21 16:42             ` Kirill Tkhai
2018-03-21 17:54               ` Matthew Wilcox
2018-03-22 16:39                 ` Kirill Tkhai [this message]
2018-03-23  9:06   ` kbuild test robot
2018-03-23  9:06     ` kbuild test robot
2018-03-23 11:26     ` Kirill Tkhai
2018-03-24 19:25   ` Vladimir Davydov
2018-03-26 15:29     ` Kirill Tkhai
2018-03-27 10:00       ` Vladimir Davydov
2018-03-27 15:17         ` Kirill Tkhai
2018-03-21 13:21 ` [PATCH 04/10] fs: Propagate shrinker::id to list_lru Kirill Tkhai
2018-03-24 18:50   ` Vladimir Davydov
2018-03-26 15:29     ` Kirill Tkhai
2018-03-21 13:22 ` [PATCH 05/10] list_lru: Add memcg argument to list_lru_from_kmem() Kirill Tkhai
2018-04-02  3:17   ` [lkp-robot] [list_lru] 42658d54ce: BUG:unable_to_handle_kernel kernel test robot
2018-04-02  3:17     ` kernel test robot
2018-04-02  3:17     ` kernel test robot
2018-04-02  8:51     ` Kirill Tkhai
2018-04-02  8:51       ` Kirill Tkhai
2018-03-21 13:22 ` [PATCH 06/10] list_lru: Pass dst_memcg argument to memcg_drain_list_lru_node() Kirill Tkhai
2018-03-24 19:32   ` Vladimir Davydov
2018-03-26 15:30     ` Kirill Tkhai
2018-03-28 14:49       ` Kirill Tkhai
2018-03-21 13:22 ` [PATCH 07/10] list_lru: Pass lru " Kirill Tkhai
2018-03-21 13:22 ` [PATCH 08/10] mm: Set bit in memcg shrinker bitmap on first list_lru item apearance Kirill Tkhai
2018-03-24 19:45   ` Vladimir Davydov
2018-03-26 15:31     ` Kirill Tkhai
2018-03-21 13:22 ` [PATCH 09/10] mm: Iterate only over charged shrinkers during memcg shrink_slab() Kirill Tkhai
2018-03-24 20:11   ` Vladimir Davydov
2018-03-26 15:33     ` Kirill Tkhai
2018-03-21 13:23 ` [PATCH 10/10] mm: Clear shrinker bit if there are no objects related to memcg Kirill Tkhai
2018-03-24 20:33   ` Vladimir Davydov
2018-03-26 15:37     ` Kirill Tkhai
2018-03-21 13:23 ` [PATCH 00/10] Improve shrink_slab() scalability (old complexity was O(n^2), new is O(n)) Kirill Tkhai

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=ef34c7c8-0ce7-f427-6743-2cbd8d844298@virtuozzo.com \
    --to=ktkhai@virtuozzo.com \
    --cc=akpm@linux-foundation.org \
    --cc=chris@chris-wilson.co.uk \
    --cc=gregkh@linuxfoundation.org \
    --cc=guro@fb.com \
    --cc=hannes@cmpxchg.org \
    --cc=hillf.zj@alibaba-inc.com \
    --cc=jbacik@fb.com \
    --cc=linux-kernel@vger.kernel.org \
    --cc=linux-mm@kvack.org \
    --cc=linux@roeck-us.net \
    --cc=longman@redhat.com \
    --cc=mgorman@techsingularity.net \
    --cc=mhocko@kernel.org \
    --cc=minchan@kernel.org \
    --cc=mka@chromium.org \
    --cc=penguin-kernel@I-love.SAKURA.ne.jp \
    --cc=pombredanne@nexb.com \
    --cc=sfr@canb.auug.org.au \
    --cc=shakeelb@google.com \
    --cc=stummala@codeaurora.org \
    --cc=tglx@linutronix.de \
    --cc=vdavydov.dev@gmail.com \
    --cc=viro@zeniv.linux.org.uk \
    --cc=willy@infradead.org \
    --cc=ying.huang@intel.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.