All of lore.kernel.org
 help / color / mirror / Atom feed
From: Gustavo Padovan <gustavo@padovan.org>
To: Dean Jenkins <djenkins@mvista.com>
Cc: linux-bluetooth@vger.kernel.org
Subject: Re: [PATCH 4/4] Bluetooth: On socket shutdown check rfcomm session and DLC exists
Date: Tue, 21 Aug 2012 15:50:29 -0300	[thread overview]
Message-ID: <20120821185029.GE17005@joana> (raw)
In-Reply-To: <1344710830-10301-5-git-send-email-djenkins@mvista.com>

Hi Dean,

* Dean Jenkins <djenkins@mvista.com> [2012-08-11 19:47:10 +0100]:

> A race condition exists between near simultaneous asynchronous
> DLC data channel disconnection requests from the host and remote device.
> This causes the socket layer to request a socket shutdown at the same time
> the rfcomm core is processing the disconnect request from the remote
> device.
> 
> The socket layer retains a copy of a struct rfcomm_dlc d pointer.
> The d pointer refers to a copy of a struct rfcomm_session.
> When the socket layer thread performs a socket shutdown, the thread
> may wait on a rfcomm lock in rfcomm_dlc_close(). This means that
> whilst the thread waits, the rfcomm_session and/or rfcomm_dlc structures
> pointed to by d maybe freed due to rfcomm core handling. Consequently,
> when the rfcomm lock becomes available and the thread runs, a
> malfunction could occur as a freed rfcomm_session pointer and/or a
> freed d pointer will be erroneously reused.
> 
> Therefore, after the rfcomm lock is acquired, check that the struct
> rfcomm_session is still valid by searching the rfcomm session list.
> If the session is valid then validate the d pointer by searching the
> rfcomm session list of active DLCs for the rfcomm_dlc structure
> pointed by d.
> 
> If active DLCs exist when the rfcomm session is terminating,
> avoid a memory leak of rfcomm_dlc structures by ensuring that
> rfcomm_session_close() is used instead of rfcomm_session_del().
> 
> Signed-off-by: Dean Jenkins <djenkins@mvista.com>
> ---
>  net/bluetooth/rfcomm/core.c |   29 ++++++++++++++++++++++++++---
>  1 file changed, 26 insertions(+), 3 deletions(-)
> 
> diff --git a/net/bluetooth/rfcomm/core.c b/net/bluetooth/rfcomm/core.c
> index c7921fd..1a7db34 100644
> --- a/net/bluetooth/rfcomm/core.c
> +++ b/net/bluetooth/rfcomm/core.c
> @@ -496,11 +496,34 @@ static int __rfcomm_dlc_close(struct rfcomm_dlc *d, int err)
>  
>  int rfcomm_dlc_close(struct rfcomm_dlc *d, int err)
>  {
> -	int r;
> +	int r = 0;
> +	struct rfcomm_dlc *d_list;
> +	struct rfcomm_session *s, *s_list;
> +	struct list_head *p, *n, *p2, *n2;
>  
>  	rfcomm_lock();
>  
> -	r = __rfcomm_dlc_close(d, err);
> +	s = d->session;
> +	if (s) {

Please invert the check here, and add a goto unlock;. There too many
indentation levels here.

> +		/* check the session still exists after waiting on the mutex */
> +		list_for_each_safe(p, n, &session_list) {
> +			s_list = list_entry(p, struct rfcomm_session, list);

please use list_for_each_entry(), the _safe version seems to not be needed.

> +			if (s == s_list) {
> +				/* check the dlc still exists */
> +				/* after waiting on the mutex */
> +				list_for_each_safe(p2, n2, &s->dlcs) {
> +					d_list = list_entry(p2,
> +							struct rfcomm_dlc,
> +							list);


and here you can use rfcomm_dlc_get()

	Gustavo

  reply	other threads:[~2012-08-21 18:50 UTC|newest]

Thread overview: 9+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2012-08-11 18:47 [PATCH 0/4] Bluetooth: Details of rfcomm fixes - remove session refcnt Dean Jenkins
2012-08-11 18:47 ` [PATCH 1/4] Bluetooth: Remove rfcomm " Dean Jenkins
2012-08-11 18:47 ` [PATCH 2/4] Bluetooth: Return rfcomm session pointers to avoid freed session Dean Jenkins
2012-08-11 18:47 ` [PATCH 3/4] Bluetooth: Avoid rfcomm_session_timeout using freed pointer Dean Jenkins
2012-08-21 18:56   ` Gustavo Padovan
2012-08-30 15:36     ` Dean Jenkins
2012-08-11 18:47 ` [PATCH 4/4] Bluetooth: On socket shutdown check rfcomm session and DLC exists Dean Jenkins
2012-08-21 18:50   ` Gustavo Padovan [this message]
2012-08-30 15:40     ` Dean Jenkins

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=20120821185029.GE17005@joana \
    --to=gustavo@padovan.org \
    --cc=djenkins@mvista.com \
    --cc=linux-bluetooth@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 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.