rk3288 設備樹點燈

GPIO常用系統調用函數:位於include/linux/gpio.h

1,申請GPIO

static inline int gpio_request(unsigned gpio,consr char *label)

2,設置GPIO電平

static inline void gpio_set_value(unsigned ine gpio,int value)

3,獲取GPIO電平

static inline int gpio_get_value(unsigned gpio)

4,設置GPIO爲輸出,並設置電平

static inline int gpio_direction_output(unsigned gpio,int value)

5,設置GPIO爲輸入

static inline int gpio_direction_input(unsigned gpio)

 6、設備樹下添加自己的節點

hello-gpio{

                 compatible= "rockchip,drv_gpio";
                 led     =<&gpio8 GPIO_A1 GPIO_ACTIVE_LOW>;
                 led1    =<&gpio5 GPIO_C3 GPIO_ACTIVE_LOW>;
                 led2    =<&gpio0 GPIO_C1 GPIO_ACTIVE_LOW>;
                 led3    =<&gpio1 GPIO_D2 GPIO_ACTIVE_LOW>;
                 status ="okay";

                 };


7 驅動代碼:

#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/module.h>
#include <linux/delay.h>
#include <linux/gpio.h>
#include <linux/of.h>
#include <linux/of_gpio.h>
#include <linux/of_platform.h>
#include <linux/device.h>

#include <linux/platform_device.h>
#include <linux/fs.h>
#include <linux/module.h>
#include <linux/version.h>

#include <linux/init.h>
#include <linux/fs.h>


#define LED_GPIO 258  //沒用到
#define GPIO_LOW  0
#define GPIO_HIGH 1

static struct class *drv_gpio_class;  //創建一個類
static struct class_device    *drv_gpio_class_dev; //創建設備節點
static int major; //主設備號
static int gpio,gpio5_c3,gpio0_c1,gpio1_d2; //定義幾個io口


static int drv_gpio_open(struct inode *inode, struct file *file) //應用層調用
{
    printk(KERN_INFO "drv_gpio_drv_open\n");
    /* 配置爲輸出 */
    int i;
    for(i=0;i<=4;i++)
     {
      // gpio_set_value(gpio,GPIO_LOW);
      mdelay(500);
    //  gpio_set_value(gpio,GPIO_HIGH);
      mdelay(500);
     }
    return 0;    
}

static ssize_t drv_gpio_write(struct file *file, const char __user *buf, size_t count, loff_t * ppos)//應用層調用
{
    //int val;

    printk(KERN_INFO "drv_gpio_drv_write\n");

/*    copy_from_user(&val, buf, count); //    copy_to_user();

    if (val == 1)
    {
        // 點燈
        *gpio_dat &= ~(1<<pin);
    }
    else
    {
        // 滅燈
        *gpio_dat |= (1<<pin);
    }*/
    
    return 0;
}

static struct file_operations drv_gpio_fops = {
    .owner  =   THIS_MODULE,    /* 這是一個宏,推向編譯模塊時自動創建的__this_module變量 */
    .open   =   drv_gpio_open,     
    .write    =    drv_gpio_write,       
};


