开发日志 170421

昨天3D打印了一个安放电路板的结构件,然后发现没有树莓派用的M2.5的螺丝,赶紧网上下单然后开始码别的。

想了一下,人家MPU9250明明是有GPIO中断输出的,干啥要用延迟呢,改个中断吧,于是今天基本就折腾了一天中断。

其实中断也不是很难,用wiringPi这个库就可以了,或者BCM的那套也行。不过用了wiringPi之后执行需要root权限,让我不太高兴。Linux不是一切皆文件吗?Linux不是有GPIO子系统吗?借助这个子系统不就好了?

别说,还真有,用/sys/class/gpio/这个目录就可以了。这个要求编译内核时开启Device Drivers -> GPIO Support -> /sys/class/gpio/… (sysfs interface) 这个选项,树莓派官方镜像的内核已经开启了。

然后echo 端口号(BCM) > /sys/class/gpio/export来将这个接口从内核中暴露出来,接下来就可以通过/sys/class/gpio/gpio*/下的direction value edge这几个文件来进行输入输出和中断触发边沿选择了。

最后怎么用作中断呢?select/poll/epoll都可以了,它们会挂起线程知道文件内容改变。

另外这是我的参考文章:http://blog.sina.com.cn/s/blog_7880d3350102w2um.html

另外MPU9250还总是有零漂,我前几周调好了,今天上电一看飘了0.4dps,纠正过来后一看又漂了0.1dps,根本不知道该怎么处理。这倒还好,大不了系统启动时纠偏,但它要是走着走着飘起来了该咋办?

附上程序一段:

void MPU9250::getData(MPU9250 *obj) {

  int gpio_fd;
  struct pollfd fds[1];
  char buff[10];
  gpio_fd = open("/sys/class/gpio/gpio17/value",O_RDONLY);
  if(gpio_fd < 0){
    throw I2C_Exception(I2C_Exception::Device_Not_Exist);
  }
  fds[0].fd = gpio_fd;
  fds[0].events  = POLLPRI;
  read(gpio_fd,buff,10);

  const uint8_t startAddr = 0x3b;
  uint8_t data[14];
  while (obj->run) {
    // Wait for MPU9250 RAW data ready interrupt
    poll(fds,1,-1);
    if( fds[0].revents & POLLPRI) {
      lseek(gpio_fd, 0, SEEK_SET);
      read(gpio_fd, buff, 10);
    }
    // Get data
    Balabala;
  }
  close(gpio_fd);
}

启动脚本:

echo 17 > /sys/class/gpio/export
sleep 1 #将GPIO暴露出来需要时间
echo in > /sys/class/gpio/gpio17/direction
echo rising > /sys/class/gpio/gpio17/edge
./wqmbd

 

发表评论