summaryrefslogtreecommitdiffstats
path: root/net/nfc/digital_core.c
diff options
context:
space:
mode:
authorThierry Escande <thierry.escande@linux.intel.com>2014-01-27 00:31:32 +0100
committerSamuel Ortiz <sameo@linux.intel.com>2014-02-16 23:49:54 +0100
commitc813007f9ffb0b6e9f3dc43bfd9e28806aa57e5d (patch)
tree1a030aa83175313551eecfd7f23d08797481837b /net/nfc/digital_core.c
parent12e3d241e42956da168fd499347855af799f62fb (diff)
downloadlinux-stable-c813007f9ffb0b6e9f3dc43bfd9e28806aa57e5d.tar.gz
linux-stable-c813007f9ffb0b6e9f3dc43bfd9e28806aa57e5d.tar.bz2
linux-stable-c813007f9ffb0b6e9f3dc43bfd9e28806aa57e5d.zip
NFC: digital: Add ISO-DEP support for data exchange
When a type 4A target is activated, this change adds the ISO-DEP SoD when sending frames and removes it when receiving responses. Chaining is not supported so sent frames are rejected if they exceed remote FSC bytes. Signed-off-by: Thierry Escande <thierry.escande@linux.intel.com> Signed-off-by: Samuel Ortiz <sameo@linux.intel.com>
Diffstat (limited to 'net/nfc/digital_core.c')
-rw-r--r--net/nfc/digital_core.c25
1 files changed, 21 insertions, 4 deletions
diff --git a/net/nfc/digital_core.c b/net/nfc/digital_core.c
index e1f240266adf..5b440e7d9598 100644
--- a/net/nfc/digital_core.c
+++ b/net/nfc/digital_core.c
@@ -624,20 +624,30 @@ static void digital_in_send_complete(struct nfc_digital_dev *ddev, void *arg,
if (IS_ERR(resp)) {
rc = PTR_ERR(resp);
+ resp = NULL;
goto done;
}
- if (ddev->curr_protocol == NFC_PROTO_MIFARE)
+ if (ddev->curr_protocol == NFC_PROTO_MIFARE) {
rc = digital_in_recv_mifare_res(resp);
- else
- rc = ddev->skb_check_crc(resp);
+ /* crc check is done in digital_in_recv_mifare_res() */
+ goto done;
+ }
+
+ if (ddev->curr_protocol == NFC_PROTO_ISO14443) {
+ rc = digital_in_iso_dep_pull_sod(ddev, resp);
+ if (rc)
+ goto done;
+ }
+
+ rc = ddev->skb_check_crc(resp);
+done:
if (rc) {
kfree_skb(resp);
resp = NULL;
}
-done:
data_exch->cb(data_exch->cb_context, resp, rc);
kfree(data_exch);
@@ -649,6 +659,7 @@ static int digital_in_send(struct nfc_dev *nfc_dev, struct nfc_target *target,
{
struct nfc_digital_dev *ddev = nfc_get_drvdata(nfc_dev);
struct digital_data_exch *data_exch;
+ int rc;
data_exch = kzalloc(sizeof(struct digital_data_exch), GFP_KERNEL);
if (!data_exch) {
@@ -662,6 +673,12 @@ static int digital_in_send(struct nfc_dev *nfc_dev, struct nfc_target *target,
if (ddev->curr_protocol == NFC_PROTO_NFC_DEP)
return digital_in_send_dep_req(ddev, target, skb, data_exch);
+ if (ddev->curr_protocol == NFC_PROTO_ISO14443) {
+ rc = digital_in_iso_dep_push_sod(ddev, skb);
+ if (rc)
+ return rc;
+ }
+
ddev->skb_add_crc(skb);
return digital_in_send_cmd(ddev, skb, 500, digital_in_send_complete,