static int drv_gpio_probe(struct platform_device *pdev) //驅動和設備樹匹配成功時會第一個調用的入口函數
{
  int ret =-1;
  int i;
  int flag;
  struct device_node *drv_gpio_node =pdev->dev.of_node;
 printk(KERN_INFO "%s-%d: enter\n",__FUNCTION__,__LINE__);
 //gpio=of_get_named_gpio_flags(drv_gpio_node,"led", 0, & flag);
 gpio5_c3=of_get_named_gpio_flags(drv_gpio_node,"led1", 0, & flag); //獲取設備樹的資源
// gpio0_c1=of_get_named_gpio_flags(drv_gpio_node,"led2", 0, & flag);
// gpio1_d2=of_get_named_gpio_flags(drv_gpio_node,"led3", 0, & flag);

// if(!gpio_is_valid(gpio)){
    //
 //    printk(KERN_INFO "invalid gpio : %d\n",gpio);
//    return -1;
 //    }
  if(!gpio_is_valid(gpio5_c3)){
     printk(KERN_INFO "invalid gpio : %d\n",gpio5_c3);
    return -1;
     }
  /*  if(!gpio_is_valid(gpio0_c1)){
     printk(KERN_INFO "invalid gpio : %d\n",gpio5_c3);
    return -1;
     }

    if(!gpio_is_valid(gpio1_d2)){
     printk(KERN_INFO "invalid gpio : %d\n",gpio1_d2);
        return -1;
    }

 ret =gpio_request(gpio,"drv_gpio");
 if(ret!=0){
     gpio_free(gpio);
    return -EIO;
     }*/

  ret =gpio_request(gpio5_c3,"drv_gpio");
 if(ret!=0){
     gpio_free(gpio5_c3);
    return -EIO;
     }

   /*ret =gpio_request(gpio0_c1,"drv_gpio");
 if(ret!=0){
     gpio_free(gpio0_c1);
    return -EIO;
     }

    ret =gpio_request(gpio1_d2,"drv_gpio");
 if(ret!=0){
     gpio_free(gpio1_d2);
    return -EIO;
     }*/


 //gpio_direction_output(gpio,GPIO_HIGH);
 gpio_direction_output(gpio5_c3,GPIO_HIGH); //配置gpio爲輸出 且爲高
  //gpio_direction_output(gpio0_c1,GPIO_HIGH);
  //gpio_direction_output(gpio1_d2,GPIO_LOW);
 /*for(i=0;i<=4;i++)
     {
       gpio_set_value(gpio,GPIO_LOW);
      //gpio_set_value(gpio5_c3,GPIO_LOW);
      mdelay(500);
      gpio_set_value(gpio,GPIO_HIGH);
      //gpio_set_value(gpio5_c3,GPIO_HIGH);
      mdelay(500);
     }*/
 printk(KERN_INFO  "%s-%d: enter\n",__FUNCTION__,__LINE__);

major = register_chrdev(0, "rockchip_hello", &drv_gpio_fops); //創建設備節點
  drv_gpio_class = class_create(THIS_MODULE, "rockchip_hello");
 drv_gpio_class_dev = device_create(drv_gpio_class, NULL, MKDEV(major, 0), NULL, "xyz"); /* /dev/xyz */

 
  return 0;
}


static int drv_gpio_remove(struct platform_device *pdev)
{

 printk("drv_gpio_remove, remove led\n");

    device_destroy(drv_gpio_class, MKDEV(major, 0));
    class_destroy(drv_gpio_class);
    unregister_chrdev(major, "rockchip_hello");
  return 0;
}

static const struct of_device_id of_rockchip_gpio_match[]={
        {.compatible ="rockchip,drv_gpio"},
            {/*Sentinel*/}
};


static struct platform_driver rockchip_gpio_driver={
             .probe                       =drv_gpio_probe,
            .remove                     =drv_gpio_remove,
            .driver                       ={
                .name                 ="rockchip_hello",
            .owner                =THIS_MODULE,
            .of_match_table   =of_rockchip_gpio_match,
         },
};



static  int __init drv_gpio_init(void)
{

   
   printk(KERN_INFO "Enter %s\n", __FUNCTION__);
   
   platform_driver_register(&rockchip_gpio_driver);
   /*int i;
   
   for (i=0;i<=4;i++)
     {
       printk(KERN_INFO "gpio_blink:%d\n",i);
         gpio_set_value(LED_GPIO,GPIO_LOW);
         mdelay(500);
         gpio_set_value(LED_GPIO,GPIO_HIGH);
         mdelay(500);
//  printk(KERN_INFO"~~~~~~~~~~~~~~~~~~~~this is first_drv for my qt!~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\n");
         mdelay(1000);
       }*/
  return 0;
}


static void __exit drv_gpio_exit(void)
{
  platform_driver_unregister(&rockchip_gpio_driver);
 
 printk(KERN_INFO "~~~~~~~~~~~~~~~~~~~~exit first_drv!~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\n");
}

subsys_initcall(drv_gpio_init);

module_exit(drv_gpio_exit);

MODULE_LICENSE("GPL");



發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章