基于设备树的led驱动程序

发布时间:
来源: 电子工程世界

  1 #include

  2 #include

  3 #include

  4 #include

  5 #include

  6 #include

  7 #include

  8 #include

  9 #include

 10 #include

 11 #include

 12 #include

 13 #include

 14 #include

 15 

 16 static volatile unsigned long *ledcon;

 17 static volatile unsigned long *leddat;

 18 static struct class *led_class;

 19 static unsigned int pin_th;

 20 dev_t led_dev;

 21 struct cdev *cdev;

 22 

 23 

 24 /* 打开led灯 */

 25 static int led_open(struct inode *inode, struct file *file)

 26 {

 27      *ledcon &= ~(0x3 << (pin_th * 2));

 28      *ledcon |= (0x1 << (pin_th * 2));

 29      *leddat &= ~(1 << pin_th);

 30      return 0;

 31 }

 32 

 33 static struct file_operations led_fops = {

 34                .owner = THIS_MODULE,

 35                .open = led_open,

 36 };

 37 

 38 static int led_probe(struct platform_device *pdev)

 39 {

 40    int pin_info;

 41    int phy_addr;

 42    int io_base;

 43    of_property_read_s32(pdev->dev.of_node, "pin", &pin_info); 

 44    printk("pin_info = 0x%xn", pin_info);

 45    of_property_read_s32(pdev->dev.of_node, "iobase", &io_base); 

 46    printk("io_base = 0x%xn", io_base);

 47    pin_th = pin_info & (0xffff);

 48    phy_addr = (io_base | ((pin_info>>16)<<4));

 49    ledcon = ioremap(phy_addr, 2);

 50    leddat = ledcon + 1;

 51    

 52    if (alloc_chrdev_region(&led_dev, MINOR(led_dev), 1, "led"))

 53           return -1;

 54    cdev = cdev_alloc();

 55    if (!cdev)

 56           return -1;

 57    cdev_init(cdev, &led_fops);

 58    cdev_add(cdev, led_dev, 1);

 59 

 60    led_class = class_create(THIS_MODULE, "led");

 61    device_create(led_class,NULL,led_dev,NULL,"led0");   // is /dev/led0

 62 

 63    return 0;

 64    

 65 }

 66 

 67 int led_remove(struct platform_device *pdev)

 68 {

 69     device_destroy(led_class, led_dev);

 70     class_destroy(led_class);

 71     cdev_del(cdev);

 72     unregister_chrdev_region(led_dev, 1);

 73     iounmap(ledcon);

 74     return 0;

 75 }

 76 

 77 static struct of_device_id led_id[] = {

 78               {.compatible = "jz2440_led"},

 79               {},

 80 };

 81 

 82 static struct platform_driver led_drv = {

 83     .probe = led_probe,

 84     .remove = led_remove,   

 85      .driver = {

 86         .name  = "jz2440_led",

 87         .of_match_table = led_id,

 88     },

 89 };

 90 

 91 static int led_init(void)

 92 {

 93     platform_driver_register(&led_drv);

 94     return 0;

 95 }

 96 

 97 static void led_exit(void)

 98 {

 99      platform_driver_unregister(&led_drv);

100 }

101 

102 module_init(led_init);

103 module_exit(led_exit);

104 

105 MODULE_LICENSE("GPL");

以上是驱动程序,下面是设备树dts文件:

 1 #define S3C2440_GPA(_nr)    ((0<<16) + (_nr))

 2 #define S3C2440_GPB(_nr)    ((1<<16) + (_nr))

 3 #define S3C2440_GPC(_nr)    ((2<<16) + (_nr))

 4 #define S3C2440_GPD(_nr)    ((3<<16) + (_nr))

 5 #define S3C2440_GPE(_nr)    ((4<<16) + (_nr))

 6 #define S3C2440_GPF(_nr)    ((5<<16) + (_nr))

 7 #define S3C2440_GPG(_nr)    ((6<<16) + (_nr))

 8 #define S3C2440_GPH(_nr)    ((7<<16) + (_nr))

 9 #define S3C2440_GPJ(_nr)    ((8<<16) + (_nr))

10 #define S3C2440_GPK(_nr)    ((9<<16) + (_nr))

11 #define S3C2440_GPL(_nr)    ((10<<16) + (_nr))

12 #define S3C2440_GPM(_nr)    ((11<<16) + (_nr))

13  

14 /dts-v1/;

15 

16 / {

17     model = "SMDK2440";

18     compatible = "samsung,smdk2440";

19 

20     #address-cells = <1>;

21     #size-cells = <1>;

22         

23     memory@30000000 {

24         device_type = "memory";

25         reg =  <0x30000000 0x4000000>;

26     };

  

34     chosen {

35         bootargs = "noinitrd root=/dev/mtdblock4 rw init=/linuxrc console=ttySAC0,115200";

36     };

37 

38     

39     led {

40         compatible = "jz2440_led";

41         pin = ;

42         iobase = <0x56000000>;

43     };

44 };



文章来源于: 电子工程世界 原文链接

本站所有转载文章系出于传递更多信息之目的,且明确注明来源,不希望被转载的媒体或个人可与我们联系,我们将立即进行删除处理。