From: Andy Grover <agrover@redhat.com>
To: "Nicholas A. Bellinger" <nab@linux-iscsi.org>
Cc: target-devel@vger.kernel.org, linux-scsi@vger.kernel.org
Subject: Re: [PATCH 06/32] target: Convert lu_gp_ref_cnt to kref
Date: Wed, 05 Feb 2014 14:02:58 -0800 [thread overview]
Message-ID: <52F2B512.9040102@redhat.com> (raw)
In-Reply-To: <1387227157.20247.203.camel@haakon3.risingtidesystems.com>
Hi nab, I'm getting back to looking at this patchset, but wanted to just
discuss and understand this one first because all the kref ones are
similar. see below.
On 12/16/2013 12:52 PM, Nicholas A. Bellinger wrote:
> On Fri, 2013-12-13 at 15:58 -0800, Andy Grover wrote:
>> Use kref to handle reference counting
>>
>> Signed-off-by: Andy Grover <agrover@redhat.com>
>> ---
>> drivers/target/target_core_alua.c | 37 ++++++++++++++++++++-----------------
>> include/target/target_core_base.h | 2 +-
>> 2 files changed, 21 insertions(+), 18 deletions(-)
>>
>> diff --git a/drivers/target/target_core_alua.c b/drivers/target/target_core_alua.c
>> index 2ac2f11..8c01ade 100644
>> --- a/drivers/target/target_core_alua.c
>> +++ b/drivers/target/target_core_alua.c
>> @@ -54,6 +54,16 @@ static LIST_HEAD(lu_gps_list);
>>
>> struct t10_alua_lu_gp *default_lu_gp;
>>
>> +static void release_alua_lu_gp(struct kref *ref)
>> +{
>> + struct t10_alua_lu_gp *lu_gp = container_of(ref, struct t10_alua_lu_gp, refcount);
>> +
>> + kmem_cache_free(t10_alua_lu_gp_cache, lu_gp);
>> +}
>> +
>> +#define get_alua_lu_gp(x) kref_get(&x->refcount)
>> +#define put_alua_lu_gp(x) kref_put(&x->refcount, release_alua_lu_gp)
>> +
>> /*
>> * REPORT_TARGET_PORT_GROUPS
>> *
>> @@ -898,8 +908,7 @@ int core_alua_do_port_transition(
>> local_lu_gp_mem = l_dev->dev_alua_lu_gp_mem;
>> spin_lock(&local_lu_gp_mem->lu_gp_mem_lock);
>> lu_gp = local_lu_gp_mem->lu_gp;
>> - atomic_inc(&lu_gp->lu_gp_ref_cnt);
>> - smp_mb__after_atomic_inc();
>> + get_alua_lu_gp(lu_gp);
>> spin_unlock(&local_lu_gp_mem->lu_gp_mem_lock);
>> /*
>> * For storage objects that are members of the 'default_lu_gp',
>> @@ -913,8 +922,8 @@ int core_alua_do_port_transition(
>> */
>> core_alua_do_transition_tg_pt(l_tg_pt_gp, l_port, l_nacl,
>> md_buf, new_state, explicit);
>> - atomic_dec(&lu_gp->lu_gp_ref_cnt);
>> - smp_mb__after_atomic_dec();
>> +
>> + put_alua_lu_gp(lu_gp);
>> kfree(md_buf);
>> return 0;
>> }
>> @@ -985,8 +994,7 @@ int core_alua_do_port_transition(
>> l_tg_pt_gp->tg_pt_gp_id, (explicit) ? "explicit" : "implicit",
>> core_alua_dump_state(new_state));
>>
>> - atomic_dec(&lu_gp->lu_gp_ref_cnt);
>> - smp_mb__after_atomic_dec();
>> + put_alua_lu_gp(lu_gp);
>> kfree(md_buf);
>> return 0;
>> }
>> @@ -1107,7 +1115,8 @@ core_alua_allocate_lu_gp(const char *name, int def_group)
>> INIT_LIST_HEAD(&lu_gp->lu_gp_node);
>> INIT_LIST_HEAD(&lu_gp->lu_gp_mem_list);
>> spin_lock_init(&lu_gp->lu_gp_lock);
>> - atomic_set(&lu_gp->lu_gp_ref_cnt, 0);
>> +
>> + kref_init(&lu_gp->refcount);
>>
>> if (def_group) {
>> lu_gp->lu_gp_id = alua_lu_gps_counter++;
>> @@ -1200,13 +1209,7 @@ void core_alua_free_lu_gp(struct t10_alua_lu_gp *lu_gp)
>> list_del(&lu_gp->lu_gp_node);
>> alua_lu_gps_count--;
>> spin_unlock(&lu_gps_lock);
>> - /*
>> - * Allow struct t10_alua_lu_gp * referenced by core_alua_get_lu_gp_by_name()
>> - * in target_core_configfs.c:target_core_store_alua_lu_gp() to be
>> - * released with core_alua_put_lu_gp_from_name()
>> - */
>> - while (atomic_read(&lu_gp->lu_gp_ref_cnt))
>> - cpu_relax();
>> +
>> /*
>> * Release reference to struct t10_alua_lu_gp * from all associated
>> * struct se_device.
>> @@ -1241,7 +1244,7 @@ void core_alua_free_lu_gp(struct t10_alua_lu_gp *lu_gp)
>> }
>> spin_unlock(&lu_gp->lu_gp_lock);
>>
>> - kmem_cache_free(t10_alua_lu_gp_cache, lu_gp);
>> + put_alua_lu_gp(lu_gp);
>> }
>>
> The assumption that it's safe to 'Release reference to struct
> t10_alua_lu_gp * from all associated struct device' below the original
> cpu_relax(), while there are still other process contexts doing their
> respective put_alua_lu_gp() is totally wrong.
The only other spot is core_alua_do_port_transition, afaics. I think if
it races with free_lu_gp, lu_gp will either be the old lu_gp (which no
longer will have anything on lu_gp_mem_list) or will be default_lu_gp.
If it's the old lu_gp then it iterates over an empty list, and then the
lu_gp gets finally freed by the put() at the bottom.
> Furthermore, allowing a configfs_group_ops->drop_item() to return while
> there are still active references from other process contexts means that
> the parent struct config_group is no longer referenced counted (eg:
> configfs child is removed), and introduces a whole host of potential
> bugs.
>
> So that said, NAK on this patch.
I think some of the other patches used drop_item() and thus were bad,
but in this one the existing code is already calling
core_alua_free_lu_gp() from release().
Thoughts?
Thanks in advance -- Regards -- Andy
next prev parent reply other threads:[~2014-02-05 22:02 UTC|newest]
Thread overview: 81+ messages / expand[flat|nested] mbox.gz Atom feed top
2013-12-13 23:58 [PATCH 0/32] Refcounts and rbtrees to increase luns above 255 Andy Grover
2013-12-13 23:58 ` [PATCH 01/32] target: Remove unused ua_dev_list member in struct se_ua Andy Grover
2013-12-16 20:39 ` Nicholas A. Bellinger
2013-12-13 23:58 ` [PATCH 02/32] target: Don't keep looping in report_luns if too big Andy Grover
2013-12-16 20:41 ` Nicholas A. Bellinger
2013-12-13 23:58 ` [PATCH 03/32] target: Allocate more room for port default groups Andy Grover
2013-12-16 20:43 ` Nicholas A. Bellinger
2013-12-13 23:58 ` [PATCH 04/32] target: Fix sizeof in kmalloc for some default_groups arrays Andy Grover
2013-12-16 20:43 ` Nicholas A. Bellinger
2013-12-13 23:58 ` [PATCH 05/32] target: Rename some list heads used as nodes Andy Grover
2013-12-16 20:45 ` Nicholas A. Bellinger
2013-12-13 23:58 ` [PATCH 06/32] target: Convert lu_gp_ref_cnt to kref Andy Grover
2013-12-16 20:52 ` Nicholas A. Bellinger
2014-02-05 22:02 ` Andy Grover [this message]
2014-02-06 23:51 ` Nicholas A. Bellinger
2014-02-07 2:56 ` Andy Grover
2014-02-07 19:17 ` Nicholas A. Bellinger
2013-12-13 23:58 ` [PATCH 07/32] target: Convert struct alua_lu_gp_member " Andy Grover
2013-12-16 20:56 ` Nicholas A. Bellinger
2013-12-13 23:58 ` [PATCH 08/32] target: Convert tg_pt_gp_ref_cnt " Andy Grover
2013-12-16 21:00 ` Nicholas A. Bellinger
2013-12-13 23:58 ` [PATCH 09/32] target: convert tg_pt_gp_mem_ref_cnt " Andy Grover
2013-12-16 21:08 ` Nicholas A. Bellinger
2013-12-13 23:58 ` [PATCH 10/32] target: Change sep_tg_pt_ref_cnt to use kref Andy Grover
2013-12-16 21:11 ` Nicholas A. Bellinger
2013-12-13 23:58 ` [PATCH 11/32] target: Convert se_dev_entry to kref Andy Grover
2013-12-16 21:15 ` Nicholas A. Bellinger
2013-12-13 23:59 ` [PATCH 12/32] target: Convert t10_pr_registration " Andy Grover
2013-12-16 21:20 ` Nicholas A. Bellinger
2013-12-13 23:59 ` [PATCH 13/32] target: Move spinlock inside core_release_port Andy Grover
2013-12-16 21:21 ` Nicholas A. Bellinger
2013-12-13 23:59 ` [PATCH 14/32] target: Remove extra percpu_ref_init Andy Grover
2013-12-16 21:23 ` Nicholas A. Bellinger
2013-12-13 23:59 ` [PATCH 15/32] target: Refer to u32 luns as unpacked_lun Andy Grover
2013-12-16 21:25 ` Nicholas A. Bellinger
2013-12-13 23:59 ` [PATCH 16/32] target: Rename core_tpg_{pre,post}_addlun for clarity Andy Grover
2013-12-16 21:29 ` Nicholas A. Bellinger
2013-12-13 23:59 ` [PATCH 17/32] target: Don't use void* when passing dev in core_tpg_add_lun Andy Grover
2013-12-16 21:29 ` Nicholas A. Bellinger
2013-12-13 23:59 ` [PATCH 18/32] target: More core_dev_del cleanups Andy Grover
2013-12-16 21:35 ` Nicholas A. Bellinger
2013-12-13 23:59 ` [PATCH 19/32] target: Convert to rbtree for se_dev_entry in se_node_acl Andy Grover
2013-12-16 21:40 ` Nicholas A. Bellinger
2013-12-17 1:00 ` Andy Grover
2013-12-17 1:54 ` Nicholas A. Bellinger
2013-12-13 23:59 ` [PATCH 20/32] target: Convert to rbtree for se_lun list in se_portal_group Andy Grover
2013-12-16 21:42 ` Nicholas A. Bellinger
2013-12-13 23:59 ` [PATCH 21/32] target: Remove lun_link and device magic Andy Grover
2013-12-16 21:44 ` Nicholas A. Bellinger
2013-12-13 23:59 ` [PATCH 22/32] target: Convert percpu_ref to kref Andy Grover
2013-12-16 21:44 ` Nicholas A. Bellinger
2013-12-13 23:59 ` [PATCH 23/32] target: Add lun->lun_tpg pointer Andy Grover
2013-12-16 21:45 ` Nicholas A. Bellinger
2013-12-13 23:59 ` [PATCH 24/32] target: Remove tpg from core_dev_export/unexport params Andy Grover
2013-12-16 21:46 ` Nicholas A. Bellinger
2013-12-13 23:59 ` [PATCH 25/32] target: Call remove_lun instead of del_lun in fabric_port_unlink Andy Grover
2013-12-16 21:47 ` Nicholas A. Bellinger
2013-12-13 23:59 ` [PATCH 26/32] target: Convert tpg_pr_ref_count to kref Andy Grover
2013-12-16 21:50 ` Nicholas A. Bellinger
2013-12-13 23:59 ` [PATCH 27/32] target: Move call to remove_lun to the release function from drop_link Andy Grover
2013-12-16 21:51 ` Nicholas A. Bellinger
2013-12-13 23:59 ` [PATCH 28/32] target: Convert acl_pr_ref_count to kref Andy Grover
2013-12-16 21:58 ` Nicholas A. Bellinger
2013-12-13 23:59 ` [PATCH 29/32] target: Simplify params to core_tpg_del_initiator_node_acl Andy Grover
2013-12-16 22:00 ` Nicholas A. Bellinger
2013-12-13 23:59 ` [PATCH 30/32] target: Change nacl's session refcount to use existing refcount Andy Grover
2013-12-16 22:01 ` Nicholas A. Bellinger
2013-12-13 23:59 ` [PATCH 31/32] target: Don't release and re-acquire some spinlocks in loops Andy Grover
2013-12-16 22:01 ` Nicholas A. Bellinger
2013-12-13 23:59 ` [PATCH 32/32] target: Increase MAX_LUNS_PER_TPG to 16384 Andy Grover
2013-12-16 9:20 ` Hannes Reinecke
2013-12-16 9:24 ` Hannes Reinecke
2013-12-16 22:01 ` Nicholas A. Bellinger
2013-12-16 22:03 ` [PATCH 0/32] Refcounts and rbtrees to increase luns above 255 Nicholas A. Bellinger
2013-12-17 1:49 ` Andy Grover
2013-12-17 1:59 ` Nicholas A. Bellinger
2013-12-17 2:03 ` Andy Grover
2013-12-17 3:03 ` Nicholas A. Bellinger
2013-12-17 10:53 ` Hannes Reinecke
2013-12-17 17:10 ` Andy Grover
2013-12-17 21:25 ` Nicholas A. Bellinger
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=52F2B512.9040102@redhat.com \
--to=agrover@redhat.com \
--cc=linux-scsi@vger.kernel.org \
--cc=nab@linux-iscsi.org \
--cc=target-devel@vger.kernel.org \
/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 a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).