Chinaunix首页 | 论坛 | 博客
  • 博客访问: 52659
  • 博文数量: 20
  • 博客积分: 0
  • 博客等级: 民兵
  • 技术积分: 22
  • 用 户 组: 普通用户
  • 注册时间: 2015-09-16 01:37
个人简介

Nothing

文章分类

全部博文(20)

文章存档

2015年(20)

我的朋友

分类: LINUX

2015-11-05 14:11:12

转载务必注明出处,谢谢!

很久没更新,把最近做的一点小东西写上来以作备忘。
最近在折腾WRTnode,感觉还不错。

回归主题。
PWM 指的是脉冲宽度调制,通常控制舵机或者步进电机,无刷电机会用到。今天我们就讲下怎么样基于wrtnode实现这个功能。

默认wrtnode是不集成PWM的,甚至,连代码也木有。为啥嘞?因为 openwrt在3.14内核之后取消了pwm over gpio了,而我们当前的系统版本为3.10.49,悲催。经过寻找,我们找到了官方最后的源码(https://dev.openwrt.org/browser/trunk/target/linux/generic/files/drivers/pwm?rev=35328&order=name)

把里面的 gpio-pwm.c Kconfig Makefile pwm.c 四个文件下载下来,放到我们的目录下(wrtnode-sdk/target/linux/generic/files/drivers/pwm)。当然,记得include下的pwm.h也不要忘记哦(wrtnode-sdk/target/linux/generic/files/include/linux/pwm)

然后我们需要的就是make menuconfig  

Kernel modules

Other modules 



选中kmod-pwm kmod-pwm-gpio 这两项,保存。



另外,make kernel_menuconfig 

内核参数GPIO support项目里面,sysfs这项最好选上。
 

kernel_menuconfig --> File Systems --> Pseudo Filesystems --> Userspace-Driven configuration system (必须是* ,built-in方式

蓝后嘞,make V=s 编译。没多久,固件就编译完成了。
当然你需要刷写固件,因为文件系统咱们更改了,添加了 Userspace-Driven configuration system的支持。

刷机过后,就可以把(wrtnode-sdk/bin/ramips/packages/base/)下我们的ipk安装包拿出来了,快去安装吧~ 


当然啦,你安装好了,总得测试嘛。

点击(此处)折叠或打开

  1. #准备目录
  2. mkdir -p /config
  3. mount -t configfs config /config
  4. mkdir -p /config/gpio_pwm/72
  5. # 启用GPIO端口, 72是端口号
  6. echo 1 > /sys/class/pwm/gpio_pwm:72/export
  7. # 配置频率与占空比,(本例是10% on 90% off,周期的单位是纳秒,1秒=10的9次方纳秒)
  8. echo 1000000000 > /sys/class/pwm/gpio_pwm:72/period_ns
  9. echo 100000000 > /sys/class/pwm/gpio_pwm:72/duty_ns
  10. # 运行,启动GPIO端口按设定的PWM输出
  11. echo 1 > /sys/class/pwm/gpio_pwm:72/run
  12. # 停止
  13. echo 0 > /sys/class/pwm/gpio_pwm:72/run
  14. echo 1 > /sys/class/pwm/gpio_pwm:72/unexport
  15. # 清除配置
  16. rm -rf /config/gpio_pwm/72


附注上我写的一个Linux C LED呼吸灯小程序。

点击(此处)折叠或打开

  1. /*
  2. * Write By Lee at 201506010
  3. */
  4. #include <unistd.h>
  5. #include <fcntl.h>
  6. #include <stdio.h>
  7. #include <sys/types.h>
  8. #include <sys/stat.h>
  9. #include <errno.h>
  10. #include <string.h>

  11. int main(int argc, char **argv)
  12. {
  13.     /* init */
  14.     int fd_period_ns,fd_duty_ns;
  15.     int value_period_ns,value_duty_ns;
  16.     char path_period_ns[]="/sys/class/pwm/gpio_pwm:72/period_ns";
  17.     char path_duty_ns[]="/sys/class/pwm/gpio_pwm:72/duty_ns";
  18.     char str_period_ns[ 32 ]={'\0'};
  19.     char str_duty_ns[ 32 ]={'\0'};
  20.     int len = 0;
  21.     int step = 500000;
  22.     int value_total = 10000000;
  23.     unsigned int wait_time = 50*1000;

  24.     /* open file */
  25.     if ((fd_period_ns = open(path_period_ns, O_WRONLY)) == -1) {
  26.         fprintf(stderr, "Open %s Error:%s\n", path_period_ns, strerror(errno));
  27.         return(-1);
  28.     }
  29.     /* open file */
  30.     if ((fd_duty_ns = open(path_duty_ns, O_WRONLY)) == -1) {
  31.         fprintf(stderr, "Open %s Error:%s\n", path_duty_ns, strerror(errno));
  32.         return(-1);
  33.     }

  34.     /* set value */
  35.     value_period_ns=value_total;
  36.     /* write value */
  37.     len=sprintf(str_period_ns,"%d",value_period_ns);
  38.     write(fd_period_ns,str_period_ns,len);


  39.     while(1){
  40.         /* set value */
  41.         value_duty_ns=1;
  42.         while(value_duty_ns < value_period_ns){
  43.             //printf("----value_duty_ns %d value_period_ns %d\n",value_duty_ns,value_period_ns);
  44.             /* write value */
  45.             len=sprintf(str_duty_ns,"%d",value_duty_ns);
  46.             write(fd_duty_ns,str_duty_ns,len);
  47.             if(value_duty_ns > (value_total/3))
  48.                 value_duty_ns+=(step/4);
  49.             else
  50.                 value_duty_ns+=step;
  51.             usleep(wait_time);
  52.         }
  53.         value_duty_ns=value_total;
  54.         while(value_duty_ns > 0){
  55.             //printf("----value_duty_ns %d value_period_ns %d\n",value_duty_ns,value_period_ns);
  56.             /* write value */
  57.             len=sprintf(str_duty_ns,"%d",value_duty_ns);
  58.             write(fd_duty_ns,str_duty_ns,len);
  59.             if(value_duty_ns > (value_total/3))
  60.                 value_duty_ns-=(step/4);
  61.             else
  62.                 value_duty_ns-=step;
  63.             usleep(wait_time);
  64.         }
  65.     }    
  66.     /* uninit */
  67.     close(fd_period_ns);
  68.     /* uninit */
  69.     close(fd_duty_ns);

  70.     return 0;
  71. }
运行之前,需要

点击(此处)折叠或打开

  1. mkdir -p /config
  2. mount -t configfs config /config
  3. mkdir -p /config/gpio_pwm/72
  4. echo 1 > /sys/class/pwm/gpio_pwm:72/export
  5. echo 1 > /sys/class/pwm/gpio_pwm:72/run



That’s all 仅此。


PS:

在制作PWM的过程中遇到了很多问题,有的我自己并没能解决,请教了WRTnode官方群里的 ( 小子De我 ) ,在此感谢!


参考资料:

Thx for Vmmgrs :

(this uses a customized firmware, if you like to try , you can get here )


转载务必注明出处,谢谢!

阅读(2229) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~