新聞中心

        EEPW首頁 > 嵌入式系統 > 設計應用 > 控制IO端口 s3c2410_gpio_setpin()的使用

        控制IO端口 s3c2410_gpio_setpin()的使用

        作者: 時間:2016-11-20 來源:網絡 收藏
        本文基于FL2440 ARM開發板

        Linux內核版本 2.6.28.7

        本文引用地址:http://www.104case.com/article/201611/318858.htm

        arm-linux-gcc 3.4.1

        1. #include
        2. #include
        3. #include
        4. #include
        5. #include
        6. #includeinterrupt.h>/*設置中斷方式*/
        7. #include
        8. #include
        9. #include
        10. #include
        11. #include
        12. //設備名
        13. #defineIO_DEVICE_NAME"my_io"
        14. //主設備號
        15. #defineIO_DEVICE_MAJOR240
        16. //次設備號
        17. #defineIO_DEVICE_SECONDARY32
        18. //返回一個數x的第y位
        19. #defineMYBIT(x,y)((x>>y)%2)
        20. #ifndef_LINUX_IRQRETURN_H
        21. #define_LINUX_IRQRETURN_H
        22. typedefintirqreturn_t;
        23. #defineIRQ_EINT00
        24. #defineIRQ_EINT22
        25. #defineIRQ_EINT33
        26. #defineIRQ_EINT432
        27. #defineIRQ_NONE(0)
        28. #defineIRQ_HANDLED(1)
        29. #defineIRQ_RETVAL(x)((x)!=0)
        30. #endif
        31. /*
        32. *S3C2410GPIOedgedetectionforIRQs:
        33. *IRQsaregeneratedonFalling-Edge,Rising-Edge,both,lowlevelorhigglevel.
        34. *Thismustbecalled*before*thecorrespondingIRQisregistered.
        35. */
        36. #defineEXT_LOWLEVEL0
        37. #defineEXT_HIGHLEVEL1
        38. #defineEXT_FALLING_EDGE2
        39. #defineEXT_RISING_EDGE4
        40. #defineEXT_BOTH_EDGES6
        41. staticintflag_0,flag_2;//中斷轉換標志
        42. staticintcnt;
        43. DECLARE_WAIT_QUEUE_HEAD(io_wait);//聲明等待隊列
        44. voidio_con_set();
        45. staticirqreturn_tio_interrupt_0(intirq,void*dev_id,structpt_regs*regs)
        46. {
        47. printk("**********theinterrupt0works**********/n");
        48. if(flag_0==0)
        49. {
        50. cnt=(cnt+1)%2;
        51. flag_0=1;
        52. if(cnt==0)
        53. {
        54. printk("IN/n");
        55. s3c2410_gpio_setpin(S3C2410_GPB5,0);
        56. s3c2410_gpio_setpin(S3C2410_GPB6,1);
        57. }
        58. wake_up_interruptible(&io_wait);
        59. }
        60. returnIRQ_HANDLED;
        61. }
        62. staticirqreturn_tio_interrupt_2(intirq,void*dev_id,structpt_regs*regs)
        63. {
        64. printk("**********theinterrupt2works**********/n");
        65. if(flag_2==0)
        66. {
        67. cnt=(cnt+1)%2;
        68. flag_2=1;
        69. if(cnt==0)
        70. {
        71. printk("OUT/n");
        72. s3c2410_gpio_setpin(S3C2410_GPB5,1);
        73. s3c2410_gpio_setpin(S3C2410_GPB6,0);
        74. }
        75. wake_up_interruptible(&io_wait);
        76. }
        77. returnIRQ_HANDLED;
        78. }
        79. staticintio_open(structinode*inode,structfile*file)//打開設備函數
        80. {
        81. intret;
        82. set_irq_type(IRQ_EINT0,EXT_FALLING_EDGE);//設置中斷0觸發方式
        83. set_irq_type(IRQ_EINT2,EXT_FALLING_EDGE);//設置中斷2觸發方式
        84. //EXT_LOWLEVEL
        85. //EXT_HIGHLEVEL
        86. //EXT_FALLING_EDGE
        87. //EXT_RISING_EDGE
        88. //EXT_BOTH_EDGES
        89. disable_irq(IRQ_EINT0);
        90. disable_irq(IRQ_EINT2);
        91. enable_irq(IRQ_EINT0);
        92. enable_irq(IRQ_EINT2);
        93. ret=request_irq(IRQ_EINT0,io_interrupt_0,IRQF_SHARED,IO_DEVICE_NAME,1);//注冊中斷0
        94. if(ret<0)
        95. {
        96. printk("IRQ%dcannotrequest/n",IRQ_EINT0);
        97. returnret;
        98. }
        99. ret=request_irq(IRQ_EINT2,io_interrupt_2,IRQF_SHARED,IO_DEVICE_NAME,1);//注冊中斷2
        100. if(ret<0)
        101. {
        102. printk("IRQ%dcannotrequest/n",IRQ_EINT2);
        103. returnret;
        104. }
        105. printk("thedeviceisopened/n");
        106. io_con_set();
        107. cnt=0;
        108. return0;
        109. }
        110. voidio_con_set()//IO端口控制寄存器初始化
        111. {
        112. s3c2410_gpio_cfgpin(S3C2410_GPF0,S3C2410_GPF0_EINT0);
        113. s3c2410_gpio_cfgpin(S3C2410_GPF2,S3C2410_GPF2_EINT2);
        114. s3c2410_gpio_cfgpin(S3C2410_GPB5,S3C2410_GPB5_OUTP);
        115. s3c2410_gpio_cfgpin(S3C2410_GPB6,S3C2410_GPB6_OUTP);
        116. }
        117. staticintio_close(structinode*inode,structfile*file)//設備關閉函數
        118. {
        119. free_irq(IRQ_EINT0,1);//釋放中斷
        120. free_irq(IRQ_EINT2,1);//釋放中斷
        121. printk("thedeviceisclosed/n");
        122. return0;
        123. }
        124. staticssize_tio_read(structfile*filp,char*buff,size_tcount,loff_t*f_ops)//讀取IO端口
        125. {
        126. wait_event_interruptible(io_wait,flag_0);
        127. wait_event_interruptible(io_wait,flag_0);
        128. flag_0=0;
        129. flag_2=0;
        130. //printk("thevalueis%d/n",io_data);
        131. copy_to_user(buff,(char*)&cnt,sizeof(cnt));
        132. }
        133. staticstructfile_operationsio_device_fops=
        134. {
        135. .owner=THIS_MODULE,
        136. .read=io_read,
        137. .open=io_open,
        138. .release=io_close,
        139. };
        140. staticint__initio_init(void)//insmod加載驅動時執行
        141. {
        142. intret;
        143. ret=register_chrdev(IO_DEVICE_MAJOR,IO_DEVICE_NAME,&io_device_fops);
        144. if(ret<0)
        145. {
        146. printk("Failtoregistthedevice/n");
        147. returnret;
        148. }
        149. return0;
        150. }
        151. staticint__exitio_exit(void)//rmmod卸載驅動時執行
        152. {
        153. unregister_chrdev(IO_DEVICE_MAJOR,IO_DEVICE_NAME);
        154. printk("thedevicehasbeenunregisted/n");
        155. }
        156. module_init(io_init);
        157. module_exit(io_exit);
        158. MODULE_LICENSE("GPL");

        Makefile同上一篇的Makefile

        obj-m := my_io.o

        KERNELDIR ?= /arm/linux-2.6.28.7-2440

        PWD := $(shell pwd)

        default:

        $(MAKE) -C $(KERNELDIR) M=$(PWD) modules

        clean:

        rm -f *.o *.ko *.order *.symvers

        這次本人修改了下內核頭文件的目錄,將目錄./arch/arm/include下asm文件夾復制到./include

        將目錄./arch/arm/mach-s3c2410/include下mach文件夾復制到./include下

        驅動修改版

        1. #include
        2. #include
        3. #include
        4. #include
        5. #include
        6. #include/*設置中斷方式*/
        7. #include
        8. #include
        9. #include
        10. #include
        11. #include
        12. //設備名
        13. #defineIO_DEVICE_NAME"my_io"
        14. //主設備號
        15. #defineIO_DEVICE_MAJOR240
        16. //次設備號
        17. #defineIO_DEVICE_SECONDARY32
        18. //返回一個數x的第y位
        19. #defineMYBIT(x,y)((x>>y)%2)
        20. #ifndef_LINUX_IRQRETURN_H
        21. #define_LINUX_IRQRETURN_H
        22. typedefintirqreturn_t;
        23. #defineIRQ_EINT00
        24. #defineIRQ_EINT22
        25. #defineIRQ_EINT33
        26. #defineIRQ_EINT432
        27. #defineIRQ_NONE(0)
        28. #defineIRQ_HANDLED(1)
        29. #defineIRQ_RETVAL(x)((x)!=0)
        30. #endif
        31. /*
        32. *S3C2410GPIOedgedetectionforIRQs:
        33. *IRQsaregeneratedonFalling-Edge,Rising-Edge,both,lowlevelorhigglevel.
        34. *Thismustbecalled*before*thecorrespondingIRQisregistered.
        35. */
        36. #defineEXT_LOWLEVEL0
        37. #defineEXT_HIGHLEVEL1
        38. #defineEXT_FALLING_EDGE2
        39. #defineEXT_RISING_EDGE4
        40. #defineEXT_BOTH_EDGES6
        41. staticintflag_0,flag_2;//中斷轉換標志
        42. staticintcnt;
        43. DECLARE_WAIT_QUEUE_HEAD(io_wait);//聲明等待隊列
        44. voidio_con_set();
        45. staticirqreturn_tio_interrupt_0(intirq,void*dev_id,structpt_regs*regs)
        46. {
        47. if(flag_0==0)
        48. {
        49. printk("**********theinterrupt0works**********/n");
        50. cnt=(cnt+1)%2;
        51. flag_0=1;
        52. if(cnt==0)
        53. {
        54. printk("IN/n");
        55. s3c2410_gpio_setpin(S3C2410_GPB5,0);
        56. s3c2410_gpio_setpin(S3C2410_GPB6,1);
        57. }
        58. wake_up_interruptible(&io_wait);
        59. }
        60. returnIRQ_HANDLED;
        61. }
        62. staticirqreturn_tio_interrupt_2(intirq,void*dev_id,structpt_regs*regs)
        63. {
        64. if(flag_2==0)
        65. {
        66. printk("**********theinterrupt2works**********/n");
        67. cnt=(cnt+1)%2;
        68. flag_2=1;
        69. if(cnt==0)
        70. {
        71. printk("OUT/n");
        72. s3c2410_gpio_setpin(S3C2410_GPB5,1);
        73. s3c2410_gpio_setpin(S3C2410_GPB6,0);
        74. }
        75. wake_up_interruptible(&io_wait);
        76. }
        77. returnIRQ_HANDLED;
        78. }
        79. staticintio_open(structinode*inode,structfile*file)//打開設備函數
        80. {
        81. intret;
        82. set_irq_type(IRQ_EINT0,EXT_FALLING_EDGE);//設置中斷0觸發方式
        83. set_irq_type(IRQ_EINT2,EXT_FALLING_EDGE);//設置中斷2觸發方式
        84. //EXT_LOWLEVEL
        85. //EXT_HIGHLEVEL
        86. //EXT_FALLING_EDGE
        87. //EXT_RISING_EDGE
        88. //EXT_BOTH_EDGES
        89. disable_irq(IRQ_EINT0);
        90. disable_irq(IRQ_EINT2);
        91. enable_irq(IRQ_EINT0);
        92. enable_irq(IRQ_EINT2);
        93. ret=request_irq(IRQ_EINT0,io_interrupt_0,IRQF_SHARED,IO_DEVICE_NAME,1);//注冊中斷0
        94. if(ret<0)
        95. {
        96. printk("IRQ%dcannotrequest/n",IRQ_EINT0);
        97. returnret;
        98. }
        99. ret=request_irq(IRQ_EINT2,io_interrupt_2,IRQF_SHARED,IO_DEVICE_NAME,1);//注冊中斷2
        100. if(ret<0)
        101. {
        102. printk("IRQ%dcannotrequest/n",IRQ_EINT2);
        103. returnret;
        104. }
        105. printk("thedeviceisopened/n");
        106. io_con_set();
        107. cnt=0;
        108. return0;
        109. }
        110. voidio_con_set()//IO端口控制寄存器初始化
        111. {
        112. s3c2410_gpio_cfgpin(S3C2410_GPF0,S3C2410_GPF0_EINT0);
        113. s3c2410_gpio_cfgpin(S3C2410_GPF2,S3C2410_GPF2_EINT2);
        114. s3c2410_gpio_cfgpin(S3C2410_GPB5,S3C2410_GPB5_OUTP);
        115. s3c2410_gpio_cfgpin(S3C2410_GPB6,S3C2410_GPB6_OUTP);
        116. }
        117. staticintio_close(structinode*inode,structfile*file)//設備關閉函數
        118. {
        119. free_irq(IRQ_EINT0,1);//釋放中斷
        120. free_irq(IRQ_EINT2,1);//釋放中斷
        121. printk("thedeviceisclosed/n");
        122. return0;
        123. }
        124. staticssize_tio_read(structfile*filp,char*buff,size_tcount,loff_t*f_ops)//讀取IO端口
        125. {
        126. wait_event_interruptible(io_wait,flag_0&flag_2);
        127. flag_0=0;
        128. flag_2=0;
        129. //printk("thevalueis%d/n",io_data);
        130. copy_to_user(buff,(char*)&cnt,sizeof(cnt));
        131. }
        132. staticstructfile_operationsio_device_fops=
        133. {
        134. .owner=THIS_MODULE,
        135. .read=io_read,
        136. .open=io_open,
        137. .release=io_close,
        138. };
        139. staticint__initio_init(void)//insmod加載驅動時執行
        140. {
        141. intret;
        142. ret=register_chrdev(IO_DEVICE_MAJOR,IO_DEVICE_NAME,&io_device_fops);
        143. if(ret<0)
        144. {
        145. printk("Failtoregistthedevice/n");
        146. returnret;
        147. }
        148. return0;
        149. }
        150. staticint__exitio_exit(void)//rmmod卸載驅動時執行
        151. {
        152. unregister_chrdev(IO_DEVICE_MAJOR,IO_DEVICE_NAME);
        153. printk("thedevicehasbeenunregisted/n");
        154. }
        155. module_init(io_init);
        156. module_exit(io_exit);
        157. MODULE_LICENSE("GPL");

        這個驅動實際上是通過紅外傳感器檢測電平變化,來實現人數的統計,改進后能夠實現正確的通過中斷先后來識別方向,還排除了單一中斷的

        抖動干擾。



        關鍵詞: 控制IO端口s3c241

        評論


        技術專區

        關閉
        主站蜘蛛池模板: 昌乐县| 双鸭山市| 广河县| 临泉县| 铅山县| 札达县| 梅州市| 和政县| 商南县| 汾阳市| 哈尔滨市| 武定县| 黄陵县| 东兴市| 远安县| 安岳县| 广州市| 佳木斯市| 伊春市| 黑龙江省| 玉山县| 安图县| 井研县| 江永县| 北宁市| 平原县| 井陉县| 永城市| 金华市| 泸西县| 建昌县| 盐津县| 张家口市| 茂名市| 九寨沟县| 屏边| 奉贤区| 阜宁县| 新乡县| 信丰县| 青岛市|