block-6.4-2023-06-15
-----BEGIN PGP SIGNATURE----- iQJEBAABCAAuFiEEwPw5LcreJtl1+l5K99NY+ylx4KYFAmSLkkUQHGF4Ym9lQGtl cm5lbC5kawAKCRD301j7KXHgpksgD/wIh1wTJO9StdPr8NFYaBJMYoj8JCOK/cWd k9KXqe6y++xxqfLXuiHLkdWgv51vXOA7USPqMPqBcX9EHhNgB78y2gIswKZR1Slk /T+mdxwCH86+2ZnXoxeiC0mfxcSSh7D6nOmFgMeA9+mWsyj1cHgvF+MN8iU3zi+Z d2/GQZfU3YcWtASF9/q4S4t7H5sZhLfIOeNq+pXYHnGZx8yoBkFpAOaE8NxTr68+ TUaTaEtcC9nntt4gshSHDsnBHd+OHjkbHaphAw5T6Zbsu3kER/vfxAmrlHPQor1C qZhJ/dOngbzD3zSVh1U47NDL7eeVbkAXY9bWwk1y8s8MoLcJjSZjzduu+CBnh3CN 7IVVnsIA/gxx4VORTJTgfaD62kkM+g7MLKAwVw3yAtp6dbYoVh8H2ApIk0XZW3IQ oqRgViA+UvcFLHqXcm2Vq3FMlYViEd/Y9GNyGL4fbNwiCDjA3Goy0O+vn/0uNglU 5xidwV5Js9M44a0MvYQzczhbJ1mr4ujfVypVGVCOtd9tecZR+6WCGuDyM1fLlIjl eehRH+pkaDA5c0yr8h4gejFhfQiHXdMfZh0H8ul6bFy7sx8hzXfxuq+ZC+71d5KD OTlV3pPRC1JYmYB8vtWqt86AXB7t5aLaKNiObKm5WhYMiqLljZTNyZXnDMJE+NvL 25IIOEuVRA== =/8r5 -----END PGP SIGNATURE----- Merge tag 'block-6.4-2023-06-15' of git://git.kernel.dk/linux Pull block fix from Jens Axboe: "Just a single fix for blk-cg stats flushing" * tag 'block-6.4-2023-06-15' of git://git.kernel.dk/linux: blk-cgroup: Flush stats before releasing blkcg_gq
This commit is contained in:
commit
b9c1133a44
|
@ -34,6 +34,8 @@
|
|||
#include "blk-ioprio.h"
|
||||
#include "blk-throttle.h"
|
||||
|
||||
static void __blkcg_rstat_flush(struct blkcg *blkcg, int cpu);
|
||||
|
||||
/*
|
||||
* blkcg_pol_mutex protects blkcg_policy[] and policy [de]activation.
|
||||
* blkcg_pol_register_mutex nests outside of it and synchronizes entire
|
||||
|
@ -56,6 +58,8 @@ static LIST_HEAD(all_blkcgs); /* protected by blkcg_pol_mutex */
|
|||
|
||||
bool blkcg_debug_stats = false;
|
||||
|
||||
static DEFINE_RAW_SPINLOCK(blkg_stat_lock);
|
||||
|
||||
#define BLKG_DESTROY_BATCH_SIZE 64
|
||||
|
||||
/*
|
||||
|
@ -163,10 +167,20 @@ static void blkg_free(struct blkcg_gq *blkg)
|
|||
static void __blkg_release(struct rcu_head *rcu)
|
||||
{
|
||||
struct blkcg_gq *blkg = container_of(rcu, struct blkcg_gq, rcu_head);
|
||||
struct blkcg *blkcg = blkg->blkcg;
|
||||
int cpu;
|
||||
|
||||
#ifdef CONFIG_BLK_CGROUP_PUNT_BIO
|
||||
WARN_ON(!bio_list_empty(&blkg->async_bios));
|
||||
#endif
|
||||
/*
|
||||
* Flush all the non-empty percpu lockless lists before releasing
|
||||
* us, given these stat belongs to us.
|
||||
*
|
||||
* blkg_stat_lock is for serializing blkg stat update
|
||||
*/
|
||||
for_each_possible_cpu(cpu)
|
||||
__blkcg_rstat_flush(blkcg, cpu);
|
||||
|
||||
/* release the blkcg and parent blkg refs this blkg has been holding */
|
||||
css_put(&blkg->blkcg->css);
|
||||
|
@ -951,23 +965,26 @@ static void blkcg_iostat_update(struct blkcg_gq *blkg, struct blkg_iostat *cur,
|
|||
u64_stats_update_end_irqrestore(&blkg->iostat.sync, flags);
|
||||
}
|
||||
|
||||
static void blkcg_rstat_flush(struct cgroup_subsys_state *css, int cpu)
|
||||
static void __blkcg_rstat_flush(struct blkcg *blkcg, int cpu)
|
||||
{
|
||||
struct blkcg *blkcg = css_to_blkcg(css);
|
||||
struct llist_head *lhead = per_cpu_ptr(blkcg->lhead, cpu);
|
||||
struct llist_node *lnode;
|
||||
struct blkg_iostat_set *bisc, *next_bisc;
|
||||
|
||||
/* Root-level stats are sourced from system-wide IO stats */
|
||||
if (!cgroup_parent(css->cgroup))
|
||||
return;
|
||||
|
||||
rcu_read_lock();
|
||||
|
||||
lnode = llist_del_all(lhead);
|
||||
if (!lnode)
|
||||
goto out;
|
||||
|
||||
/*
|
||||
* For covering concurrent parent blkg update from blkg_release().
|
||||
*
|
||||
* When flushing from cgroup, cgroup_rstat_lock is always held, so
|
||||
* this lock won't cause contention most of time.
|
||||
*/
|
||||
raw_spin_lock(&blkg_stat_lock);
|
||||
|
||||
/*
|
||||
* Iterate only the iostat_cpu's queued in the lockless list.
|
||||
*/
|
||||
|
@ -991,13 +1008,19 @@ static void blkcg_rstat_flush(struct cgroup_subsys_state *css, int cpu)
|
|||
if (parent && parent->parent)
|
||||
blkcg_iostat_update(parent, &blkg->iostat.cur,
|
||||
&blkg->iostat.last);
|
||||
percpu_ref_put(&blkg->refcnt);
|
||||
}
|
||||
|
||||
raw_spin_unlock(&blkg_stat_lock);
|
||||
out:
|
||||
rcu_read_unlock();
|
||||
}
|
||||
|
||||
static void blkcg_rstat_flush(struct cgroup_subsys_state *css, int cpu)
|
||||
{
|
||||
/* Root-level stats are sourced from system-wide IO stats */
|
||||
if (cgroup_parent(css->cgroup))
|
||||
__blkcg_rstat_flush(css_to_blkcg(css), cpu);
|
||||
}
|
||||
|
||||
/*
|
||||
* We source root cgroup stats from the system-wide stats to avoid
|
||||
* tracking the same information twice and incurring overhead when no
|
||||
|
@ -2075,7 +2098,6 @@ void blk_cgroup_bio_start(struct bio *bio)
|
|||
|
||||
llist_add(&bis->lnode, lhead);
|
||||
WRITE_ONCE(bis->lqueued, true);
|
||||
percpu_ref_get(&bis->blkg->refcnt);
|
||||
}
|
||||
|
||||
u64_stats_update_end_irqrestore(&bis->sync, flags);
|
||||
|
|
Loading…
Reference in New Issue