我试图编写 i2c 设备驱动程序,一切都很好:
- 成功检测到设备
- sysfs 类中的设备也创建了 value 属性
- 然后我初始化一个 hrtimer 并启动它
- 我正在尝试从属性的存储功能发送数据,它工作正常
但是当我尝试从 hrtimer 回调函数发送数据时,我的系统出现故障。这是一些代码(我删除了包含、定义和不重要的代码):
led-indicator.h
struct timer_job {
ktime_t period;
struct hrtimer timer;
...
};
struct ledindicator {
struct i2c_client *client;
struct device *device;
struct timer_job job;
int value;
};
led-indicator.c
include "led-indicator.h"
static struct ledindicator *li;
// device attribute [value] store function
static ssize_t value_store(struct device *device, struct device_attribute *attr, const char *buffer, size_t count)
{
int val;
kstrtoint(buffer, 10, &val);
li->value = val;
i2c_smbus_write_byte_data(li->client, 0xBA, 0x02); // this is work fine
LOG("New value is %d \n", li->value);
return count;
}
//timer callback, fire each timer_job.period
static enum hrtimer_restart send_next(struct hrtimer * tim) {
long start = jiffies;
struct timer_job *job = container_of(tim, struct timer_job, timer);
i2c_smbus_write_byte_data(li->client, 0xBA, 0x02); // this cause system fault
hrtimer_forward_now(tim, job->period);
return HRTIMER_RESTART;
}
//when device is detected I am create sysfs device and init timer.
enter code here//Also I am crate led_indicator structure and save i2c_client pointer for future use
static int li_probe(struct i2c_client *client, const struct i2c_device_id *id)
{
int ret = 0;
li = kmalloc(sizeof(*li), GFP_KERNEL);
li->client = client;
li->value = 0;
...
// here creating device and attribute for it
...
hrtimer_init(&(li->job.timer), CLOCK_MONOTONIC, HRTIMER_MODE_REL);
li->job.timer.function = send_next;
li->job.period = ktime_set(1, 0); //1 sec
hrtimer_start(&(li->job.timer), li->job.period, HRTIMER_MODE_REL);
return ret;
}
怎么了?