Android jogball 驱动分析(2)

struct gpio_event_platform_data {
        const char *name;/*名字*/
        struct gpio_event_info **info;/*gpio_event的结构指针*/
        size_t info_count;/*注册到axis中的info 结构体的数量*/
        int (*power)(const struct gpio_event_platform_data *pdata, bool on);/*电源管理回调函数*/
};

5 代码分析

5.1 通用代码
driver/input/misc/gpio_event.c
/*gpio_event基本数据结构*/
struct gpio_event {
        struct input_dev *input_dev;
        const struct gpio_event_platform_data *info;
        struct early_suspend early_suspend;
        void *state[0];
};

/*注册给input的回调函数*/
static int gpio_input_event(struct input_dev *dev, unsigned int type, unsigned int code, int value)

/*调用下层给的回调函数来实现具体的注册*/
static int gpio_event_call_all_func(struct gpio_event *ip, int func)
/*电源管理*/
#ifdef CONFIG_HAS_EARLYSUSPEND
void gpio_event_suspend(struct early_suspend *h)

void gpio_event_resume(struct early_suspend *h)
#endif
/*注册*/
static int __init gpio_event_probe(struct platform_device *pdev)
/*注销*/
static int gpio_event_remove(struct platform_device *pdev)

static struct platform_driver gpio_event_driver
static int __devinit gpio_event_init(void)

static void __exit gpio_event_exit(void)
gpio_event.c:主要是gpio_event子系统的框架

5.2 soc代码
driver/input/misc/gpio_axis.c
struct gpio_axis_state {
struct input_dev *input_dev;/*input设备结构*/
struct gpio_event_axis_info *info; /*坐标系数据结构*/
uint32_t pos; /*位置*/
struct hrtimer emc_hrtimer_delay; /* 延时时间*/
atomic_t atomic_emc_hrtimer_is_run; /*延时的原子变量*/
};
/*上报input数据*/
static void gpio_event_update_axis(struct gpio_axis_state *as, int report)
/*时间处理函数*/
static enum hrtimer_restart emc_progress_hrtimer_handler_func(struct hrtimer *timer)
/*中断处理函数*/
static irqreturn_t gpio_axis_irq_handler(int irq, void *dev_id)
/*给上层的注册回调函数*/
int gpio_event_axis_func(struct input_dev *input_dev, struct gpio_event_info *info, void **data, int func)

5.3 platform代码
例如:/arch/arm/match-msm/board-72×7.c
uint16_t hero_axis_map(struct gpio_event_axis_info *info, uint16_t in)
{
        struct hero_axis_info *ai = container_of(info, struct hero_axis_info, info);
        uint16_t out = ai->out_state;
 
if (nav_just_on) {
        if (jiffies == nav_on_jiffies || jiffies == nav_on_jiffies + 1)
                goto ignore;
        nav_just_on = 0;
}
 
if((ai->in_state ^ in) & 1) /*检测在方向1上有没有数值变化*/
        out--;
if((ai->n_state ^ in) & 2) /*检测在方向1相对方向上有没有数值变化*/
        out++;
ai->;out_state = out;
ignore:
        ai->in_state = in;
if (ai->out_state - ai->temp_state == ai->threshold) {
        ai->temp_state++;
        ai->out_state = ai->temp_state;
} else if (ai->temp_state - ai-out_state == ai->threshold) {
        ai->temp_state--;
        ai->out_state = ai->temp_state;
} else if (abs(ai->out_state - ai->;temp_state) > ai->threshold)
        ai->temp_state = ai->out_state;
 
return ai->temp_state;
}
以上函数,是最终的数据解析函数,也就是把硬件中读出来的数据,转化为实际的位置变化的函数。此函数主要做了差错控制,增加
了程序的鲁棒性和可订制性。

static struct hero_axis_info hero_x_axis = {
        .threshold = 1,
                .info = {
                .info.func = gpio_event_axis_func,
                .count = ARRAY_SIZE(hero_x_axis_gpios),
                .type = EV_REL,
                .code = REL_X,
                .decoded_size = 1U << ARRAY_SIZE(hero_x_axis_gpios),
                .map = hero_axis_map,
                .gpio = hero_x_axis_gpios,
                .flags = GPIOEAF_PRINT_UNKNOWN_DIRECTION /*| GPIOEAF_PRINT_RAW | GPIOEAF_PRINT_EVENT */,
                .enable_emc_protect_delay = 1 * NSEC_PER_MSEC,
        }
};
X轴上的info结构体的初始化

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:https://www.heiqu.com/25000.html