linux/drivers/input/mouse/cyapa_gen3.c

/*
 * Cypress APA trackpad with I2C interface
 *
 * Author: Dudley Du <[email protected]>
 * Further cleanup and restructuring by:
 *   Daniel Kurtz <[email protected]>
 *   Benson Leung <[email protected]>
 *
 * Copyright (C) 2011-2015 Cypress Semiconductor, Inc.
 * Copyright (C) 2011-2012 Google, Inc.
 *
 * This file is subject to the terms and conditions of the GNU General Public
 * License.  See the file COPYING in the main directory of this archive for
 * more details.
 */

#include <linux/delay.h>
#include <linux/i2c.h>
#include <linux/input.h>
#include <linux/input/mt.h>
#include <linux/module.h>
#include <linux/slab.h>
#include <linux/unaligned.h>
#include "cyapa.h"


#define GEN3_MAX_FINGERS
#define GEN3_FINGER_NUM(x)

#define BLK_HEAD_BYTES

/* Macro for register map group offset. */
#define PRODUCT_ID_SIZE
#define QUERY_DATA_SIZE
#define REG_PROTOCOL_GEN_QUERY_OFFSET

#define REG_OFFSET_DATA_BASE
#define REG_OFFSET_COMMAND_BASE
#define REG_OFFSET_QUERY_BASE

#define CYAPA_OFFSET_SOFT_RESET
#define OP_RECALIBRATION_MASK
#define OP_REPORT_BASELINE_MASK
#define REG_OFFSET_MAX_BASELINE
#define REG_OFFSET_MIN_BASELINE

#define REG_OFFSET_POWER_MODE
#define SET_POWER_MODE_DELAY
#define SET_POWER_MODE_TRIES

#define GEN3_BL_CMD_CHECKSUM_SEED
#define GEN3_BL_CMD_INITIATE_BL
#define GEN3_BL_CMD_WRITE_BLOCK
#define GEN3_BL_CMD_VERIFY_BLOCK
#define GEN3_BL_CMD_TERMINATE_BL
#define GEN3_BL_CMD_LAUNCH_APP

/*
 * CYAPA trackpad device states.
 * Used in register 0x00, bit1-0, DeviceStatus field.
 * Other values indicate device is in an abnormal state and must be reset.
 */
#define CYAPA_DEV_NORMAL
#define CYAPA_DEV_BUSY

#define CYAPA_FW_BLOCK_SIZE
#define CYAPA_FW_READ_SIZE
#define CYAPA_FW_HDR_START
#define CYAPA_FW_HDR_BLOCK_COUNT
#define CYAPA_FW_HDR_BLOCK_START
#define CYAPA_FW_HDR_SIZE
#define CYAPA_FW_DATA_START
#define CYAPA_FW_DATA_BLOCK_COUNT
#define CYAPA_FW_DATA_BLOCK_START
#define CYAPA_FW_DATA_SIZE
#define CYAPA_FW_SIZE
#define CYAPA_CMD_LEN

#define GEN3_BL_IDLE_FW_MAJ_VER_OFFSET
#define GEN3_BL_IDLE_FW_MIN_VER_OFFSET


struct cyapa_touch {} __packed;

struct cyapa_reg_data {} __packed;

struct gen3_write_block_cmd {} __packed;

static const u8 security_key[] =;
static const u8 bl_activate[] =;
static const u8 bl_deactivate[] =;
static const u8 bl_exit[] =;


 /* for byte read/write command */
#define CMD_RESET
#define CMD_POWER_MODE
#define CMD_DEV_STATUS
#define CMD_REPORT_MAX_BASELINE
#define CMD_REPORT_MIN_BASELINE
#define SMBUS_BYTE_CMD(cmd)
#define CYAPA_SMBUS_RESET
#define CYAPA_SMBUS_POWER_MODE
#define CYAPA_SMBUS_DEV_STATUS
#define CYAPA_SMBUS_MAX_BASELINE
#define CYAPA_SMBUS_MIN_BASELINE

 /* for group registers read/write command */
#define REG_GROUP_DATA
#define REG_GROUP_CMD
#define REG_GROUP_QUERY
#define SMBUS_GROUP_CMD(grp)
#define CYAPA_SMBUS_GROUP_DATA
#define CYAPA_SMBUS_GROUP_CMD
#define CYAPA_SMBUS_GROUP_QUERY

 /* for register block read/write command */
#define CMD_BL_STATUS
#define CMD_BL_HEAD
#define CMD_BL_CMD
#define CMD_BL_DATA
#define CMD_BL_ALL
#define CMD_BLK_PRODUCT_ID
#define CMD_BLK_HEAD
#define SMBUS_BLOCK_CMD(cmd)

