2 * Copyright (C) 2010,Imagis Technology Co. Ltd. All Rights Reserved.
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; either version 2 of the License, or
7 * (at your option) any later version.
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
16 #include <linux/i2c.h>
17 #include <linux/delay.h>
18 #include <linux/slab.h>
19 #include <linux/firmware.h>
20 #include <linux/stat.h>
21 #include <asm/unaligned.h>
22 #include <linux/uaccess.h>
23 #include <linux/fcntl.h>
24 #include <linux/file.h>
26 #include <linux/err.h>
29 #include "ist30xx_update.h"
30 #include "ist30xx_tracking.h"
33 #include "ist30xx_misc.h"
36 #if IST30XX_INTERNAL_BIN
37 #include "./firmware/core_prime.h"
38 #if IST30XX_MULTIPLE_TSP
39 //#include "./firmware/core_prime.h"
41 #endif // IST30XX_INTERNAL_BIN
43 struct ist30xx_tags *ts_tags;
45 u32 ist30xx_fw_ver = 0;
46 u32 ist30xx_param_ver = 0;
47 u32 ist30xx_sub_ver = 0;
49 extern struct ist30xx_data *ts_data;
51 extern void ist30xx_disable_irq(struct ist30xx_data *data);
52 extern void ist30xx_enable_irq(struct ist30xx_data *data);
54 int ist30xx_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg *msgs,
55 int msg_num, u8 *cmd_buf)
58 int idx = msg_num - 1;
59 int size = msgs[idx].len;
62 int trans_size, max_size = 0;
64 if (msg_num == WRITE_CMD_MSG_LEN)
65 max_size = I2C_MAX_WRITE_SIZE;
66 else if (msg_num == READ_CMD_MSG_LEN)
67 max_size = I2C_MAX_READ_SIZE;
69 if (unlikely(max_size == 0)) {
70 tsp_err("%s() : transaction size(%d)\n", __func__, max_size);
74 if (msg_num == WRITE_CMD_MSG_LEN) {
75 msg_buf = kmalloc(max_size + IST30XX_ADDR_LEN, GFP_KERNEL);
78 memcpy(msg_buf, cmd_buf, IST30XX_ADDR_LEN);
83 trans_size = (size >= max_size ? max_size : size);
85 msgs[idx].len = trans_size;
86 if (msg_num == WRITE_CMD_MSG_LEN) {
87 memcpy(&msg_buf[IST30XX_ADDR_LEN], pbuf, trans_size);
88 msgs[idx].buf = msg_buf;
89 msgs[idx].len += IST30XX_ADDR_LEN;
91 ret = i2c_transfer(adap, msgs, msg_num);
92 if (unlikely(ret != msg_num)) {
93 tsp_err("%s() : i2c_transfer failed(%d), num=%d\n",
94 __func__, ret, msg_num);
98 if (msg_num == WRITE_CMD_MSG_LEN)
101 msgs[idx].buf += trans_size;
106 if (msg_num == WRITE_CMD_MSG_LEN)
112 int ist30xx_read_buf(struct i2c_client *client, u32 cmd, u32 *buf, u16 len)
115 u32 le_reg = cpu_to_be32(cmd);
117 struct i2c_msg msg[READ_CMD_MSG_LEN] = {
119 .addr = client->addr,
121 .len = IST30XX_ADDR_LEN,
122 .buf = (u8 *)&le_reg,
125 .addr = client->addr,
127 .len = len * IST30XX_DATA_LEN,
132 ret = ist30xx_i2c_transfer(client->adapter, msg, READ_CMD_MSG_LEN, NULL);
133 if (unlikely(ret != READ_CMD_MSG_LEN))
136 for (i = 0; i < len; i++)
137 buf[i] = cpu_to_be32(buf[i]);
142 int ist30xx_write_buf(struct i2c_client *client, u32 cmd, u32 *buf, u16 len)
147 u8 cmd_buf[IST30XX_ADDR_LEN];
148 u8 msg_buf[IST30XX_DATA_LEN * (len + 1)];
150 put_unaligned_be32(cmd, cmd_buf);
152 if (likely(len > 0)) {
153 for (i = 0; i < len; i++)
154 put_unaligned_be32(buf[i], msg_buf + (i * IST30XX_DATA_LEN));
156 /* then add dummy data(4byte) */
157 put_unaligned_be32(0, msg_buf);
161 msg.addr = client->addr;
163 msg.len = IST30XX_DATA_LEN * len;
166 ret = ist30xx_i2c_transfer(client->adapter, &msg, WRITE_CMD_MSG_LEN,
168 if (unlikely(ret != WRITE_CMD_MSG_LEN))
174 int ist30xxb_burst_read(struct i2c_client *client, u32 addr,
179 int max_len = I2C_MAX_READ_SIZE / IST30XX_DATA_LEN;
181 addr |= IST30XXB_BURST_ACCESS;
183 for (i = 0; i < len; i += max_len) {
184 if (len < max_len) max_len = len;
186 ret = ist30xx_read_buf(client, addr, buf32, max_len);
188 tsp_err("Burst fail, addr: %x\n", __func__, addr);
192 addr += max_len * IST30XX_DATA_LEN;
199 #define IST30XXB_ISP_READ (1)
200 #define IST30XXB_ISP_WRITE (2)
201 #define IST30XXB_ISP_ERASE_ALL (3)
202 #define IST30XXB_ISP_ERASE_PAGE (4)
204 int ist30xxb_isp_reset(void)
208 #if (IMAGIS_TSP_IC == IMAGIS_IST3038)
209 ret = ist30xx_write_cmd(ts_data->client, IST30XXB_REG_EEPMODE, 0x180);
213 ret = ist30xx_write_cmd(ts_data->client, IST30XXB_REG_EEPPWRCTRL, 0xB200);
217 ret = ist30xx_write_cmd(ts_data->client, IST30XXB_REG_EEPPWRCTRL, 0x9200);
226 int ist30xxb_isp_enable(bool enable)
231 ret = ist30xx_write_cmd(ts_data->client, IST30XXB_REG_EEPISPEN, 0x1);
235 ret = ist30xx_write_cmd(ts_data->client, IST30XXB_REG_LDOOSC, 0x74C8);
239 ret = ist30xx_write_cmd(ts_data->client, IST30XXB_REG_CLKDIV, 0x3);
243 #if (IMAGIS_TSP_IC != IMAGIS_IST3038)
244 ret = ist30xx_write_cmd(ts_data->client,
245 IST30XXB_REG_PADCTRL, 0x03300000);
252 ret = ist30xx_write_cmd(ts_data->client, IST30XXB_REG_WDTCON, 0x0);
256 ret = ist30xx_write_cmd(ts_data->client, IST30XXB_REG_EEPISPEN, 0x0);
266 int ist30xxb_isp_mode(int mode)
272 case IST30XXB_ISP_READ:
275 case IST30XXB_ISP_WRITE:
278 case IST30XXB_ISP_ERASE_ALL:
281 case IST30XXB_ISP_ERASE_PAGE:
285 tsp_err("ISP fail, unknown mode\n");
289 ret = ist30xx_write_cmd(ts_data->client, IST30XXB_REG_EEPMODE, val);
291 tsp_err("ISP fail, IST30XXB_REG_EEPMODE\n");
298 int ist30xxb_isp_erase(struct i2c_client *client, int mode, u32 addr)
302 u8 buf[EEPROM_PAGE_SIZE] = { 0, };
304 ret = ist30xxb_isp_mode(mode);
308 ret = ist30xx_write_cmd(client, IST30XXB_REG_EEPADDR, addr);
310 tsp_err("ISP fail, IST30XXB_REG_EEPADDR\n");
314 val = (EEPROM_PAGE_SIZE / IST30XX_DATA_LEN);
315 ret = ist30xx_write_buf(client, IST30XXB_REG_EEPWDAT, (u32 *)buf, val);
317 tsp_err("ISP fail, IST30XXB_REG_EEPWDAT\n");
323 ist30xxb_isp_reset();
328 int ist30xxb_isp_write(struct i2c_client *client, u32 addr,
329 const u32 *buf32, int len)
333 ret = ist30xx_write_cmd(client, IST30XXB_REG_EEPADDR, addr);
335 tsp_err("ISP fail, IST30XXB_REG_EEPADDR\n");
339 ret = ist30xx_write_buf(client, IST30XXB_REG_EEPWDAT, (u32 *)buf32, len);
341 tsp_err("ISP fail, IST30XXB_REG_EEPWDAT\n");
348 int ist30xxb_isp_read(struct i2c_client *client, u32 addr,
353 int max_len = I2C_MAX_READ_SIZE / IST30XX_DATA_LEN;
355 for (i = 0; i < len; i += max_len) {
356 if (len < max_len) max_len = len;
358 /* IST30xxB ISP read mode */
359 ret = ist30xxb_isp_mode(IST30XXB_ISP_READ);
363 ret = ist30xx_write_cmd(client, IST30XXB_REG_EEPADDR, addr);
365 tsp_err("ISP fail, IST30XXB_REG_EEPADDR\n");
369 ret = ist30xx_read_buf(client, IST30XXB_REG_EEPRDAT, buf32, max_len);
371 tsp_err("ISP fail, IST30XXB_REG_EEPWDAT\n");
375 addr += max_len * IST30XX_DATA_LEN;
382 int ist30xxb_cmd_read_chksum(struct i2c_client *client,
383 u32 start_addr, u32 end_addr, u32 *chksum)
386 u32 val = (1 << 31); // Chkecksum enable
389 val |= (end_addr / IST30XX_DATA_LEN - 1) << 16;
391 ret = ist30xx_write_cmd(client, IST30XXB_REG_CHKSMOD, val);
393 tsp_err("ISP fail, IST30XXB_REG_CHKSMOD (%x)\n", val);
398 ret = ist30xx_read_cmd(client, IST30XXB_REG_CHKSDAT, chksum);
400 tsp_err("ISP fail, IST30XXB_REG_CHKSDAT (%x)\n", chksum);
407 int ist30xxb_read_chksum(struct i2c_client *client, u32 *chksum)
410 u32 start_addr, end_addr;
411 u32 chksum1 = 0, chksum2 = 0;
414 end_addr = ts_data->tags.fw_addr + ts_data->tags.fw_size;
415 ret = ist30xxb_cmd_read_chksum(client, start_addr, end_addr, &chksum1);
419 start_addr = ts_data->tags.cfg_addr;
420 end_addr = ts_data->tags.sensor3_addr + ts_data->tags.sensor3_size;
421 ret = ist30xxb_cmd_read_chksum(client, start_addr, end_addr, &chksum2);
425 *chksum = chksum1 | (chksum2 << 16);
427 tsp_info("chksum: %x(%x~%x, %x~%x)\n", *chksum,
428 0, ts_data->tags.fw_addr + ts_data->tags.fw_size,
429 start_addr, end_addr);
434 int ist30xxb_read_chksum_all(struct i2c_client *client, u32 *chksum)
437 u32 start_addr, end_addr;
440 end_addr = IST30XX_EEPROM_SIZE;
441 ret = ist30xxb_cmd_read_chksum(client, start_addr, end_addr, chksum);
445 tsp_info("chksum: %x(%x~%x)\n", *chksum, start_addr, end_addr);
450 int ist30xxb_isp_fw_read(struct i2c_client *client, u32 *buf32)
455 u16 addr = EEPROM_BASE_ADDR;
456 int len = EEPROM_PAGE_SIZE / IST30XX_DATA_LEN;
460 /* IST30xxB ISP enable */
461 ret = ist30xxb_isp_enable(true);
465 for (i = 0; i < IST30XX_EEPROM_SIZE; i += EEPROM_PAGE_SIZE) {
466 ret = ist30xxb_isp_read(client, addr, buf32, len);
468 goto isp_fw_read_end;
470 addr += EEPROM_PAGE_SIZE;
475 /* IST30xxB ISP disable */
476 ist30xxb_isp_enable(false);
480 int ist30xxb_isp_fw_update(struct i2c_client *client, const u8 *buf,
485 u32 page_cnt = IST30XX_EEPROM_SIZE / EEPROM_PAGE_SIZE;
486 u16 addr = EEPROM_BASE_ADDR;
487 int len = EEPROM_PAGE_SIZE / IST30XX_DATA_LEN;
489 ist30xx_tracking(TRACK_CMD_FWUPDATE);
491 /* IST30xxB ISP enable */
492 ret = ist30xxb_isp_enable(true);
494 goto isp_fw_update_end;
496 /* IST30xxB ISP erase */
497 ret = ist30xxb_isp_erase(client, IST30XXB_ISP_ERASE_ALL, 0);
499 goto isp_fw_update_end;
501 #if (IMAGIS_TSP_IC == IMAGIS_IST3038)
502 /* IST30xxB ISP read all checksum */
503 ret = ist30xxb_read_chksum_all(client, chksum);
505 goto isp_fw_update_end;
507 /* IST30xxB compare checksum */
508 if (unlikely(*chksum != 0))
509 goto isp_fw_update_end;
512 /* IST30xxB power reset */
515 /* IST30xxB ISP enable */
516 ret = ist30xxb_isp_enable(true);
518 goto isp_fw_update_end;
520 for (i = 0; i < page_cnt; i++) {
521 /* IST30xxB ISP write mode */
522 ret = ist30xxb_isp_mode(IST30XXB_ISP_WRITE);
524 goto isp_fw_update_end;
526 ret = ist30xxb_isp_write(client, addr, (u32 *)buf, len);
528 goto isp_fw_update_end;
530 addr += EEPROM_PAGE_SIZE;
531 buf += EEPROM_PAGE_SIZE;
535 ist30xxb_isp_reset();
538 #if (IMAGIS_TSP_IC == IMAGIS_IST3038)
539 ist30xxb_read_chksum_all(client, chksum);
543 /* IST30xxB ISP disable */
544 ist30xxb_isp_enable(false);
548 int ist30xx_fw_write(struct i2c_client *client, const u8 *buf)
552 u32 *buf32 = (u32 *)(buf + ts_data->fw.index);
553 u32 size = ts_data->fw.size;
555 if (unlikely((size <= 0) || (size > IST30XX_EEPROM_SIZE)))
559 len = (size >= EEPROM_PAGE_SIZE ? EEPROM_PAGE_SIZE : size);
561 ret = ist30xx_write_buf(client, CMD_ENTER_FW_UPDATE, buf32, (len >> 2));
574 u32 ist30xx_parse_ver(int flag, const u8 *buf)
577 u32 *buf32 = (u32 *)buf;
580 ver = (u32)buf32[(ts_data->tags.flag_addr + 60) >> 2];
581 else if (flag == FLAG_SUB)
582 ver = (u32)buf32[(ts_data->tags.flag_addr + 52) >> 2];
583 else if (flag == FLAG_PARAM)
584 ver = (u32)(buf32[(ts_data->tags.cfg_addr + 4) >> 2] & 0xFFFF);
586 tsp_warn("Parsing ver's flag is not corrent!\n");
592 int calib_ms_delay = WAIT_CALIB_CNT;
593 int ist30xx_calib_wait(void)
595 int cnt = calib_ms_delay;
597 ts_data->status.calib_msg = 0;
601 if (ts_data->status.calib_msg) {
602 tsp_info("Calibration status : %d, Max raw gap : %d - (%08x)\n",
603 CALIB_TO_STATUS(ts_data->status.calib_msg),
604 CALIB_TO_GAP(ts_data->status.calib_msg),
605 ts_data->status.calib_msg);
607 if (CALIB_TO_OS_VALUE(ts_data->status.calib_msg) == 0xFFFF)
609 else if (CALIB_TO_STATUS(ts_data->status.calib_msg) == 0)
610 return 0; // Calibrate success
615 tsp_warn("Calibration time out\n");
620 int ist30xx_calibrate(int wait_cnt)
624 tsp_info("*** Calibrate %ds ***\n", calib_ms_delay / 10);
626 ts_data->status.update = 1;
628 ist30xx_disable_irq(ts_data);
629 ist30xx_reset(false);
631 ret = ist30xx_cmd_calibrate(ts_data->client);
635 ist30xx_enable_irq(ts_data);
636 ret = ist30xx_calib_wait();
641 ist30xx_disable_irq(ts_data);
643 ist30xx_reset(false);
645 ts_data->status.update = 2;
647 ist30xx_enable_irq(ts_data);
653 int ist30xx_parse_tags(struct ist30xx_data *data, const u8 *buf, const u32 size)
657 ts_tags = (struct ist30xx_tags *)(&buf[size - sizeof(struct ist30xx_tags)]);
659 if (!strncmp(ts_tags->magic1, IST30XX_TAG_MAGIC, sizeof(ts_tags->magic1))
660 && !strncmp(ts_tags->magic2, IST30XX_TAG_MAGIC, sizeof(ts_tags->magic2))
662 data->fw.index = ts_tags->fw_addr;
663 data->fw.size = ts_tags->flag_addr - ts_tags->fw_addr +
665 data->fw.chksum = ts_tags->chksum;
666 data->tags = *ts_tags;
671 tsp_verb("Tagts magic1: %s, magic2: %s\n",
672 ts_tags->magic1, ts_tags->magic2);
673 tsp_verb(" fw: %x(%x)\n", ts_tags->fw_addr, ts_tags->fw_size);
674 tsp_verb(" flag: %x(%x)\n", ts_tags->flag_addr, ts_tags->flag_size);
675 tsp_verb(" cfg: %x(%x)\n", ts_tags->cfg_addr, ts_tags->cfg_size);
676 tsp_verb(" sensor1: %x(%x)\n", ts_tags->sensor1_addr,
677 ts_tags->sensor1_size);
678 tsp_verb(" sensor2: %x(%x)\n", ts_tags->sensor2_addr,
679 ts_tags->sensor2_size);
680 tsp_verb(" sensor3: %x(%x)\n", ts_tags->sensor3_addr,
681 ts_tags->sensor3_size);
682 tsp_verb(" chksum: %x\n", ts_tags->chksum);
683 tsp_verb(" build time : %04d/%02d/%02d (%02d:%02d:%02d)\n",
684 ts_tags->year, ts_tags->month, ts_tags->day,
685 ts_tags->hour, ts_tags->min, ts_tags->sec);
690 void ist30xx_get_update_info(struct ist30xx_data *data, const u8 *buf,
695 ret = ist30xx_parse_tags(data, buf, size);
696 if (unlikely(ret != TAGS_PARSE_OK))
697 tsp_warn("Cannot find tags of F/W, make a tags by 'tagts.exe'\n");
700 #if (IST30XX_DEBUG) && (IST30XX_INTERNAL_BIN)
701 extern TSP_INFO ist30xx_tsp_info;
702 extern TKEY_INFO ist30xx_tkey_info;
703 int ist30xx_get_tkey_info(struct ist30xx_data *data)
706 TSP_INFO *tsp = &ist30xx_tsp_info;
707 TKEY_INFO *tkey = &ist30xx_tkey_info;
710 cfg_buf = (u8 *)&data->fw.buf[data->tags.cfg_addr];
712 tkey->enable = (bool)(cfg_buf[0x321] & 1);
713 tkey->axis_rx = (bool)((cfg_buf[0x321] >> 1) & 1);
714 tkey->key_num = (u8)cfg_buf[0x322];
715 tkey->baseline = (u16)((cfg_buf[0x324] << 8) | cfg_buf[0x323]);
716 tkey->ch_num[0] = (u8)cfg_buf[0x326];
717 tkey->ch_num[1] = (u8)cfg_buf[0x327];
718 tkey->ch_num[2] = (u8)cfg_buf[0x328];
719 tkey->ch_num[3] = (u8)cfg_buf[0x329];
720 tkey->ch_num[4] = (u8)cfg_buf[0x32A];
723 if (tsp->dir.swap_xy)
728 if (tsp->dir.swap_xy)
737 #define TSP_INFO_SWAP_XY (1 << 0)
738 #define TSP_INFO_FLIP_X (1 << 1)
739 #define TSP_INFO_FLIP_Y (1 << 2)
740 int ist30xx_get_tsp_info(struct ist30xx_data *data)
743 TSP_INFO *tsp = &ist30xx_tsp_info;
744 u8 *cfg_buf, *sensor_buf;
746 cfg_buf = (u8 *)&data->fw.buf[data->tags.cfg_addr];
747 sensor_buf = (u8 *)&data->fw.buf[data->tags.sensor1_addr];
749 tsp->finger_num = (u8)cfg_buf[0x304];
750 tsp->dir.swap_xy = (bool)(cfg_buf[0x305] & TSP_INFO_SWAP_XY ? true : false);
751 tsp->dir.flip_x = (bool)(cfg_buf[0x305] & TSP_INFO_FLIP_X ? true : false);
752 tsp->dir.flip_y = (bool)(cfg_buf[0x305] & TSP_INFO_FLIP_Y ? true : false);
753 tsp->baseline = (u16)((cfg_buf[0x319] << 8) | cfg_buf[0x318]);
755 tsp->ch_num.tx = (u8)sensor_buf[0x40];
756 tsp->ch_num.rx = (u8)sensor_buf[0x41];
758 tsp->node.len = tsp->ch_num.tx * tsp->ch_num.rx;
759 tsp->height = (tsp->dir.swap_xy ? tsp->ch_num.rx : tsp->ch_num.tx);
760 tsp->width = (tsp->dir.swap_xy ? tsp->ch_num.tx : tsp->ch_num.rx);
764 #endif // (IST30XX_DEBUG) && (IST30XX_INTERNAL_BIN)
767 #define update_next_step(ret) { if (unlikely(ret)) goto end; }
768 int ist30xx_fw_update(struct i2c_client *client, const u8 *buf, int size,
773 struct ist30xx_fw *fw = &ts_data->fw;
775 tsp_info("*** Firmware update ***\n");
776 tsp_info(" core: %x, param: %x, sub: %x (addr: 0x%x ~ 0x%x)\n",
777 ist30xx_fw_ver, ist30xx_param_ver, ist30xx_sub_ver,
778 fw->index, (fw->index + fw->size));
780 ts_data->status.update = 1;
782 ist30xx_disable_irq(ts_data);
786 if (mode) { /* ISP Mode */
787 ret = ist30xxb_isp_fw_update(client, buf, &chksum);
788 update_next_step(ret);
789 } else { /* I2C SW Mode */
790 ret = ist30xx_cmd_update(client, CMD_ENTER_FW_UPDATE);
791 update_next_step(ret);
793 ret = ist30xx_fw_write(client, buf);
794 update_next_step(ret);
798 buf += IST30XX_EEPROM_SIZE;
799 size -= IST30XX_EEPROM_SIZE;
801 ist30xx_reset(false);
803 ret = ist30xx_read_cmd(client, CMD_GET_CHECKSUM, &chksum);
804 if (unlikely((ret) || (chksum != fw->chksum)))
807 ret = ist30xx_get_ver_info(ts_data);
808 update_next_step(ret);
812 tsp_warn("Firmware update Fail!, ret=%d\n", ret);
813 } else if (unlikely(chksum != fw->chksum)) {
814 tsp_warn("Error CheckSum: %x(%x)\n", chksum, fw->chksum);
818 ist30xx_enable_irq(ts_data);
820 ts_data->status.update = 2;
825 int ist30xx_fw_recovery(struct ist30xx_data *data)
828 u8 *fw = data->fw.buf;
829 int fw_size = data->fw.buf_size;
831 ist30xx_get_update_info(data, fw, fw_size);
832 ist30xx_fw_ver = ist30xx_parse_ver(FLAG_FW, fw);
833 ist30xx_param_ver = ist30xx_parse_ver(FLAG_PARAM, fw);
834 ist30xx_sub_ver = ist30xx_parse_ver(FLAG_SUB, fw);
836 mutex_lock(&ist30xx_mutex);
837 ret = ist30xx_fw_update(data->client, fw, fw_size, true);
838 ist30xx_calibrate(1);
839 mutex_unlock(&ist30xx_mutex);
846 #if IST30XX_INTERNAL_BIN
847 int ist30xx_check_fw(struct ist30xx_data *data, const u8 *buf)
852 ret = ist30xx_read_cmd(data->client, CMD_GET_CHECKSUM, &chksum);
856 if (unlikely(chksum != data->fw.chksum)) {
857 tsp_warn("Checksum compare error, (IC: %08x, Bin: %08x)\n",
858 chksum, data->fw.chksum);
865 bool ist30xx_check_valid_vendor(u32 tsp_vendor)
867 switch (tsp_vendor) {
871 case TSP_TYPE_MELFAS:
873 case TSP_TYPE_SYNOPEX:
875 case TSP_TYPE_TAEYANG:
878 case TSP_TYPE_OTHERS:
887 #if IST30XX_MULTIPLE_TSP
888 void ist30xx_set_tsp_fw(struct ist30xx_data *data)
891 struct ist30xx_fw *fw = &data->fw;
893 switch (data->tsp_type) {
897 fw->buf = (u8 *)ist30xxb_fw;
898 fw->buf_size = sizeof(ist30xxb_fw);
902 fw->buf = (u8 *)ist30xxb_fw2;
903 fw->buf_size = sizeof(ist30xxb_fw2);
906 case TSP_TYPE_UNKNOWN:
909 tsp_warn("Unknown TSP vendor(0x%x)\n", data->tsp_type);
912 tsp_info("TSP vendor : %s(%x)\n", str, data->tsp_type);
914 ist30xx_get_update_info(ts_data, fw->buf, fw->buf_size);
915 ist30xx_fw_ver = ist30xx_parse_ver(FLAG_FW, fw->buf);
916 ist30xx_param_ver = ist30xx_parse_ver(FLAG_PARAM, fw->buf);
917 ist30xx_sub_ver = ist30xx_parse_ver(FLAG_SUB, fw->buf);
919 #endif // IST30XX_MULTIPLE_TSP
921 int ist30xx_check_auto_update(struct ist30xx_data *data)
924 int retry = IST30XX_FW_UPDATE_RETRY;
925 u32 tsp_type = TSP_TYPE_UNKNOWN;
927 bool tsp_check = false;
928 struct ist30xx_fw *fw = &data->fw;
931 ret = ist30xx_read_cmd(data->client,
932 CMD_GET_TSP_PANNEL_TYPE, &tsp_type);
933 if (likely(ret == 0)) {
934 if (likely(ist30xx_check_valid_vendor(tsp_type) == true))
940 retry = IST30XX_FW_UPDATE_RETRY;
942 if (unlikely(!tsp_check))
945 ist30xx_get_ver_info(data);
947 if (likely((fw->param_ver > 0) && (fw->param_ver < 0xFFFFFFFF))) {
948 if (unlikely(((fw->core_ver & MASK_FW_VER) != IST30XX_FW_VER3) &&
949 ((fw->core_ver & MASK_FW_VER) != IST30XX_FW_VER4) &&
950 ((fw->core_ver & MASK_FW_VER) != IST30XX_FW_VER5)))
953 tsp_info("Version compare IC: %x(%x), BIN: %x(%x)\n",
954 fw->param_ver, fw->core_ver, ist30xx_param_ver, ist30xx_fw_ver);
956 /* If FW version is same, check FW checksum */
957 if (likely((fw->core_ver == ist30xx_fw_ver) &&
958 (fw->param_ver == ist30xx_param_ver) &&
959 (fw->sub_ver == 0))) {
960 ret = ist30xx_read_cmd(data->client, CMD_GET_CHECKSUM, &chksum);
961 if (unlikely((ret) || (chksum != fw->chksum))) {
962 tsp_warn("Checksum error, IC: %x, Bin: %x (ret: %d)\n",
963 chksum, fw->chksum, ret);
969 * fw->core_ver : FW core version in TSP IC
970 * fw->param_ver : FW version if TSP IC
971 * ist30xx_fw_ver : FW core version in FW Binary
972 * ist30xx_fw_ver : FW version in FW Binary
974 /* If the ver of binary is higher than ver of IC, FW update operate. */
976 if (likely((fw->core_ver >= ist30xx_fw_ver) &&
977 (fw->param_ver >= ist30xx_param_ver)))
985 int ist30xx_auto_bin_update(struct ist30xx_data *data)
988 int retry = IST30XX_FW_UPDATE_RETRY;
989 struct ist30xx_fw *fw = &data->fw;
991 fw->buf = (u8 *)ist30xxb_fw;
992 fw->buf_size = sizeof(ist30xxb_fw);
994 #if IST30XX_MULTIPLE_TSP
995 ist30xx_set_tsp_fw(data);
997 ist30xx_get_update_info(data, fw->buf, fw->buf_size);
998 ist30xx_fw_ver = ist30xx_parse_ver(FLAG_FW, fw->buf);
999 ist30xx_param_ver = ist30xx_parse_ver(FLAG_PARAM, fw->buf);
1000 ist30xx_sub_ver = ist30xx_parse_ver(FLAG_SUB, fw->buf);
1003 tsp_info("IC: %x, Binary ver core: %x, param: %x, sub: %x\n",
1004 data->chip_id, ist30xx_fw_ver, ist30xx_param_ver, ist30xx_sub_ver);
1006 mutex_lock(&ist30xx_mutex);
1007 ret = ist30xx_check_auto_update(data);
1008 mutex_unlock(&ist30xx_mutex);
1010 if (likely(ret >= 0))
1013 update_bin: // TSP is not ready / FW update
1014 tsp_info("Update version. param(core): %x(%x, %x) -> %x(%x, %x)\n",
1015 fw->param_ver, fw->core_ver, fw->sub_ver,
1016 ist30xx_param_ver, ist30xx_fw_ver, ist30xx_sub_ver);
1018 mutex_lock(&ist30xx_mutex);
1020 ret = ist30xx_fw_update(data->client, fw->buf, fw->buf_size, true);
1024 mutex_unlock(&ist30xx_mutex);
1029 if (unlikely(retry > 0 && ist30xx_check_fw(data, fw->buf)))
1032 ist30xx_calibrate(IST30XX_FW_UPDATE_RETRY);
1036 #endif // IST30XX_INTERNAL_BIN
1038 #define MAX_FILE_PATH 255
1039 /* sysfs: /sys/class/touch/firmware/firmware */
1040 ssize_t ist30xx_fw_store(struct device *dev, struct device_attribute *attr,
1041 const char *buf, size_t size)
1047 mm_segment_t old_fs = { 0 };
1048 struct file *fp = NULL;
1049 long fsize = 0, nread = 0;
1050 char fw_path[MAX_FILE_PATH];
1051 const struct firmware *request_fw = NULL;
1055 sscanf(buf, "%d %d", &mode, &calib);
1058 case MASK_UPDATE_INTERNAL:
1059 #if IST30XX_INTERNAL_BIN
1060 fw = ts_data->fw.buf;
1061 fw_size = ts_data->fw.buf_size;
1063 tsp_warn("Not support internal bin!!\n", );
1068 case MASK_UPDATE_FW:
1069 ret = request_firmware(&request_fw, IST30XXB_FW_NAME,
1070 &ts_data->client->dev);
1072 tsp_warn("File not found, %s\n", IST30XXB_FW_NAME);
1076 fw = (u8 *)request_fw->data;
1077 fw_size = (u32)request_fw->size;
1080 case MASK_UPDATE_SDCARD:
1084 snprintf(fw_path, MAX_FILE_PATH, "/sdcard/touch/firmware/%s",
1086 fp = filp_open(fw_path, O_RDONLY, 0);
1088 tsp_info("file %s open error:%d\n", fw_path, (s32)fp);
1092 fsize = fp->f_path.dentry->d_inode->i_size;
1094 buff = kzalloc((size_t)fsize, GFP_KERNEL);
1096 tsp_info("fail to alloc buffer\n");
1100 nread = vfs_read(fp, (char __user *)buff, fsize, &fp->f_pos);
1101 if (nread != fsize) {
1102 tsp_info("mismatch fw size\n");
1107 fw_size = (u32)fsize;
1109 filp_close(fp, current->files);
1110 tsp_info("firmware is loaded!!\n");
1113 case MASK_UPDATE_ERASE:
1114 tsp_info("EEPROM all erase!!\n");
1116 mutex_lock(&ist30xx_mutex);
1117 ist30xx_disable_irq(ts_data);
1118 ist30xxb_isp_enable(true);
1119 ist30xxb_isp_erase(ts_data->client, IST30XXB_ISP_ERASE_ALL, 0);
1120 ist30xxb_isp_enable(false);
1121 ist30xx_reset(false);
1122 ist30xx_enable_irq(ts_data);
1123 mutex_unlock(&ist30xx_mutex);
1125 ist30xx_start(ts_data);
1131 ist30xx_get_update_info(ts_data, fw, fw_size);
1132 ist30xx_fw_ver = ist30xx_parse_ver(FLAG_FW, fw);
1133 ist30xx_param_ver = ist30xx_parse_ver(FLAG_PARAM, fw);
1134 ist30xx_sub_ver = ist30xx_parse_ver(FLAG_SUB, fw);
1136 mutex_lock(&ist30xx_mutex);
1137 ist30xx_fw_update(ts_data->client, fw, fw_size, true);
1140 ist30xx_calibrate(1);
1141 mutex_unlock(&ist30xx_mutex);
1143 ist30xx_start(ts_data);
1145 if (request_fw != NULL)
1146 release_firmware(request_fw);
1152 filp_close(fp, NULL);
1160 /* sysfs: /sys/class/touch/firmware/fw_sdcard */
1161 ssize_t ist30xx_fw_sdcard_show(struct device *dev,
1162 struct device_attribute *attr, char *buf)
1167 mm_segment_t old_fs = { 0 };
1168 struct file *fp = NULL;
1169 long fsize = 0, nread = 0;
1170 char fw_path[MAX_FILE_PATH];
1175 snprintf(fw_path, MAX_FILE_PATH, "/sdcard/touch/firmware/%s",
1177 fp = filp_open(fw_path, O_RDONLY, 0);
1179 tsp_info("file %s open error:%d\n", fw_path, (s32)fp);
1183 fsize = fp->f_path.dentry->d_inode->i_size;
1185 buff = kzalloc((size_t)fsize, GFP_KERNEL);
1187 tsp_info("fail to alloc buffer\n");
1191 nread = vfs_read(fp, (char __user *)buff, fsize, &fp->f_pos);
1192 if (nread != fsize) {
1193 tsp_info("mismatch fw size\n");
1198 fw_size = (u32)fsize;
1200 filp_close(fp, current->files);
1201 tsp_info("firmware is loaded!!\n");
1203 ist30xx_get_update_info(ts_data, fw, fw_size);
1204 ist30xx_fw_ver = ist30xx_parse_ver(FLAG_FW, fw);
1205 ist30xx_param_ver = ist30xx_parse_ver(FLAG_PARAM, fw);
1206 ist30xx_sub_ver = ist30xx_parse_ver(FLAG_SUB, fw);
1208 mutex_lock(&ist30xx_mutex);
1209 ist30xx_fw_update(ts_data->client, fw, fw_size, true);
1210 mutex_unlock(&ist30xx_mutex);
1212 ist30xx_start(ts_data);
1219 filp_close(fp, NULL);
1226 /* sysfs: /sys/class/touch/firmware/firmware */
1227 ssize_t ist30xx_fw_status_show(struct device *dev,
1228 struct device_attribute *attr, char *buf)
1232 switch (ts_data->status.update) {
1234 count = sprintf(buf, "Downloading\n");
1237 count = sprintf(buf, "Update success, ver %x(%x) -> %x(%x, %x), "
1238 "status : %d, gap : %d\n",
1239 ts_data->fw.prev_param_ver, ts_data->fw.prev_core_ver,
1240 ts_data->fw.param_ver, ts_data->fw.core_ver,
1241 ts_data->fw.sub_ver,
1242 CALIB_TO_STATUS(ts_data->status.calib_msg),
1243 CALIB_TO_GAP(ts_data->status.calib_msg));
1246 count = sprintf(buf, "Pass\n");
1252 /* sysfs: /sys/class/touch/firmware/fw_read */
1253 u32 buf32_eeprom[IST30XX_EEPROM_SIZE / IST30XX_DATA_LEN];
1254 ssize_t ist30xx_fw_read_show(struct device *dev, struct device_attribute *attr,
1258 u8 *buf8 = (u8 *)buf32_eeprom;;
1260 mutex_lock(&ist30xx_mutex);
1261 ist30xx_disable_irq(ts_data);
1263 ist30xxb_isp_fw_read(ts_data->client, buf32_eeprom);
1264 for (i = 0; i < IST30XX_EEPROM_SIZE; i += 16) {
1265 tsp_debug("%07x: %02x%02x %02x%02x %02x%02x %02x%02x "
1266 "%02x%02x %02x%02x %02x%02x %02x%02x\n", i,
1267 buf8[i], buf8[i + 1], buf8[i + 2], buf8[i + 3],
1268 buf8[i + 4], buf8[i + 5], buf8[i + 6], buf8[i + 7],
1269 buf8[i + 8], buf8[i + 9], buf8[i + 10], buf8[i + 11],
1270 buf8[i + 12], buf8[i + 13], buf8[i + 14], buf8[i + 15]);
1273 ist30xx_reset(false);
1274 ist30xx_enable_irq(ts_data);
1275 mutex_unlock(&ist30xx_mutex);
1277 ist30xx_start(ts_data);
1282 /* sysfs: /sys/class/touch/firmware/version */
1283 ssize_t ist30xx_fw_version_show(struct device *dev,
1284 struct device_attribute *attr, char *buf)
1288 count = sprintf(buf, "ID: %x, f/w core: %x, param: %x, sub: %x\n",
1289 ts_data->chip_id, ts_data->fw.core_ver,
1290 ts_data->fw.param_ver, ts_data->fw.sub_ver);
1292 #if IST30XX_INTERNAL_BIN
1296 ist30xx_get_update_info(ts_data, ts_data->fw.buf, ts_data->fw.buf_size);
1298 count += snprintf(msg, sizeof(msg),
1299 " Header - f/w ver: %x, param: %x, sub: %x\r\n",
1300 ist30xx_parse_ver(FLAG_FW, ts_data->fw.buf),
1301 ist30xx_parse_ver(FLAG_PARAM, ts_data->fw.buf),
1302 ist30xx_parse_ver(FLAG_SUB, ts_data->fw.buf));
1303 strncat(buf, msg, sizeof(msg));
1312 static DEVICE_ATTR(fw_read, S_IRWXUGO, ist30xx_fw_read_show, NULL);
1313 static DEVICE_ATTR(firmware, S_IRWXUGO, ist30xx_fw_status_show,
1315 static DEVICE_ATTR(fw_sdcard, S_IRWXUGO, ist30xx_fw_sdcard_show, NULL);
1316 static DEVICE_ATTR(version, S_IRWXUGO, ist30xx_fw_version_show, NULL);
1318 struct class *ist30xx_class;
1319 struct device *ist30xx_fw_dev;
1321 static struct attribute *fw_attributes[] = {
1322 &dev_attr_fw_read.attr,
1323 &dev_attr_firmware.attr,
1324 &dev_attr_fw_sdcard.attr,
1325 &dev_attr_version.attr,
1329 static struct attribute_group fw_attr_group = {
1330 .attrs = fw_attributes,
1333 int ist30xx_init_update_sysfs(void)
1335 /* /sys/class/touch */
1336 ist30xx_class = class_create(THIS_MODULE, "touch");
1338 /* /sys/class/touch/firmware */
1339 ist30xx_fw_dev = device_create(ist30xx_class, NULL, 0, NULL, "firmware");
1341 /* /sys/class/touch/firmware/... */
1342 if (unlikely(sysfs_create_group(&ist30xx_fw_dev->kobj, &fw_attr_group)))
1343 tsp_err("Failed to create sysfs group(%s)!\n", "firmware");
1345 ts_data->status.update = 0;
1346 ts_data->status.calib = 0;