in pn533/pn533.c [2249:2316]
static int pn533_transceive(struct nfc_dev *nfc_dev,
struct nfc_target *target, struct sk_buff *skb,
data_exchange_cb_t cb, void *cb_context)
{
struct pn533 *dev = nfc_get_drvdata(nfc_dev);
struct pn533_data_exchange_arg *arg = NULL;
int rc;
if (!dev->tgt_active_prot) {
nfc_err(dev->dev,
"Can't exchange data if there is no active target\n");
rc = -EINVAL;
goto error;
}
arg = kmalloc(sizeof(*arg), GFP_KERNEL);
if (!arg) {
rc = -ENOMEM;
goto error;
}
arg->cb = cb;
arg->cb_context = cb_context;
switch (dev->device_type) {
case PN533_DEVICE_PASORI:
if (dev->tgt_active_prot == NFC_PROTO_FELICA) {
rc = pn533_send_data_async(dev, PN533_CMD_IN_COMM_THRU,
skb,
pn533_data_exchange_complete,
arg);
break;
}
fallthrough;
default:
/* jumbo frame ? */
if (skb->len > PN533_CMD_DATAEXCH_DATA_MAXLEN) {
rc = pn533_fill_fragment_skbs(dev, skb);
if (rc < 0)
goto error;
skb = skb_dequeue(&dev->fragment_skb);
if (!skb) {
rc = -EIO;
goto error;
}
} else {
*(u8 *)skb_push(skb, sizeof(u8)) = 1; /* TG */
}
rc = pn533_send_data_async(dev, PN533_CMD_IN_DATA_EXCHANGE,
skb, pn533_data_exchange_complete,
arg);
break;
}
if (rc < 0) /* rc from send_async */
goto error;
return 0;
error:
kfree(arg);
dev_kfree_skb(skb);
return rc;
}