zoukankan      html  css  js  c++  java
  • IMX6输出可控PWM

    驱动部分

    #include <linux/init.h>
    #include <linux/module.h>
    #include <linux/moduleparam.h>
    #include <linux/errno.h>
    #include <linux/miscdevice.h>
    #include <linux/types.h>
    #include <linux/io.h>
    #include <linux/pwm.h>
    #include <linux/fs.h>  
    
    /************硬件相关***************/
    #include <mach/iomux-mx6q.h>
    
    #define PWM_FREQENCY 1
    #define DEV_NAME    "mypwm"
    #define PWM_DEBUG 1   
    /*pwm for this my_pwm*/
    struct pwm_device *pwm = NULL;
    
    static int my_pwm_open(struct inode *inode, struct file *filp)
    {
    
       if(pwm != NULL)
    	   return -EBUSY;
    
       /**
    	* my_pwm正好挂载在I.MX6的pwm4上,所以这里申请3号(从零开始算)PWM
    	*/
       pwm = pwm_request(3, "my_pwm");
       if ( pwm == NULL ) {
    	   printk(KERN_ALERT"my_pwm open error.
    ");
       }
    	#ifdef PWM_DEBUG
    	printk(KERN_ALERT"my_pwm opened
    ");
    	#endif
       return 0;
    }
    
    static int my_pwm_release(struct inode *inode, struct file *filp)
    {
       pwm_disable(pwm);			   // 关闭pwm
       pwm_free(pwm);				   // 释放pwm
       pwm = NULL;
    	#ifdef PWM_DEBUG
    		printk(KERN_ALERT"my_pwm closed
    ");
        #endif
       return 0;
    }
    
    static long my_pwm_ioctl(struct file *filp,
    					   unsigned int cmd, unsigned long arg)
    {
       if(pwm == NULL)
    	   return -EINVAL;
    
       if(arg < 0)
    	   return -EINVAL;
    
       switch (cmd) {
       case PWM_FREQENCY:
    	   if(arg==0)
    	   	{
    		   pwm_disable(pwm);
    		   #ifdef PWM_DEBUG
    		   	printk(KERN_ALERT"my_pwm off
    ");
    		   #endif
    	   	}
    	   else
    	   {
    		   pwm_config(pwm, 1000000000/arg/2, 1000000000/arg);
    		   pwm_enable(pwm);
    		   #ifdef PWM_DEBUG
    		   	printk(KERN_ALERT"my_pwm on
    ");
    		   #endif
    	   }
    	   break;
       default:
    	   break;
       }
    
       return 0;
    }
    
    static struct file_operations my_pwm_fops = {
       .owner			   = THIS_MODULE,
       .unlocked_ioctl	   = my_pwm_ioctl,
       .open			   = my_pwm_open,
       .release 		   = my_pwm_release,
    };
    
    static struct miscdevice my_pwm_miscdev =
    {
    	.minor	= MISC_DYNAMIC_MINOR,
    	.name	= DEV_NAME,
    	.fops	= &my_pwm_fops,
    };
    
    static int __init my_pwm_init(void)
    {
      	 //printk(KERN_ALERT"check my_pwm init.
    ");
       	misc_register(&my_pwm_miscdev);//misc杂项设备是主设备号为10的驱动设备,自动创建节点
    	mxc_iomux_v3_setup_pad(MX6Q_PAD_SD1_CMD__PWM4_PWMO);
    	#ifdef PWM_DEBUG
    		printk(KERN_ALERT"my_pwm init
    ");
    	#endif
       	return 0;
    }
    
    static void __exit my_pwm_exit(void)
    {
      misc_deregister(&my_pwm_miscdev);
      #ifdef PWM_DEBUG
    		printk(KERN_ALERT"my_pwm removed
    ");
      #endif
    }
    
    module_init(my_pwm_init);
    module_exit(my_pwm_exit);
    
    MODULE_DESCRIPTION("pwm_my_pwm driver");
    MODULE_LICENSE("GPL");
    

      测试程序

    #include<stdio.h>
    #include<stdlib.h>
    #include <sys/types.h>
    #include <sys/stat.h>
    #include <sys/ioctl.h>
    #include <fcntl.h>
    #include <poll.h>
    #include <signal.h>
    #include <unistd.h>
    #include <fcntl.h>
    
    #define PWM_SET_FREQ 1
    #define PWM_STOP     0
    
    
    int fd;
    int main(int argc, char **argv)//dev state freq
    {
    	char* filename;
    	long int freq;
    
    	filename=argv[1];
    	if (argc != 4)
    	    {
    		  printf("parm limited!
    ");
    		  return 0;
    		}
    	printf("open %s 
    ",filename);
    	fd=open(filename,O_RDWR);
    	if(fd<0)
    	{
    		printf("can't open
    ");
    		return 0;
    	}
    	if(!strcmp("on",argv[2]))
    	{
    		printf("PWM ON!
    ");
    		freq=atol(argv[3]);
    		ioctl(fd,PWM_SET_FREQ,freq);
    		printf("PWM FREQ set:%d Hz 
    ",freq);
    	}
    	else if(!strcmp("off",argv[2]))
    	{
    		ioctl(fd,PWM_STOP);
    		printf("PWM stop!
    ");
    	}
    	else
    		printf("error:param wrong!
    ");
    		while(1)
    		{
    			sleep(1000);
    		}
    	close(fd);
    	return 0;
    }
    

      

    转载请注明出处:http://www.cnblogs.com/tla001/ 一起学习,一起进步
  • 相关阅读:
    Leetcode Binary Tree Preorder Traversal
    Leetcode Minimum Depth of Binary Tree
    Leetcode 148. Sort List
    Leetcode 61. Rotate List
    Leetcode 86. Partition List
    Leetcode 21. Merge Two Sorted Lists
    Leetcode 143. Reorder List
    J2EE项目应用开发过程中的易错点
    JNDI初认识
    奔腾的代码
  • 原文地址:https://www.cnblogs.com/tla001/p/5541524.html
Copyright © 2011-2022 走看看