NFC: Read NFCC is fused or unfused

Implement kernel ioctl to read if NFCC is fused or not

CRs-Fixed: 692604
Change-Id: I588c3bcf0fc52e8b857fdeaa1f9f2a343efec744
Signed-off-by: Nakul Kadannavar <nakulk@codeaurora.org>
diff --git a/drivers/nfc/nfc-nci.c b/drivers/nfc/nfc-nci.c
index 9ba0a87..e51da7f 100644
--- a/drivers/nfc/nfc-nci.c
+++ b/drivers/nfc/nfc-nci.c
@@ -762,6 +762,60 @@
 }
 
 /*
+ * Inside nfc_ioctl_nfcc_efuse
+ *
+ * @brief   nfc_ioctl_nfcc_efuse
+ *
+ */
+int nfc_ioctl_nfcc_efuse(struct file *filp, unsigned int cmd,
+				unsigned long arg)
+{
+	int r = 0;
+	unsigned short slave_addr = 0xE;
+	unsigned short curr_addr;
+	unsigned char efuse_addr  = EFUSE_REG;
+	unsigned char efuse_value = 0xFF;
+
+	struct qca199x_dev *qca199x_dev = filp->private_data;
+
+	curr_addr = qca199x_dev->client->addr;
+	qca199x_dev->client->addr = slave_addr;
+
+	r = nfc_i2c_write(qca199x_dev->client,
+				&efuse_addr, 1);
+	if (r < 0) {
+		/* Restore original NFCC slave I2C address */
+		qca199x_dev->client->addr = curr_addr;
+		dev_err(&qca199x_dev->client->dev,
+		"ERROR_WRITE_FAIL : i2c write fail\n");
+		return -EIO;
+	}
+
+	/*
+	 * NFCC chip needs to be at least
+	 * 10usec high before make it low
+	 */
+	usleep_range(10, 15);
+
+	r = i2c_master_recv(qca199x_dev->client, &efuse_value,
+					sizeof(efuse_value));
+	if (r < 0) {
+		/* Restore original NFCC slave I2C address */
+		qca199x_dev->client->addr = curr_addr;
+		dev_err(&qca199x_dev->client->dev,
+		"ERROR_I2C_RCV_FAIL : i2c recv fail\n");
+		return -EIO;
+	}
+
+	dev_dbg(&qca199x_dev->client->dev, "%s : EFUSE_VALUE %02x\n",
+	__func__, efuse_value);
+
+	/* Restore original NFCC slave I2C address */
+	qca199x_dev->client->addr = curr_addr;
+	return efuse_value;
+}
+
+/*
  * Inside nfc_ioctl_nfcc_version
  *
  * @brief   nfc_ioctl_nfcc_version
@@ -934,7 +988,7 @@
 static long nfc_ioctl(struct file *pfile, unsigned int cmd, unsigned long arg)
 {
 	int r = 0;
-
+	struct qca199x_dev *qca199x_dev = pfile->private_data;
 	switch (cmd) {
 
 	case NFC_SET_PWR:
@@ -956,6 +1010,14 @@
 	case NFCC_INITIAL_CORE_RESET_NTF:
 		r = nfc_ioctl_core_reset_ntf(pfile, cmd, arg);
 		break;
+	case NFC_GET_EFUSE:
+		r = nfc_ioctl_nfcc_efuse(pfile, cmd, arg);
+		if (r < 0) {
+			r = 0xFF;
+			dev_err(&qca199x_dev->client->dev,
+			"nfc_ioctl : FAILED TO READ EFUSE TYPE\n");
+		}
+		break;
 	default:
 		r = -ENOIOCTLCMD;
 	}
diff --git a/drivers/nfc/nfc-nci.h b/drivers/nfc/nfc-nci.h
index 8186861..398fa3f 100644
--- a/drivers/nfc/nfc-nci.h
+++ b/drivers/nfc/nfc-nci.h
@@ -60,6 +60,7 @@
 #define SET_RX_BLOCK	_IOW(0xE9, 0x04, unsigned int)
 #define SET_EMULATOR_TEST_POINT		_IOW(0xE9, 0x05, unsigned int)
 #define NFCC_VERSION				_IOW(0xE9, 0x08, unsigned int)
+#define NFC_GET_EFUSE				_IOW(0xE9, 0x09, unsigned int)
 #define NFCC_INITIAL_CORE_RESET_NTF		_IOW(0xE9, 0x10, unsigned int)
 
 #define NFC_MAX_I2C_TRANSFER	(0x0400)