/* register block read/write command in bootloader mode */
#define CYAPA_SMBUS_BL_STATUS
#define CYAPA_SMBUS_BL_HEAD
#define CYAPA_SMBUS_BL_CMD
#define CYAPA_SMBUS_BL_DATA
#define CYAPA_SMBUS_BL_ALL

/* register block read/write command in operational mode */
#define CYAPA_SMBUS_BLK_PRODUCT_ID
#define CYAPA_SMBUS_BLK_HEAD

struct cyapa_cmd_len {};

/* maps generic CYAPA_CMD_* code to the I2C equivalent */
static const struct cyapa_cmd_len cyapa_i2c_cmds[] =;

static const struct cyapa_cmd_len cyapa_smbus_cmds[] =;

static int cyapa_gen3_try_poll_handler(struct cyapa *cyapa);

/*
 * cyapa_smbus_read_block - perform smbus block read command
 * @cyapa  - private data structure of the driver
 * @cmd    - the properly encoded smbus command
 * @len    - expected length of smbus command result
 * @values - buffer to store smbus command result
 *
 * Returns negative errno, else the number of bytes written.
 *
 * Note:
 * In trackpad device, the memory block allocated for I2C register map
 * is 256 bytes, so the max read block for I2C bus is 256 bytes.
 */
ssize_t cyapa_smbus_read_block(struct cyapa *cyapa, u8 cmd, size_t len,
				      u8 *values)
{}

static s32 cyapa_read_byte(struct cyapa *cyapa, u8 cmd_idx)
{}

static s32 cyapa_write_byte(struct cyapa *cyapa, u8 cmd_idx, u8 value)
{}

ssize_t cyapa_i2c_reg_read_block(struct cyapa *cyapa, u8 reg, size_t len,
					u8 *values)
{}

static ssize_t cyapa_i2c_reg_write_block(struct cyapa *cyapa, u8 reg,
					 size_t len, const u8 *values)
{}

ssize_t cyapa_read_block(struct cyapa *cyapa, u8 cmd_idx, u8 *values)
{}

/*
 * Determine the Gen3 trackpad device's current operating state.
 *
 */
static int cyapa_gen3_state_parse(struct cyapa *cyapa, u8 *reg_data, int len)
{}

/*
 * Enter bootloader by soft resetting the device.
 *
 * If device is already in the bootloader, the function just returns.
 * Otherwise, reset the device; after reset, device enters bootloader idle
 * state immediately.
 *
 * Returns:
 *   0        on success
 *   -EAGAIN  device was reset, but is not now in bootloader idle state
 *   < 0      if the device never responds within the timeout
 */
static int cyapa_gen3_bl_enter(struct cyapa *cyapa)
{}

static int cyapa_gen3_bl_activate(struct cyapa *cyapa)
{}

static int cyapa_gen3_bl_deactivate(struct cyapa *cyapa)
{}

/*
 * Exit bootloader
 *
 * Send bl_exit command, then wait 50 - 100 ms to let device transition to
 * operational mode.  If this is the first time the device's firmware is
 * running, it can take up to 2 seconds to calibrate its sensors.  So, poll
 * the device's new state for up to 2 seconds.
 *
 * Returns:
 *   -EIO    failure while reading from device
 *   -EAGAIN device is stuck in bootloader, b/c it has invalid firmware
 *   0       device is supported and in operational mode
 */
static int cyapa_gen3_bl_exit(struct cyapa *cyapa)
{}

static u16 cyapa_gen3_csum(const u8 *buf, size_t count)
{}

/*
 * Verify the integrity of a CYAPA firmware image file.
 *
 * The firmware image file is 30848 bytes, composed of 482 64-byte blocks.
 *
 * The first 2 blocks are the firmware header.
 * The next 480 blocks are the firmware image.
 *
 * The first two bytes of the header hold the header checksum, computed by
 * summing the other 126 bytes of the header.
 * The last two bytes of the header hold the firmware image checksum, computed
 * by summing the 30720 bytes of the image modulo 0xffff.
 *
 * Both checksums are stored little-endian.
 */
static int cyapa_gen3_check_fw(struct cyapa *cyapa, const struct firmware *fw)
{}

/*
 * Write a |len| byte long buffer |buf| to the device, by chopping it up into a
 * sequence of smaller |CYAPA_CMD_LEN|-length write commands.
 *
 * The data bytes for a write command are prepended with the 1-byte offset
 * of the data relative to the start of |buf|.
 */
static int cyapa_gen3_write_buffer(struct cyapa *cyapa,
		const u8 *buf, size_t len)
{}

