aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/nfc/pn533.c27
-rw-r--r--include/linux/nfc.h7
-rw-r--r--include/net/nfc/nfc.h4
-rw-r--r--net/nfc/core.c35
-rw-r--r--net/nfc/netlink.c62
-rw-r--r--net/nfc/nfc.h3
6 files changed, 136 insertions, 2 deletions
diff --git a/drivers/nfc/pn533.c b/drivers/nfc/pn533.c
index 605a08a62e45..c6b9bc5ac6e6 100644
--- a/drivers/nfc/pn533.c
+++ b/drivers/nfc/pn533.c
@@ -260,6 +260,10 @@ struct pn533_cmd_jump_dep_response {
260#define PN533_INIT_TARGET_PASSIVE 0x1 260#define PN533_INIT_TARGET_PASSIVE 0x1
261#define PN533_INIT_TARGET_DEP 0x2 261#define PN533_INIT_TARGET_DEP 0x2
262 262
263#define PN533_INIT_TARGET_RESP_FRAME_MASK 0x3
264#define PN533_INIT_TARGET_RESP_ACTIVE 0x1
265#define PN533_INIT_TARGET_RESP_DEP 0x4
266
263struct pn533_cmd_init_target { 267struct pn533_cmd_init_target {
264 u8 mode; 268 u8 mode;
265 u8 mifare[6]; 269 u8 mifare[6];
@@ -1128,10 +1132,13 @@ static int pn533_init_target_frame(struct pn533_frame *frame,
1128 return 0; 1132 return 0;
1129} 1133}
1130 1134
1135#define ATR_REQ_GB_OFFSET 17
1131static int pn533_init_target_complete(struct pn533 *dev, void *arg, 1136static int pn533_init_target_complete(struct pn533 *dev, void *arg,
1132 u8 *params, int params_len) 1137 u8 *params, int params_len)
1133{ 1138{
1134 struct pn533_cmd_init_target_response *resp; 1139 struct pn533_cmd_init_target_response *resp;
1140 u8 frame, comm_mode = NFC_COMM_PASSIVE, *gb;
1141 size_t gb_len;
1135 1142
1136 nfc_dev_dbg(&dev->interface->dev, "%s", __func__); 1143 nfc_dev_dbg(&dev->interface->dev, "%s", __func__);
1137 1144
@@ -1143,11 +1150,27 @@ static int pn533_init_target_complete(struct pn533 *dev, void *arg,
1143 return params_len; 1150 return params_len;
1144 } 1151 }
1145 1152
1153 if (params_len < ATR_REQ_GB_OFFSET + 1)
1154 return -EINVAL;
1155
1146 resp = (struct pn533_cmd_init_target_response *) params; 1156 resp = (struct pn533_cmd_init_target_response *) params;
1147 1157
1148 nfc_dev_dbg(&dev->interface->dev, "Target mode 0x%x\n", resp->mode); 1158 nfc_dev_dbg(&dev->interface->dev, "Target mode 0x%x param len %d\n",
1159 resp->mode, params_len);
1149 1160
1150 return 0; 1161 frame = resp->mode & PN533_INIT_TARGET_RESP_FRAME_MASK;
1162 if (frame == PN533_INIT_TARGET_RESP_ACTIVE)
1163 comm_mode = NFC_COMM_ACTIVE;
1164
1165 /* Again, only DEP */
1166 if ((resp->mode & PN533_INIT_TARGET_RESP_DEP) == 0)
1167 return -EOPNOTSUPP;
1168
1169 gb = resp->cmd + ATR_REQ_GB_OFFSET;
1170 gb_len = params_len - (ATR_REQ_GB_OFFSET + 1);
1171
1172 return nfc_tm_activated(dev->nfc_dev, NFC_PROTO_NFC_DEP_MASK,
1173 comm_mode, gb, gb_len);
1151} 1174}
1152 1175
1153static int pn533_init_target(struct nfc_dev *nfc_dev, u32 protocols) 1176static int pn533_init_target(struct nfc_dev *nfc_dev, u32 protocols)
diff --git a/include/linux/nfc.h b/include/linux/nfc.h
index 548715881fb0..d124e9273fcb 100644
--- a/include/linux/nfc.h
+++ b/include/linux/nfc.h
@@ -56,6 +56,10 @@
56 * %NFC_ATTR_PROTOCOLS) 56 * %NFC_ATTR_PROTOCOLS)
57 * @NFC_EVENT_DEVICE_REMOVED: event emitted when a device is removed 57 * @NFC_EVENT_DEVICE_REMOVED: event emitted when a device is removed
58 * (it sends %NFC_ATTR_DEVICE_INDEX) 58 * (it sends %NFC_ATTR_DEVICE_INDEX)
59 * @NFC_EVENT_TM_ACTIVATED: event emitted when the adapter is activated in
60 * target mode.
61 * @NFC_EVENT_DEVICE_DEACTIVATED: event emitted when the adapter is deactivated
62 * from target mode.
59 */ 63 */
60enum nfc_commands { 64enum nfc_commands {
61 NFC_CMD_UNSPEC, 65 NFC_CMD_UNSPEC,
@@ -71,6 +75,8 @@ enum nfc_commands {
71 NFC_EVENT_DEVICE_ADDED, 75 NFC_EVENT_DEVICE_ADDED,
72 NFC_EVENT_DEVICE_REMOVED, 76 NFC_EVENT_DEVICE_REMOVED,
73 NFC_EVENT_TARGET_LOST, 77 NFC_EVENT_TARGET_LOST,
78 NFC_EVENT_TM_ACTIVATED,
79 NFC_EVENT_TM_DEACTIVATED,
74/* private: internal use only */ 80/* private: internal use only */
75 __NFC_CMD_AFTER_LAST 81 __NFC_CMD_AFTER_LAST
76}; 82};
@@ -122,6 +128,7 @@ enum nfc_attrs {
122#define NFC_NFCID1_MAXSIZE 10 128#define NFC_NFCID1_MAXSIZE 10
123#define NFC_SENSB_RES_MAXSIZE 12 129#define NFC_SENSB_RES_MAXSIZE 12
124#define NFC_SENSF_RES_MAXSIZE 18 130#define NFC_SENSF_RES_MAXSIZE 18
131#define NFC_GB_MAXSIZE 48
125 132
126/* NFC protocols */ 133/* NFC protocols */
127#define NFC_PROTO_JEWEL 1 134#define NFC_PROTO_JEWEL 1
diff --git a/include/net/nfc/nfc.h b/include/net/nfc/nfc.h
index 97aa0e81aa83..41573b4bd78a 100644
--- a/include/net/nfc/nfc.h
+++ b/include/net/nfc/nfc.h
@@ -198,4 +198,8 @@ int nfc_target_lost(struct nfc_dev *dev, u32 target_idx);
198int nfc_dep_link_is_up(struct nfc_dev *dev, u32 target_idx, 198int nfc_dep_link_is_up(struct nfc_dev *dev, u32 target_idx,
199 u8 comm_mode, u8 rf_mode); 199 u8 comm_mode, u8 rf_mode);
200 200
201int nfc_tm_activated(struct nfc_dev *dev, u32 protocol, u8 comm_mode,
202 u8 *gb, size_t gb_len);
203int nfc_tm_deactivated(struct nfc_dev *dev);
204
201#endif /* __NET_NFC_H */ 205#endif /* __NET_NFC_H */
diff --git a/net/nfc/core.c b/net/nfc/core.c
index c83717bfcb8a..17f147430b7c 100644
--- a/net/nfc/core.c
+++ b/net/nfc/core.c
@@ -455,6 +455,41 @@ u8 *nfc_get_local_general_bytes(struct nfc_dev *dev, size_t *gb_len)
455} 455}
456EXPORT_SYMBOL(nfc_get_local_general_bytes); 456EXPORT_SYMBOL(nfc_get_local_general_bytes);
457 457
458int nfc_tm_activated(struct nfc_dev *dev, u32 protocol, u8 comm_mode,
459 u8 *gb, size_t gb_len)
460{
461 int rc;
462
463 device_lock(&dev->dev);
464
465 dev->polling = false;
466
467 if (gb != NULL) {
468 rc = nfc_set_remote_general_bytes(dev, gb, gb_len);
469 if (rc < 0)
470 goto out;
471 }
472
473 if (protocol == NFC_PROTO_NFC_DEP_MASK)
474 nfc_dep_link_is_up(dev, 0, comm_mode, NFC_RF_TARGET);
475
476 rc = nfc_genl_tm_activated(dev, protocol);
477
478out:
479 device_unlock(&dev->dev);
480
481 return rc;
482}
483EXPORT_SYMBOL(nfc_tm_activated);
484
485int nfc_tm_deactivated(struct nfc_dev *dev)
486{
487 dev->dep_link_up = false;
488
489 return nfc_genl_tm_deactivated(dev);
490}
491EXPORT_SYMBOL(nfc_tm_deactivated);
492
458/** 493/**
459 * nfc_alloc_send_skb - allocate a skb for data exchange responses 494 * nfc_alloc_send_skb - allocate a skb for data exchange responses
460 * 495 *
diff --git a/net/nfc/netlink.c b/net/nfc/netlink.c
index a18fd56798fc..21eaa9b5c6bf 100644
--- a/net/nfc/netlink.c
+++ b/net/nfc/netlink.c
@@ -221,6 +221,68 @@ free_msg:
221 return -EMSGSIZE; 221 return -EMSGSIZE;
222} 222}
223 223
224int nfc_genl_tm_activated(struct nfc_dev *dev, u32 protocol)
225{
226 struct sk_buff *msg;
227 void *hdr;
228
229 msg = nlmsg_new(NLMSG_GOODSIZE, GFP_KERNEL);
230 if (!msg)
231 return -ENOMEM;
232
233 hdr = genlmsg_put(msg, 0, 0, &nfc_genl_family, 0,
234 NFC_EVENT_TM_ACTIVATED);
235 if (!hdr)
236 goto free_msg;
237
238 if (nla_put_u32(msg, NFC_ATTR_DEVICE_INDEX, dev->idx))
239 goto nla_put_failure;
240 if (nla_put_u32(msg, NFC_ATTR_TM_PROTOCOLS, protocol))
241 goto nla_put_failure;
242
243 genlmsg_end(msg, hdr);
244
245 genlmsg_multicast(msg, 0, nfc_genl_event_mcgrp.id, GFP_KERNEL);
246
247 return 0;
248
249nla_put_failure:
250 genlmsg_cancel(msg, hdr);
251free_msg:
252 nlmsg_free(msg);
253 return -EMSGSIZE;
254}
255
256int nfc_genl_tm_deactivated(struct nfc_dev *dev)
257{
258 struct sk_buff *msg;
259 void *hdr;
260
261 msg = nlmsg_new(NLMSG_GOODSIZE, GFP_KERNEL);
262 if (!msg)
263 return -ENOMEM;
264
265 hdr = genlmsg_put(msg, 0, 0, &nfc_genl_family, 0,
266 NFC_EVENT_TM_DEACTIVATED);
267 if (!hdr)
268 goto free_msg;
269
270 if (nla_put_u32(msg, NFC_ATTR_DEVICE_INDEX, dev->idx))
271 goto nla_put_failure;
272
273 genlmsg_end(msg, hdr);
274
275 genlmsg_multicast(msg, 0, nfc_genl_event_mcgrp.id, GFP_KERNEL);
276
277 return 0;
278
279nla_put_failure:
280 genlmsg_cancel(msg, hdr);
281free_msg:
282 nlmsg_free(msg);
283 return -EMSGSIZE;
284}
285
224int nfc_genl_device_added(struct nfc_dev *dev) 286int nfc_genl_device_added(struct nfc_dev *dev)
225{ 287{
226 struct sk_buff *msg; 288 struct sk_buff *msg;
diff --git a/net/nfc/nfc.h b/net/nfc/nfc.h
index 7d9708f2a66c..cd9fcbe57464 100644
--- a/net/nfc/nfc.h
+++ b/net/nfc/nfc.h
@@ -128,6 +128,9 @@ int nfc_genl_dep_link_up_event(struct nfc_dev *dev, u32 target_idx,
128 u8 comm_mode, u8 rf_mode); 128 u8 comm_mode, u8 rf_mode);
129int nfc_genl_dep_link_down_event(struct nfc_dev *dev); 129int nfc_genl_dep_link_down_event(struct nfc_dev *dev);
130 130
131int nfc_genl_tm_activated(struct nfc_dev *dev, u32 protocol);
132int nfc_genl_tm_deactivated(struct nfc_dev *dev);
133
131struct nfc_dev *nfc_get_device(unsigned int idx); 134struct nfc_dev *nfc_get_device(unsigned int idx);
132 135
133static inline void nfc_put_device(struct nfc_dev *dev) 136static inline void nfc_put_device(struct nfc_dev *dev)