diff options
Diffstat (limited to 'drivers/nfc/st21nfca')
-rw-r--r-- | drivers/nfc/st21nfca/i2c.c | 34 | ||||
-rw-r--r-- | drivers/nfc/st21nfca/st21nfca.c | 59 | ||||
-rw-r--r-- | drivers/nfc/st21nfca/st21nfca.h | 21 | ||||
-rw-r--r-- | drivers/nfc/st21nfca/st21nfca_dep.c | 59 |
4 files changed, 72 insertions, 101 deletions
diff --git a/drivers/nfc/st21nfca/i2c.c b/drivers/nfc/st21nfca/i2c.c index ff31939978ae..0ea756b77519 100644 --- a/drivers/nfc/st21nfca/i2c.c +++ b/drivers/nfc/st21nfca/i2c.c @@ -271,6 +271,7 @@ static int st21nfca_hci_i2c_write(void *phy_id, struct sk_buff *skb) static int get_frame_size(u8 *buf, int buflen) { int len = 0; + if (buf[len + 1] == ST21NFCA_SOF_EOF) return 0; @@ -311,6 +312,7 @@ static int check_crc(u8 *buf, int buflen) static int st21nfca_hci_i2c_repack(struct sk_buff *skb) { int i, j, r, size; + if (skb->len < 1 || (skb->len > 1 && skb->data[1] != 0)) return -EBADMSG; @@ -525,24 +527,19 @@ static int st21nfca_hci_i2c_of_request_resources(struct i2c_client *client) } /* GPIO request and configuration */ - r = devm_gpio_request(&client->dev, gpio, "clf_enable"); + r = devm_gpio_request_one(&client->dev, gpio, GPIOF_OUT_INIT_HIGH, + "clf_enable"); if (r) { nfc_err(&client->dev, "Failed to request enable pin\n"); return -ENODEV; } - r = gpio_direction_output(gpio, 1); - if (r) { - nfc_err(&client->dev, "Failed to set enable pin direction as output\n"); - return -ENODEV; - } phy->gpio_ena = gpio; /* IRQ */ r = irq_of_parse_and_map(pp, 0); if (r < 0) { - nfc_err(&client->dev, - "Unable to get irq, error: %d\n", r); + nfc_err(&client->dev, "Unable to get irq, error: %d\n", r); return r; } @@ -576,32 +573,20 @@ static int st21nfca_hci_i2c_request_resources(struct i2c_client *client) phy->gpio_ena = pdata->gpio_ena; phy->irq_polarity = pdata->irq_polarity; - r = devm_gpio_request(&client->dev, phy->gpio_irq, "wake_up"); + r = devm_gpio_request_one(&client->dev, phy->gpio_irq, GPIOF_IN, + "wake_up"); if (r) { pr_err("%s : gpio_request failed\n", __FILE__); return -ENODEV; } - r = gpio_direction_input(phy->gpio_irq); - if (r) { - pr_err("%s : gpio_direction_input failed\n", __FILE__); - return -ENODEV; - } - if (phy->gpio_ena > 0) { - r = devm_gpio_request(&client->dev, - phy->gpio_ena, "clf_enable"); + r = devm_gpio_request_one(&client->dev, phy->gpio_ena, + GPIOF_OUT_INIT_HIGH, "clf_enable"); if (r) { pr_err("%s : ena gpio_request failed\n", __FILE__); return -ENODEV; } - r = gpio_direction_output(phy->gpio_ena, 1); - - if (r) { - pr_err("%s : ena gpio_direction_output failed\n", - __FILE__); - return -ENODEV; - } } /* IRQ */ @@ -711,7 +696,6 @@ static struct i2c_driver st21nfca_hci_i2c_driver = { .driver = { .owner = THIS_MODULE, .name = ST21NFCA_HCI_I2C_DRIVER_NAME, - .owner = THIS_MODULE, .of_match_table = of_match_ptr(of_st21nfca_i2c_match), }, .probe = st21nfca_hci_i2c_probe, diff --git a/drivers/nfc/st21nfca/st21nfca.c b/drivers/nfc/st21nfca/st21nfca.c index a902b0551c86..a89e56c2c749 100644 --- a/drivers/nfc/st21nfca/st21nfca.c +++ b/drivers/nfc/st21nfca/st21nfca.c @@ -34,7 +34,7 @@ #define ST21NFCA_RF_READER_CMD_PRESENCE_CHECK 0x30 #define ST21NFCA_RF_READER_ISO15693_GATE 0x12 -#define ST21NFCA_RF_READER_ISO15693_INVENTORY 0x01 +#define ST21NFCA_RF_READER_ISO15693_INVENTORY 0x01 /* * Reader gate for communication with contact-less cards using Type A @@ -45,21 +45,42 @@ #define ST21NFCA_RF_READER_14443_3_A_ATQA 0x03 #define ST21NFCA_RF_READER_14443_3_A_SAK 0x04 +#define ST21NFCA_RF_READER_F_DATARATE 0x01 +#define ST21NFCA_RF_READER_F_DATARATE_106 0x01 +#define ST21NFCA_RF_READER_F_DATARATE_212 0x02 +#define ST21NFCA_RF_READER_F_DATARATE_424 0x04 +#define ST21NFCA_RF_READER_F_POL_REQ 0x02 +#define ST21NFCA_RF_READER_F_POL_REQ_DEFAULT 0xffff0000 +#define ST21NFCA_RF_READER_F_NFCID2 0x03 +#define ST21NFCA_RF_READER_F_NFCID1 0x04 + +#define ST21NFCA_RF_CARD_F_MODE 0x01 +#define ST21NFCA_RF_CARD_F_NFCID2_LIST 0x04 +#define ST21NFCA_RF_CARD_F_NFCID1 0x05 +#define ST21NFCA_RF_CARD_F_SENS_RES 0x06 +#define ST21NFCA_RF_CARD_F_SEL_RES 0x07 +#define ST21NFCA_RF_CARD_F_DATARATE 0x08 +#define ST21NFCA_RF_CARD_F_DATARATE_212_424 0x01 + #define ST21NFCA_DEVICE_MGNT_GATE 0x01 #define ST21NFCA_DEVICE_MGNT_PIPE 0x02 -#define ST21NFCA_DM_GETINFO 0x13 -#define ST21NFCA_DM_GETINFO_PIPE_LIST 0x02 -#define ST21NFCA_DM_GETINFO_PIPE_INFO 0x01 -#define ST21NFCA_DM_PIPE_CREATED 0x02 -#define ST21NFCA_DM_PIPE_OPEN 0x04 -#define ST21NFCA_DM_RF_ACTIVE 0x80 -#define ST21NFCA_DM_DISCONNECT 0x30 +#define ST21NFCA_DM_GETINFO 0x13 +#define ST21NFCA_DM_GETINFO_PIPE_LIST 0x02 +#define ST21NFCA_DM_GETINFO_PIPE_INFO 0x01 +#define ST21NFCA_DM_PIPE_CREATED 0x02 +#define ST21NFCA_DM_PIPE_OPEN 0x04 +#define ST21NFCA_DM_RF_ACTIVE 0x80 +#define ST21NFCA_DM_DISCONNECT 0x30 #define ST21NFCA_DM_IS_PIPE_OPEN(p) \ ((p & 0x0f) == (ST21NFCA_DM_PIPE_CREATED | ST21NFCA_DM_PIPE_OPEN)) -#define ST21NFCA_NFC_MODE 0x03 /* NFC_MODE parameter*/ +#define ST21NFCA_NFC_MODE 0x03 /* NFC_MODE parameter*/ +#define ST21NFCA_EVT_FIELD_ON 0x11 +#define ST21NFCA_EVT_CARD_DEACTIVATED 0x12 +#define ST21NFCA_EVT_CARD_ACTIVATED 0x13 +#define ST21NFCA_EVT_FIELD_OFF 0x14 static DECLARE_BITMAP(dev_mask, ST21NFCA_NUM_DEVICES); @@ -355,8 +376,8 @@ static int st21nfca_hci_start_poll(struct nfc_hci_dev *hdev, if (r < 0) return r; - pol_req = - be32_to_cpu(ST21NFCA_RF_READER_F_POL_REQ_DEFAULT); + pol_req = be32_to_cpu((__force __be32) + ST21NFCA_RF_READER_F_POL_REQ_DEFAULT); r = nfc_hci_set_param(hdev, ST21NFCA_RF_READER_F_GATE, ST21NFCA_RF_READER_F_POL_REQ, (u8 *) &pol_req, 4); @@ -790,6 +811,7 @@ static int st21nfca_hci_check_presence(struct nfc_hci_dev *hdev, struct nfc_target *target) { u8 fwi = 0x11; + switch (target->hci_reader_gate) { case NFC_HCI_RF_READER_A_GATE: case NFC_HCI_RF_READER_B_GATE: @@ -839,20 +861,16 @@ static int st21nfca_hci_event_received(struct nfc_hci_dev *hdev, u8 gate, if (gate == ST21NFCA_RF_CARD_F_GATE) { r = st21nfca_tm_event_send_data(hdev, skb, gate); if (r < 0) - goto exit; + return r; return 0; - } else { - info->dep_info.curr_nfc_dep_pni = 0; - return 1; } - break; + info->dep_info.curr_nfc_dep_pni = 0; + return 1; default: return 1; } kfree_skb(skb); return 0; -exit: - return r; } static struct nfc_hci_ops st21nfca_hci_ops = { @@ -904,8 +922,11 @@ int st21nfca_hci_probe(void *phy_id, struct nfc_phy_ops *phy_ops, * persistent info to discriminate 2 identical chips */ dev_num = find_first_zero_bit(dev_mask, ST21NFCA_NUM_DEVICES); + if (dev_num >= ST21NFCA_NUM_DEVICES) - goto err_alloc_hdev; + return -ENODEV; + + set_bit(dev_num, dev_mask); scnprintf(init_data.session_id, sizeof(init_data.session_id), "%s%2x", "ST21AH", dev_num); diff --git a/drivers/nfc/st21nfca/st21nfca.h b/drivers/nfc/st21nfca/st21nfca.h index 96fe5a62dc0d..a0b77f1ba6d9 100644 --- a/drivers/nfc/st21nfca/st21nfca.h +++ b/drivers/nfc/st21nfca/st21nfca.h @@ -82,30 +82,9 @@ struct st21nfca_hci_info { #define ST21NFCA_WR_XCHG_DATA 0x10 #define ST21NFCA_RF_READER_F_GATE 0x14 -#define ST21NFCA_RF_READER_F_DATARATE 0x01 -#define ST21NFCA_RF_READER_F_DATARATE_106 0x01 -#define ST21NFCA_RF_READER_F_DATARATE_212 0x02 -#define ST21NFCA_RF_READER_F_DATARATE_424 0x04 -#define ST21NFCA_RF_READER_F_POL_REQ 0x02 -#define ST21NFCA_RF_READER_F_POL_REQ_DEFAULT 0xffff0000 -#define ST21NFCA_RF_READER_F_NFCID2 0x03 -#define ST21NFCA_RF_READER_F_NFCID1 0x04 -#define ST21NFCA_RF_READER_F_SENS_RES 0x05 #define ST21NFCA_RF_CARD_F_GATE 0x24 -#define ST21NFCA_RF_CARD_F_MODE 0x01 -#define ST21NFCA_RF_CARD_F_NFCID2_LIST 0x04 -#define ST21NFCA_RF_CARD_F_NFCID1 0x05 -#define ST21NFCA_RF_CARD_F_SENS_RES 0x06 -#define ST21NFCA_RF_CARD_F_SEL_RES 0x07 -#define ST21NFCA_RF_CARD_F_DATARATE 0x08 -#define ST21NFCA_RF_CARD_F_DATARATE_106 0x00 -#define ST21NFCA_RF_CARD_F_DATARATE_212_424 0x01 #define ST21NFCA_EVT_SEND_DATA 0x10 -#define ST21NFCA_EVT_FIELD_ON 0x11 -#define ST21NFCA_EVT_CARD_DEACTIVATED 0x12 -#define ST21NFCA_EVT_CARD_ACTIVATED 0x13 -#define ST21NFCA_EVT_FIELD_OFF 0x14 #endif /* __LOCAL_ST21NFCA_H_ */ diff --git a/drivers/nfc/st21nfca/st21nfca_dep.c b/drivers/nfc/st21nfca/st21nfca_dep.c index b2d9957b57f8..bfb6df56c505 100644 --- a/drivers/nfc/st21nfca/st21nfca_dep.c +++ b/drivers/nfc/st21nfca/st21nfca_dep.c @@ -121,6 +121,7 @@ static void st21nfca_tx_work(struct work_struct *work) struct nfc_dev *dev; struct sk_buff *skb; + if (info) { dev = info->hdev->ndev; skb = info->dep_info.tx_pending; @@ -128,9 +129,8 @@ static void st21nfca_tx_work(struct work_struct *work) device_lock(&dev->dev); nfc_hci_send_cmd_async(info->hdev, ST21NFCA_RF_READER_F_GATE, - ST21NFCA_WR_XCHG_DATA, - skb->data, skb->len, - info->async_cb, info); + ST21NFCA_WR_XCHG_DATA, skb->data, skb->len, + info->async_cb, info); device_unlock(&dev->dev); kfree_skb(skb); } @@ -185,8 +185,10 @@ static int st21nfca_tm_send_atr_res(struct nfc_hci_dev *hdev, info->dep_info.curr_nfc_dep_pni = 0; - return nfc_hci_send_event(hdev, ST21NFCA_RF_CARD_F_GATE, + r = nfc_hci_send_event(hdev, ST21NFCA_RF_CARD_F_GATE, ST21NFCA_EVT_SEND_DATA, skb->data, skb->len); + kfree_skb(skb); + return r; } static int st21nfca_tm_recv_atr_req(struct nfc_hci_dev *hdev, @@ -197,10 +199,6 @@ static int st21nfca_tm_recv_atr_req(struct nfc_hci_dev *hdev, int r; skb_trim(skb, skb->len - 1); - if (IS_ERR(skb)) { - r = PTR_ERR(skb); - goto exit; - } if (!skb->len) { r = -EIO; @@ -214,6 +212,11 @@ static int st21nfca_tm_recv_atr_req(struct nfc_hci_dev *hdev, atr_req = (struct st21nfca_atr_req *)skb->data; + if (atr_req->length < sizeof(struct st21nfca_atr_req)) { + r = -EPROTO; + goto exit; + } + r = st21nfca_tm_send_atr_res(hdev, atr_req); if (r) goto exit; @@ -237,7 +240,6 @@ static int st21nfca_tm_send_psl_res(struct nfc_hci_dev *hdev, struct st21nfca_psl_res *psl_res; struct sk_buff *skb; u8 bitrate[2] = {0, 0}; - int r; skb = alloc_skb(sizeof(struct st21nfca_psl_res), GFP_KERNEL); @@ -254,6 +256,8 @@ static int st21nfca_tm_send_psl_res(struct nfc_hci_dev *hdev, r = nfc_hci_send_event(hdev, ST21NFCA_RF_CARD_F_GATE, ST21NFCA_EVT_SEND_DATA, skb->data, skb->len); + if (r < 0) + goto error; /* * ST21NFCA only support P2P passive. @@ -269,8 +273,11 @@ static int st21nfca_tm_send_psl_res(struct nfc_hci_dev *hdev, } /* Send an event to change bitrate change event to card f */ - return nfc_hci_send_event(hdev, ST21NFCA_RF_CARD_F_GATE, + r = nfc_hci_send_event(hdev, ST21NFCA_RF_CARD_F_GATE, ST21NFCA_EVT_CARD_F_BITRATE, bitrate, 2); +error: + kfree_skb(skb); + return r; } static int st21nfca_tm_recv_psl_req(struct nfc_hci_dev *hdev, @@ -280,11 +287,6 @@ static int st21nfca_tm_recv_psl_req(struct nfc_hci_dev *hdev, int r; skb_trim(skb, skb->len - 1); - if (IS_ERR(skb)) { - r = PTR_ERR(skb); - skb = NULL; - goto exit; - } if (!skb->len) { r = -EIO; @@ -314,7 +316,7 @@ int st21nfca_tm_send_dep_res(struct nfc_hci_dev *hdev, struct sk_buff *skb) *skb_push(skb, 1) = skb->len; r = nfc_hci_send_event(hdev, ST21NFCA_RF_CARD_F_GATE, - ST21NFCA_EVT_SEND_DATA, skb->data, skb->len); + ST21NFCA_EVT_SEND_DATA, skb->data, skb->len); kfree_skb(skb); return r; @@ -330,11 +332,6 @@ static int st21nfca_tm_recv_dep_req(struct nfc_hci_dev *hdev, struct st21nfca_hci_info *info = nfc_hci_get_clientdata(hdev); skb_trim(skb, skb->len - 1); - if (IS_ERR(skb)) { - r = PTR_ERR(skb); - skb = NULL; - goto exit; - } size = 4; @@ -368,12 +365,6 @@ static int st21nfca_tm_recv_dep_req(struct nfc_hci_dev *hdev, break; } - if (IS_ERR(skb)) { - r = PTR_ERR(skb); - skb = NULL; - goto exit; - } - skb_pull(skb, size); return nfc_tm_data_received(hdev->ndev, skb); @@ -437,8 +428,6 @@ static void st21nfca_im_send_psl_req(struct nfc_hci_dev *hdev, u8 did, u8 bsi, *skb_push(skb, 1) = info->dep_info.to | 0x10; st21nfca_im_send_pdu(info, skb); - - kfree_skb(skb); } #define ST21NFCA_CB_TYPE_READER_F 1 @@ -452,7 +441,7 @@ static void st21nfca_im_recv_atr_res_cb(void *context, struct sk_buff *skb, if (err != 0) return; - if (IS_ERR(skb)) + if (!skb) return; switch (info->async_cb_type) { @@ -484,8 +473,7 @@ static void st21nfca_im_recv_atr_res_cb(void *context, struct sk_buff *skb, ST21NFCA_PP2LRI(atr_res->ppi)); break; default: - if (err == 0) - kfree_skb(skb); + kfree_skb(skb); break; } } @@ -522,7 +510,7 @@ int st21nfca_im_send_atr_req(struct nfc_hci_dev *hdev, u8 *gb, size_t gb_len) memset(atr_req->nfcid3, 0, NFC_NFCID3_MAXSIZE); target = hdev->ndev->targets; - if (target->sensf_res) + if (target->sensf_res_len > 0) memcpy(atr_req->nfcid3, target->sensf_res, target->sensf_res_len); else @@ -565,7 +553,7 @@ static void st21nfca_im_recv_dep_res_cb(void *context, struct sk_buff *skb, if (err != 0) return; - if (IS_ERR(skb)) + if (!skb) return; switch (info->async_cb_type) { @@ -615,8 +603,7 @@ static void st21nfca_im_recv_dep_res_cb(void *context, struct sk_buff *skb, } exit: - if (err == 0) - kfree_skb(skb); + kfree_skb(skb); } int st21nfca_im_send_dep_req(struct nfc_hci_dev *hdev, struct sk_buff *skb) |