1165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/*
2165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * TI TRF7970a RFID/NFC Transceiver Driver
3165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer *
4165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * Copyright (C) 2013 Texas Instruments Incorporated - http://www.ti.com
5165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer *
6165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * Author: Erick Macias <emacias@ti.com>
7165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * Author: Felipe Balbi <balbi@ti.com>
8165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * Author: Mark A. Greer <mgreer@animalcreek.com>
9165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer *
10165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * This program is free software: you can redistribute it and/or modify
11165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * it under the terms of the GNU General Public License version 2  of
12165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * the License as published by the Free Software Foundation.
13165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer */
14165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
15165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#include <linux/module.h>
16165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#include <linux/device.h>
17165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#include <linux/netdevice.h>
18165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#include <linux/interrupt.h>
19e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer#include <linux/pm_runtime.h>
20165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#include <linux/nfc.h>
21165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#include <linux/skbuff.h>
22165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#include <linux/delay.h>
23165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#include <linux/gpio.h>
24165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#include <linux/of.h>
25165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#include <linux/of_gpio.h>
26165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#include <linux/spi/spi.h>
27165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#include <linux/regulator/consumer.h>
28165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
29165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#include <net/nfc/nfc.h>
30165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#include <net/nfc/digital.h>
31165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
32165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* There are 3 ways the host can communicate with the trf7970a:
33165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * parallel mode, SPI with Slave Select (SS) mode, and SPI without
34165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * SS mode.  The driver only supports the two SPI modes.
35165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer *
36165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * The trf7970a is very timing sensitive and the VIN, EN2, and EN
37165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * pins must asserted in that order and with specific delays in between.
38165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * The delays used in the driver were provided by TI and have been
3995064bd95a822659f4a606b485aba5009d70fc88Mark A. Greer * confirmed to work with this driver.  There is a bug with the current
4095064bd95a822659f4a606b485aba5009d70fc88Mark A. Greer * version of the trf7970a that requires that EN2 remain low no matter
4195064bd95a822659f4a606b485aba5009d70fc88Mark A. Greer * what.  If it goes high, it will generate an RF field even when in
4295064bd95a822659f4a606b485aba5009d70fc88Mark A. Greer * passive target mode.  TI has indicated that the chip will work okay
4395064bd95a822659f4a606b485aba5009d70fc88Mark A. Greer * when EN2 is left low.  The 'en2-rf-quirk' device tree property
4495064bd95a822659f4a606b485aba5009d70fc88Mark A. Greer * indicates that trf7970a currently being used has the erratum and
4595064bd95a822659f4a606b485aba5009d70fc88Mark A. Greer * that EN2 must be kept low.
46165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer *
47165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * Timeouts are implemented using the delayed workqueue kernel facility.
48165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * Timeouts are required so things don't hang when there is no response
49165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * from the trf7970a (or tag).  Using this mechanism creates a race with
50165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * interrupts, however.  That is, an interrupt and a timeout could occur
51165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * closely enough together that one is blocked by the mutex while the other
52165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * executes.  When the timeout handler executes first and blocks the
53165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * interrupt handler, it will eventually set the state to IDLE so the
54165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * interrupt handler will check the state and exit with no harm done.
55165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * When the interrupt handler executes first and blocks the timeout handler,
56165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * the cancel_delayed_work() call will know that it didn't cancel the
57165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * work item (i.e., timeout) and will return zero.  That return code is
58165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * used by the timer handler to indicate that it should ignore the timeout
59165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * once its unblocked.
60165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer *
61165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * Aborting an active command isn't as simple as it seems because the only
62165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * way to abort a command that's already been sent to the tag is so turn
63165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * off power to the tag.  If we do that, though, we'd have to go through
64165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * the entire anticollision procedure again but the digital layer doesn't
6513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer * support that.  So, if an abort is received before trf7970a_send_cmd()
66165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * has sent the command to the tag, it simply returns -ECANCELED.  If the
67165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * command has already been sent to the tag, then the driver continues
68165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * normally and recieves the response data (or error) but just before
69165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * sending the data upstream, it frees the rx_skb and sends -ECANCELED
70165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * upstream instead.  If the command failed, that error will be sent
71165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * upstream.
72165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer *
73165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * When recieving data from a tag and the interrupt status register has
74165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * only the SRX bit set, it means that all of the data has been received
75165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * (once what's in the fifo has been read).  However, depending on timing
76165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * an interrupt status with only the SRX bit set may not be recived.  In
775fa3af352b991e2e5c674728411d1cc4a4923e4dMark A. Greer * those cases, the timeout mechanism is used to wait 20 ms in case more
785fa3af352b991e2e5c674728411d1cc4a4923e4dMark A. Greer * data arrives.  After 20 ms, it is assumed that all of the data has been
79165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * received and the accumulated rx data is sent upstream.  The
80165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * 'TRF7970A_ST_WAIT_FOR_RX_DATA_CONT' state is used for this purpose
81165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * (i.e., it indicates that some data has been received but we're not sure
82165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * if there is more coming so a timeout in this state means all data has
835fa3af352b991e2e5c674728411d1cc4a4923e4dMark A. Greer * been received and there isn't an error).  The delay is 20 ms since delays
845fa3af352b991e2e5c674728411d1cc4a4923e4dMark A. Greer * of ~16 ms have been observed during testing.
85165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer *
8638b4eb1f7fa87079a5a40f5d2ec4b5c0c7f14a4bMark A. Greer * When transmitting a frame larger than the FIFO size (127 bytes), the
8738b4eb1f7fa87079a5a40f5d2ec4b5c0c7f14a4bMark A. Greer * driver will wait 20 ms for the FIFO to drain past the low-watermark
8838b4eb1f7fa87079a5a40f5d2ec4b5c0c7f14a4bMark A. Greer * and generate an interrupt.  The low-watermark set to 32 bytes so the
8938b4eb1f7fa87079a5a40f5d2ec4b5c0c7f14a4bMark A. Greer * interrupt should fire after 127 - 32 = 95 bytes have been sent.  At
9038b4eb1f7fa87079a5a40f5d2ec4b5c0c7f14a4bMark A. Greer * the lowest possible bit rate (6.62 kbps for 15693), it will take up
9138b4eb1f7fa87079a5a40f5d2ec4b5c0c7f14a4bMark A. Greer * to ~14.35 ms so 20 ms is used for the timeout.
9238b4eb1f7fa87079a5a40f5d2ec4b5c0c7f14a4bMark A. Greer *
93165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * Type 2 write and sector select commands respond with a 4-bit ACK or NACK.
94165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * Having only 4 bits in the FIFO won't normally generate an interrupt so
95165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * driver enables the '4_bit_RX' bit of the Special Functions register 1
96165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * to cause an interrupt in that case.  Leaving that bit for a read command
97165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * messes up the data returned so it is only enabled when the framing is
98165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * 'NFC_DIGITAL_FRAMING_NFCA_T2T' and the command is not a read command.
99165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * Unfortunately, that means that the driver has to peek into tx frames
100165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * when the framing is 'NFC_DIGITAL_FRAMING_NFCA_T2T'.  This is done by
101165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * the trf7970a_per_cmd_config() routine.
1029d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer *
1039d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * ISO/IEC 15693 frames specify whether to use single or double sub-carrier
1049d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * frequencies and whether to use low or high data rates in the flags byte
1059d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * of the frame.  This means that the driver has to peek at all 15693 frames
1069d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * to determine what speed to set the communication to.  In addition, write
1079d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * and lock commands use the OPTION flag to indicate that an EOF must be
1089d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * sent to the tag before it will send its response.  So the driver has to
1099d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * examine all frames for that reason too.
1109d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer *
1119d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * It is unclear how long to wait before sending the EOF.  According to the
1129d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * Note under Table 1-1 in section 1.6 of
1139d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * http://www.ti.com/lit/ug/scbu011/scbu011.pdf, that wait should be at least
1149d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * 10 ms for TI Tag-it HF-I tags; however testing has shown that is not long
11538b4eb1f7fa87079a5a40f5d2ec4b5c0c7f14a4bMark A. Greer * enough so 20 ms is used.  So the timer is set to 40 ms - 20 ms to drain
11638b4eb1f7fa87079a5a40f5d2ec4b5c0c7f14a4bMark A. Greer * up to 127 bytes in the FIFO at the lowest bit rate plus another 20 ms to
11738b4eb1f7fa87079a5a40f5d2ec4b5c0c7f14a4bMark A. Greer * ensure the wait is long enough before sending the EOF.  This seems to work
1189d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * reliably.
119165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer */
120165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1218006289108fa9635d16a65d9db16da06d7dce201Mark A. Greer#define TRF7970A_SUPPORTED_PROTOCOLS \
1229d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		(NFC_PROTO_MIFARE_MASK | NFC_PROTO_ISO14443_MASK |	\
1236857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer		 NFC_PROTO_ISO14443_B_MASK | NFC_PROTO_FELICA_MASK | \
12413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		 NFC_PROTO_ISO15693_MASK | NFC_PROTO_NFC_DEP_MASK)
125165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
126e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer#define TRF7970A_AUTOSUSPEND_DELAY		30000 /* 30 seconds */
127e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer
128165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_RX_SKB_ALLOC_SIZE		256
129165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1301568bfef18a9150d83b0f91aa254cef7ebead4cdMark A. Greer#define TRF7970A_FIFO_SIZE			127
131165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
132165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* TX length is 3 nibbles long ==> 4KB - 1 bytes max */
133165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_TX_MAX				(4096 - 1)
134165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1351961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer#define TRF7970A_WAIT_FOR_TX_IRQ		20
1365fa3af352b991e2e5c674728411d1cc4a4923e4dMark A. Greer#define TRF7970A_WAIT_FOR_RX_DATA_TIMEOUT	20
13738b4eb1f7fa87079a5a40f5d2ec4b5c0c7f14a4bMark A. Greer#define TRF7970A_WAIT_FOR_FIFO_DRAIN_TIMEOUT	20
13838b4eb1f7fa87079a5a40f5d2ec4b5c0c7f14a4bMark A. Greer#define TRF7970A_WAIT_TO_ISSUE_ISO15693_EOF	40
139165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1404e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer/* Guard times for various RF technologies (in us) */
1414e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer#define TRF7970A_GUARD_TIME_NFCA		5000
1424e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer#define TRF7970A_GUARD_TIME_NFCB		5000
1434e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer#define TRF7970A_GUARD_TIME_NFCF		20000
1444e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer#define TRF7970A_GUARD_TIME_15693		1000
1454e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer
146165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* Quirks */
147165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* Erratum: When reading IRQ Status register on trf7970a, we must issue a
148165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * read continuous command for IRQ Status and Collision Position registers.
149165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer */
150772079eb77587e0242752fa67685a8132d899f79Mark A. Greer#define TRF7970A_QUIRK_IRQ_STATUS_READ		BIT(0)
15195064bd95a822659f4a606b485aba5009d70fc88Mark A. Greer#define TRF7970A_QUIRK_EN2_MUST_STAY_LOW	BIT(1)
152165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
153165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* Direct commands */
154165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_IDLE			0x00
155165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_SOFT_INIT			0x03
156165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_RF_COLLISION		0x04
157165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_RF_COLLISION_RESPONSE_N	0x05
158165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_RF_COLLISION_RESPONSE_0	0x06
159165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_FIFO_RESET			0x0f
160165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_TRANSMIT_NO_CRC		0x10
161165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_TRANSMIT			0x11
162165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_DELAY_TRANSMIT_NO_CRC	0x12
163165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_DELAY_TRANSMIT		0x13
164165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_EOF			0x14
165165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_CLOSE_SLOT			0x15
166165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_BLOCK_RX			0x16
167165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_ENABLE_RX			0x17
168851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer#define TRF7970A_CMD_TEST_INT_RF		0x18
169851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer#define TRF7970A_CMD_TEST_EXT_RF		0x19
170165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_RX_GAIN_ADJUST		0x1a
171165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
172165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* Bits determining whether its a direct command or register R/W,
173165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * whether to use a continuous SPI transaction or not, and the actual
174165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * direct cmd opcode or regster address.
175165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer */
176165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_BIT_CTRL			BIT(7)
177165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_BIT_RW			BIT(6)
178165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_BIT_CONTINUOUS		BIT(5)
179165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_BIT_OPCODE(opcode)		((opcode) & 0x1f)
180165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
181165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* Registers addresses */
182165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CHIP_STATUS_CTRL		0x00
183165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL			0x01
184165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO14443B_TX_OPTIONS		0x02
185165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO14443A_HIGH_BITRATE_OPTIONS	0x03
186165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_TX_TIMER_SETTING_H_BYTE	0x04
187165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_TX_TIMER_SETTING_L_BYTE	0x05
188165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_TX_PULSE_LENGTH_CTRL		0x06
189165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_RX_NO_RESPONSE_WAIT		0x07
190165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_RX_WAIT_TIME			0x08
191165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_SYS_CLK_CTRL		0x09
192165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_RX_SPECIAL_SETTINGS		0x0a
193165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_REG_IO_CTRL			0x0b
194165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_IRQ_STATUS			0x0c
195165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_COLLISION_IRQ_MASK		0x0d
196165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_COLLISION_POSITION		0x0e
197165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_RSSI_OSC_STATUS		0x0f
198165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_SPECIAL_FCN_REG1		0x10
199165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_SPECIAL_FCN_REG2		0x11
200165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_RAM1				0x12
201165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_RAM2				0x13
202165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS	0x14
203165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_NFC_LOW_FIELD_LEVEL		0x16
204165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_NFCID1				0x17
205165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_NFC_TARGET_LEVEL		0x18
206165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF79070A_NFC_TARGET_PROTOCOL		0x19
207165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_TEST_REGISTER1			0x1a
208165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_TEST_REGISTER2			0x1b
209165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_FIFO_STATUS			0x1c
210165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_TX_LENGTH_BYTE1		0x1d
211165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_TX_LENGTH_BYTE2		0x1e
212165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_FIFO_IO_REGISTER		0x1f
213165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
214165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* Chip Status Control Register Bits */
215165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CHIP_STATUS_VRS5_3		BIT(0)
216165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CHIP_STATUS_REC_ON		BIT(1)
217165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CHIP_STATUS_AGC_ON		BIT(2)
218165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CHIP_STATUS_PM_ON		BIT(3)
219165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CHIP_STATUS_RF_PWR		BIT(4)
220165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CHIP_STATUS_RF_ON		BIT(5)
221165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CHIP_STATUS_DIRECT		BIT(6)
222165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CHIP_STATUS_STBY		BIT(7)
223165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
224165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* ISO Control Register Bits */
225165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_15693_SGL_1OF4_662	0x00
226165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_15693_SGL_1OF256_662	0x01
227165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_15693_SGL_1OF4_2648	0x02
228165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_15693_SGL_1OF256_2648	0x03
229165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_15693_DBL_1OF4_667a	0x04
230165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_15693_DBL_1OF256_667	0x05
231165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_15693_DBL_1OF4_2669	0x06
232165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_15693_DBL_1OF256_2669	0x07
233165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_14443A_106		0x08
234165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_14443A_212		0x09
235165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_14443A_424		0x0a
236165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_14443A_848		0x0b
237165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_14443B_106		0x0c
238165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_14443B_212		0x0d
239165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_14443B_424		0x0e
240165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_14443B_848		0x0f
241165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_FELICA_212		0x1a
242165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_FELICA_424		0x1b
24313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_ISO_CTRL_NFC_NFCA_106		0x01
24413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_ISO_CTRL_NFC_NFCF_212		0x02
24513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_ISO_CTRL_NFC_NFCF_424		0x03
24613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_ISO_CTRL_NFC_CE_14443A		0x00
24713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_ISO_CTRL_NFC_CE_14443B		0x01
24813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_ISO_CTRL_NFC_CE		BIT(2)
24913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_ISO_CTRL_NFC_ACTIVE		BIT(3)
25013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_ISO_CTRL_NFC_INITIATOR		BIT(4)
25113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_ISO_CTRL_NFC_NFC_CE_MODE	BIT(5)
252165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_RFID			BIT(5)
253165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_DIR_MODE		BIT(6)
254165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_RX_CRC_N		BIT(7)	/* true == No CRC */
255165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
256165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_RFID_SPEED_MASK	0x1f
257165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
258165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* Modulator and SYS_CLK Control Register Bits */
259165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_DEPTH(n)		((n) & 0x7)
260165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_DEPTH_ASK10		(TRF7970A_MODULATOR_DEPTH(0))
261165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_DEPTH_OOK		(TRF7970A_MODULATOR_DEPTH(1))
262165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_DEPTH_ASK7		(TRF7970A_MODULATOR_DEPTH(2))
263165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_DEPTH_ASK8_5		(TRF7970A_MODULATOR_DEPTH(3))
264165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_DEPTH_ASK13		(TRF7970A_MODULATOR_DEPTH(4))
265165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_DEPTH_ASK16		(TRF7970A_MODULATOR_DEPTH(5))
266165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_DEPTH_ASK22		(TRF7970A_MODULATOR_DEPTH(6))
267165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_DEPTH_ASK30		(TRF7970A_MODULATOR_DEPTH(7))
268165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_EN_ANA		BIT(3)
269165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_CLK(n)		(((n) & 0x3) << 4)
270165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_CLK_DISABLED		(TRF7970A_MODULATOR_CLK(0))
271165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_CLK_3_6		(TRF7970A_MODULATOR_CLK(1))
272165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_CLK_6_13		(TRF7970A_MODULATOR_CLK(2))
273165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_CLK_13_27		(TRF7970A_MODULATOR_CLK(3))
274165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_EN_OOK		BIT(6)
275165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_27MHZ		BIT(7)
276165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
27713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_RX_SPECIAL_SETTINGS_NO_LIM	BIT(0)
27813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_RX_SPECIAL_SETTINGS_AGCR	BIT(1)
27913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_RX_SPECIAL_SETTINGS_GD_0DB	(0x0 << 2)
28013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_RX_SPECIAL_SETTINGS_GD_5DB	(0x1 << 2)
28113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_RX_SPECIAL_SETTINGS_GD_10DB	(0x2 << 2)
28213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_RX_SPECIAL_SETTINGS_GD_15DB	(0x3 << 2)
28313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_RX_SPECIAL_SETTINGS_HBT	BIT(4)
28413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_RX_SPECIAL_SETTINGS_M848	BIT(5)
28513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_RX_SPECIAL_SETTINGS_C424	BIT(6)
28613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_RX_SPECIAL_SETTINGS_C212	BIT(7)
28713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
28813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_REG_IO_CTRL_VRS(v)		((v) & 0x07)
28913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_REG_IO_CTRL_IO_LOW		BIT(5)
29013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_REG_IO_CTRL_EN_EXT_PA		BIT(6)
29113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_REG_IO_CTRL_AUTO_REG		BIT(7)
29213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
293165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* IRQ Status Register Bits */
294165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_IRQ_STATUS_NORESP		BIT(0) /* ISO15693 only */
29513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_IRQ_STATUS_NFC_COL_ERROR	BIT(0)
296165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_IRQ_STATUS_COL			BIT(1)
297165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_IRQ_STATUS_FRAMING_EOF_ERROR	BIT(2)
29813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_IRQ_STATUS_NFC_RF		BIT(2)
299165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_IRQ_STATUS_PARITY_ERROR	BIT(3)
30013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_IRQ_STATUS_NFC_SDD		BIT(3)
301165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_IRQ_STATUS_CRC_ERROR		BIT(4)
30213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_IRQ_STATUS_NFC_PROTO_ERROR	BIT(4)
303165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_IRQ_STATUS_FIFO		BIT(5)
304165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_IRQ_STATUS_SRX			BIT(6)
305165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_IRQ_STATUS_TX			BIT(7)
306165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
307165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_IRQ_STATUS_ERROR				\
308165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		(TRF7970A_IRQ_STATUS_COL |			\
309165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		 TRF7970A_IRQ_STATUS_FRAMING_EOF_ERROR |	\
310165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		 TRF7970A_IRQ_STATUS_PARITY_ERROR |		\
311165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		 TRF7970A_IRQ_STATUS_CRC_ERROR)
312165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
313851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer#define TRF7970A_RSSI_OSC_STATUS_RSSI_MASK	(BIT(2) | BIT(1) | BIT(0))
314851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer#define TRF7970A_RSSI_OSC_STATUS_RSSI_X_MASK	(BIT(5) | BIT(4) | BIT(3))
315851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer#define TRF7970A_RSSI_OSC_STATUS_RSSI_OSC_OK	BIT(6)
316851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer
317165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_SPECIAL_FCN_REG1_COL_7_6		BIT(0)
318165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_SPECIAL_FCN_REG1_14_ANTICOLL		BIT(1)
319165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_SPECIAL_FCN_REG1_4_BIT_RX		BIT(2)
320165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_SPECIAL_FCN_REG1_SP_DIR_MODE		BIT(3)
321165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_SPECIAL_FCN_REG1_NEXT_SLOT_37US	BIT(4)
322165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_SPECIAL_FCN_REG1_PAR43			BIT(5)
323165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
324165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS_WLH_124	(0x0 << 2)
325165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS_WLH_120	(0x1 << 2)
326165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS_WLH_112	(0x2 << 2)
327165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS_WLH_96	(0x3 << 2)
328165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS_WLL_4	0x0
329165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS_WLL_8	0x1
330165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS_WLL_16	0x2
331165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS_WLL_32	0x3
332165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
33313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_NFC_LOW_FIELD_LEVEL_RFDET(v)	((v) & 0x07)
33413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_NFC_LOW_FIELD_LEVEL_CLEX_DIS	BIT(7)
33513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
33613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_NFC_TARGET_LEVEL_RFDET(v)	((v) & 0x07)
33713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_NFC_TARGET_LEVEL_HI_RF		BIT(3)
33813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_NFC_TARGET_LEVEL_SDD_EN	BIT(3)
33913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_NFC_TARGET_LEVEL_LD_S_4BYTES	(0x0 << 6)
34013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_NFC_TARGET_LEVEL_LD_S_7BYTES	(0x1 << 6)
34113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer#define TRF7970A_NFC_TARGET_LEVEL_LD_S_10BYTES	(0x2 << 6)
34213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
343cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer#define TRF79070A_NFC_TARGET_PROTOCOL_NFCBR_106		BIT(0)
344cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer#define TRF79070A_NFC_TARGET_PROTOCOL_NFCBR_212		BIT(1)
345cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer#define TRF79070A_NFC_TARGET_PROTOCOL_NFCBR_424		(BIT(0) | BIT(1))
346cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer#define TRF79070A_NFC_TARGET_PROTOCOL_PAS_14443B	BIT(2)
347cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer#define TRF79070A_NFC_TARGET_PROTOCOL_PAS_106		BIT(3)
348cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer#define TRF79070A_NFC_TARGET_PROTOCOL_FELICA		BIT(4)
349cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer#define TRF79070A_NFC_TARGET_PROTOCOL_RF_L		BIT(6)
350cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer#define TRF79070A_NFC_TARGET_PROTOCOL_RF_H		BIT(7)
351cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
352cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer#define TRF79070A_NFC_TARGET_PROTOCOL_106A		\
353cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	 (TRF79070A_NFC_TARGET_PROTOCOL_RF_H |		\
354cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	  TRF79070A_NFC_TARGET_PROTOCOL_RF_L |		\
355cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	  TRF79070A_NFC_TARGET_PROTOCOL_PAS_106 |	\
356cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	  TRF79070A_NFC_TARGET_PROTOCOL_NFCBR_106)
357cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
358cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer#define TRF79070A_NFC_TARGET_PROTOCOL_106B		\
359cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	 (TRF79070A_NFC_TARGET_PROTOCOL_RF_H |		\
360cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	  TRF79070A_NFC_TARGET_PROTOCOL_RF_L |		\
361cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	  TRF79070A_NFC_TARGET_PROTOCOL_PAS_14443B |	\
362cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	  TRF79070A_NFC_TARGET_PROTOCOL_NFCBR_106)
363cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
364cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer#define TRF79070A_NFC_TARGET_PROTOCOL_212F		\
365cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	 (TRF79070A_NFC_TARGET_PROTOCOL_RF_H |		\
366cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	  TRF79070A_NFC_TARGET_PROTOCOL_RF_L |		\
367cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	  TRF79070A_NFC_TARGET_PROTOCOL_FELICA |	\
368cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	  TRF79070A_NFC_TARGET_PROTOCOL_NFCBR_212)
369cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
370cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer#define TRF79070A_NFC_TARGET_PROTOCOL_424F		\
371cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	 (TRF79070A_NFC_TARGET_PROTOCOL_RF_H |		\
372cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	  TRF79070A_NFC_TARGET_PROTOCOL_RF_L |		\
373cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	  TRF79070A_NFC_TARGET_PROTOCOL_FELICA |	\
374cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	  TRF79070A_NFC_TARGET_PROTOCOL_NFCBR_424)
375cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
376165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_FIFO_STATUS_OVERFLOW		BIT(7)
377165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
378165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* NFC (ISO/IEC 14443A) Type 2 Tag commands */
379165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define NFC_T2T_CMD_READ			0x30
380165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
3819d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer/* ISO 15693 commands codes */
3829d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_INVENTORY			0x01
3839d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_READ_SINGLE_BLOCK		0x20
3849d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_WRITE_SINGLE_BLOCK		0x21
3859d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_LOCK_BLOCK			0x22
3869d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_READ_MULTIPLE_BLOCK	0x23
3879d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_WRITE_MULTIPLE_BLOCK	0x24
3889d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_SELECT			0x25
3899d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_RESET_TO_READY		0x26
3909d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_WRITE_AFI			0x27
3919d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_LOCK_AFI			0x28
3929d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_WRITE_DSFID		0x29
3939d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_LOCK_DSFID			0x2a
3949d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_GET_SYSTEM_INFO		0x2b
3959d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_GET_MULTIPLE_BLOCK_SECURITY_STATUS	0x2c
3969d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer
3979d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer/* ISO 15693 request and response flags */
3989d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_REQ_FLAG_SUB_CARRIER		BIT(0)
3999d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_REQ_FLAG_DATA_RATE		BIT(1)
4009d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_REQ_FLAG_INVENTORY		BIT(2)
4019d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_REQ_FLAG_PROTOCOL_EXT		BIT(3)
4029d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_REQ_FLAG_SELECT		BIT(4)
4039d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_REQ_FLAG_AFI			BIT(4)
4049d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_REQ_FLAG_ADDRESS		BIT(5)
4059d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_REQ_FLAG_NB_SLOTS		BIT(5)
4069d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_REQ_FLAG_OPTION		BIT(6)
4079d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer
4089d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_REQ_FLAG_SPEED_MASK \
4099d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		(ISO15693_REQ_FLAG_SUB_CARRIER | ISO15693_REQ_FLAG_DATA_RATE)
4109d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer
411165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerenum trf7970a_state {
412ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	TRF7970A_ST_PWR_OFF,
413b5e17d9b5bd7e53696bce21e38eec5b9bb8abb88Mark A. Greer	TRF7970A_ST_RF_OFF,
414165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	TRF7970A_ST_IDLE,
415165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	TRF7970A_ST_IDLE_RX_BLOCKED,
416165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	TRF7970A_ST_WAIT_FOR_TX_FIFO,
417165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	TRF7970A_ST_WAIT_FOR_RX_DATA,
418165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	TRF7970A_ST_WAIT_FOR_RX_DATA_CONT,
4199d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	TRF7970A_ST_WAIT_TO_ISSUE_EOF,
42013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	TRF7970A_ST_LISTENING,
421cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	TRF7970A_ST_LISTENING_MD,
422165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	TRF7970A_ST_MAX
423165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer};
424165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
425165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstruct trf7970a {
426165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	enum trf7970a_state		state;
427165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	struct device			*dev;
428165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	struct spi_device		*spi;
429165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	struct regulator		*regulator;
430165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	struct nfc_digital_dev		*ddev;
431165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	u32				quirks;
43213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	bool				is_initiator;
433165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	bool				aborting;
434165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	struct sk_buff			*tx_skb;
435165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	struct sk_buff			*rx_skb;
436165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	nfc_digital_cmd_complete_t	cb;
437165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	void				*cb_arg;
438ebcc5a0d08e6a680558ed74f5dd724427ff5a29bMark A. Greer	u8				chip_status_ctrl;
439165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	u8				iso_ctrl;
44049d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer	u8				iso_ctrl_tech;
44112e9ade309db51e7ea26be3b4fd5bc6057ddc175Mark A. Greer	u8				modulator_sys_clk_ctrl;
442165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	u8				special_fcn_reg1;
4434e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer	unsigned int			guard_time;
444165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	int				technology;
445165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	int				framing;
446cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	u8				md_rf_tech;
447165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	u8				tx_cmd;
4489d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	bool				issue_eof;
449165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	int				en2_gpio;
450165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	int				en_gpio;
451165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	struct mutex			lock;
452165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	unsigned int			timeout;
453165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	bool				ignore_timeout;
454165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	struct delayed_work		timeout_work;
455165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer};
456165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
457165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
458165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_cmd(struct trf7970a *trf, u8 opcode)
459165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
460165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	u8 cmd = TRF7970A_CMD_BIT_CTRL | TRF7970A_CMD_BIT_OPCODE(opcode);
461165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	int ret;
462165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
463165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_dbg(trf->dev, "cmd: 0x%x\n", cmd);
464165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
465165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	ret = spi_write(trf->spi, &cmd, 1);
466165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (ret)
467165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_err(trf->dev, "%s - cmd: 0x%x, ret: %d\n", __func__, cmd,
468165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer				ret);
469165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	return ret;
470165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
471165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
472165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_read(struct trf7970a *trf, u8 reg, u8 *val)
473165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
474165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	u8 addr = TRF7970A_CMD_BIT_RW | reg;
475165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	int ret;
476165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
477165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	ret = spi_write_then_read(trf->spi, &addr, 1, val, 1);
478165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (ret)
479165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_err(trf->dev, "%s - addr: 0x%x, ret: %d\n", __func__, addr,
480165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer				ret);
481165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
482165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_dbg(trf->dev, "read(0x%x): 0x%x\n", addr, *val);
483165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
484165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	return ret;
485165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
486165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
4873e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greerstatic int trf7970a_read_cont(struct trf7970a *trf, u8 reg, u8 *buf, size_t len)
488165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
489165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	u8 addr = reg | TRF7970A_CMD_BIT_RW | TRF7970A_CMD_BIT_CONTINUOUS;
4903e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer	struct spi_transfer t[2];
4913e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer	struct spi_message m;
492165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	int ret;
493165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
494165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_dbg(trf->dev, "read_cont(0x%x, %zd)\n", addr, len);
495165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
4963e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer	spi_message_init(&m);
4973e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer
4983e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer	memset(&t, 0, sizeof(t));
4993e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer
5003e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer	t[0].tx_buf = &addr;
5013e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer	t[0].len = sizeof(addr);
5023e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer	spi_message_add_tail(&t[0], &m);
5033e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer
5043e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer	t[1].rx_buf = buf;
5053e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer	t[1].len = len;
5063e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer	spi_message_add_tail(&t[1], &m);
5073e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer
5083e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer	ret = spi_sync(trf->spi, &m);
509165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (ret)
510165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_err(trf->dev, "%s - addr: 0x%x, ret: %d\n", __func__, addr,
511165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer				ret);
512165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	return ret;
513165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
514165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
515165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_write(struct trf7970a *trf, u8 reg, u8 val)
516165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
517165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	u8 buf[2] = { reg, val };
518165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	int ret;
519165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
520165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_dbg(trf->dev, "write(0x%x): 0x%x\n", reg, val);
521165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
522165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	ret = spi_write(trf->spi, buf, 2);
523165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (ret)
524165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_err(trf->dev, "%s - write: 0x%x 0x%x, ret: %d\n", __func__,
525165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer				buf[0], buf[1], ret);
526165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
527165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	return ret;
528165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
529165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
530165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_read_irqstatus(struct trf7970a *trf, u8 *status)
531165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
532165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	int ret;
533165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	u8 buf[2];
534165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	u8 addr;
535165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
536165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	addr = TRF7970A_IRQ_STATUS | TRF7970A_CMD_BIT_RW;
537165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
538772079eb77587e0242752fa67685a8132d899f79Mark A. Greer	if (trf->quirks & TRF7970A_QUIRK_IRQ_STATUS_READ) {
539165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		addr |= TRF7970A_CMD_BIT_CONTINUOUS;
540165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		ret = spi_write_then_read(trf->spi, &addr, 1, buf, 2);
541165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	} else {
542165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		ret = spi_write_then_read(trf->spi, &addr, 1, buf, 1);
543165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
544165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
545165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (ret)
546165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_err(trf->dev, "%s - irqstatus: Status read failed: %d\n",
547165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer				__func__, ret);
548165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	else
549165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		*status = buf[0];
550165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
551165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	return ret;
552165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
553165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
554cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greerstatic int trf7970a_read_target_proto(struct trf7970a *trf, u8 *target_proto)
555cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer{
556cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	int ret;
557cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	u8 buf[2];
558cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	u8 addr;
559cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
560cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	addr = TRF79070A_NFC_TARGET_PROTOCOL | TRF7970A_CMD_BIT_RW |
561cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		TRF7970A_CMD_BIT_CONTINUOUS;
562cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
563cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	ret = spi_write_then_read(trf->spi, &addr, 1, buf, 2);
564cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	if (ret)
565cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		dev_err(trf->dev, "%s - target_proto: Read failed: %d\n",
566cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer				__func__, ret);
567cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	else
568cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		*target_proto = buf[0];
569cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
570cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	return ret;
571cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer}
572cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
573cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greerstatic int trf7970a_mode_detect(struct trf7970a *trf, u8 *rf_tech)
574cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer{
575cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	int ret;
576cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	u8 target_proto, tech;
577cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
578cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	ret = trf7970a_read_target_proto(trf, &target_proto);
579cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	if (ret)
580cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		return ret;
581cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
582cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	switch (target_proto) {
583cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	case TRF79070A_NFC_TARGET_PROTOCOL_106A:
584cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		tech = NFC_DIGITAL_RF_TECH_106A;
585cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		break;
586cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	case TRF79070A_NFC_TARGET_PROTOCOL_106B:
587cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		tech = NFC_DIGITAL_RF_TECH_106B;
588cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		break;
589cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	case TRF79070A_NFC_TARGET_PROTOCOL_212F:
590cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		tech = NFC_DIGITAL_RF_TECH_212F;
591cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		break;
592cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	case TRF79070A_NFC_TARGET_PROTOCOL_424F:
593cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		tech = NFC_DIGITAL_RF_TECH_424F;
594cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		break;
595cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	default:
596cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		dev_dbg(trf->dev, "%s - mode_detect: target_proto: 0x%x\n",
597cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer				__func__, target_proto);
598cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		return -EIO;
599cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	}
600cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
601cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	*rf_tech = tech;
602cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
603cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	return ret;
604cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer}
605cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
606165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic void trf7970a_send_upstream(struct trf7970a *trf)
607165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
608165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_kfree_skb_any(trf->tx_skb);
609165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf->tx_skb = NULL;
610165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
611165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (trf->rx_skb && !IS_ERR(trf->rx_skb) && !trf->aborting)
612165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		print_hex_dump_debug("trf7970a rx data: ", DUMP_PREFIX_NONE,
613165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer				16, 1, trf->rx_skb->data, trf->rx_skb->len,
614165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer				false);
615165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
616165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf->state = TRF7970A_ST_IDLE;
617165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
618165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (trf->aborting) {
619165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_dbg(trf->dev, "Abort process complete\n");
620165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
621165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		if (!IS_ERR(trf->rx_skb)) {
622165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			kfree_skb(trf->rx_skb);
623165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			trf->rx_skb = ERR_PTR(-ECANCELED);
624165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		}
625165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
626165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		trf->aborting = false;
627165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
628165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
629165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf->cb(trf->ddev, trf->cb_arg, trf->rx_skb);
630165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
631165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf->rx_skb = NULL;
632165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
633165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
634165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic void trf7970a_send_err_upstream(struct trf7970a *trf, int errno)
635165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
636165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_dbg(trf->dev, "Error - state: %d, errno: %d\n", trf->state, errno);
637165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
6386fb9edcb43d0b1bf0ac2aaf6ba488d105c45f477Mark A. Greer	cancel_delayed_work(&trf->timeout_work);
6396fb9edcb43d0b1bf0ac2aaf6ba488d105c45f477Mark A. Greer
640165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	kfree_skb(trf->rx_skb);
641165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf->rx_skb = ERR_PTR(errno);
642165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
643165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf7970a_send_upstream(trf);
644165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
645165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
646165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_transmit(struct trf7970a *trf, struct sk_buff *skb,
6477a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer		unsigned int len, u8 *prefix, unsigned int prefix_len)
648165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
6497a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer	struct spi_transfer t[2];
6507a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer	struct spi_message m;
651165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	unsigned int timeout;
652165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	int ret;
653165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
654165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	print_hex_dump_debug("trf7970a tx data: ", DUMP_PREFIX_NONE,
655165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			16, 1, skb->data, len, false);
656165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
6577a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer	spi_message_init(&m);
6587a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer
6597a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer	memset(&t, 0, sizeof(t));
6607a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer
6617a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer	t[0].tx_buf = prefix;
6627a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer	t[0].len = prefix_len;
6637a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer	spi_message_add_tail(&t[0], &m);
6647a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer
6657a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer	t[1].tx_buf = skb->data;
6667a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer	t[1].len = len;
6677a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer	spi_message_add_tail(&t[1], &m);
6687a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer
6697a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer	ret = spi_sync(trf->spi, &m);
670165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (ret) {
671165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_err(trf->dev, "%s - Can't send tx data: %d\n", __func__,
672165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer				ret);
673165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		return ret;
674165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
675165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
676165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	skb_pull(skb, len);
677165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
678165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (skb->len > 0) {
679165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		trf->state = TRF7970A_ST_WAIT_FOR_TX_FIFO;
680165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		timeout = TRF7970A_WAIT_FOR_FIFO_DRAIN_TIMEOUT;
681165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	} else {
6829d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		if (trf->issue_eof) {
6839d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer			trf->state = TRF7970A_ST_WAIT_TO_ISSUE_EOF;
6849d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer			timeout = TRF7970A_WAIT_TO_ISSUE_ISO15693_EOF;
6859d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		} else {
6869d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer			trf->state = TRF7970A_ST_WAIT_FOR_RX_DATA;
6871961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer
6881961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer			if (!trf->timeout)
6891961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer				timeout = TRF7970A_WAIT_FOR_TX_IRQ;
6901961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer			else
6911961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer				timeout = trf->timeout;
6929d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		}
693165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
694165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
695165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_dbg(trf->dev, "Setting timeout for %d ms, state: %d\n", timeout,
696165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			trf->state);
697165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
698165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	schedule_delayed_work(&trf->timeout_work, msecs_to_jiffies(timeout));
699165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
700165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	return 0;
701165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
702165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
703165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic void trf7970a_fill_fifo(struct trf7970a *trf)
704165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
705165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	struct sk_buff *skb = trf->tx_skb;
706165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	unsigned int len;
707165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	int ret;
708165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	u8 fifo_bytes;
7097a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer	u8 prefix;
710165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
711165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	ret = trf7970a_read(trf, TRF7970A_FIFO_STATUS, &fifo_bytes);
712165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (ret) {
713165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		trf7970a_send_err_upstream(trf, ret);
714165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		return;
715165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
716165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
717165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_dbg(trf->dev, "Filling FIFO - fifo_bytes: 0x%x\n", fifo_bytes);
718165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
7194542e8345af6076c87d036c7bd3f9dfa30768b1eMark A. Greer	fifo_bytes &= ~TRF7970A_FIFO_STATUS_OVERFLOW;
720165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
721165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	/* Calculate how much more data can be written to the fifo */
722165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	len = TRF7970A_FIFO_SIZE - fifo_bytes;
7230e840ed59ba79670b66bba8c1d50b6f67e72d3fbMark A. Greer	if (!len) {
7240e840ed59ba79670b66bba8c1d50b6f67e72d3fbMark A. Greer		schedule_delayed_work(&trf->timeout_work,
7250e840ed59ba79670b66bba8c1d50b6f67e72d3fbMark A. Greer			msecs_to_jiffies(TRF7970A_WAIT_FOR_FIFO_DRAIN_TIMEOUT));
7260e840ed59ba79670b66bba8c1d50b6f67e72d3fbMark A. Greer		return;
7270e840ed59ba79670b66bba8c1d50b6f67e72d3fbMark A. Greer	}
7280e840ed59ba79670b66bba8c1d50b6f67e72d3fbMark A. Greer
729165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	len = min(skb->len, len);
730165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
7317a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer	prefix = TRF7970A_CMD_BIT_CONTINUOUS | TRF7970A_FIFO_IO_REGISTER;
7327a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer
7337a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer	ret = trf7970a_transmit(trf, skb, len, &prefix, sizeof(prefix));
734165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (ret)
735165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		trf7970a_send_err_upstream(trf, ret);
736165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
737165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
738165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic void trf7970a_drain_fifo(struct trf7970a *trf, u8 status)
739165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
740165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	struct sk_buff *skb = trf->rx_skb;
741165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	int ret;
742165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	u8 fifo_bytes;
743165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
744165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (status & TRF7970A_IRQ_STATUS_ERROR) {
745165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		trf7970a_send_err_upstream(trf, -EIO);
746165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		return;
747165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
748165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
749165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	ret = trf7970a_read(trf, TRF7970A_FIFO_STATUS, &fifo_bytes);
750165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (ret) {
751165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		trf7970a_send_err_upstream(trf, ret);
752165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		return;
753165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
754165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
755165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_dbg(trf->dev, "Draining FIFO - fifo_bytes: 0x%x\n", fifo_bytes);
756165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
7574542e8345af6076c87d036c7bd3f9dfa30768b1eMark A. Greer	fifo_bytes &= ~TRF7970A_FIFO_STATUS_OVERFLOW;
7584542e8345af6076c87d036c7bd3f9dfa30768b1eMark A. Greer
759165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (!fifo_bytes)
760165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		goto no_rx_data;
761165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
762165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (fifo_bytes > skb_tailroom(skb)) {
763165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		skb = skb_copy_expand(skb, skb_headroom(skb),
764165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer				max_t(int, fifo_bytes,
765165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer					TRF7970A_RX_SKB_ALLOC_SIZE),
766165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer				GFP_KERNEL);
767165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		if (!skb) {
768165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			trf7970a_send_err_upstream(trf, -ENOMEM);
769165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			return;
770165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		}
771165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
772165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		kfree_skb(trf->rx_skb);
773165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		trf->rx_skb = skb;
774165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
775165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
776165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	ret = trf7970a_read_cont(trf, TRF7970A_FIFO_IO_REGISTER,
777165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			skb_put(skb, fifo_bytes), fifo_bytes);
778165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (ret) {
779165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		trf7970a_send_err_upstream(trf, ret);
780165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		return;
781165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
782165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
783165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	/* If received Type 2 ACK/NACK, shift right 4 bits and pass up */
784165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if ((trf->framing == NFC_DIGITAL_FRAMING_NFCA_T2T) && (skb->len == 1) &&
785165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			(trf->special_fcn_reg1 ==
786165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer				 TRF7970A_SPECIAL_FCN_REG1_4_BIT_RX)) {
787165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		skb->data[0] >>= 4;
788165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		status = TRF7970A_IRQ_STATUS_SRX;
789165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	} else {
790165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		trf->state = TRF7970A_ST_WAIT_FOR_RX_DATA_CONT;
7915d8f759424d3d7da998a7a9eee702071c8e5d381Mark A. Greer
7925d8f759424d3d7da998a7a9eee702071c8e5d381Mark A. Greer		ret = trf7970a_read(trf, TRF7970A_FIFO_STATUS, &fifo_bytes);
7935d8f759424d3d7da998a7a9eee702071c8e5d381Mark A. Greer		if (ret) {
7945d8f759424d3d7da998a7a9eee702071c8e5d381Mark A. Greer			trf7970a_send_err_upstream(trf, ret);
7955d8f759424d3d7da998a7a9eee702071c8e5d381Mark A. Greer			return;
7965d8f759424d3d7da998a7a9eee702071c8e5d381Mark A. Greer		}
7975d8f759424d3d7da998a7a9eee702071c8e5d381Mark A. Greer
7985d8f759424d3d7da998a7a9eee702071c8e5d381Mark A. Greer		fifo_bytes &= ~TRF7970A_FIFO_STATUS_OVERFLOW;
7995d8f759424d3d7da998a7a9eee702071c8e5d381Mark A. Greer
8005d8f759424d3d7da998a7a9eee702071c8e5d381Mark A. Greer		/* If there are bytes in the FIFO, set status to '0' so
8015d8f759424d3d7da998a7a9eee702071c8e5d381Mark A. Greer		 * the if stmt below doesn't fire and the driver will wait
8025d8f759424d3d7da998a7a9eee702071c8e5d381Mark A. Greer		 * for the trf7970a to generate another RX interrupt.
8035d8f759424d3d7da998a7a9eee702071c8e5d381Mark A. Greer		 */
8045d8f759424d3d7da998a7a9eee702071c8e5d381Mark A. Greer		if (fifo_bytes)
8055d8f759424d3d7da998a7a9eee702071c8e5d381Mark A. Greer			status = 0;
806165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
807165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
808165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerno_rx_data:
809165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (status == TRF7970A_IRQ_STATUS_SRX) { /* Receive complete */
810165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		trf7970a_send_upstream(trf);
811165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		return;
812165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
813165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
814165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_dbg(trf->dev, "Setting timeout for %d ms\n",
815165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			TRF7970A_WAIT_FOR_RX_DATA_TIMEOUT);
816165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
817165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	schedule_delayed_work(&trf->timeout_work,
818165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			msecs_to_jiffies(TRF7970A_WAIT_FOR_RX_DATA_TIMEOUT));
819165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
820165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
821165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic irqreturn_t trf7970a_irq(int irq, void *dev_id)
822165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
823165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	struct trf7970a *trf = dev_id;
824165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	int ret;
82513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	u8 status, fifo_bytes, iso_ctrl;
826165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
827165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	mutex_lock(&trf->lock);
828165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
829b5e17d9b5bd7e53696bce21e38eec5b9bb8abb88Mark A. Greer	if (trf->state == TRF7970A_ST_RF_OFF) {
830165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		mutex_unlock(&trf->lock);
831165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		return IRQ_NONE;
832165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
833165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
834165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	ret = trf7970a_read_irqstatus(trf, &status);
835165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (ret) {
836165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		mutex_unlock(&trf->lock);
837165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		return IRQ_NONE;
838165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
839165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
840165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_dbg(trf->dev, "IRQ - state: %d, status: 0x%x\n", trf->state,
841165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			status);
842165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
843165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (!status) {
844165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		mutex_unlock(&trf->lock);
845165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		return IRQ_NONE;
846165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
847165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
848165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	switch (trf->state) {
849165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	case TRF7970A_ST_IDLE:
850165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	case TRF7970A_ST_IDLE_RX_BLOCKED:
85113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		/* If initiator and getting interrupts caused by RF noise,
85213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		 * turn off the receiver to avoid unnecessary interrupts.
85313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		 * It will be turned back on in trf7970a_send_cmd() when
85413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		 * the next command is issued.
855165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		 */
85613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		if (trf->is_initiator && (status & TRF7970A_IRQ_STATUS_ERROR)) {
857165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			trf7970a_cmd(trf, TRF7970A_CMD_BLOCK_RX);
858165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			trf->state = TRF7970A_ST_IDLE_RX_BLOCKED;
859165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		}
860165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
861165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		trf7970a_cmd(trf, TRF7970A_CMD_FIFO_RESET);
862165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		break;
863165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	case TRF7970A_ST_WAIT_FOR_TX_FIFO:
864165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		if (status & TRF7970A_IRQ_STATUS_TX) {
865165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			trf->ignore_timeout =
866165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer				!cancel_delayed_work(&trf->timeout_work);
867165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			trf7970a_fill_fifo(trf);
868165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		} else {
869165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			trf7970a_send_err_upstream(trf, -EIO);
870165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		}
871165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		break;
872165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	case TRF7970A_ST_WAIT_FOR_RX_DATA:
873165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	case TRF7970A_ST_WAIT_FOR_RX_DATA_CONT:
874165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		if (status & TRF7970A_IRQ_STATUS_SRX) {
875165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			trf->ignore_timeout =
876165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer				!cancel_delayed_work(&trf->timeout_work);
877165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			trf7970a_drain_fifo(trf, status);
878bece3c544fee62ba7750f70b214d612fd02dcc8fMark A. Greer		} else if (status & TRF7970A_IRQ_STATUS_FIFO) {
879bece3c544fee62ba7750f70b214d612fd02dcc8fMark A. Greer			ret = trf7970a_read(trf, TRF7970A_FIFO_STATUS,
880bece3c544fee62ba7750f70b214d612fd02dcc8fMark A. Greer					&fifo_bytes);
881bece3c544fee62ba7750f70b214d612fd02dcc8fMark A. Greer
882bece3c544fee62ba7750f70b214d612fd02dcc8fMark A. Greer			fifo_bytes &= ~TRF7970A_FIFO_STATUS_OVERFLOW;
883bece3c544fee62ba7750f70b214d612fd02dcc8fMark A. Greer
884bece3c544fee62ba7750f70b214d612fd02dcc8fMark A. Greer			if (ret)
885bece3c544fee62ba7750f70b214d612fd02dcc8fMark A. Greer				trf7970a_send_err_upstream(trf, ret);
886bece3c544fee62ba7750f70b214d612fd02dcc8fMark A. Greer			else if (!fifo_bytes)
887bece3c544fee62ba7750f70b214d612fd02dcc8fMark A. Greer				trf7970a_cmd(trf, TRF7970A_CMD_FIFO_RESET);
88813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		} else if ((status == TRF7970A_IRQ_STATUS_TX) ||
88913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				(!trf->is_initiator &&
89013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				 (status == (TRF7970A_IRQ_STATUS_TX |
89113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer					     TRF7970A_IRQ_STATUS_NFC_RF)))) {
8924dd836e46c3ddcb2020646c867be589658440be0Mark A. Greer			trf7970a_cmd(trf, TRF7970A_CMD_FIFO_RESET);
8931961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer
8941961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer			if (!trf->timeout) {
8951961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer				trf->ignore_timeout = !cancel_delayed_work(
8961961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer						&trf->timeout_work);
8971961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer				trf->rx_skb = ERR_PTR(0);
8981961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer				trf7970a_send_upstream(trf);
8991961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer				break;
9001961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer			}
90113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
90213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			if (trf->is_initiator)
90313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				break;
90413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
90513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			iso_ctrl = trf->iso_ctrl;
90613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
90713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			switch (trf->framing) {
90813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			case NFC_DIGITAL_FRAMING_NFCA_STANDARD:
90913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				trf->tx_cmd = TRF7970A_CMD_TRANSMIT_NO_CRC;
91013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				iso_ctrl |= TRF7970A_ISO_CTRL_RX_CRC_N;
91113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				trf->iso_ctrl = 0xff; /* Force ISO_CTRL write */
91213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				break;
91313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			case NFC_DIGITAL_FRAMING_NFCA_STANDARD_WITH_CRC_A:
91413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				trf->tx_cmd = TRF7970A_CMD_TRANSMIT;
91513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				iso_ctrl &= ~TRF7970A_ISO_CTRL_RX_CRC_N;
91613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				trf->iso_ctrl = 0xff; /* Force ISO_CTRL write */
91713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				break;
91813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			case NFC_DIGITAL_FRAMING_NFCA_ANTICOL_COMPLETE:
91913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				ret = trf7970a_write(trf,
92013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer					TRF7970A_SPECIAL_FCN_REG1,
92113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer					TRF7970A_SPECIAL_FCN_REG1_14_ANTICOLL);
92213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				if (ret)
923b9e3016a5369839bf923c8d2bec9d1552e50f3f3Mark A. Greer					goto err_unlock_exit;
92413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
92513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				trf->special_fcn_reg1 =
92613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer					TRF7970A_SPECIAL_FCN_REG1_14_ANTICOLL;
92713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				break;
92813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			default:
92913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				break;
93013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			}
93113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
93213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			if (iso_ctrl != trf->iso_ctrl) {
93313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				ret = trf7970a_write(trf, TRF7970A_ISO_CTRL,
93413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer						iso_ctrl);
93513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				if (ret)
936b9e3016a5369839bf923c8d2bec9d1552e50f3f3Mark A. Greer					goto err_unlock_exit;
93713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
93813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				trf->iso_ctrl = iso_ctrl;
93913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			}
9404dd836e46c3ddcb2020646c867be589658440be0Mark A. Greer		} else {
941165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			trf7970a_send_err_upstream(trf, -EIO);
942165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		}
943165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		break;
9449d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	case TRF7970A_ST_WAIT_TO_ISSUE_EOF:
9459d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		if (status != TRF7970A_IRQ_STATUS_TX)
9469d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer			trf7970a_send_err_upstream(trf, -EIO);
9479d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		break;
94813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	case TRF7970A_ST_LISTENING:
94913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		if (status & TRF7970A_IRQ_STATUS_SRX) {
95013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			trf->ignore_timeout =
95113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				!cancel_delayed_work(&trf->timeout_work);
95213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			trf7970a_drain_fifo(trf, status);
95313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		} else if (!(status & TRF7970A_IRQ_STATUS_NFC_RF)) {
95413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			trf7970a_send_err_upstream(trf, -EIO);
95513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		}
95613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		break;
957cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	case TRF7970A_ST_LISTENING_MD:
958cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		if (status & TRF7970A_IRQ_STATUS_SRX) {
959cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer			trf->ignore_timeout =
960cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer				!cancel_delayed_work(&trf->timeout_work);
961cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
962cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer			ret = trf7970a_mode_detect(trf, &trf->md_rf_tech);
963cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer			if (ret) {
964cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer				trf7970a_send_err_upstream(trf, ret);
965cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer			} else {
966cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer				trf->state = TRF7970A_ST_LISTENING;
967cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer				trf7970a_drain_fifo(trf, status);
968cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer			}
969cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		} else if (!(status & TRF7970A_IRQ_STATUS_NFC_RF)) {
970cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer			trf7970a_send_err_upstream(trf, -EIO);
971cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		}
972cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		break;
973165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	default:
974165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_err(trf->dev, "%s - Driver in invalid state: %d\n",
975165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer				__func__, trf->state);
976165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
977165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
978b9e3016a5369839bf923c8d2bec9d1552e50f3f3Mark A. Greererr_unlock_exit:
979165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	mutex_unlock(&trf->lock);
980165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	return IRQ_HANDLED;
981165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
982165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
9839d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greerstatic void trf7970a_issue_eof(struct trf7970a *trf)
9849d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer{
9859d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	int ret;
9869d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer
9879d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	dev_dbg(trf->dev, "Issuing EOF\n");
9889d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer
9899d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	ret = trf7970a_cmd(trf, TRF7970A_CMD_FIFO_RESET);
9909d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	if (ret)
9919d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		trf7970a_send_err_upstream(trf, ret);
9929d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer
9939d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	ret = trf7970a_cmd(trf, TRF7970A_CMD_EOF);
9949d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	if (ret)
9959d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		trf7970a_send_err_upstream(trf, ret);
9969d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer
9979d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	trf->state = TRF7970A_ST_WAIT_FOR_RX_DATA;
9989d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer
9999d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	dev_dbg(trf->dev, "Setting timeout for %d ms, state: %d\n",
10009d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer			trf->timeout, trf->state);
10019d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer
10029d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	schedule_delayed_work(&trf->timeout_work,
10039d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer			msecs_to_jiffies(trf->timeout));
10049d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer}
10059d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer
1006165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic void trf7970a_timeout_work_handler(struct work_struct *work)
1007165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
1008165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	struct trf7970a *trf = container_of(work, struct trf7970a,
1009165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			timeout_work.work);
1010165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1011165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_dbg(trf->dev, "Timeout - state: %d, ignore_timeout: %d\n",
1012165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			trf->state, trf->ignore_timeout);
1013165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1014165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	mutex_lock(&trf->lock);
1015165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1016165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (trf->ignore_timeout)
1017165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		trf->ignore_timeout = false;
1018165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	else if (trf->state == TRF7970A_ST_WAIT_FOR_RX_DATA_CONT)
1019afa5b5f13e0e2372e440f3ab44620d4e10fca496Mark A. Greer		trf7970a_drain_fifo(trf, TRF7970A_IRQ_STATUS_SRX);
10209d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	else if (trf->state == TRF7970A_ST_WAIT_TO_ISSUE_EOF)
10219d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		trf7970a_issue_eof(trf);
1022165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	else
1023165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		trf7970a_send_err_upstream(trf, -ETIMEDOUT);
1024165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1025165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	mutex_unlock(&trf->lock);
1026165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
1027165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1028165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_init(struct trf7970a *trf)
1029165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
1030165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	int ret;
1031165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1032165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_dbg(trf->dev, "Initializing device - state: %d\n", trf->state);
1033165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1034165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	ret = trf7970a_cmd(trf, TRF7970A_CMD_SOFT_INIT);
1035165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (ret)
1036165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		goto err_out;
1037165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1038165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	ret = trf7970a_cmd(trf, TRF7970A_CMD_IDLE);
1039165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (ret)
1040165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		goto err_out;
1041165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
10424e007f810664541078e619d050f6290bf137aa61Mark A. Greer	usleep_range(1000, 2000);
10434e007f810664541078e619d050f6290bf137aa61Mark A. Greer
10447149d6bfecadc255e9d964782a9fdd70f610f1eaMark A. Greer	trf->chip_status_ctrl &= ~TRF7970A_CHIP_STATUS_RF_ON;
10457149d6bfecadc255e9d964782a9fdd70f610f1eaMark A. Greer
10466c08df422ede7db94776b8099a5f43597629234cMark A. Greer	ret = trf7970a_write(trf, TRF7970A_MODULATOR_SYS_CLK_CTRL, 0);
10476c08df422ede7db94776b8099a5f43597629234cMark A. Greer	if (ret)
10486c08df422ede7db94776b8099a5f43597629234cMark A. Greer		goto err_out;
10496c08df422ede7db94776b8099a5f43597629234cMark A. Greer
10506c08df422ede7db94776b8099a5f43597629234cMark A. Greer	trf->modulator_sys_clk_ctrl = 0;
10516c08df422ede7db94776b8099a5f43597629234cMark A. Greer
1052165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	ret = trf7970a_write(trf, TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS,
1053165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS_WLH_96 |
1054165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS_WLL_32);
1055165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (ret)
1056165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		goto err_out;
1057165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1058165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	ret = trf7970a_write(trf, TRF7970A_SPECIAL_FCN_REG1, 0);
1059165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (ret)
1060165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		goto err_out;
1061165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1062165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf->special_fcn_reg1 = 0;
1063165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
106449d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer	trf->iso_ctrl = 0xff;
1065165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	return 0;
1066165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1067165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greererr_out:
1068165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_dbg(trf->dev, "Couldn't init device: %d\n", ret);
1069165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	return ret;
1070165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
1071165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1072165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic void trf7970a_switch_rf_off(struct trf7970a *trf)
1073165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
1074cfc708dbe4022324bcd2bcb5817dd29f1f91299dMark A. Greer	if ((trf->state == TRF7970A_ST_PWR_OFF) ||
1075cfc708dbe4022324bcd2bcb5817dd29f1f91299dMark A. Greer			(trf->state == TRF7970A_ST_RF_OFF))
1076cfc708dbe4022324bcd2bcb5817dd29f1f91299dMark A. Greer		return;
1077cfc708dbe4022324bcd2bcb5817dd29f1f91299dMark A. Greer
1078165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_dbg(trf->dev, "Switching rf off\n");
1079165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1080a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer	trf->chip_status_ctrl &= ~TRF7970A_CHIP_STATUS_RF_ON;
1081a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer
1082a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer	trf7970a_write(trf, TRF7970A_CHIP_STATUS_CTRL, trf->chip_status_ctrl);
1083a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer
1084165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf->aborting = false;
1085b5e17d9b5bd7e53696bce21e38eec5b9bb8abb88Mark A. Greer	trf->state = TRF7970A_ST_RF_OFF;
1086e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer
1087e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer	pm_runtime_mark_last_busy(trf->dev);
1088e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer	pm_runtime_put_autosuspend(trf->dev);
1089165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
1090165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
10910a1de84205d3fe7baa3d013ebf703416b1919eccMark A. Greerstatic int trf7970a_switch_rf_on(struct trf7970a *trf)
1092165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
1093a08e54549e743ea3704da939f92caf3eaa8471d3Mark A. Greer	int ret;
1094a08e54549e743ea3704da939f92caf3eaa8471d3Mark A. Greer
1095165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_dbg(trf->dev, "Switching rf on\n");
1096165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1097e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer	pm_runtime_get_sync(trf->dev);
1098165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1099ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	if (trf->state != TRF7970A_ST_RF_OFF) { /* Power on, RF off */
1100ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer		dev_err(trf->dev, "%s - Incorrect state: %d\n", __func__,
1101ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer				trf->state);
1102ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer		return -EINVAL;
1103ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	}
1104ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
1105a08e54549e743ea3704da939f92caf3eaa8471d3Mark A. Greer	ret = trf7970a_init(trf);
1106a08e54549e743ea3704da939f92caf3eaa8471d3Mark A. Greer	if (ret) {
1107a08e54549e743ea3704da939f92caf3eaa8471d3Mark A. Greer		dev_err(trf->dev, "%s - Can't initialize: %d\n", __func__, ret);
11080a1de84205d3fe7baa3d013ebf703416b1919eccMark A. Greer		return ret;
1109a08e54549e743ea3704da939f92caf3eaa8471d3Mark A. Greer	}
1110a08e54549e743ea3704da939f92caf3eaa8471d3Mark A. Greer
1111e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer	trf->state = TRF7970A_ST_IDLE;
11120a1de84205d3fe7baa3d013ebf703416b1919eccMark A. Greer
11130a1de84205d3fe7baa3d013ebf703416b1919eccMark A. Greer	return 0;
1114165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
1115165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1116165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_switch_rf(struct nfc_digital_dev *ddev, bool on)
1117165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
1118165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	struct trf7970a *trf = nfc_digital_get_drvdata(ddev);
11190a1de84205d3fe7baa3d013ebf703416b1919eccMark A. Greer	int ret = 0;
1120165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1121165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_dbg(trf->dev, "Switching RF - state: %d, on: %d\n", trf->state, on);
1122165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1123165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	mutex_lock(&trf->lock);
1124165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1125165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (on) {
1126165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		switch (trf->state) {
1127ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer		case TRF7970A_ST_PWR_OFF:
1128b5e17d9b5bd7e53696bce21e38eec5b9bb8abb88Mark A. Greer		case TRF7970A_ST_RF_OFF:
11290a1de84205d3fe7baa3d013ebf703416b1919eccMark A. Greer			ret = trf7970a_switch_rf_on(trf);
1130165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			break;
1131165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		case TRF7970A_ST_IDLE:
1132165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		case TRF7970A_ST_IDLE_RX_BLOCKED:
1133165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			break;
1134165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		default:
1135165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			dev_err(trf->dev, "%s - Invalid request: %d %d\n",
1136165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer					__func__, trf->state, on);
1137165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			trf7970a_switch_rf_off(trf);
11380a1de84205d3fe7baa3d013ebf703416b1919eccMark A. Greer			ret = -EINVAL;
1139165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		}
1140165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	} else {
1141165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		switch (trf->state) {
1142ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer		case TRF7970A_ST_PWR_OFF:
1143b5e17d9b5bd7e53696bce21e38eec5b9bb8abb88Mark A. Greer		case TRF7970A_ST_RF_OFF:
1144165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			break;
1145165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		default:
1146165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			dev_err(trf->dev, "%s - Invalid request: %d %d\n",
1147165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer					__func__, trf->state, on);
11480a1de84205d3fe7baa3d013ebf703416b1919eccMark A. Greer			ret = -EINVAL;
1149165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			/* FALLTHROUGH */
1150165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		case TRF7970A_ST_IDLE:
1151165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		case TRF7970A_ST_IDLE_RX_BLOCKED:
115213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		case TRF7970A_ST_WAIT_FOR_RX_DATA:
115313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		case TRF7970A_ST_WAIT_FOR_RX_DATA_CONT:
1154165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			trf7970a_switch_rf_off(trf);
1155165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		}
1156165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
1157165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1158165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	mutex_unlock(&trf->lock);
11590a1de84205d3fe7baa3d013ebf703416b1919eccMark A. Greer	return ret;
1160165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
1161165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1162307e5caf6fb1dac1b9cfa1d78138d77e46517b56Mark A. Greerstatic int trf7970a_in_config_rf_tech(struct trf7970a *trf, int tech)
1163165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
1164165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	int ret = 0;
1165165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1166165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_dbg(trf->dev, "rf technology: %d\n", tech);
1167165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1168165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	switch (tech) {
1169165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	case NFC_DIGITAL_RF_TECH_106A:
117049d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer		trf->iso_ctrl_tech = TRF7970A_ISO_CTRL_14443A_106;
117112e9ade309db51e7ea26be3b4fd5bc6057ddc175Mark A. Greer		trf->modulator_sys_clk_ctrl = TRF7970A_MODULATOR_DEPTH_OOK;
11724e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer		trf->guard_time = TRF7970A_GUARD_TIME_NFCA;
1173165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		break;
1174742b1f9fa292a1b8f5c8368464e114c9b71c2a81Mark A. Greer	case NFC_DIGITAL_RF_TECH_106B:
1175742b1f9fa292a1b8f5c8368464e114c9b71c2a81Mark A. Greer		trf->iso_ctrl_tech = TRF7970A_ISO_CTRL_14443B_106;
1176742b1f9fa292a1b8f5c8368464e114c9b71c2a81Mark A. Greer		trf->modulator_sys_clk_ctrl = TRF7970A_MODULATOR_DEPTH_ASK10;
11774e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer		trf->guard_time = TRF7970A_GUARD_TIME_NFCB;
1178742b1f9fa292a1b8f5c8368464e114c9b71c2a81Mark A. Greer		break;
11796857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer	case NFC_DIGITAL_RF_TECH_212F:
11806857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer		trf->iso_ctrl_tech = TRF7970A_ISO_CTRL_FELICA_212;
11816857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer		trf->modulator_sys_clk_ctrl = TRF7970A_MODULATOR_DEPTH_ASK10;
11824e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer		trf->guard_time = TRF7970A_GUARD_TIME_NFCF;
11836857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer		break;
11846857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer	case NFC_DIGITAL_RF_TECH_424F:
11856857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer		trf->iso_ctrl_tech = TRF7970A_ISO_CTRL_FELICA_424;
11866857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer		trf->modulator_sys_clk_ctrl = TRF7970A_MODULATOR_DEPTH_ASK10;
11874e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer		trf->guard_time = TRF7970A_GUARD_TIME_NFCF;
11886857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer		break;
11899d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	case NFC_DIGITAL_RF_TECH_ISO15693:
119049d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer		trf->iso_ctrl_tech = TRF7970A_ISO_CTRL_15693_SGL_1OF4_2648;
119112e9ade309db51e7ea26be3b4fd5bc6057ddc175Mark A. Greer		trf->modulator_sys_clk_ctrl = TRF7970A_MODULATOR_DEPTH_OOK;
11924e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer		trf->guard_time = TRF7970A_GUARD_TIME_15693;
11939d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		break;
1194165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	default:
1195165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_dbg(trf->dev, "Unsupported rf technology: %d\n", tech);
1196165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		return -EINVAL;
1197165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
1198165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1199165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf->technology = tech;
1200165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
120113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	/* If in initiator mode and not changing the RF tech due to a
120213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	 * PSL sequence (indicated by 'trf->iso_ctrl == 0xff' from
120313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	 * trf7970a_init()), clear the NFC Target Detection Level register
120413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	 * due to erratum.
120513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	 */
120613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	if (trf->iso_ctrl == 0xff)
120713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		ret = trf7970a_write(trf, TRF7970A_NFC_TARGET_LEVEL, 0);
120813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
1209165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	return ret;
1210165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
1211165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1212851ee3cbf850501104e76683e439a4061f378a96Mark A. Greerstatic int trf7970a_is_rf_field(struct trf7970a *trf, bool *is_rf_field)
1213851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer{
1214851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer	int ret;
1215851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer	u8 rssi;
1216851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer
1217851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer	ret = trf7970a_write(trf, TRF7970A_CHIP_STATUS_CTRL,
1218851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer			trf->chip_status_ctrl | TRF7970A_CHIP_STATUS_REC_ON);
1219851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer	if (ret)
1220851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer		return ret;
1221851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer
1222851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer	ret = trf7970a_cmd(trf, TRF7970A_CMD_TEST_EXT_RF);
1223851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer	if (ret)
1224851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer		return ret;
1225851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer
1226851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer	usleep_range(50, 60);
1227851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer
1228851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer	ret = trf7970a_read(trf, TRF7970A_RSSI_OSC_STATUS, &rssi);
1229851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer	if (ret)
1230851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer		return ret;
1231851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer
1232851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer	ret = trf7970a_write(trf, TRF7970A_CHIP_STATUS_CTRL,
1233851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer			trf->chip_status_ctrl);
1234851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer	if (ret)
1235851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer		return ret;
1236851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer
1237851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer	if (rssi & TRF7970A_RSSI_OSC_STATUS_RSSI_MASK)
1238851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer		*is_rf_field = true;
1239851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer	else
1240851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer		*is_rf_field = false;
1241851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer
1242851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer	return 0;
1243851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer}
1244851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer
1245307e5caf6fb1dac1b9cfa1d78138d77e46517b56Mark A. Greerstatic int trf7970a_in_config_framing(struct trf7970a *trf, int framing)
1246165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
124749d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer	u8 iso_ctrl = trf->iso_ctrl_tech;
1248851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer	bool is_rf_field = false;
124949d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer	int ret;
125049d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer
1251165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_dbg(trf->dev, "framing: %d\n", framing);
1252165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1253165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	switch (framing) {
1254165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	case NFC_DIGITAL_FRAMING_NFCA_SHORT:
1255165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	case NFC_DIGITAL_FRAMING_NFCA_STANDARD:
1256165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		trf->tx_cmd = TRF7970A_CMD_TRANSMIT_NO_CRC;
125749d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer		iso_ctrl |= TRF7970A_ISO_CTRL_RX_CRC_N;
1258165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		break;
1259165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	case NFC_DIGITAL_FRAMING_NFCA_STANDARD_WITH_CRC_A:
12608006289108fa9635d16a65d9db16da06d7dce201Mark A. Greer	case NFC_DIGITAL_FRAMING_NFCA_T4T:
1261742b1f9fa292a1b8f5c8368464e114c9b71c2a81Mark A. Greer	case NFC_DIGITAL_FRAMING_NFCB:
1262742b1f9fa292a1b8f5c8368464e114c9b71c2a81Mark A. Greer	case NFC_DIGITAL_FRAMING_NFCB_T4T:
12636857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer	case NFC_DIGITAL_FRAMING_NFCF:
12646857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer	case NFC_DIGITAL_FRAMING_NFCF_T3T:
12659d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	case NFC_DIGITAL_FRAMING_ISO15693_INVENTORY:
12669d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	case NFC_DIGITAL_FRAMING_ISO15693_T5T:
126713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	case NFC_DIGITAL_FRAMING_NFCA_NFC_DEP:
126813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	case NFC_DIGITAL_FRAMING_NFCF_NFC_DEP:
1269165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		trf->tx_cmd = TRF7970A_CMD_TRANSMIT;
127049d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer		iso_ctrl &= ~TRF7970A_ISO_CTRL_RX_CRC_N;
1271165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		break;
1272165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	case NFC_DIGITAL_FRAMING_NFCA_T2T:
1273165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		trf->tx_cmd = TRF7970A_CMD_TRANSMIT;
127449d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer		iso_ctrl |= TRF7970A_ISO_CTRL_RX_CRC_N;
1275165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		break;
1276165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	default:
1277165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_dbg(trf->dev, "Unsupported Framing: %d\n", framing);
1278165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		return -EINVAL;
1279165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
1280165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1281165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf->framing = framing;
1282165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1283851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer	if (!(trf->chip_status_ctrl & TRF7970A_CHIP_STATUS_RF_ON)) {
1284851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer		ret = trf7970a_is_rf_field(trf, &is_rf_field);
1285851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer		if (ret)
1286851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer			return ret;
1287851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer
1288851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer		if (is_rf_field)
1289851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer			return -EBUSY;
1290851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer	}
1291851ee3cbf850501104e76683e439a4061f378a96Mark A. Greer
129249d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer	if (iso_ctrl != trf->iso_ctrl) {
129349d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer		ret = trf7970a_write(trf, TRF7970A_ISO_CTRL, iso_ctrl);
129449d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer		if (ret)
129549d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer			return ret;
129649d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer
129749d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer		trf->iso_ctrl = iso_ctrl;
1298a0822a7e3b7333689b1c8cb92782e299791c2795Mark A. Greer
1299a0822a7e3b7333689b1c8cb92782e299791c2795Mark A. Greer		ret = trf7970a_write(trf, TRF7970A_MODULATOR_SYS_CLK_CTRL,
130012e9ade309db51e7ea26be3b4fd5bc6057ddc175Mark A. Greer				trf->modulator_sys_clk_ctrl);
1301a0822a7e3b7333689b1c8cb92782e299791c2795Mark A. Greer		if (ret)
1302a0822a7e3b7333689b1c8cb92782e299791c2795Mark A. Greer			return ret;
130349d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer	}
130449d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer
1305a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer	if (!(trf->chip_status_ctrl & TRF7970A_CHIP_STATUS_RF_ON)) {
1306a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer		ret = trf7970a_write(trf, TRF7970A_CHIP_STATUS_CTRL,
1307a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer				trf->chip_status_ctrl |
1308a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer					TRF7970A_CHIP_STATUS_RF_ON);
1309a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer		if (ret)
1310a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer			return ret;
1311a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer
1312a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer		trf->chip_status_ctrl |= TRF7970A_CHIP_STATUS_RF_ON;
1313a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer
13144e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer		usleep_range(trf->guard_time, trf->guard_time + 1000);
1315a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer	}
1316a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer
131749d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer	return 0;
1318165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
1319165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1320165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_in_configure_hw(struct nfc_digital_dev *ddev, int type,
1321165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		int param)
1322165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
1323165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	struct trf7970a *trf = nfc_digital_get_drvdata(ddev);
132418422e686ef043b9abe004326ac9ffa1e38b81ecMark A. Greer	int ret;
1325165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1326165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_dbg(trf->dev, "Configure hw - type: %d, param: %d\n", type, param);
1327165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1328165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	mutex_lock(&trf->lock);
1329165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
133013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	trf->is_initiator = true;
133113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
1332ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	if ((trf->state == TRF7970A_ST_PWR_OFF) ||
1333ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer			(trf->state == TRF7970A_ST_RF_OFF)) {
13340a1de84205d3fe7baa3d013ebf703416b1919eccMark A. Greer		ret = trf7970a_switch_rf_on(trf);
13350a1de84205d3fe7baa3d013ebf703416b1919eccMark A. Greer		if (ret)
13360a1de84205d3fe7baa3d013ebf703416b1919eccMark A. Greer			goto err_unlock;
13370a1de84205d3fe7baa3d013ebf703416b1919eccMark A. Greer	}
1338165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1339165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	switch (type) {
1340165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	case NFC_DIGITAL_CONFIG_RF_TECH:
1341307e5caf6fb1dac1b9cfa1d78138d77e46517b56Mark A. Greer		ret = trf7970a_in_config_rf_tech(trf, param);
1342165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		break;
1343165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	case NFC_DIGITAL_CONFIG_FRAMING:
1344307e5caf6fb1dac1b9cfa1d78138d77e46517b56Mark A. Greer		ret = trf7970a_in_config_framing(trf, param);
1345165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		break;
1346165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	default:
1347165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_dbg(trf->dev, "Unknown type: %d\n", type);
1348165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		ret = -EINVAL;
1349165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
1350165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
13510a1de84205d3fe7baa3d013ebf703416b1919eccMark A. Greererr_unlock:
1352165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	mutex_unlock(&trf->lock);
1353165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	return ret;
1354165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
1355165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
13569d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greerstatic int trf7970a_is_iso15693_write_or_lock(u8 cmd)
13579d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer{
13589d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	switch (cmd) {
13599d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	case ISO15693_CMD_WRITE_SINGLE_BLOCK:
13609d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	case ISO15693_CMD_LOCK_BLOCK:
13619d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	case ISO15693_CMD_WRITE_MULTIPLE_BLOCK:
13629d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	case ISO15693_CMD_WRITE_AFI:
13639d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	case ISO15693_CMD_LOCK_AFI:
13649d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	case ISO15693_CMD_WRITE_DSFID:
13659d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	case ISO15693_CMD_LOCK_DSFID:
13669d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		return 1;
13679d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		break;
13689d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	default:
13699d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		return 0;
13709d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	}
13719d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer}
13729d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer
1373165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_per_cmd_config(struct trf7970a *trf, struct sk_buff *skb)
1374165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
1375165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	u8 *req = skb->data;
13769d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	u8 special_fcn_reg1, iso_ctrl;
1377165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	int ret;
1378165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
13799d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	trf->issue_eof = false;
13809d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer
1381165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	/* When issuing Type 2 read command, make sure the '4_bit_RX' bit in
1382165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	 * special functions register 1 is cleared; otherwise, its a write or
1383165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	 * sector select command and '4_bit_RX' must be set.
13849d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	 *
13859d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	 * When issuing an ISO 15693 command, inspect the flags byte to see
13869d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	 * what speed to use.  Also, remember if the OPTION flag is set on
13879d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	 * a Type 5 write or lock command so the driver will know that it
13889d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	 * has to send an EOF in order to get a response.
1389165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	 */
1390165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if ((trf->technology == NFC_DIGITAL_RF_TECH_106A) &&
1391165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			(trf->framing == NFC_DIGITAL_FRAMING_NFCA_T2T)) {
1392165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		if (req[0] == NFC_T2T_CMD_READ)
1393165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			special_fcn_reg1 = 0;
1394165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		else
1395165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			special_fcn_reg1 = TRF7970A_SPECIAL_FCN_REG1_4_BIT_RX;
1396165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1397165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		if (special_fcn_reg1 != trf->special_fcn_reg1) {
1398165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			ret = trf7970a_write(trf, TRF7970A_SPECIAL_FCN_REG1,
1399165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer					special_fcn_reg1);
1400165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			if (ret)
1401165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer				return ret;
1402165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1403165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			trf->special_fcn_reg1 = special_fcn_reg1;
1404165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		}
14059d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer	} else if (trf->technology == NFC_DIGITAL_RF_TECH_ISO15693) {
14069d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		iso_ctrl = trf->iso_ctrl & ~TRF7970A_ISO_CTRL_RFID_SPEED_MASK;
14079d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer
14089d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		switch (req[0] & ISO15693_REQ_FLAG_SPEED_MASK) {
14099d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		case 0x00:
14109d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer			iso_ctrl |= TRF7970A_ISO_CTRL_15693_SGL_1OF4_662;
14119d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer			break;
14129d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		case ISO15693_REQ_FLAG_SUB_CARRIER:
14139d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer			iso_ctrl |= TRF7970A_ISO_CTRL_15693_DBL_1OF4_667a;
14149d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer			break;
14159d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		case ISO15693_REQ_FLAG_DATA_RATE:
14169d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer			iso_ctrl |= TRF7970A_ISO_CTRL_15693_SGL_1OF4_2648;
14179d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer			break;
14189d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		case (ISO15693_REQ_FLAG_SUB_CARRIER |
14199d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer				ISO15693_REQ_FLAG_DATA_RATE):
14209d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer			iso_ctrl |= TRF7970A_ISO_CTRL_15693_DBL_1OF4_2669;
14219d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer			break;
14229d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		}
14239d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer
14249d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		if (iso_ctrl != trf->iso_ctrl) {
14259d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer			ret = trf7970a_write(trf, TRF7970A_ISO_CTRL, iso_ctrl);
14269d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer			if (ret)
14279d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer				return ret;
14289d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer
14299d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer			trf->iso_ctrl = iso_ctrl;
14309d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		}
14319d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer
14329d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer		if ((trf->framing == NFC_DIGITAL_FRAMING_ISO15693_T5T) &&
14339d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer				trf7970a_is_iso15693_write_or_lock(req[1]) &&
14349d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer				(req[0] & ISO15693_REQ_FLAG_OPTION))
14359d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer			trf->issue_eof = true;
1436165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
1437165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1438165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	return 0;
1439165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
1440165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
144113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greerstatic int trf7970a_send_cmd(struct nfc_digital_dev *ddev,
1442165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		struct sk_buff *skb, u16 timeout,
1443165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		nfc_digital_cmd_complete_t cb, void *arg)
1444165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
1445165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	struct trf7970a *trf = nfc_digital_get_drvdata(ddev);
14467a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer	u8 prefix[5];
1447165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	unsigned int len;
1448165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	int ret;
1449aff0564aa7b2118a1d76dc0118dfdbf4beaf4b8cMark A. Greer	u8 status;
1450165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1451165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_dbg(trf->dev, "New request - state: %d, timeout: %d ms, len: %d\n",
1452165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			trf->state, timeout, skb->len);
1453165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1454165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (skb->len > TRF7970A_TX_MAX)
1455165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		return -EINVAL;
1456165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1457165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	mutex_lock(&trf->lock);
1458165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1459165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if ((trf->state != TRF7970A_ST_IDLE) &&
1460165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			(trf->state != TRF7970A_ST_IDLE_RX_BLOCKED)) {
1461165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_err(trf->dev, "%s - Bogus state: %d\n", __func__,
1462165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer				trf->state);
1463165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		ret = -EIO;
1464165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		goto out_err;
1465165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
1466165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1467165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (trf->aborting) {
1468165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_dbg(trf->dev, "Abort process complete\n");
1469165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		trf->aborting = false;
1470165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		ret = -ECANCELED;
1471165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		goto out_err;
1472165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
1473165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
14741961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer	if (timeout) {
14751961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer		trf->rx_skb = nfc_alloc_recv_skb(TRF7970A_RX_SKB_ALLOC_SIZE,
14761961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer				GFP_KERNEL);
14771961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer		if (!trf->rx_skb) {
14781961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer			dev_dbg(trf->dev, "Can't alloc rx_skb\n");
14791961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer			ret = -ENOMEM;
14801961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer			goto out_err;
14811961843ceeca0d3e55744bba7ae8d9e23d04cf6aMark A. Greer		}
1482165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
1483165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1484165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (trf->state == TRF7970A_ST_IDLE_RX_BLOCKED) {
1485165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		ret = trf7970a_cmd(trf, TRF7970A_CMD_ENABLE_RX);
1486165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		if (ret)
1487165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			goto out_err;
1488165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1489165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		trf->state = TRF7970A_ST_IDLE;
1490165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
1491165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
149213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	if (trf->is_initiator) {
149313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		ret = trf7970a_per_cmd_config(trf, skb);
149413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		if (ret)
149513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			goto out_err;
149613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	}
1497165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1498165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf->ddev = ddev;
1499165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf->tx_skb = skb;
1500165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf->cb = cb;
1501165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf->cb_arg = arg;
1502165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf->timeout = timeout;
1503165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf->ignore_timeout = false;
1504165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1505165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	len = skb->len;
1506165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1507165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	/* TX data must be prefixed with a FIFO reset cmd, a cmd that depends
1508165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	 * on what the current framing is, the address of the TX length byte 1
1509165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	 * register (0x1d), and the 2 byte length of the data to be transmitted.
15107a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer	 * That totals 5 bytes.
1511165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	 */
1512165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	prefix[0] = TRF7970A_CMD_BIT_CTRL |
1513165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			TRF7970A_CMD_BIT_OPCODE(TRF7970A_CMD_FIFO_RESET);
1514165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	prefix[1] = TRF7970A_CMD_BIT_CTRL |
1515165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			TRF7970A_CMD_BIT_OPCODE(trf->tx_cmd);
1516165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	prefix[2] = TRF7970A_CMD_BIT_CONTINUOUS | TRF7970A_TX_LENGTH_BYTE1;
1517165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1518165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (trf->framing == NFC_DIGITAL_FRAMING_NFCA_SHORT) {
1519165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		prefix[3] = 0x00;
1520165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		prefix[4] = 0x0f; /* 7 bits */
1521165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	} else {
1522165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		prefix[3] = (len & 0xf00) >> 4;
1523165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		prefix[3] |= ((len & 0xf0) >> 4);
1524165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		prefix[4] = ((len & 0x0f) << 4);
1525165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
1526165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1527165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	len = min_t(int, skb->len, TRF7970A_FIFO_SIZE);
1528165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1529aff0564aa7b2118a1d76dc0118dfdbf4beaf4b8cMark A. Greer	/* Clear possible spurious interrupt */
1530aff0564aa7b2118a1d76dc0118dfdbf4beaf4b8cMark A. Greer	ret = trf7970a_read_irqstatus(trf, &status);
1531aff0564aa7b2118a1d76dc0118dfdbf4beaf4b8cMark A. Greer	if (ret)
1532aff0564aa7b2118a1d76dc0118dfdbf4beaf4b8cMark A. Greer		goto out_err;
1533aff0564aa7b2118a1d76dc0118dfdbf4beaf4b8cMark A. Greer
15347a1e5552af61dce180f70c6fafe31553254b3728Mark A. Greer	ret = trf7970a_transmit(trf, skb, len, prefix, sizeof(prefix));
1535165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (ret) {
1536165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		kfree_skb(trf->rx_skb);
1537165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		trf->rx_skb = NULL;
1538165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
1539165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1540165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerout_err:
1541165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	mutex_unlock(&trf->lock);
1542165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	return ret;
1543165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
1544165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
154513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greerstatic int trf7970a_tg_config_rf_tech(struct trf7970a *trf, int tech)
1546165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
154713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	int ret = 0;
154813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
154913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	dev_dbg(trf->dev, "rf technology: %d\n", tech);
155013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
155113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	switch (tech) {
155213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	case NFC_DIGITAL_RF_TECH_106A:
155313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		trf->iso_ctrl_tech = TRF7970A_ISO_CTRL_NFC_NFC_CE_MODE |
155413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			TRF7970A_ISO_CTRL_NFC_CE |
155513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			TRF7970A_ISO_CTRL_NFC_CE_14443A;
155613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		trf->modulator_sys_clk_ctrl = TRF7970A_MODULATOR_DEPTH_OOK;
155713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		break;
155813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	case NFC_DIGITAL_RF_TECH_212F:
155913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		trf->iso_ctrl_tech = TRF7970A_ISO_CTRL_NFC_NFC_CE_MODE |
156013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			TRF7970A_ISO_CTRL_NFC_NFCF_212;
156113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		trf->modulator_sys_clk_ctrl = TRF7970A_MODULATOR_DEPTH_ASK10;
156213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		break;
156313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	case NFC_DIGITAL_RF_TECH_424F:
156413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		trf->iso_ctrl_tech = TRF7970A_ISO_CTRL_NFC_NFC_CE_MODE |
156513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			TRF7970A_ISO_CTRL_NFC_NFCF_424;
156613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		trf->modulator_sys_clk_ctrl = TRF7970A_MODULATOR_DEPTH_ASK10;
156713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		break;
156813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	default:
156913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		dev_dbg(trf->dev, "Unsupported rf technology: %d\n", tech);
157013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		return -EINVAL;
157113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	}
157213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
157313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	trf->technology = tech;
1574165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
157513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	/* Normally we write the ISO_CTRL register in
157613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	 * trf7970a_tg_config_framing() because the framing can change
157713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	 * the value written.  However, when sending a PSL RES,
157813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	 * digital_tg_send_psl_res_complete() doesn't call
157913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	 * trf7970a_tg_config_framing() so we must write the register
158013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	 * here.
158113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	 */
158213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	if ((trf->framing == NFC_DIGITAL_FRAMING_NFC_DEP_ACTIVATED) &&
158313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			(trf->iso_ctrl_tech != trf->iso_ctrl)) {
158413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		ret = trf7970a_write(trf, TRF7970A_ISO_CTRL,
158513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				trf->iso_ctrl_tech);
158613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
158713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		trf->iso_ctrl = trf->iso_ctrl_tech;
158813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	}
1589165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
159013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	return ret;
1591165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
1592165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
159313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer/* Since this is a target routine, several of the framing calls are
159413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer * made between receiving the request and sending the response so they
159513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer * should take effect until after the response is sent.  This is accomplished
159613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer * by skipping the ISO_CTRL register write here and doing it in the interrupt
159713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer * handler.
159813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer */
159913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greerstatic int trf7970a_tg_config_framing(struct trf7970a *trf, int framing)
160013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer{
160113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	u8 iso_ctrl = trf->iso_ctrl_tech;
160213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	int ret;
160313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
160413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	dev_dbg(trf->dev, "framing: %d\n", framing);
160513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
160613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	switch (framing) {
160713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	case NFC_DIGITAL_FRAMING_NFCA_NFC_DEP:
160813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		trf->tx_cmd = TRF7970A_CMD_TRANSMIT_NO_CRC;
160913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		iso_ctrl |= TRF7970A_ISO_CTRL_RX_CRC_N;
161013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		break;
161113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	case NFC_DIGITAL_FRAMING_NFCA_STANDARD:
161213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	case NFC_DIGITAL_FRAMING_NFCA_STANDARD_WITH_CRC_A:
161313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	case NFC_DIGITAL_FRAMING_NFCA_ANTICOL_COMPLETE:
161413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		/* These ones are applied in the interrupt handler */
161513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		iso_ctrl = trf->iso_ctrl; /* Don't write to ISO_CTRL yet */
161613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		break;
161713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	case NFC_DIGITAL_FRAMING_NFCF_NFC_DEP:
161813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		trf->tx_cmd = TRF7970A_CMD_TRANSMIT;
161913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		iso_ctrl &= ~TRF7970A_ISO_CTRL_RX_CRC_N;
162013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		break;
162113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	case NFC_DIGITAL_FRAMING_NFC_DEP_ACTIVATED:
162213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		trf->tx_cmd = TRF7970A_CMD_TRANSMIT;
162313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		iso_ctrl &= ~TRF7970A_ISO_CTRL_RX_CRC_N;
162413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		break;
162513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	default:
162613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		dev_dbg(trf->dev, "Unsupported Framing: %d\n", framing);
162713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		return -EINVAL;
162813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	}
162913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
163013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	trf->framing = framing;
163113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
163213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	if (iso_ctrl != trf->iso_ctrl) {
163313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		ret = trf7970a_write(trf, TRF7970A_ISO_CTRL, iso_ctrl);
163413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		if (ret)
163513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			return ret;
163613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
163713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		trf->iso_ctrl = iso_ctrl;
163813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
163913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		ret = trf7970a_write(trf, TRF7970A_MODULATOR_SYS_CLK_CTRL,
164013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				trf->modulator_sys_clk_ctrl);
164113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		if (ret)
164213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			return ret;
164313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	}
164413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
164513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	if (!(trf->chip_status_ctrl & TRF7970A_CHIP_STATUS_RF_ON)) {
164613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		ret = trf7970a_write(trf, TRF7970A_CHIP_STATUS_CTRL,
164713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				trf->chip_status_ctrl |
164813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer					TRF7970A_CHIP_STATUS_RF_ON);
164913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		if (ret)
165013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			return ret;
165113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
165213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		trf->chip_status_ctrl |= TRF7970A_CHIP_STATUS_RF_ON;
165313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	}
165413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
165513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	return 0;
165613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer}
165713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
165813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greerstatic int trf7970a_tg_configure_hw(struct nfc_digital_dev *ddev, int type,
165913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		int param)
1660165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
1661165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	struct trf7970a *trf = nfc_digital_get_drvdata(ddev);
166213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	int ret;
166313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
166413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	dev_dbg(trf->dev, "Configure hw - type: %d, param: %d\n", type, param);
166513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
166613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	mutex_lock(&trf->lock);
166713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
166813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	trf->is_initiator = false;
1669165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
167013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	if ((trf->state == TRF7970A_ST_PWR_OFF) ||
167113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			(trf->state == TRF7970A_ST_RF_OFF)) {
167213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		ret = trf7970a_switch_rf_on(trf);
167313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		if (ret)
167413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			goto err_unlock;
167513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	}
167613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
167713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	switch (type) {
167813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	case NFC_DIGITAL_CONFIG_RF_TECH:
167913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		ret = trf7970a_tg_config_rf_tech(trf, param);
168013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		break;
168113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	case NFC_DIGITAL_CONFIG_FRAMING:
168213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		ret = trf7970a_tg_config_framing(trf, param);
168313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		break;
168413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	default:
168513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		dev_dbg(trf->dev, "Unknown type: %d\n", type);
168613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		ret = -EINVAL;
168713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	}
1688165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
168913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greererr_unlock:
169013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	mutex_unlock(&trf->lock);
169113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	return ret;
1692165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
1693165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1694cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greerstatic int _trf7970a_tg_listen(struct nfc_digital_dev *ddev, u16 timeout,
1695cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		nfc_digital_cmd_complete_t cb, void *arg, bool mode_detect)
1696165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
1697165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	struct trf7970a *trf = nfc_digital_get_drvdata(ddev);
169813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	int ret;
169913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
170013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	mutex_lock(&trf->lock);
1701165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
170213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	if ((trf->state != TRF7970A_ST_IDLE) &&
170313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			(trf->state != TRF7970A_ST_IDLE_RX_BLOCKED)) {
170413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		dev_err(trf->dev, "%s - Bogus state: %d\n", __func__,
170513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				trf->state);
170613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		ret = -EIO;
170713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		goto out_err;
170813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	}
170913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
171013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	if (trf->aborting) {
171113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		dev_dbg(trf->dev, "Abort process complete\n");
171213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		trf->aborting = false;
171313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		ret = -ECANCELED;
171413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		goto out_err;
171513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	}
171613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
171713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	trf->rx_skb = nfc_alloc_recv_skb(TRF7970A_RX_SKB_ALLOC_SIZE,
171813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			GFP_KERNEL);
171913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	if (!trf->rx_skb) {
172013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		dev_dbg(trf->dev, "Can't alloc rx_skb\n");
172113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		ret = -ENOMEM;
172213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		goto out_err;
172313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	}
172413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
172513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	ret = trf7970a_write(trf, TRF7970A_RX_SPECIAL_SETTINGS,
172613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			TRF7970A_RX_SPECIAL_SETTINGS_HBT |
172713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			TRF7970A_RX_SPECIAL_SETTINGS_M848 |
172813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			TRF7970A_RX_SPECIAL_SETTINGS_C424 |
172913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			TRF7970A_RX_SPECIAL_SETTINGS_C212);
173013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	if (ret)
1731fc0ae24386142299db14dfea7f32a20022d94d90Mark A. Greer		goto out_err;
173213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
173313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	ret = trf7970a_write(trf, TRF7970A_REG_IO_CTRL,
173413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			TRF7970A_REG_IO_CTRL_VRS(0x1));
173513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	if (ret)
1736fc0ae24386142299db14dfea7f32a20022d94d90Mark A. Greer		goto out_err;
1737165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
173813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	ret = trf7970a_write(trf, TRF7970A_NFC_LOW_FIELD_LEVEL,
173913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			TRF7970A_NFC_LOW_FIELD_LEVEL_RFDET(0x3));
174013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	if (ret)
1741fc0ae24386142299db14dfea7f32a20022d94d90Mark A. Greer		goto out_err;
174213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
174313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	ret = trf7970a_write(trf, TRF7970A_NFC_TARGET_LEVEL,
174413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			TRF7970A_NFC_TARGET_LEVEL_RFDET(0x7));
174513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	if (ret)
1746fc0ae24386142299db14dfea7f32a20022d94d90Mark A. Greer		goto out_err;
174713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
174813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	trf->ddev = ddev;
174913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	trf->cb = cb;
175013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	trf->cb_arg = arg;
175113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	trf->timeout = timeout;
175213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	trf->ignore_timeout = false;
175313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
175413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	ret = trf7970a_cmd(trf, TRF7970A_CMD_ENABLE_RX);
175513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	if (ret)
175613b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		goto out_err;
175713b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
1758cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	trf->state = mode_detect ? TRF7970A_ST_LISTENING_MD :
1759cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer				   TRF7970A_ST_LISTENING;
176013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
176113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	schedule_delayed_work(&trf->timeout_work, msecs_to_jiffies(timeout));
176213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer
176313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greerout_err:
176413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	mutex_unlock(&trf->lock);
176513b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	return ret;
1766165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
1767165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1768cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greerstatic int trf7970a_tg_listen(struct nfc_digital_dev *ddev, u16 timeout,
1769cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		nfc_digital_cmd_complete_t cb, void *arg)
1770cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer{
1771cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	struct trf7970a *trf = nfc_digital_get_drvdata(ddev);
1772cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
1773cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	dev_dbg(trf->dev, "Listen - state: %d, timeout: %d ms\n",
1774cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer			trf->state, timeout);
1775cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
1776cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	return _trf7970a_tg_listen(ddev, timeout, cb, arg, false);
1777cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer}
1778cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
1779cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greerstatic int trf7970a_tg_listen_md(struct nfc_digital_dev *ddev,
1780cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		u16 timeout, nfc_digital_cmd_complete_t cb, void *arg)
1781cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer{
1782cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	struct trf7970a *trf = nfc_digital_get_drvdata(ddev);
1783cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	int ret;
1784cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
1785cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	dev_dbg(trf->dev, "Listen MD - state: %d, timeout: %d ms\n",
1786cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer			trf->state, timeout);
1787cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
1788cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	ret = trf7970a_tg_configure_hw(ddev, NFC_DIGITAL_CONFIG_RF_TECH,
1789cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer			NFC_DIGITAL_RF_TECH_106A);
1790cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	if (ret)
1791cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		return ret;
1792cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
1793cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	ret = trf7970a_tg_configure_hw(ddev, NFC_DIGITAL_CONFIG_FRAMING,
1794cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer			NFC_DIGITAL_FRAMING_NFCA_NFC_DEP);
1795cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	if (ret)
1796cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer		return ret;
1797cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
1798cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	return _trf7970a_tg_listen(ddev, timeout, cb, arg, true);
1799cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer}
1800cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
1801cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greerstatic int trf7970a_tg_get_rf_tech(struct nfc_digital_dev *ddev, u8 *rf_tech)
1802cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer{
1803cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	struct trf7970a *trf = nfc_digital_get_drvdata(ddev);
1804cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
1805cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	dev_dbg(trf->dev, "Get RF Tech - state: %d, rf_tech: %d\n",
1806cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer			trf->state, trf->md_rf_tech);
1807cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
1808cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	*rf_tech = trf->md_rf_tech;
1809cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
1810cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	return 0;
1811cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer}
1812cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer
1813165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic void trf7970a_abort_cmd(struct nfc_digital_dev *ddev)
1814165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
1815165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	struct trf7970a *trf = nfc_digital_get_drvdata(ddev);
1816165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1817165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	dev_dbg(trf->dev, "Abort process initiated\n");
1818165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1819165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	mutex_lock(&trf->lock);
18205876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer
18215876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer	switch (trf->state) {
18225876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer	case TRF7970A_ST_WAIT_FOR_TX_FIFO:
18235876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer	case TRF7970A_ST_WAIT_FOR_RX_DATA:
18245876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer	case TRF7970A_ST_WAIT_FOR_RX_DATA_CONT:
18255876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer	case TRF7970A_ST_WAIT_TO_ISSUE_EOF:
18265876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer		trf->aborting = true;
18275876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer		break;
182813b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	case TRF7970A_ST_LISTENING:
182913b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		trf->ignore_timeout = !cancel_delayed_work(&trf->timeout_work);
183013b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		trf7970a_send_err_upstream(trf, -ECANCELED);
183113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		dev_dbg(trf->dev, "Abort process complete\n");
183213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer		break;
18335876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer	default:
18345876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer		break;
18355876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer	}
18365876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer
1837165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	mutex_unlock(&trf->lock);
1838165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
1839165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1840165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic struct nfc_digital_ops trf7970a_nfc_ops = {
1841165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	.in_configure_hw	= trf7970a_in_configure_hw,
184213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	.in_send_cmd		= trf7970a_send_cmd,
1843165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	.tg_configure_hw	= trf7970a_tg_configure_hw,
184413b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	.tg_send_cmd		= trf7970a_send_cmd,
1845165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	.tg_listen		= trf7970a_tg_listen,
1846cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	.tg_listen_md		= trf7970a_tg_listen_md,
1847cb174aba86fe10ddac8b692c90a9480526c02953Mark A. Greer	.tg_get_rf_tech		= trf7970a_tg_get_rf_tech,
1848165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	.switch_rf		= trf7970a_switch_rf,
1849165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	.abort_cmd		= trf7970a_abort_cmd,
1850165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer};
1851165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1852ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greerstatic int trf7970a_power_up(struct trf7970a *trf)
1853ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer{
1854ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	int ret;
1855ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
1856ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	dev_dbg(trf->dev, "Powering up - state: %d\n", trf->state);
1857ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
1858ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	if (trf->state != TRF7970A_ST_PWR_OFF)
1859ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer		return 0;
1860ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
1861ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	ret = regulator_enable(trf->regulator);
1862ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	if (ret) {
1863ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer		dev_err(trf->dev, "%s - Can't enable VIN: %d\n", __func__, ret);
1864ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer		return ret;
1865ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	}
1866ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
1867ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	usleep_range(5000, 6000);
1868ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
1869ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	if (!(trf->quirks & TRF7970A_QUIRK_EN2_MUST_STAY_LOW)) {
1870ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer		gpio_set_value(trf->en2_gpio, 1);
1871ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer		usleep_range(1000, 2000);
1872ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	}
1873ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
1874ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	gpio_set_value(trf->en_gpio, 1);
1875ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
1876ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	usleep_range(20000, 21000);
1877ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
1878ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	trf->state = TRF7970A_ST_RF_OFF;
1879ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
1880ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	return 0;
1881ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer}
1882ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
1883ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greerstatic int trf7970a_power_down(struct trf7970a *trf)
1884ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer{
1885ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	int ret;
1886ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
1887ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	dev_dbg(trf->dev, "Powering down - state: %d\n", trf->state);
1888ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
1889ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	if (trf->state == TRF7970A_ST_PWR_OFF)
1890ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer		return 0;
1891ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
1892ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	if (trf->state != TRF7970A_ST_RF_OFF) {
1893ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer		dev_dbg(trf->dev, "Can't power down - not RF_OFF state (%d)\n",
1894ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer				trf->state);
1895ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer		return -EBUSY;
1896ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	}
1897ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
1898ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	gpio_set_value(trf->en_gpio, 0);
1899ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	gpio_set_value(trf->en2_gpio, 0);
1900ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
1901ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	ret = regulator_disable(trf->regulator);
1902ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	if (ret)
1903ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer		dev_err(trf->dev, "%s - Can't disable VIN: %d\n", __func__,
1904ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer				ret);
1905ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
1906ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	trf->state = TRF7970A_ST_PWR_OFF;
1907ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
1908ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	return ret;
1909ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer}
1910ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
1911b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greerstatic int trf7970a_startup(struct trf7970a *trf)
1912b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer{
1913b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	int ret;
1914b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer
1915b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	ret = trf7970a_power_up(trf);
1916b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	if (ret)
1917b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer		return ret;
1918b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer
1919b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	pm_runtime_set_active(trf->dev);
1920b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	pm_runtime_enable(trf->dev);
1921b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	pm_runtime_mark_last_busy(trf->dev);
1922b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer
1923b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	return 0;
1924b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer}
1925b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer
1926b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greerstatic void trf7970a_shutdown(struct trf7970a *trf)
1927b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer{
1928b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	switch (trf->state) {
1929b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	case TRF7970A_ST_WAIT_FOR_TX_FIFO:
1930b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	case TRF7970A_ST_WAIT_FOR_RX_DATA:
1931b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	case TRF7970A_ST_WAIT_FOR_RX_DATA_CONT:
1932b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	case TRF7970A_ST_WAIT_TO_ISSUE_EOF:
193313b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer	case TRF7970A_ST_LISTENING:
1934b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer		trf7970a_send_err_upstream(trf, -ECANCELED);
1935b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer		/* FALLTHROUGH */
1936b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	case TRF7970A_ST_IDLE:
1937b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	case TRF7970A_ST_IDLE_RX_BLOCKED:
1938b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer		trf7970a_switch_rf_off(trf);
1939b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer		break;
1940b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	default:
1941b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer		break;
1942b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	}
1943b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer
1944b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	pm_runtime_disable(trf->dev);
1945b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	pm_runtime_set_suspended(trf->dev);
1946b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer
1947b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	trf7970a_power_down(trf);
1948b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer}
1949b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer
1950fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greerstatic int trf7970a_get_autosuspend_delay(struct device_node *np)
1951fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer{
1952fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer	int autosuspend_delay, ret;
1953fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer
1954fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer	ret = of_property_read_u32(np, "autosuspend-delay", &autosuspend_delay);
1955fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer	if (ret)
1956fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer		autosuspend_delay = TRF7970A_AUTOSUSPEND_DELAY;
1957fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer
1958fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer	return autosuspend_delay;
1959fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer}
1960fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer
19613bd14233aa0733fbc6c3f75ec928f1a393522644Mark A. Greerstatic int trf7970a_get_vin_voltage_override(struct device_node *np,
19623bd14233aa0733fbc6c3f75ec928f1a393522644Mark A. Greer		u32 *vin_uvolts)
19633bd14233aa0733fbc6c3f75ec928f1a393522644Mark A. Greer{
19643bd14233aa0733fbc6c3f75ec928f1a393522644Mark A. Greer	return of_property_read_u32(np, "vin-voltage-override", vin_uvolts);
19653bd14233aa0733fbc6c3f75ec928f1a393522644Mark A. Greer}
19663bd14233aa0733fbc6c3f75ec928f1a393522644Mark A. Greer
1967165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_probe(struct spi_device *spi)
1968165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
1969165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	struct device_node *np = spi->dev.of_node;
1970165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	struct trf7970a *trf;
1971fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer	int uvolts, autosuspend_delay, ret;
1972165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1973165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (!np) {
1974165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_err(&spi->dev, "No Device Tree entry\n");
1975165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		return -EINVAL;
1976165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
1977165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1978165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf = devm_kzalloc(&spi->dev, sizeof(*trf), GFP_KERNEL);
1979165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (!trf)
1980165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		return -ENOMEM;
1981165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1982ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	trf->state = TRF7970A_ST_PWR_OFF;
1983165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf->dev = &spi->dev;
1984165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf->spi = spi;
1985165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
1986165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	spi->mode = SPI_MODE_1;
1987165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	spi->bits_per_word = 8;
1988165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
198924707296c762d1828c4a51aa1872dc275dc3fcccMark A. Greer	ret = spi_setup(spi);
199024707296c762d1828c4a51aa1872dc275dc3fcccMark A. Greer	if (ret < 0) {
199124707296c762d1828c4a51aa1872dc275dc3fcccMark A. Greer		dev_err(trf->dev, "Can't set up SPI Communication\n");
199224707296c762d1828c4a51aa1872dc275dc3fcccMark A. Greer		return ret;
199324707296c762d1828c4a51aa1872dc275dc3fcccMark A. Greer	}
199424707296c762d1828c4a51aa1872dc275dc3fcccMark A. Greer
1995772079eb77587e0242752fa67685a8132d899f79Mark A. Greer	if (of_property_read_bool(np, "irq-status-read-quirk"))
1996772079eb77587e0242752fa67685a8132d899f79Mark A. Greer		trf->quirks |= TRF7970A_QUIRK_IRQ_STATUS_READ;
1997772079eb77587e0242752fa67685a8132d899f79Mark A. Greer
1998165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	/* There are two enable pins - both must be present */
1999165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf->en_gpio = of_get_named_gpio(np, "ti,enable-gpios", 0);
2000165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (!gpio_is_valid(trf->en_gpio)) {
2001165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_err(trf->dev, "No EN GPIO property\n");
2002165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		return trf->en_gpio;
2003165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
2004165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
2005165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	ret = devm_gpio_request_one(trf->dev, trf->en_gpio,
2006f23b73526b82ca2ef333362e704a51d817c1ffc1Mark A. Greer			GPIOF_DIR_OUT | GPIOF_INIT_LOW, "trf7970a EN");
2007165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (ret) {
2008165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_err(trf->dev, "Can't request EN GPIO: %d\n", ret);
2009165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		return ret;
2010165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
2011165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
2012165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf->en2_gpio = of_get_named_gpio(np, "ti,enable-gpios", 1);
2013165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (!gpio_is_valid(trf->en2_gpio)) {
2014165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_err(trf->dev, "No EN2 GPIO property\n");
2015165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		return trf->en2_gpio;
2016165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
2017165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
2018165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	ret = devm_gpio_request_one(trf->dev, trf->en2_gpio,
2019f23b73526b82ca2ef333362e704a51d817c1ffc1Mark A. Greer			GPIOF_DIR_OUT | GPIOF_INIT_LOW, "trf7970a EN2");
2020165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (ret) {
2021165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_err(trf->dev, "Can't request EN2 GPIO: %d\n", ret);
2022165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		return ret;
2023165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
2024165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
202595064bd95a822659f4a606b485aba5009d70fc88Mark A. Greer	if (of_property_read_bool(np, "en2-rf-quirk"))
202695064bd95a822659f4a606b485aba5009d70fc88Mark A. Greer		trf->quirks |= TRF7970A_QUIRK_EN2_MUST_STAY_LOW;
202795064bd95a822659f4a606b485aba5009d70fc88Mark A. Greer
2028165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	ret = devm_request_threaded_irq(trf->dev, spi->irq, NULL,
2029165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			trf7970a_irq, IRQF_TRIGGER_RISING | IRQF_ONESHOT,
2030165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			"trf7970a", trf);
2031165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (ret) {
2032165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_err(trf->dev, "Can't request IRQ#%d: %d\n", spi->irq, ret);
2033165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		return ret;
2034165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
2035165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
2036165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	mutex_init(&trf->lock);
2037165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	INIT_DELAYED_WORK(&trf->timeout_work, trf7970a_timeout_work_handler);
2038165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
2039165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf->regulator = devm_regulator_get(&spi->dev, "vin");
2040165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (IS_ERR(trf->regulator)) {
2041165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		ret = PTR_ERR(trf->regulator);
2042165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_err(trf->dev, "Can't get VIN regulator: %d\n", ret);
2043165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		goto err_destroy_lock;
2044165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
2045165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
2046165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	ret = regulator_enable(trf->regulator);
2047165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (ret) {
2048165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_err(trf->dev, "Can't enable VIN: %d\n", ret);
2049165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		goto err_destroy_lock;
2050165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
2051165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
20523bd14233aa0733fbc6c3f75ec928f1a393522644Mark A. Greer	ret = trf7970a_get_vin_voltage_override(np, &uvolts);
20533bd14233aa0733fbc6c3f75ec928f1a393522644Mark A. Greer	if (ret)
20543bd14233aa0733fbc6c3f75ec928f1a393522644Mark A. Greer		uvolts = regulator_get_voltage(trf->regulator);
2055ebcc5a0d08e6a680558ed74f5dd724427ff5a29bMark A. Greer
2056ebcc5a0d08e6a680558ed74f5dd724427ff5a29bMark A. Greer	if (uvolts > 4000000)
2057ebcc5a0d08e6a680558ed74f5dd724427ff5a29bMark A. Greer		trf->chip_status_ctrl = TRF7970A_CHIP_STATUS_VRS5_3;
2058ebcc5a0d08e6a680558ed74f5dd724427ff5a29bMark A. Greer
2059165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	trf->ddev = nfc_digital_allocate_device(&trf7970a_nfc_ops,
2060165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer			TRF7970A_SUPPORTED_PROTOCOLS,
206113b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer			NFC_DIGITAL_DRV_CAPS_IN_CRC |
206213b4272a8264220ec043a922fd1fa05da72d57aeMark A. Greer				NFC_DIGITAL_DRV_CAPS_TG_CRC, 0, 0);
2063165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (!trf->ddev) {
2064165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_err(trf->dev, "Can't allocate NFC digital device\n");
2065165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		ret = -ENOMEM;
2066165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		goto err_disable_regulator;
2067165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
2068165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
2069165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	nfc_digital_set_parent_dev(trf->ddev, trf->dev);
2070165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	nfc_digital_set_drvdata(trf->ddev, trf);
2071165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	spi_set_drvdata(spi, trf);
2072165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
2073fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer	autosuspend_delay = trf7970a_get_autosuspend_delay(np);
2074fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer
2075fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer	pm_runtime_set_autosuspend_delay(trf->dev, autosuspend_delay);
2076e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer	pm_runtime_use_autosuspend(trf->dev);
2077ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
2078b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	ret = trf7970a_startup(trf);
2079ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	if (ret)
2080ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer		goto err_free_ddev;
2081ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
2082165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	ret = nfc_digital_register_device(trf->ddev);
2083165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	if (ret) {
2084165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		dev_err(trf->dev, "Can't register NFC digital device: %d\n",
2085165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer				ret);
2086b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer		goto err_shutdown;
2087165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	}
2088165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
2089165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	return 0;
2090165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
2091b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greererr_shutdown:
2092b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	trf7970a_shutdown(trf);
2093ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greererr_free_ddev:
2094165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	nfc_digital_free_device(trf->ddev);
2095165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greererr_disable_regulator:
2096165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	regulator_disable(trf->regulator);
2097165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greererr_destroy_lock:
2098165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	mutex_destroy(&trf->lock);
2099165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	return ret;
2100165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
2101165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
2102165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_remove(struct spi_device *spi)
2103165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{
2104165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	struct trf7970a *trf = spi_get_drvdata(spi);
2105165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
2106165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	mutex_lock(&trf->lock);
2107165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
2108b528281b8b7a9c379baf37720191a799fbc9800cMark A. Greer	trf7970a_shutdown(trf);
2109ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer
2110ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	mutex_unlock(&trf->lock);
2111e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer
2112165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	nfc_digital_unregister_device(trf->ddev);
2113165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	nfc_digital_free_device(trf->ddev);
2114165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
2115165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	regulator_disable(trf->regulator);
2116165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
2117165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	mutex_destroy(&trf->lock);
2118165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
2119165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	return 0;
2120165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}
2121165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
212277c9539dc1284677539af442ac3629c9baf01202Mark A. Greer#ifdef CONFIG_PM_SLEEP
212377c9539dc1284677539af442ac3629c9baf01202Mark A. Greerstatic int trf7970a_suspend(struct device *dev)
212477c9539dc1284677539af442ac3629c9baf01202Mark A. Greer{
212577c9539dc1284677539af442ac3629c9baf01202Mark A. Greer	struct spi_device *spi = container_of(dev, struct spi_device, dev);
212677c9539dc1284677539af442ac3629c9baf01202Mark A. Greer	struct trf7970a *trf = spi_get_drvdata(spi);
212777c9539dc1284677539af442ac3629c9baf01202Mark A. Greer
212877c9539dc1284677539af442ac3629c9baf01202Mark A. Greer	dev_dbg(dev, "Suspend\n");
212977c9539dc1284677539af442ac3629c9baf01202Mark A. Greer
213077c9539dc1284677539af442ac3629c9baf01202Mark A. Greer	mutex_lock(&trf->lock);
213177c9539dc1284677539af442ac3629c9baf01202Mark A. Greer
213277c9539dc1284677539af442ac3629c9baf01202Mark A. Greer	trf7970a_shutdown(trf);
213377c9539dc1284677539af442ac3629c9baf01202Mark A. Greer
213477c9539dc1284677539af442ac3629c9baf01202Mark A. Greer	mutex_unlock(&trf->lock);
213577c9539dc1284677539af442ac3629c9baf01202Mark A. Greer
2136671970f531378e2a22ba0168d85dfca1f4e082c4Mark A. Greer	return 0;
213777c9539dc1284677539af442ac3629c9baf01202Mark A. Greer}
213877c9539dc1284677539af442ac3629c9baf01202Mark A. Greer
213977c9539dc1284677539af442ac3629c9baf01202Mark A. Greerstatic int trf7970a_resume(struct device *dev)
214077c9539dc1284677539af442ac3629c9baf01202Mark A. Greer{
214177c9539dc1284677539af442ac3629c9baf01202Mark A. Greer	struct spi_device *spi = container_of(dev, struct spi_device, dev);
214277c9539dc1284677539af442ac3629c9baf01202Mark A. Greer	struct trf7970a *trf = spi_get_drvdata(spi);
214355ef2e75ccf0d91f7b2f4251dc3b9e56df840928Mark A. Greer	int ret;
214477c9539dc1284677539af442ac3629c9baf01202Mark A. Greer
214577c9539dc1284677539af442ac3629c9baf01202Mark A. Greer	dev_dbg(dev, "Resume\n");
214677c9539dc1284677539af442ac3629c9baf01202Mark A. Greer
214777c9539dc1284677539af442ac3629c9baf01202Mark A. Greer	mutex_lock(&trf->lock);
214877c9539dc1284677539af442ac3629c9baf01202Mark A. Greer
214977c9539dc1284677539af442ac3629c9baf01202Mark A. Greer	ret = trf7970a_startup(trf);
215077c9539dc1284677539af442ac3629c9baf01202Mark A. Greer
215177c9539dc1284677539af442ac3629c9baf01202Mark A. Greer	mutex_unlock(&trf->lock);
215277c9539dc1284677539af442ac3629c9baf01202Mark A. Greer
215377c9539dc1284677539af442ac3629c9baf01202Mark A. Greer	return ret;
215477c9539dc1284677539af442ac3629c9baf01202Mark A. Greer}
215577c9539dc1284677539af442ac3629c9baf01202Mark A. Greer#endif
215677c9539dc1284677539af442ac3629c9baf01202Mark A. Greer
2157e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer#ifdef CONFIG_PM_RUNTIME
2158e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greerstatic int trf7970a_pm_runtime_suspend(struct device *dev)
2159e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer{
2160e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer	struct spi_device *spi = container_of(dev, struct spi_device, dev);
2161e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer	struct trf7970a *trf = spi_get_drvdata(spi);
2162e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer	int ret;
2163e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer
2164e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer	dev_dbg(dev, "Runtime suspend\n");
2165e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer
2166ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	mutex_lock(&trf->lock);
2167e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer
2168ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	ret = trf7970a_power_down(trf);
2169e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer
2170ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	mutex_unlock(&trf->lock);
2171e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer
2172e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer	return ret;
2173e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer}
2174e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer
2175e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greerstatic int trf7970a_pm_runtime_resume(struct device *dev)
2176e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer{
2177e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer	struct spi_device *spi = container_of(dev, struct spi_device, dev);
2178e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer	struct trf7970a *trf = spi_get_drvdata(spi);
2179e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer	int ret;
2180e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer
2181e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer	dev_dbg(dev, "Runtime resume\n");
2182e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer
2183ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	ret = trf7970a_power_up(trf);
2184ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	if (!ret)
2185ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer		pm_runtime_mark_last_busy(dev);
2186e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer
2187ceccd6aa50887352e66d0edf68d8be510a639da6Mark A. Greer	return ret;
2188e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer}
2189e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer#endif
2190e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer
2191e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greerstatic const struct dev_pm_ops trf7970a_pm_ops = {
219277c9539dc1284677539af442ac3629c9baf01202Mark A. Greer	SET_SYSTEM_SLEEP_PM_OPS(trf7970a_suspend, trf7970a_resume)
2193e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer	SET_RUNTIME_PM_OPS(trf7970a_pm_runtime_suspend,
2194e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer			trf7970a_pm_runtime_resume, NULL)
2195e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer};
2196e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer
2197165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic const struct spi_device_id trf7970a_id_table[] = {
2198772079eb77587e0242752fa67685a8132d899f79Mark A. Greer	{ "trf7970a", 0 },
2199165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	{ }
2200165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer};
2201165063f1dac43e48ceb907490fff0a8413b9a32dMark A. GreerMODULE_DEVICE_TABLE(spi, trf7970a_id_table);
2202165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
2203165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic struct spi_driver trf7970a_spi_driver = {
2204165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	.probe		= trf7970a_probe,
2205165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	.remove		= trf7970a_remove,
2206165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	.id_table	= trf7970a_id_table,
2207165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	.driver		= {
2208165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		.name	= "trf7970a",
2209165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer		.owner	= THIS_MODULE,
2210e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer		.pm	= &trf7970a_pm_ops,
2211165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer	},
2212165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer};
2213165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
2214165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greermodule_spi_driver(trf7970a_spi_driver);
2215165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer
2216165063f1dac43e48ceb907490fff0a8413b9a32dMark A. GreerMODULE_AUTHOR("Mark A. Greer <mgreer@animalcreek.com>");
2217165063f1dac43e48ceb907490fff0a8413b9a32dMark A. GreerMODULE_LICENSE("GPL v2");
2218165063f1dac43e48ceb907490fff0a8413b9a32dMark A. GreerMODULE_DESCRIPTION("TI trf7970a RFID/NFC Transceiver Driver");
2219