/*
 * A firmware block write command writes 64 bytes of data to a single flash
 * page in the device.  The 78-byte block write command has the format:
 *   <0xff> <CMD> <Key> <Start> <Data> <Data-Checksum> <CMD Checksum>
 *
 *  <0xff>  - every command starts with 0xff
 *  <CMD>   - the write command value is 0x39
 *  <Key>   - write commands include an 8-byte key: { 00 01 02 03 04 05 06 07 }
 *  <Block> - Memory Block number (address / 64) (16-bit, big-endian)
 *  <Data>  - 64 bytes of firmware image data
 *  <Data Checksum> - sum of 64 <Data> bytes, modulo 0xff
 *  <CMD Checksum> - sum of 77 bytes, from 0xff to <Data Checksum>
 *
 * Each write command is split into 5 i2c write transactions of up to 16 bytes.
 * Each transaction starts with an i2c register offset: (00, 10, 20, 30, 40).
 */
static int cyapa_gen3_write_fw_block(struct cyapa *cyapa,
		u16 block, const u8 *data)
{}

static int cyapa_gen3_write_blocks(struct cyapa *cyapa,
		size_t start_block, size_t block_count,
		const u8 *image_data)
{}

static int cyapa_gen3_do_fw_update(struct cyapa *cyapa,
		const struct firmware *fw)
{}

static ssize_t cyapa_gen3_do_calibrate(struct device *dev,
				     struct device_attribute *attr,
				     const char *buf, size_t count)
{}

static ssize_t cyapa_gen3_show_baseline(struct device *dev,
				   struct device_attribute *attr, char *buf)
{}

/*
 * cyapa_get_wait_time_for_pwr_cmd
 *
 * Compute the amount of time we need to wait after updating the touchpad
 * power mode. The touchpad needs to consume the incoming power mode set
 * command at the current clock rate.
 */

static u16 cyapa_get_wait_time_for_pwr_cmd(u8 pwr_mode)
{}

/*
 * Set device power mode
 *
 * Write to the field to configure power state. Power states include :
 *   Full : Max scans and report rate.
 *   Idle : Report rate set by user specified time.
 *   ButtonOnly : No scans for fingers. When the button is triggered,
 *     a slave interrupt is asserted to notify host to wake up.
 *   Off : Only awake for i2c commands from host. No function for button
 *     or touch sensors.
 *
 * The power_mode command should conform to the following :
 *   Full : 0x3f
 *   Idle : Configurable from 20 to 1000ms. See note below for
 *     cyapa_sleep_time_to_pwr_cmd and cyapa_pwr_cmd_to_sleep_time
 *   ButtonOnly : 0x01
 *   Off : 0x00
 *
 * Device power mode can only be set when device is in operational mode.
 */
static int cyapa_gen3_set_power_mode(struct cyapa *cyapa, u8 power_mode,
		u16 always_unused, enum cyapa_pm_stage pm_stage)
{}

static int cyapa_gen3_set_proximity(struct cyapa *cyapa, bool enable)
{}

static int cyapa_gen3_get_query_data(struct cyapa *cyapa)
{}

static int cyapa_gen3_bl_query_data(struct cyapa *cyapa)
{}

/*
 * Check if device is operational.
 *
 * An operational device is responding, has exited bootloader, and has
 * firmware supported by this driver.
 *
 * Returns:
 *   -EBUSY  no device or in bootloader
 *   -EIO    failure while reading from device
 *   -EAGAIN device is still in bootloader
 *           if ->state = CYAPA_STATE_BL_IDLE, device has invalid firmware
 *   -EINVAL device is in operational mode, but not supported by this driver
 *   0       device is supported
 */
static int cyapa_gen3_do_operational_check(struct cyapa *cyapa)
{}

/*
 * Return false, do not continue process
 * Return true, continue process.
 */
static bool cyapa_gen3_irq_cmd_handler(struct cyapa *cyapa)
{}

static int cyapa_gen3_event_process(struct cyapa *cyapa,
				    struct cyapa_reg_data *data)
{}

static int cyapa_gen3_irq_handler(struct cyapa *cyapa)
{}

/*
 * This function will be called in the cyapa_gen3_set_power_mode function,
 * and it's known that it may failed in some situation after the set power
 * mode command was sent. So this function is aimed to avoid the knwon
 * and unwanted output I2C and data parse error messages.
 */
static int cyapa_gen3_try_poll_handler(struct cyapa *cyapa)
{}

static int cyapa_gen3_initialize(struct cyapa *cyapa) {}
static int cyapa_gen3_bl_initiate(struct cyapa *cyapa,
		const struct firmware *fw) {}
static int cyapa_gen3_empty_output_data(struct cyapa *cyapa,
		u8 *buf, int *len, cb_sort func) {}

const struct cyapa_dev_ops cyapa_gen3_ops =;