NFC: nci: clear NCI_DATA_EXCHANGE before calling the NFC stack callback
diff mbox series

Message ID 20181109160118.32737-1-michael.thalmeier@hale.at
State New
Delegated to: Samuel Ortiz
Headers show
Series
  • NFC: nci: clear NCI_DATA_EXCHANGE before calling the NFC stack callback
Related show

Commit Message

Michael Thalmeier Nov. 9, 2018, 4:01 p.m. UTC
From: Michael Thalmeier <michael@thalmeier.at>

By calling the nfc core callback (cb) in nci_data_exchange_complete the
userspace task will get notified that response data is available for the
current request.
When the userspace task then reads the return data and immediately
issues another request, it was possible that this will be done before
the NCI_DATA_EXCHANGE is cleared.
The result is that nci_transceive will return -EBUSY and the NFC stack
(rawsock.c:rawsock_tx_work) will report an error and shut down the
socket. Not only is this quite a harsh behaviour for this situation,
but additionally any following attempt to poll for NFC tags will result
in an error "there is an active target" since the previous active tag is
not cleanly deactivated.

With this change NCI_DATA_EXCHANGE will get cleard before calling into
the NFC stack, which fixes this situation.

Signed-off-by: Michael Thalmeier <michael.thalmeier@hale.at>
---
 net/nfc/nci/data.c | 2 ++
 1 file changed, 2 insertions(+)

Patch
diff mbox series

diff --git a/net/nfc/nci/data.c b/net/nfc/nci/data.c
index 908f25e..57d5980 100644
--- a/net/nfc/nci/data.c
+++ b/net/nfc/nci/data.c
@@ -56,6 +56,7 @@  void nci_data_exchange_complete(struct nci_dev *ndev, struct sk_buff *skb,
 	/* data exchange is complete, stop the data timer */
 	del_timer_sync(&ndev->data_timer);
 	clear_bit(NCI_DATA_EXCHANGE_TO, &ndev->flags);
+	clear_bit(NCI_DATA_EXCHANGE, &ndev->flags);
 
 	if (cb) {
 		/* forward skb to nfc core */
@@ -66,6 +67,7 @@  void nci_data_exchange_complete(struct nci_dev *ndev, struct sk_buff *skb,
 		/* no waiting callback, free skb */
 		kfree_skb(skb);
 	}
+	return;
 
 exit:
 	clear_bit(NCI_DATA_EXCHANGE, &ndev->flags);