trf7970a.c revision 4e64eff837fb682dfb2a1188fb036d75ec57375c
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 65165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * support that. So, if an abort is received before trf7970a_in_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 * 86165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * Type 2 write and sector select commands respond with a 4-bit ACK or NACK. 87165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * Having only 4 bits in the FIFO won't normally generate an interrupt so 88165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * driver enables the '4_bit_RX' bit of the Special Functions register 1 89165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * to cause an interrupt in that case. Leaving that bit for a read command 90165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * messes up the data returned so it is only enabled when the framing is 91165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * 'NFC_DIGITAL_FRAMING_NFCA_T2T' and the command is not a read command. 92165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * Unfortunately, that means that the driver has to peek into tx frames 93165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * when the framing is 'NFC_DIGITAL_FRAMING_NFCA_T2T'. This is done by 94165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * the trf7970a_per_cmd_config() routine. 959d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * 969d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * ISO/IEC 15693 frames specify whether to use single or double sub-carrier 979d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * frequencies and whether to use low or high data rates in the flags byte 989d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * of the frame. This means that the driver has to peek at all 15693 frames 999d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * to determine what speed to set the communication to. In addition, write 1009d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * and lock commands use the OPTION flag to indicate that an EOF must be 1019d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * sent to the tag before it will send its response. So the driver has to 1029d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * examine all frames for that reason too. 1039d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * 1049d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * It is unclear how long to wait before sending the EOF. According to the 1059d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * Note under Table 1-1 in section 1.6 of 1069d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * http://www.ti.com/lit/ug/scbu011/scbu011.pdf, that wait should be at least 1079d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * 10 ms for TI Tag-it HF-I tags; however testing has shown that is not long 1089d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * enough. For this reason, the driver waits 20 ms which seems to work 1099d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * reliably. 110165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer */ 111165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1128006289108fa9635d16a65d9db16da06d7dce201Mark A. Greer#define TRF7970A_SUPPORTED_PROTOCOLS \ 1139d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer (NFC_PROTO_MIFARE_MASK | NFC_PROTO_ISO14443_MASK | \ 1146857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer NFC_PROTO_ISO14443_B_MASK | NFC_PROTO_FELICA_MASK | \ 1156857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer NFC_PROTO_ISO15693_MASK) 116165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 117e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer#define TRF7970A_AUTOSUSPEND_DELAY 30000 /* 30 seconds */ 118e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer 119165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* TX data must be prefixed with a FIFO reset cmd, a cmd that depends 120165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * on what the current framing is, the address of the TX length byte 1 121165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * register (0x1d), and the 2 byte length of the data to be transmitted. 122165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * That totals 5 bytes. 123165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer */ 124165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_TX_SKB_HEADROOM 5 125165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 126165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_RX_SKB_ALLOC_SIZE 256 127165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1281568bfef18a9150d83b0f91aa254cef7ebead4cdMark A. Greer#define TRF7970A_FIFO_SIZE 127 129165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 130165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* TX length is 3 nibbles long ==> 4KB - 1 bytes max */ 131165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_TX_MAX (4096 - 1) 132165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1335fa3af352b991e2e5c674728411d1cc4a4923e4dMark A. Greer#define TRF7970A_WAIT_FOR_RX_DATA_TIMEOUT 20 134165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_WAIT_FOR_FIFO_DRAIN_TIMEOUT 3 1359d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define TRF7970A_WAIT_TO_ISSUE_ISO15693_EOF 20 136165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1374e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer/* Guard times for various RF technologies (in us) */ 1384e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer#define TRF7970A_GUARD_TIME_NFCA 5000 1394e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer#define TRF7970A_GUARD_TIME_NFCB 5000 1404e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer#define TRF7970A_GUARD_TIME_NFCF 20000 1414e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer#define TRF7970A_GUARD_TIME_15693 1000 1424e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer 143165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* Quirks */ 144165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* Erratum: When reading IRQ Status register on trf7970a, we must issue a 145165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * read continuous command for IRQ Status and Collision Position registers. 146165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer */ 147772079eb77587e0242752fa67685a8132d899f79Mark A. Greer#define TRF7970A_QUIRK_IRQ_STATUS_READ BIT(0) 14895064bd95a822659f4a606b485aba5009d70fc88Mark A. Greer#define TRF7970A_QUIRK_EN2_MUST_STAY_LOW BIT(1) 149165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 150165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* Direct commands */ 151165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_IDLE 0x00 152165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_SOFT_INIT 0x03 153165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_RF_COLLISION 0x04 154165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_RF_COLLISION_RESPONSE_N 0x05 155165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_RF_COLLISION_RESPONSE_0 0x06 156165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_FIFO_RESET 0x0f 157165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_TRANSMIT_NO_CRC 0x10 158165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_TRANSMIT 0x11 159165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_DELAY_TRANSMIT_NO_CRC 0x12 160165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_DELAY_TRANSMIT 0x13 161165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_EOF 0x14 162165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_CLOSE_SLOT 0x15 163165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_BLOCK_RX 0x16 164165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_ENABLE_RX 0x17 165165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_TEST_EXT_RF 0x18 166165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_TEST_INT_RF 0x19 167165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_RX_GAIN_ADJUST 0x1a 168165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 169165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* Bits determining whether its a direct command or register R/W, 170165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * whether to use a continuous SPI transaction or not, and the actual 171165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * direct cmd opcode or regster address. 172165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer */ 173165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_BIT_CTRL BIT(7) 174165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_BIT_RW BIT(6) 175165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_BIT_CONTINUOUS BIT(5) 176165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CMD_BIT_OPCODE(opcode) ((opcode) & 0x1f) 177165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 178165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* Registers addresses */ 179165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CHIP_STATUS_CTRL 0x00 180165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL 0x01 181165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO14443B_TX_OPTIONS 0x02 182165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO14443A_HIGH_BITRATE_OPTIONS 0x03 183165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_TX_TIMER_SETTING_H_BYTE 0x04 184165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_TX_TIMER_SETTING_L_BYTE 0x05 185165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_TX_PULSE_LENGTH_CTRL 0x06 186165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_RX_NO_RESPONSE_WAIT 0x07 187165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_RX_WAIT_TIME 0x08 188165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_SYS_CLK_CTRL 0x09 189165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_RX_SPECIAL_SETTINGS 0x0a 190165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_REG_IO_CTRL 0x0b 191165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_IRQ_STATUS 0x0c 192165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_COLLISION_IRQ_MASK 0x0d 193165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_COLLISION_POSITION 0x0e 194165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_RSSI_OSC_STATUS 0x0f 195165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_SPECIAL_FCN_REG1 0x10 196165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_SPECIAL_FCN_REG2 0x11 197165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_RAM1 0x12 198165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_RAM2 0x13 199165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS 0x14 200165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_NFC_LOW_FIELD_LEVEL 0x16 201165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_NFCID1 0x17 202165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_NFC_TARGET_LEVEL 0x18 203165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF79070A_NFC_TARGET_PROTOCOL 0x19 204165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_TEST_REGISTER1 0x1a 205165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_TEST_REGISTER2 0x1b 206165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_FIFO_STATUS 0x1c 207165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_TX_LENGTH_BYTE1 0x1d 208165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_TX_LENGTH_BYTE2 0x1e 209165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_FIFO_IO_REGISTER 0x1f 210165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 211165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* Chip Status Control Register Bits */ 212165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CHIP_STATUS_VRS5_3 BIT(0) 213165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CHIP_STATUS_REC_ON BIT(1) 214165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CHIP_STATUS_AGC_ON BIT(2) 215165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CHIP_STATUS_PM_ON BIT(3) 216165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CHIP_STATUS_RF_PWR BIT(4) 217165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CHIP_STATUS_RF_ON BIT(5) 218165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CHIP_STATUS_DIRECT BIT(6) 219165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_CHIP_STATUS_STBY BIT(7) 220165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 221165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* ISO Control Register Bits */ 222165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_15693_SGL_1OF4_662 0x00 223165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_15693_SGL_1OF256_662 0x01 224165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_15693_SGL_1OF4_2648 0x02 225165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_15693_SGL_1OF256_2648 0x03 226165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_15693_DBL_1OF4_667a 0x04 227165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_15693_DBL_1OF256_667 0x05 228165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_15693_DBL_1OF4_2669 0x06 229165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_15693_DBL_1OF256_2669 0x07 230165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_14443A_106 0x08 231165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_14443A_212 0x09 232165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_14443A_424 0x0a 233165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_14443A_848 0x0b 234165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_14443B_106 0x0c 235165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_14443B_212 0x0d 236165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_14443B_424 0x0e 237165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_14443B_848 0x0f 238165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_FELICA_212 0x1a 239165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_FELICA_424 0x1b 240165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_RFID BIT(5) 241165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_DIR_MODE BIT(6) 242165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_RX_CRC_N BIT(7) /* true == No CRC */ 243165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 244165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ISO_CTRL_RFID_SPEED_MASK 0x1f 245165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 246165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* Modulator and SYS_CLK Control Register Bits */ 247165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_DEPTH(n) ((n) & 0x7) 248165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_DEPTH_ASK10 (TRF7970A_MODULATOR_DEPTH(0)) 249165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_DEPTH_OOK (TRF7970A_MODULATOR_DEPTH(1)) 250165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_DEPTH_ASK7 (TRF7970A_MODULATOR_DEPTH(2)) 251165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_DEPTH_ASK8_5 (TRF7970A_MODULATOR_DEPTH(3)) 252165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_DEPTH_ASK13 (TRF7970A_MODULATOR_DEPTH(4)) 253165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_DEPTH_ASK16 (TRF7970A_MODULATOR_DEPTH(5)) 254165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_DEPTH_ASK22 (TRF7970A_MODULATOR_DEPTH(6)) 255165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_DEPTH_ASK30 (TRF7970A_MODULATOR_DEPTH(7)) 256165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_EN_ANA BIT(3) 257165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_CLK(n) (((n) & 0x3) << 4) 258165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_CLK_DISABLED (TRF7970A_MODULATOR_CLK(0)) 259165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_CLK_3_6 (TRF7970A_MODULATOR_CLK(1)) 260165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_CLK_6_13 (TRF7970A_MODULATOR_CLK(2)) 261165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_CLK_13_27 (TRF7970A_MODULATOR_CLK(3)) 262165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_EN_OOK BIT(6) 263165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_MODULATOR_27MHZ BIT(7) 264165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 265165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* IRQ Status Register Bits */ 266165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_IRQ_STATUS_NORESP BIT(0) /* ISO15693 only */ 267165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_IRQ_STATUS_COL BIT(1) 268165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_IRQ_STATUS_FRAMING_EOF_ERROR BIT(2) 269165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_IRQ_STATUS_PARITY_ERROR BIT(3) 270165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_IRQ_STATUS_CRC_ERROR BIT(4) 271165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_IRQ_STATUS_FIFO BIT(5) 272165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_IRQ_STATUS_SRX BIT(6) 273165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_IRQ_STATUS_TX BIT(7) 274165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 275165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_IRQ_STATUS_ERROR \ 276165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer (TRF7970A_IRQ_STATUS_COL | \ 277165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer TRF7970A_IRQ_STATUS_FRAMING_EOF_ERROR | \ 278165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer TRF7970A_IRQ_STATUS_PARITY_ERROR | \ 279165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer TRF7970A_IRQ_STATUS_CRC_ERROR) 280165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 281165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_SPECIAL_FCN_REG1_COL_7_6 BIT(0) 282165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_SPECIAL_FCN_REG1_14_ANTICOLL BIT(1) 283165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_SPECIAL_FCN_REG1_4_BIT_RX BIT(2) 284165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_SPECIAL_FCN_REG1_SP_DIR_MODE BIT(3) 285165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_SPECIAL_FCN_REG1_NEXT_SLOT_37US BIT(4) 286165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_SPECIAL_FCN_REG1_PAR43 BIT(5) 287165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 288165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS_WLH_124 (0x0 << 2) 289165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS_WLH_120 (0x1 << 2) 290165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS_WLH_112 (0x2 << 2) 291165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS_WLH_96 (0x3 << 2) 292165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS_WLL_4 0x0 293165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS_WLL_8 0x1 294165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS_WLL_16 0x2 295165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS_WLL_32 0x3 296165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 297165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define TRF7970A_FIFO_STATUS_OVERFLOW BIT(7) 298165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 299165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer/* NFC (ISO/IEC 14443A) Type 2 Tag commands */ 300165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer#define NFC_T2T_CMD_READ 0x30 301165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 3029d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer/* ISO 15693 commands codes */ 3039d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_INVENTORY 0x01 3049d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_READ_SINGLE_BLOCK 0x20 3059d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_WRITE_SINGLE_BLOCK 0x21 3069d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_LOCK_BLOCK 0x22 3079d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_READ_MULTIPLE_BLOCK 0x23 3089d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_WRITE_MULTIPLE_BLOCK 0x24 3099d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_SELECT 0x25 3109d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_RESET_TO_READY 0x26 3119d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_WRITE_AFI 0x27 3129d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_LOCK_AFI 0x28 3139d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_WRITE_DSFID 0x29 3149d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_LOCK_DSFID 0x2a 3159d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_GET_SYSTEM_INFO 0x2b 3169d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_CMD_GET_MULTIPLE_BLOCK_SECURITY_STATUS 0x2c 3179d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer 3189d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer/* ISO 15693 request and response flags */ 3199d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_REQ_FLAG_SUB_CARRIER BIT(0) 3209d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_REQ_FLAG_DATA_RATE BIT(1) 3219d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_REQ_FLAG_INVENTORY BIT(2) 3229d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_REQ_FLAG_PROTOCOL_EXT BIT(3) 3239d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_REQ_FLAG_SELECT BIT(4) 3249d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_REQ_FLAG_AFI BIT(4) 3259d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_REQ_FLAG_ADDRESS BIT(5) 3269d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_REQ_FLAG_NB_SLOTS BIT(5) 3279d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_REQ_FLAG_OPTION BIT(6) 3289d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer 3299d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer#define ISO15693_REQ_FLAG_SPEED_MASK \ 3309d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer (ISO15693_REQ_FLAG_SUB_CARRIER | ISO15693_REQ_FLAG_DATA_RATE) 3319d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer 332165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerenum trf7970a_state { 333165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer TRF7970A_ST_OFF, 334165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer TRF7970A_ST_IDLE, 335165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer TRF7970A_ST_IDLE_RX_BLOCKED, 336165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer TRF7970A_ST_WAIT_FOR_TX_FIFO, 337165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer TRF7970A_ST_WAIT_FOR_RX_DATA, 338165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer TRF7970A_ST_WAIT_FOR_RX_DATA_CONT, 3399d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer TRF7970A_ST_WAIT_TO_ISSUE_EOF, 340165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer TRF7970A_ST_MAX 341165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}; 342165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 343165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstruct trf7970a { 344165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer enum trf7970a_state state; 345165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct device *dev; 346165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct spi_device *spi; 347165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct regulator *regulator; 348165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct nfc_digital_dev *ddev; 349165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer u32 quirks; 350165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer bool aborting; 351165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct sk_buff *tx_skb; 352165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct sk_buff *rx_skb; 353165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer nfc_digital_cmd_complete_t cb; 354165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer void *cb_arg; 355ebcc5a0d08e6a680558ed74f5dd724427ff5a29bMark A. Greer u8 chip_status_ctrl; 356165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer u8 iso_ctrl; 35749d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer u8 iso_ctrl_tech; 35812e9ade309db51e7ea26be3b4fd5bc6057ddc175Mark A. Greer u8 modulator_sys_clk_ctrl; 359165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer u8 special_fcn_reg1; 3604e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer unsigned int guard_time; 361165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer int technology; 362165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer int framing; 363165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer u8 tx_cmd; 3649d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer bool issue_eof; 365165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer int en2_gpio; 366165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer int en_gpio; 367165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct mutex lock; 368165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer unsigned int timeout; 369165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer bool ignore_timeout; 370165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct delayed_work timeout_work; 371165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}; 372165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 373165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 374165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_cmd(struct trf7970a *trf, u8 opcode) 375165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 376165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer u8 cmd = TRF7970A_CMD_BIT_CTRL | TRF7970A_CMD_BIT_OPCODE(opcode); 377165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer int ret; 378165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 379165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "cmd: 0x%x\n", cmd); 380165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 381165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = spi_write(trf->spi, &cmd, 1); 382165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) 383165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_err(trf->dev, "%s - cmd: 0x%x, ret: %d\n", __func__, cmd, 384165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret); 385165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return ret; 386165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 387165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 388165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_read(struct trf7970a *trf, u8 reg, u8 *val) 389165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 390165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer u8 addr = TRF7970A_CMD_BIT_RW | reg; 391165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer int ret; 392165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 393165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = spi_write_then_read(trf->spi, &addr, 1, val, 1); 394165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) 395165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_err(trf->dev, "%s - addr: 0x%x, ret: %d\n", __func__, addr, 396165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret); 397165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 398165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "read(0x%x): 0x%x\n", addr, *val); 399165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 400165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return ret; 401165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 402165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 4033e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greerstatic int trf7970a_read_cont(struct trf7970a *trf, u8 reg, u8 *buf, size_t len) 404165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 405165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer u8 addr = reg | TRF7970A_CMD_BIT_RW | TRF7970A_CMD_BIT_CONTINUOUS; 4063e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer struct spi_transfer t[2]; 4073e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer struct spi_message m; 408165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer int ret; 409165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 410165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "read_cont(0x%x, %zd)\n", addr, len); 411165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 4123e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer spi_message_init(&m); 4133e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer 4143e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer memset(&t, 0, sizeof(t)); 4153e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer 4163e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer t[0].tx_buf = &addr; 4173e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer t[0].len = sizeof(addr); 4183e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer spi_message_add_tail(&t[0], &m); 4193e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer 4203e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer t[1].rx_buf = buf; 4213e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer t[1].len = len; 4223e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer spi_message_add_tail(&t[1], &m); 4233e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer 4243e7f335689ebfa0a68814dfe9f0588076fb9ad01Mark A. Greer ret = spi_sync(trf->spi, &m); 425165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) 426165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_err(trf->dev, "%s - addr: 0x%x, ret: %d\n", __func__, addr, 427165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret); 428165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return ret; 429165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 430165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 431165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_write(struct trf7970a *trf, u8 reg, u8 val) 432165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 433165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer u8 buf[2] = { reg, val }; 434165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer int ret; 435165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 436165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "write(0x%x): 0x%x\n", reg, val); 437165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 438165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = spi_write(trf->spi, buf, 2); 439165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) 440165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_err(trf->dev, "%s - write: 0x%x 0x%x, ret: %d\n", __func__, 441165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer buf[0], buf[1], ret); 442165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 443165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return ret; 444165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 445165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 446165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_read_irqstatus(struct trf7970a *trf, u8 *status) 447165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 448165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer int ret; 449165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer u8 buf[2]; 450165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer u8 addr; 451165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 452165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer addr = TRF7970A_IRQ_STATUS | TRF7970A_CMD_BIT_RW; 453165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 454772079eb77587e0242752fa67685a8132d899f79Mark A. Greer if (trf->quirks & TRF7970A_QUIRK_IRQ_STATUS_READ) { 455165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer addr |= TRF7970A_CMD_BIT_CONTINUOUS; 456165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = spi_write_then_read(trf->spi, &addr, 1, buf, 2); 457165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } else { 458165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = spi_write_then_read(trf->spi, &addr, 1, buf, 1); 459165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 460165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 461165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) 462165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_err(trf->dev, "%s - irqstatus: Status read failed: %d\n", 463165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer __func__, ret); 464165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer else 465165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer *status = buf[0]; 466165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 467165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return ret; 468165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 469165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 470165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic void trf7970a_send_upstream(struct trf7970a *trf) 471165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 472165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer u8 rssi; 473165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 474165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_kfree_skb_any(trf->tx_skb); 475165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->tx_skb = NULL; 476165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 477165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (trf->rx_skb && !IS_ERR(trf->rx_skb) && !trf->aborting) 478165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer print_hex_dump_debug("trf7970a rx data: ", DUMP_PREFIX_NONE, 479165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 16, 1, trf->rx_skb->data, trf->rx_skb->len, 480165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer false); 481165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 482165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer /* According to the manual it is "good form" to reset the fifo and 483165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * read the RSSI levels & oscillator status register here. It doesn't 484165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * explain why. 485165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer */ 486165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_cmd(trf, TRF7970A_CMD_FIFO_RESET); 487165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_read(trf, TRF7970A_RSSI_OSC_STATUS, &rssi); 488165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 489165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->state = TRF7970A_ST_IDLE; 490165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 491165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (trf->aborting) { 492165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Abort process complete\n"); 493165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 494165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (!IS_ERR(trf->rx_skb)) { 495165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer kfree_skb(trf->rx_skb); 496165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->rx_skb = ERR_PTR(-ECANCELED); 497165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 498165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 499165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->aborting = false; 500165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 501165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 502165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->cb(trf->ddev, trf->cb_arg, trf->rx_skb); 503165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 504165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->rx_skb = NULL; 505165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 506165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 507165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic void trf7970a_send_err_upstream(struct trf7970a *trf, int errno) 508165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 509165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Error - state: %d, errno: %d\n", trf->state, errno); 510165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 511165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer kfree_skb(trf->rx_skb); 512165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->rx_skb = ERR_PTR(errno); 513165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 514165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_send_upstream(trf); 515165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 516165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 517165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_transmit(struct trf7970a *trf, struct sk_buff *skb, 518165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer unsigned int len) 519165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 520165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer unsigned int timeout; 521165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer int ret; 522165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 523165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer print_hex_dump_debug("trf7970a tx data: ", DUMP_PREFIX_NONE, 524165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 16, 1, skb->data, len, false); 525165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 526165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = spi_write(trf->spi, skb->data, len); 527165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) { 528165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_err(trf->dev, "%s - Can't send tx data: %d\n", __func__, 529165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret); 530165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return ret; 531165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 532165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 533165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer skb_pull(skb, len); 534165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 535165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (skb->len > 0) { 536165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->state = TRF7970A_ST_WAIT_FOR_TX_FIFO; 537165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer timeout = TRF7970A_WAIT_FOR_FIFO_DRAIN_TIMEOUT; 538165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } else { 5399d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer if (trf->issue_eof) { 5409d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer trf->state = TRF7970A_ST_WAIT_TO_ISSUE_EOF; 5419d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer timeout = TRF7970A_WAIT_TO_ISSUE_ISO15693_EOF; 5429d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer } else { 5439d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer trf->state = TRF7970A_ST_WAIT_FOR_RX_DATA; 5449d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer timeout = trf->timeout; 5459d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer } 546165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 547165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 548165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Setting timeout for %d ms, state: %d\n", timeout, 549165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->state); 550165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 551165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer schedule_delayed_work(&trf->timeout_work, msecs_to_jiffies(timeout)); 552165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 553165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return 0; 554165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 555165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 556165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic void trf7970a_fill_fifo(struct trf7970a *trf) 557165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 558165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct sk_buff *skb = trf->tx_skb; 559165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer unsigned int len; 560165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer int ret; 561165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer u8 fifo_bytes; 562165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 563165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = trf7970a_read(trf, TRF7970A_FIFO_STATUS, &fifo_bytes); 564165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) { 565165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_send_err_upstream(trf, ret); 566165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return; 567165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 568165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 569165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Filling FIFO - fifo_bytes: 0x%x\n", fifo_bytes); 570165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 5714542e8345af6076c87d036c7bd3f9dfa30768b1eMark A. Greer fifo_bytes &= ~TRF7970A_FIFO_STATUS_OVERFLOW; 572165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 573165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer /* Calculate how much more data can be written to the fifo */ 574165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer len = TRF7970A_FIFO_SIZE - fifo_bytes; 575165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer len = min(skb->len, len); 576165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 577165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = trf7970a_transmit(trf, skb, len); 578165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) 579165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_send_err_upstream(trf, ret); 580165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 581165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 582165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic void trf7970a_drain_fifo(struct trf7970a *trf, u8 status) 583165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 584165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct sk_buff *skb = trf->rx_skb; 585165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer int ret; 586165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer u8 fifo_bytes; 587165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 588165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (status & TRF7970A_IRQ_STATUS_ERROR) { 589165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_send_err_upstream(trf, -EIO); 590165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return; 591165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 592165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 593165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = trf7970a_read(trf, TRF7970A_FIFO_STATUS, &fifo_bytes); 594165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) { 595165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_send_err_upstream(trf, ret); 596165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return; 597165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 598165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 599165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Draining FIFO - fifo_bytes: 0x%x\n", fifo_bytes); 600165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 6014542e8345af6076c87d036c7bd3f9dfa30768b1eMark A. Greer fifo_bytes &= ~TRF7970A_FIFO_STATUS_OVERFLOW; 6024542e8345af6076c87d036c7bd3f9dfa30768b1eMark A. Greer 603165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (!fifo_bytes) 604165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer goto no_rx_data; 605165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 606165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (fifo_bytes > skb_tailroom(skb)) { 607165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer skb = skb_copy_expand(skb, skb_headroom(skb), 608165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer max_t(int, fifo_bytes, 609165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer TRF7970A_RX_SKB_ALLOC_SIZE), 610165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer GFP_KERNEL); 611165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (!skb) { 612165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_send_err_upstream(trf, -ENOMEM); 613165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return; 614165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 615165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 616165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer kfree_skb(trf->rx_skb); 617165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->rx_skb = skb; 618165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 619165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 620165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = trf7970a_read_cont(trf, TRF7970A_FIFO_IO_REGISTER, 621165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer skb_put(skb, fifo_bytes), fifo_bytes); 622165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) { 623165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_send_err_upstream(trf, ret); 624165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return; 625165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 626165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 627165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer /* If received Type 2 ACK/NACK, shift right 4 bits and pass up */ 628165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if ((trf->framing == NFC_DIGITAL_FRAMING_NFCA_T2T) && (skb->len == 1) && 629165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer (trf->special_fcn_reg1 == 630165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer TRF7970A_SPECIAL_FCN_REG1_4_BIT_RX)) { 631165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer skb->data[0] >>= 4; 632165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer status = TRF7970A_IRQ_STATUS_SRX; 633165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } else { 634165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->state = TRF7970A_ST_WAIT_FOR_RX_DATA_CONT; 635165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 636165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 637165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerno_rx_data: 638165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (status == TRF7970A_IRQ_STATUS_SRX) { /* Receive complete */ 639165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_send_upstream(trf); 640165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return; 641165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 642165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 643165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Setting timeout for %d ms\n", 644165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer TRF7970A_WAIT_FOR_RX_DATA_TIMEOUT); 645165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 646165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer schedule_delayed_work(&trf->timeout_work, 647165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer msecs_to_jiffies(TRF7970A_WAIT_FOR_RX_DATA_TIMEOUT)); 648165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 649165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 650165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic irqreturn_t trf7970a_irq(int irq, void *dev_id) 651165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 652165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct trf7970a *trf = dev_id; 653165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer int ret; 654165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer u8 status; 655165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 656165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer mutex_lock(&trf->lock); 657165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 658165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (trf->state == TRF7970A_ST_OFF) { 659165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer mutex_unlock(&trf->lock); 660165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return IRQ_NONE; 661165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 662165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 663165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = trf7970a_read_irqstatus(trf, &status); 664165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) { 665165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer mutex_unlock(&trf->lock); 666165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return IRQ_NONE; 667165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 668165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 669165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "IRQ - state: %d, status: 0x%x\n", trf->state, 670165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer status); 671165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 672165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (!status) { 673165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer mutex_unlock(&trf->lock); 674165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return IRQ_NONE; 675165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 676165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 677165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer switch (trf->state) { 678165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer case TRF7970A_ST_IDLE: 679165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer case TRF7970A_ST_IDLE_RX_BLOCKED: 680165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer /* If getting interrupts caused by RF noise, turn off the 681165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * receiver to avoid unnecessary interrupts. It will be 682165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * turned back on in trf7970a_in_send_cmd() when the next 683165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * command is issued. 684165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer */ 685165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (status & TRF7970A_IRQ_STATUS_ERROR) { 686165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_cmd(trf, TRF7970A_CMD_BLOCK_RX); 687165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->state = TRF7970A_ST_IDLE_RX_BLOCKED; 688165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 689165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 690165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_cmd(trf, TRF7970A_CMD_FIFO_RESET); 691165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer break; 692165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer case TRF7970A_ST_WAIT_FOR_TX_FIFO: 693165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (status & TRF7970A_IRQ_STATUS_TX) { 694165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->ignore_timeout = 695165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer !cancel_delayed_work(&trf->timeout_work); 696165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_fill_fifo(trf); 697165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } else { 698165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_send_err_upstream(trf, -EIO); 699165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 700165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer break; 701165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer case TRF7970A_ST_WAIT_FOR_RX_DATA: 702165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer case TRF7970A_ST_WAIT_FOR_RX_DATA_CONT: 703165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (status & TRF7970A_IRQ_STATUS_SRX) { 704165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->ignore_timeout = 705165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer !cancel_delayed_work(&trf->timeout_work); 706165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_drain_fifo(trf, status); 7074dd836e46c3ddcb2020646c867be589658440be0Mark A. Greer } else if (status == TRF7970A_IRQ_STATUS_TX) { 7084dd836e46c3ddcb2020646c867be589658440be0Mark A. Greer trf7970a_cmd(trf, TRF7970A_CMD_FIFO_RESET); 7094dd836e46c3ddcb2020646c867be589658440be0Mark A. Greer } else { 710165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_send_err_upstream(trf, -EIO); 711165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 712165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer break; 7139d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer case TRF7970A_ST_WAIT_TO_ISSUE_EOF: 7149d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer if (status != TRF7970A_IRQ_STATUS_TX) 7159d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer trf7970a_send_err_upstream(trf, -EIO); 7169d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer break; 717165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer default: 718165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_err(trf->dev, "%s - Driver in invalid state: %d\n", 719165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer __func__, trf->state); 720165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 721165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 722165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer mutex_unlock(&trf->lock); 723165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return IRQ_HANDLED; 724165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 725165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 7269d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greerstatic void trf7970a_issue_eof(struct trf7970a *trf) 7279d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer{ 7289d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer int ret; 7299d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer 7309d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer dev_dbg(trf->dev, "Issuing EOF\n"); 7319d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer 7329d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer ret = trf7970a_cmd(trf, TRF7970A_CMD_FIFO_RESET); 7339d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer if (ret) 7349d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer trf7970a_send_err_upstream(trf, ret); 7359d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer 7369d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer ret = trf7970a_cmd(trf, TRF7970A_CMD_EOF); 7379d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer if (ret) 7389d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer trf7970a_send_err_upstream(trf, ret); 7399d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer 7409d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer trf->state = TRF7970A_ST_WAIT_FOR_RX_DATA; 7419d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer 7429d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer dev_dbg(trf->dev, "Setting timeout for %d ms, state: %d\n", 7439d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer trf->timeout, trf->state); 7449d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer 7459d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer schedule_delayed_work(&trf->timeout_work, 7469d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer msecs_to_jiffies(trf->timeout)); 7479d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer} 7489d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer 749165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic void trf7970a_timeout_work_handler(struct work_struct *work) 750165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 751165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct trf7970a *trf = container_of(work, struct trf7970a, 752165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer timeout_work.work); 753165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 754165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Timeout - state: %d, ignore_timeout: %d\n", 755165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->state, trf->ignore_timeout); 756165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 757165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer mutex_lock(&trf->lock); 758165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 759165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (trf->ignore_timeout) 760165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->ignore_timeout = false; 761165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer else if (trf->state == TRF7970A_ST_WAIT_FOR_RX_DATA_CONT) 762165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_send_upstream(trf); /* No more rx data so send up */ 7639d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer else if (trf->state == TRF7970A_ST_WAIT_TO_ISSUE_EOF) 7649d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer trf7970a_issue_eof(trf); 765165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer else 766165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_send_err_upstream(trf, -ETIMEDOUT); 767165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 768165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer mutex_unlock(&trf->lock); 769165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 770165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 771165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_init(struct trf7970a *trf) 772165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 773165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer int ret; 774165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 775165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Initializing device - state: %d\n", trf->state); 776165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 777165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = trf7970a_cmd(trf, TRF7970A_CMD_SOFT_INIT); 778165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) 779165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer goto err_out; 780165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 781165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = trf7970a_cmd(trf, TRF7970A_CMD_IDLE); 782165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) 783165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer goto err_out; 784165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 7856c08df422ede7db94776b8099a5f43597629234cMark A. Greer ret = trf7970a_write(trf, TRF7970A_MODULATOR_SYS_CLK_CTRL, 0); 7866c08df422ede7db94776b8099a5f43597629234cMark A. Greer if (ret) 7876c08df422ede7db94776b8099a5f43597629234cMark A. Greer goto err_out; 7886c08df422ede7db94776b8099a5f43597629234cMark A. Greer 7896c08df422ede7db94776b8099a5f43597629234cMark A. Greer trf->modulator_sys_clk_ctrl = 0; 7906c08df422ede7db94776b8099a5f43597629234cMark A. Greer 791b887eb09d3cbda145d9fff4b9a56c384edd07ed7Mark A. Greer /* Must clear NFC Target Detection Level reg due to erratum */ 792b887eb09d3cbda145d9fff4b9a56c384edd07ed7Mark A. Greer ret = trf7970a_write(trf, TRF7970A_NFC_TARGET_LEVEL, 0); 793b887eb09d3cbda145d9fff4b9a56c384edd07ed7Mark A. Greer if (ret) 794b887eb09d3cbda145d9fff4b9a56c384edd07ed7Mark A. Greer goto err_out; 795b887eb09d3cbda145d9fff4b9a56c384edd07ed7Mark A. Greer 796165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = trf7970a_write(trf, TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS, 797165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS_WLH_96 | 798165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer TRF7970A_ADJUTABLE_FIFO_IRQ_LEVELS_WLL_32); 799165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) 800165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer goto err_out; 801165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 802165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = trf7970a_write(trf, TRF7970A_SPECIAL_FCN_REG1, 0); 803165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) 804165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer goto err_out; 805165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 806165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->special_fcn_reg1 = 0; 807165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 80849d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer trf->iso_ctrl = 0xff; 809165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return 0; 810165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 811165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greererr_out: 812165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Couldn't init device: %d\n", ret); 813165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return ret; 814165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 815165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 816165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic void trf7970a_switch_rf_off(struct trf7970a *trf) 817165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 818165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Switching rf off\n"); 819165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 820a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer trf->chip_status_ctrl &= ~TRF7970A_CHIP_STATUS_RF_ON; 821a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer 822a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer trf7970a_write(trf, TRF7970A_CHIP_STATUS_CTRL, trf->chip_status_ctrl); 823a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer 824165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->aborting = false; 825165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->state = TRF7970A_ST_OFF; 826e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer 827e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer pm_runtime_mark_last_busy(trf->dev); 828e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer pm_runtime_put_autosuspend(trf->dev); 829165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 830165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 83118422e686ef043b9abe004326ac9ffa1e38b81ecMark A. Greerstatic void trf7970a_switch_rf_on(struct trf7970a *trf) 832165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 833a08e54549e743ea3704da939f92caf3eaa8471d3Mark A. Greer int ret; 834a08e54549e743ea3704da939f92caf3eaa8471d3Mark A. Greer 835165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Switching rf on\n"); 836165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 837e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer pm_runtime_get_sync(trf->dev); 838165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 839a08e54549e743ea3704da939f92caf3eaa8471d3Mark A. Greer ret = trf7970a_init(trf); 840a08e54549e743ea3704da939f92caf3eaa8471d3Mark A. Greer if (ret) { 841a08e54549e743ea3704da939f92caf3eaa8471d3Mark A. Greer dev_err(trf->dev, "%s - Can't initialize: %d\n", __func__, ret); 842a08e54549e743ea3704da939f92caf3eaa8471d3Mark A. Greer return; 843a08e54549e743ea3704da939f92caf3eaa8471d3Mark A. Greer } 844a08e54549e743ea3704da939f92caf3eaa8471d3Mark A. Greer 845e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer trf->state = TRF7970A_ST_IDLE; 846165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 847165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 848165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_switch_rf(struct nfc_digital_dev *ddev, bool on) 849165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 850165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct trf7970a *trf = nfc_digital_get_drvdata(ddev); 851165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 852165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Switching RF - state: %d, on: %d\n", trf->state, on); 853165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 854165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer mutex_lock(&trf->lock); 855165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 856165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (on) { 857165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer switch (trf->state) { 858165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer case TRF7970A_ST_OFF: 85918422e686ef043b9abe004326ac9ffa1e38b81ecMark A. Greer trf7970a_switch_rf_on(trf); 860165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer break; 861165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer case TRF7970A_ST_IDLE: 862165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer case TRF7970A_ST_IDLE_RX_BLOCKED: 863165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer break; 864165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer default: 865165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_err(trf->dev, "%s - Invalid request: %d %d\n", 866165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer __func__, trf->state, on); 867165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_switch_rf_off(trf); 868165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 869165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } else { 870165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer switch (trf->state) { 871165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer case TRF7970A_ST_OFF: 872165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer break; 873165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer default: 874165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_err(trf->dev, "%s - Invalid request: %d %d\n", 875165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer __func__, trf->state, on); 876165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer /* FALLTHROUGH */ 877165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer case TRF7970A_ST_IDLE: 878165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer case TRF7970A_ST_IDLE_RX_BLOCKED: 879165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_switch_rf_off(trf); 880165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 881165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 882165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 883165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer mutex_unlock(&trf->lock); 88418422e686ef043b9abe004326ac9ffa1e38b81ecMark A. Greer return 0; 885165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 886165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 887165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_config_rf_tech(struct trf7970a *trf, int tech) 888165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 889165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer int ret = 0; 890165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 891165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "rf technology: %d\n", tech); 892165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 893165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer switch (tech) { 894165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer case NFC_DIGITAL_RF_TECH_106A: 89549d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer trf->iso_ctrl_tech = TRF7970A_ISO_CTRL_14443A_106; 89612e9ade309db51e7ea26be3b4fd5bc6057ddc175Mark A. Greer trf->modulator_sys_clk_ctrl = TRF7970A_MODULATOR_DEPTH_OOK; 8974e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer trf->guard_time = TRF7970A_GUARD_TIME_NFCA; 898165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer break; 899742b1f9fa292a1b8f5c8368464e114c9b71c2a81Mark A. Greer case NFC_DIGITAL_RF_TECH_106B: 900742b1f9fa292a1b8f5c8368464e114c9b71c2a81Mark A. Greer trf->iso_ctrl_tech = TRF7970A_ISO_CTRL_14443B_106; 901742b1f9fa292a1b8f5c8368464e114c9b71c2a81Mark A. Greer trf->modulator_sys_clk_ctrl = TRF7970A_MODULATOR_DEPTH_ASK10; 9024e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer trf->guard_time = TRF7970A_GUARD_TIME_NFCB; 903742b1f9fa292a1b8f5c8368464e114c9b71c2a81Mark A. Greer break; 9046857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer case NFC_DIGITAL_RF_TECH_212F: 9056857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer trf->iso_ctrl_tech = TRF7970A_ISO_CTRL_FELICA_212; 9066857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer trf->modulator_sys_clk_ctrl = TRF7970A_MODULATOR_DEPTH_ASK10; 9074e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer trf->guard_time = TRF7970A_GUARD_TIME_NFCF; 9086857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer break; 9096857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer case NFC_DIGITAL_RF_TECH_424F: 9106857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer trf->iso_ctrl_tech = TRF7970A_ISO_CTRL_FELICA_424; 9116857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer trf->modulator_sys_clk_ctrl = TRF7970A_MODULATOR_DEPTH_ASK10; 9124e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer trf->guard_time = TRF7970A_GUARD_TIME_NFCF; 9136857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer break; 9149d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer case NFC_DIGITAL_RF_TECH_ISO15693: 91549d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer trf->iso_ctrl_tech = TRF7970A_ISO_CTRL_15693_SGL_1OF4_2648; 91612e9ade309db51e7ea26be3b4fd5bc6057ddc175Mark A. Greer trf->modulator_sys_clk_ctrl = TRF7970A_MODULATOR_DEPTH_OOK; 9174e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer trf->guard_time = TRF7970A_GUARD_TIME_15693; 9189d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer break; 919165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer default: 920165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Unsupported rf technology: %d\n", tech); 921165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return -EINVAL; 922165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 923165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 924165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->technology = tech; 925165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 926165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return ret; 927165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 928165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 929165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_config_framing(struct trf7970a *trf, int framing) 930165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 93149d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer u8 iso_ctrl = trf->iso_ctrl_tech; 93249d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer int ret; 93349d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer 934165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "framing: %d\n", framing); 935165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 936165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer switch (framing) { 937165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer case NFC_DIGITAL_FRAMING_NFCA_SHORT: 938165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer case NFC_DIGITAL_FRAMING_NFCA_STANDARD: 939165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->tx_cmd = TRF7970A_CMD_TRANSMIT_NO_CRC; 94049d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer iso_ctrl |= TRF7970A_ISO_CTRL_RX_CRC_N; 941165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer break; 942165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer case NFC_DIGITAL_FRAMING_NFCA_STANDARD_WITH_CRC_A: 9438006289108fa9635d16a65d9db16da06d7dce201Mark A. Greer case NFC_DIGITAL_FRAMING_NFCA_T4T: 944742b1f9fa292a1b8f5c8368464e114c9b71c2a81Mark A. Greer case NFC_DIGITAL_FRAMING_NFCB: 945742b1f9fa292a1b8f5c8368464e114c9b71c2a81Mark A. Greer case NFC_DIGITAL_FRAMING_NFCB_T4T: 9466857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer case NFC_DIGITAL_FRAMING_NFCF: 9476857bb96271cd40ffb38825d43897d716310e3dbMark A. Greer case NFC_DIGITAL_FRAMING_NFCF_T3T: 9489d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer case NFC_DIGITAL_FRAMING_ISO15693_INVENTORY: 9499d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer case NFC_DIGITAL_FRAMING_ISO15693_T5T: 950165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->tx_cmd = TRF7970A_CMD_TRANSMIT; 95149d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer iso_ctrl &= ~TRF7970A_ISO_CTRL_RX_CRC_N; 952165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer break; 953165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer case NFC_DIGITAL_FRAMING_NFCA_T2T: 954165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->tx_cmd = TRF7970A_CMD_TRANSMIT; 95549d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer iso_ctrl |= TRF7970A_ISO_CTRL_RX_CRC_N; 956165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer break; 957165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer default: 958165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Unsupported Framing: %d\n", framing); 959165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return -EINVAL; 960165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 961165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 962165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->framing = framing; 963165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 96449d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer if (iso_ctrl != trf->iso_ctrl) { 96549d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer ret = trf7970a_write(trf, TRF7970A_ISO_CTRL, iso_ctrl); 96649d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer if (ret) 96749d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer return ret; 96849d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer 96949d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer trf->iso_ctrl = iso_ctrl; 970a0822a7e3b7333689b1c8cb92782e299791c2795Mark A. Greer 971a0822a7e3b7333689b1c8cb92782e299791c2795Mark A. Greer ret = trf7970a_write(trf, TRF7970A_MODULATOR_SYS_CLK_CTRL, 97212e9ade309db51e7ea26be3b4fd5bc6057ddc175Mark A. Greer trf->modulator_sys_clk_ctrl); 973a0822a7e3b7333689b1c8cb92782e299791c2795Mark A. Greer if (ret) 974a0822a7e3b7333689b1c8cb92782e299791c2795Mark A. Greer return ret; 97549d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer } 97649d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer 977a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer if (!(trf->chip_status_ctrl & TRF7970A_CHIP_STATUS_RF_ON)) { 978a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer ret = trf7970a_write(trf, TRF7970A_CHIP_STATUS_CTRL, 979a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer trf->chip_status_ctrl | 980a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer TRF7970A_CHIP_STATUS_RF_ON); 981a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer if (ret) 982a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer return ret; 983a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer 984a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer trf->chip_status_ctrl |= TRF7970A_CHIP_STATUS_RF_ON; 985a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer 9864e64eff837fb682dfb2a1188fb036d75ec57375cMark A. Greer usleep_range(trf->guard_time, trf->guard_time + 1000); 987a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer } 988a1d2dc5b407ae18b59b7a129c93c8eb5ad7b1c80Mark A. Greer 98949d19cc794e73c3383283a5366ff31572d71a795Mark A. Greer return 0; 990165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 991165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 992165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_in_configure_hw(struct nfc_digital_dev *ddev, int type, 993165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer int param) 994165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 995165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct trf7970a *trf = nfc_digital_get_drvdata(ddev); 99618422e686ef043b9abe004326ac9ffa1e38b81ecMark A. Greer int ret; 997165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 998165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Configure hw - type: %d, param: %d\n", type, param); 999165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1000165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer mutex_lock(&trf->lock); 1001165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 100218422e686ef043b9abe004326ac9ffa1e38b81ecMark A. Greer if (trf->state == TRF7970A_ST_OFF) 100318422e686ef043b9abe004326ac9ffa1e38b81ecMark A. Greer trf7970a_switch_rf_on(trf); 1004165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1005165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer switch (type) { 1006165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer case NFC_DIGITAL_CONFIG_RF_TECH: 1007165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = trf7970a_config_rf_tech(trf, param); 1008165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer break; 1009165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer case NFC_DIGITAL_CONFIG_FRAMING: 1010165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = trf7970a_config_framing(trf, param); 1011165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer break; 1012165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer default: 1013165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Unknown type: %d\n", type); 1014165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = -EINVAL; 1015165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 1016165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1017165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer mutex_unlock(&trf->lock); 1018165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return ret; 1019165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 1020165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 10219d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greerstatic int trf7970a_is_iso15693_write_or_lock(u8 cmd) 10229d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer{ 10239d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer switch (cmd) { 10249d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer case ISO15693_CMD_WRITE_SINGLE_BLOCK: 10259d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer case ISO15693_CMD_LOCK_BLOCK: 10269d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer case ISO15693_CMD_WRITE_MULTIPLE_BLOCK: 10279d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer case ISO15693_CMD_WRITE_AFI: 10289d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer case ISO15693_CMD_LOCK_AFI: 10299d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer case ISO15693_CMD_WRITE_DSFID: 10309d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer case ISO15693_CMD_LOCK_DSFID: 10319d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer return 1; 10329d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer break; 10339d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer default: 10349d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer return 0; 10359d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer } 10369d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer} 10379d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer 1038165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_per_cmd_config(struct trf7970a *trf, struct sk_buff *skb) 1039165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 1040165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer u8 *req = skb->data; 10419d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer u8 special_fcn_reg1, iso_ctrl; 1042165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer int ret; 1043165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 10449d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer trf->issue_eof = false; 10459d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer 1046165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer /* When issuing Type 2 read command, make sure the '4_bit_RX' bit in 1047165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * special functions register 1 is cleared; otherwise, its a write or 1048165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * sector select command and '4_bit_RX' must be set. 10499d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * 10509d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * When issuing an ISO 15693 command, inspect the flags byte to see 10519d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * what speed to use. Also, remember if the OPTION flag is set on 10529d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * a Type 5 write or lock command so the driver will know that it 10539d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer * has to send an EOF in order to get a response. 1054165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer */ 1055165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if ((trf->technology == NFC_DIGITAL_RF_TECH_106A) && 1056165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer (trf->framing == NFC_DIGITAL_FRAMING_NFCA_T2T)) { 1057165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (req[0] == NFC_T2T_CMD_READ) 1058165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer special_fcn_reg1 = 0; 1059165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer else 1060165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer special_fcn_reg1 = TRF7970A_SPECIAL_FCN_REG1_4_BIT_RX; 1061165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1062165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (special_fcn_reg1 != trf->special_fcn_reg1) { 1063165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = trf7970a_write(trf, TRF7970A_SPECIAL_FCN_REG1, 1064165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer special_fcn_reg1); 1065165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) 1066165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return ret; 1067165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1068165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->special_fcn_reg1 = special_fcn_reg1; 1069165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 10709d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer } else if (trf->technology == NFC_DIGITAL_RF_TECH_ISO15693) { 10719d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer iso_ctrl = trf->iso_ctrl & ~TRF7970A_ISO_CTRL_RFID_SPEED_MASK; 10729d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer 10739d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer switch (req[0] & ISO15693_REQ_FLAG_SPEED_MASK) { 10749d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer case 0x00: 10759d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer iso_ctrl |= TRF7970A_ISO_CTRL_15693_SGL_1OF4_662; 10769d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer break; 10779d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer case ISO15693_REQ_FLAG_SUB_CARRIER: 10789d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer iso_ctrl |= TRF7970A_ISO_CTRL_15693_DBL_1OF4_667a; 10799d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer break; 10809d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer case ISO15693_REQ_FLAG_DATA_RATE: 10819d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer iso_ctrl |= TRF7970A_ISO_CTRL_15693_SGL_1OF4_2648; 10829d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer break; 10839d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer case (ISO15693_REQ_FLAG_SUB_CARRIER | 10849d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer ISO15693_REQ_FLAG_DATA_RATE): 10859d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer iso_ctrl |= TRF7970A_ISO_CTRL_15693_DBL_1OF4_2669; 10869d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer break; 10879d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer } 10889d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer 10899d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer if (iso_ctrl != trf->iso_ctrl) { 10909d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer ret = trf7970a_write(trf, TRF7970A_ISO_CTRL, iso_ctrl); 10919d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer if (ret) 10929d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer return ret; 10939d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer 10949d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer trf->iso_ctrl = iso_ctrl; 10959d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer } 10969d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer 10979d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer if ((trf->framing == NFC_DIGITAL_FRAMING_ISO15693_T5T) && 10989d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer trf7970a_is_iso15693_write_or_lock(req[1]) && 10999d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer (req[0] & ISO15693_REQ_FLAG_OPTION)) 11009d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer trf->issue_eof = true; 1101165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 1102165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1103165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return 0; 1104165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 1105165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1106165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_in_send_cmd(struct nfc_digital_dev *ddev, 1107165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct sk_buff *skb, u16 timeout, 1108165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer nfc_digital_cmd_complete_t cb, void *arg) 1109165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 1110165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct trf7970a *trf = nfc_digital_get_drvdata(ddev); 1111165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer char *prefix; 1112165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer unsigned int len; 1113165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer int ret; 1114165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1115165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "New request - state: %d, timeout: %d ms, len: %d\n", 1116165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->state, timeout, skb->len); 1117165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1118165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (skb->len > TRF7970A_TX_MAX) 1119165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return -EINVAL; 1120165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1121165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer mutex_lock(&trf->lock); 1122165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1123165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if ((trf->state != TRF7970A_ST_IDLE) && 1124165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer (trf->state != TRF7970A_ST_IDLE_RX_BLOCKED)) { 1125165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_err(trf->dev, "%s - Bogus state: %d\n", __func__, 1126165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->state); 1127165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = -EIO; 1128165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer goto out_err; 1129165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 1130165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1131165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (trf->aborting) { 1132165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Abort process complete\n"); 1133165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->aborting = false; 1134165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = -ECANCELED; 1135165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer goto out_err; 1136165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 1137165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1138165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->rx_skb = nfc_alloc_recv_skb(TRF7970A_RX_SKB_ALLOC_SIZE, 1139165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer GFP_KERNEL); 1140165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (!trf->rx_skb) { 1141165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Can't alloc rx_skb\n"); 1142165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = -ENOMEM; 1143165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer goto out_err; 1144165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 1145165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1146165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (trf->state == TRF7970A_ST_IDLE_RX_BLOCKED) { 1147165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = trf7970a_cmd(trf, TRF7970A_CMD_ENABLE_RX); 1148165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) 1149165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer goto out_err; 1150165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1151165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->state = TRF7970A_ST_IDLE; 1152165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 1153165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1154165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = trf7970a_per_cmd_config(trf, skb); 1155165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) 1156165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer goto out_err; 1157165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1158165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->ddev = ddev; 1159165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->tx_skb = skb; 1160165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->cb = cb; 1161165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->cb_arg = arg; 1162165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->timeout = timeout; 1163165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->ignore_timeout = false; 1164165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1165165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer len = skb->len; 1166165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer prefix = skb_push(skb, TRF7970A_TX_SKB_HEADROOM); 1167165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1168165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer /* TX data must be prefixed with a FIFO reset cmd, a cmd that depends 1169165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * on what the current framing is, the address of the TX length byte 1 1170165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer * register (0x1d), and the 2 byte length of the data to be transmitted. 1171165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer */ 1172165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer prefix[0] = TRF7970A_CMD_BIT_CTRL | 1173165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer TRF7970A_CMD_BIT_OPCODE(TRF7970A_CMD_FIFO_RESET); 1174165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer prefix[1] = TRF7970A_CMD_BIT_CTRL | 1175165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer TRF7970A_CMD_BIT_OPCODE(trf->tx_cmd); 1176165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer prefix[2] = TRF7970A_CMD_BIT_CONTINUOUS | TRF7970A_TX_LENGTH_BYTE1; 1177165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1178165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (trf->framing == NFC_DIGITAL_FRAMING_NFCA_SHORT) { 1179165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer prefix[3] = 0x00; 1180165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer prefix[4] = 0x0f; /* 7 bits */ 1181165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } else { 1182165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer prefix[3] = (len & 0xf00) >> 4; 1183165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer prefix[3] |= ((len & 0xf0) >> 4); 1184165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer prefix[4] = ((len & 0x0f) << 4); 1185165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 1186165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1187165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer len = min_t(int, skb->len, TRF7970A_FIFO_SIZE); 1188165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1189165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = trf7970a_transmit(trf, skb, len); 1190165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) { 1191165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer kfree_skb(trf->rx_skb); 1192165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->rx_skb = NULL; 1193165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 1194165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1195165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerout_err: 1196165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer mutex_unlock(&trf->lock); 1197165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return ret; 1198165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 1199165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1200165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_tg_configure_hw(struct nfc_digital_dev *ddev, 1201165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer int type, int param) 1202165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 1203165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct trf7970a *trf = nfc_digital_get_drvdata(ddev); 1204165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1205165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Unsupported interface\n"); 1206165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1207165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return -EINVAL; 1208165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 1209165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1210165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_tg_send_cmd(struct nfc_digital_dev *ddev, 1211165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct sk_buff *skb, u16 timeout, 1212165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer nfc_digital_cmd_complete_t cb, void *arg) 1213165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 1214165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct trf7970a *trf = nfc_digital_get_drvdata(ddev); 1215165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1216165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Unsupported interface\n"); 1217165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1218165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return -EINVAL; 1219165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 1220165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1221165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_tg_listen(struct nfc_digital_dev *ddev, 1222165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer u16 timeout, nfc_digital_cmd_complete_t cb, void *arg) 1223165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 1224165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct trf7970a *trf = nfc_digital_get_drvdata(ddev); 1225165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1226165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Unsupported interface\n"); 1227165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1228165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return -EINVAL; 1229165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 1230165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1231165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic void trf7970a_abort_cmd(struct nfc_digital_dev *ddev) 1232165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 1233165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct trf7970a *trf = nfc_digital_get_drvdata(ddev); 1234165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1235165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_dbg(trf->dev, "Abort process initiated\n"); 1236165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1237165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer mutex_lock(&trf->lock); 12385876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer 12395876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer switch (trf->state) { 12405876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer case TRF7970A_ST_WAIT_FOR_TX_FIFO: 12415876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer case TRF7970A_ST_WAIT_FOR_RX_DATA: 12425876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer case TRF7970A_ST_WAIT_FOR_RX_DATA_CONT: 12435876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer case TRF7970A_ST_WAIT_TO_ISSUE_EOF: 12445876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer trf->aborting = true; 12455876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer break; 12465876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer default: 12475876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer break; 12485876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer } 12495876bc75e2d3174cd1cd944ee33edc77cd1173caMark A. Greer 1250165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer mutex_unlock(&trf->lock); 1251165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 1252165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1253165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic struct nfc_digital_ops trf7970a_nfc_ops = { 1254165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer .in_configure_hw = trf7970a_in_configure_hw, 1255165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer .in_send_cmd = trf7970a_in_send_cmd, 1256165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer .tg_configure_hw = trf7970a_tg_configure_hw, 1257165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer .tg_send_cmd = trf7970a_tg_send_cmd, 1258165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer .tg_listen = trf7970a_tg_listen, 1259165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer .switch_rf = trf7970a_switch_rf, 1260165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer .abort_cmd = trf7970a_abort_cmd, 1261165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}; 1262165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1263fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greerstatic int trf7970a_get_autosuspend_delay(struct device_node *np) 1264fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer{ 1265fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer int autosuspend_delay, ret; 1266fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer 1267fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer ret = of_property_read_u32(np, "autosuspend-delay", &autosuspend_delay); 1268fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer if (ret) 1269fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer autosuspend_delay = TRF7970A_AUTOSUSPEND_DELAY; 1270fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer 1271fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer return autosuspend_delay; 1272fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer} 1273fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer 12743bd14233aa0733fbc6c3f75ec928f1a393522644Mark A. Greerstatic int trf7970a_get_vin_voltage_override(struct device_node *np, 12753bd14233aa0733fbc6c3f75ec928f1a393522644Mark A. Greer u32 *vin_uvolts) 12763bd14233aa0733fbc6c3f75ec928f1a393522644Mark A. Greer{ 12773bd14233aa0733fbc6c3f75ec928f1a393522644Mark A. Greer return of_property_read_u32(np, "vin-voltage-override", vin_uvolts); 12783bd14233aa0733fbc6c3f75ec928f1a393522644Mark A. Greer} 12793bd14233aa0733fbc6c3f75ec928f1a393522644Mark A. Greer 1280165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_probe(struct spi_device *spi) 1281165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 1282165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct device_node *np = spi->dev.of_node; 1283165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct trf7970a *trf; 1284fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer int uvolts, autosuspend_delay, ret; 1285165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1286165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (!np) { 1287165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_err(&spi->dev, "No Device Tree entry\n"); 1288165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return -EINVAL; 1289165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 1290165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1291165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf = devm_kzalloc(&spi->dev, sizeof(*trf), GFP_KERNEL); 1292165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (!trf) 1293165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return -ENOMEM; 1294165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1295165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->state = TRF7970A_ST_OFF; 1296165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->dev = &spi->dev; 1297165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->spi = spi; 1298165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1299165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer spi->mode = SPI_MODE_1; 1300165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer spi->bits_per_word = 8; 1301165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 130224707296c762d1828c4a51aa1872dc275dc3fcccMark A. Greer ret = spi_setup(spi); 130324707296c762d1828c4a51aa1872dc275dc3fcccMark A. Greer if (ret < 0) { 130424707296c762d1828c4a51aa1872dc275dc3fcccMark A. Greer dev_err(trf->dev, "Can't set up SPI Communication\n"); 130524707296c762d1828c4a51aa1872dc275dc3fcccMark A. Greer return ret; 130624707296c762d1828c4a51aa1872dc275dc3fcccMark A. Greer } 130724707296c762d1828c4a51aa1872dc275dc3fcccMark A. Greer 1308772079eb77587e0242752fa67685a8132d899f79Mark A. Greer if (of_property_read_bool(np, "irq-status-read-quirk")) 1309772079eb77587e0242752fa67685a8132d899f79Mark A. Greer trf->quirks |= TRF7970A_QUIRK_IRQ_STATUS_READ; 1310772079eb77587e0242752fa67685a8132d899f79Mark A. Greer 1311165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer /* There are two enable pins - both must be present */ 1312165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->en_gpio = of_get_named_gpio(np, "ti,enable-gpios", 0); 1313165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (!gpio_is_valid(trf->en_gpio)) { 1314165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_err(trf->dev, "No EN GPIO property\n"); 1315165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return trf->en_gpio; 1316165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 1317165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1318165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = devm_gpio_request_one(trf->dev, trf->en_gpio, 1319f23b73526b82ca2ef333362e704a51d817c1ffc1Mark A. Greer GPIOF_DIR_OUT | GPIOF_INIT_LOW, "trf7970a EN"); 1320165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) { 1321165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_err(trf->dev, "Can't request EN GPIO: %d\n", ret); 1322165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return ret; 1323165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 1324165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1325165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->en2_gpio = of_get_named_gpio(np, "ti,enable-gpios", 1); 1326165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (!gpio_is_valid(trf->en2_gpio)) { 1327165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_err(trf->dev, "No EN2 GPIO property\n"); 1328165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return trf->en2_gpio; 1329165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 1330165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1331165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = devm_gpio_request_one(trf->dev, trf->en2_gpio, 1332f23b73526b82ca2ef333362e704a51d817c1ffc1Mark A. Greer GPIOF_DIR_OUT | GPIOF_INIT_LOW, "trf7970a EN2"); 1333165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) { 1334165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_err(trf->dev, "Can't request EN2 GPIO: %d\n", ret); 1335165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return ret; 1336165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 1337165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 133895064bd95a822659f4a606b485aba5009d70fc88Mark A. Greer if (of_property_read_bool(np, "en2-rf-quirk")) 133995064bd95a822659f4a606b485aba5009d70fc88Mark A. Greer trf->quirks |= TRF7970A_QUIRK_EN2_MUST_STAY_LOW; 134095064bd95a822659f4a606b485aba5009d70fc88Mark A. Greer 1341165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = devm_request_threaded_irq(trf->dev, spi->irq, NULL, 1342165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_irq, IRQF_TRIGGER_RISING | IRQF_ONESHOT, 1343165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer "trf7970a", trf); 1344165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) { 1345165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_err(trf->dev, "Can't request IRQ#%d: %d\n", spi->irq, ret); 1346165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return ret; 1347165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 1348165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1349165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer mutex_init(&trf->lock); 1350165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer INIT_DELAYED_WORK(&trf->timeout_work, trf7970a_timeout_work_handler); 1351165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1352165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->regulator = devm_regulator_get(&spi->dev, "vin"); 1353165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (IS_ERR(trf->regulator)) { 1354165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = PTR_ERR(trf->regulator); 1355165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_err(trf->dev, "Can't get VIN regulator: %d\n", ret); 1356165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer goto err_destroy_lock; 1357165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 1358165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1359165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = regulator_enable(trf->regulator); 1360165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) { 1361165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_err(trf->dev, "Can't enable VIN: %d\n", ret); 1362165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer goto err_destroy_lock; 1363165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 1364165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 13653bd14233aa0733fbc6c3f75ec928f1a393522644Mark A. Greer ret = trf7970a_get_vin_voltage_override(np, &uvolts); 13663bd14233aa0733fbc6c3f75ec928f1a393522644Mark A. Greer if (ret) 13673bd14233aa0733fbc6c3f75ec928f1a393522644Mark A. Greer uvolts = regulator_get_voltage(trf->regulator); 1368ebcc5a0d08e6a680558ed74f5dd724427ff5a29bMark A. Greer 1369ebcc5a0d08e6a680558ed74f5dd724427ff5a29bMark A. Greer if (uvolts > 4000000) 1370ebcc5a0d08e6a680558ed74f5dd724427ff5a29bMark A. Greer trf->chip_status_ctrl = TRF7970A_CHIP_STATUS_VRS5_3; 1371ebcc5a0d08e6a680558ed74f5dd724427ff5a29bMark A. Greer 1372165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf->ddev = nfc_digital_allocate_device(&trf7970a_nfc_ops, 1373165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer TRF7970A_SUPPORTED_PROTOCOLS, 1374165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer NFC_DIGITAL_DRV_CAPS_IN_CRC, TRF7970A_TX_SKB_HEADROOM, 1375165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 0); 1376165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (!trf->ddev) { 1377165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_err(trf->dev, "Can't allocate NFC digital device\n"); 1378165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = -ENOMEM; 1379165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer goto err_disable_regulator; 1380165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 1381165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1382165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer nfc_digital_set_parent_dev(trf->ddev, trf->dev); 1383165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer nfc_digital_set_drvdata(trf->ddev, trf); 1384165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer spi_set_drvdata(spi, trf); 1385165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1386fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer autosuspend_delay = trf7970a_get_autosuspend_delay(np); 1387fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer 1388fd0c8280cf47104e87dc10828ded541b4e84dedaMark A. Greer pm_runtime_set_autosuspend_delay(trf->dev, autosuspend_delay); 1389e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer pm_runtime_use_autosuspend(trf->dev); 1390e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer pm_runtime_enable(trf->dev); 1391e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer 1392165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret = nfc_digital_register_device(trf->ddev); 1393165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer if (ret) { 1394165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer dev_err(trf->dev, "Can't register NFC digital device: %d\n", 1395165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer ret); 1396165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer goto err_free_ddev; 1397165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 1398165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1399165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return 0; 1400165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1401165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greererr_free_ddev: 1402e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer pm_runtime_disable(trf->dev); 1403165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer nfc_digital_free_device(trf->ddev); 1404165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greererr_disable_regulator: 1405165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer regulator_disable(trf->regulator); 1406165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greererr_destroy_lock: 1407165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer mutex_destroy(&trf->lock); 1408165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return ret; 1409165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 1410165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1411165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic int trf7970a_remove(struct spi_device *spi) 1412165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer{ 1413165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer struct trf7970a *trf = spi_get_drvdata(spi); 1414165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1415165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer mutex_lock(&trf->lock); 1416165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1417165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer switch (trf->state) { 1418165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer case TRF7970A_ST_WAIT_FOR_TX_FIFO: 1419165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer case TRF7970A_ST_WAIT_FOR_RX_DATA: 1420165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer case TRF7970A_ST_WAIT_FOR_RX_DATA_CONT: 14219d9304b32154be5908a3abbb46215297b9ce0a4cMark A. Greer case TRF7970A_ST_WAIT_TO_ISSUE_EOF: 1422165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer trf7970a_send_err_upstream(trf, -ECANCELED); 1423e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer /* FALLTHROUGH */ 1424e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer case TRF7970A_ST_IDLE: 1425e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer case TRF7970A_ST_IDLE_RX_BLOCKED: 1426e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer pm_runtime_put_sync(trf->dev); 1427165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer break; 1428165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer default: 1429165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer break; 1430165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer } 1431165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1432165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer mutex_unlock(&trf->lock); 1433165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1434e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer pm_runtime_disable(trf->dev); 1435e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer 1436165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer nfc_digital_unregister_device(trf->ddev); 1437165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer nfc_digital_free_device(trf->ddev); 1438165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1439165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer regulator_disable(trf->regulator); 1440165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1441165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer mutex_destroy(&trf->lock); 1442165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1443165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer return 0; 1444165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer} 1445165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1446e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer#ifdef CONFIG_PM_RUNTIME 1447e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greerstatic int trf7970a_pm_runtime_suspend(struct device *dev) 1448e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer{ 1449e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer struct spi_device *spi = container_of(dev, struct spi_device, dev); 1450e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer struct trf7970a *trf = spi_get_drvdata(spi); 1451e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer int ret; 1452e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer 1453e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer dev_dbg(dev, "Runtime suspend\n"); 1454e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer 1455e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer if (trf->state != TRF7970A_ST_OFF) { 1456e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer dev_dbg(dev, "Can't suspend - not in OFF state (%d)\n", 1457e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer trf->state); 1458e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer return -EBUSY; 1459e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer } 1460e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer 1461e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer gpio_set_value(trf->en_gpio, 0); 1462e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer gpio_set_value(trf->en2_gpio, 0); 1463e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer 1464e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer ret = regulator_disable(trf->regulator); 1465e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer if (ret) 1466e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer dev_err(dev, "%s - Can't disable VIN: %d\n", __func__, ret); 1467e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer 1468e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer return ret; 1469e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer} 1470e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer 1471e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greerstatic int trf7970a_pm_runtime_resume(struct device *dev) 1472e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer{ 1473e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer struct spi_device *spi = container_of(dev, struct spi_device, dev); 1474e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer struct trf7970a *trf = spi_get_drvdata(spi); 1475e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer int ret; 1476e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer 1477e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer dev_dbg(dev, "Runtime resume\n"); 1478e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer 1479e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer ret = regulator_enable(trf->regulator); 1480e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer if (ret) { 1481e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer dev_err(dev, "%s - Can't enable VIN: %d\n", __func__, ret); 1482e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer return ret; 1483e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer } 1484e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer 1485e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer usleep_range(5000, 6000); 1486e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer 148795064bd95a822659f4a606b485aba5009d70fc88Mark A. Greer if (!(trf->quirks & TRF7970A_QUIRK_EN2_MUST_STAY_LOW)) { 148895064bd95a822659f4a606b485aba5009d70fc88Mark A. Greer gpio_set_value(trf->en2_gpio, 1); 148995064bd95a822659f4a606b485aba5009d70fc88Mark A. Greer usleep_range(1000, 2000); 149095064bd95a822659f4a606b485aba5009d70fc88Mark A. Greer } 149195064bd95a822659f4a606b485aba5009d70fc88Mark A. Greer 1492e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer gpio_set_value(trf->en_gpio, 1); 1493e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer 1494e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer usleep_range(20000, 21000); 1495e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer 1496e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer pm_runtime_mark_last_busy(dev); 1497e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer 1498e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer return 0; 1499e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer} 1500e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer#endif 1501e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer 1502e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greerstatic const struct dev_pm_ops trf7970a_pm_ops = { 1503e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer SET_RUNTIME_PM_OPS(trf7970a_pm_runtime_suspend, 1504e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer trf7970a_pm_runtime_resume, NULL) 1505e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer}; 1506e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer 1507165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic const struct spi_device_id trf7970a_id_table[] = { 1508772079eb77587e0242752fa67685a8132d899f79Mark A. Greer { "trf7970a", 0 }, 1509165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer { } 1510165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}; 1511165063f1dac43e48ceb907490fff0a8413b9a32dMark A. GreerMODULE_DEVICE_TABLE(spi, trf7970a_id_table); 1512165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1513165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greerstatic struct spi_driver trf7970a_spi_driver = { 1514165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer .probe = trf7970a_probe, 1515165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer .remove = trf7970a_remove, 1516165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer .id_table = trf7970a_id_table, 1517165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer .driver = { 1518165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer .name = "trf7970a", 1519165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer .owner = THIS_MODULE, 1520e6403b7c756f9d694332870ba0c2be7a4aa0b8c0Mark A. Greer .pm = &trf7970a_pm_ops, 1521165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer }, 1522165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer}; 1523165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1524165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greermodule_spi_driver(trf7970a_spi_driver); 1525165063f1dac43e48ceb907490fff0a8413b9a32dMark A. Greer 1526165063f1dac43e48ceb907490fff0a8413b9a32dMark A. GreerMODULE_AUTHOR("Mark A. Greer <mgreer@animalcreek.com>"); 1527165063f1dac43e48ceb907490fff0a8413b9a32dMark A. GreerMODULE_LICENSE("GPL v2"); 1528165063f1dac43e48ceb907490fff0a8413b9a32dMark A. GreerMODULE_DESCRIPTION("TI trf7970a RFID/NFC Transceiver Driver"); 1529