新聞中心

EEPW首頁 > 嵌入式系統(tǒng) > 設(shè)計應(yīng)用 > 控制IO端口 s3c2410_gpio_setpin()的使用

控制IO端口 s3c2410_gpio_setpin()的使用

作者: 時間:2016-11-20 來源:網(wǎng)絡(luò) 收藏
本文基于FL2440 ARM開發(fā)板

Linux內(nèi)核版本 2.6.28.7

本文引用地址:http://butianyuan.cn/article/201611/318858.htm

arm-linux-gcc 3.4.1

  1. #include
  2. #include
  3. #include
  4. #include
  5. #include
  6. #includeinterrupt.h>/*設(shè)置中斷方式*/
  7. #include
  8. #include
  9. #include
  10. #include
  11. #include
  12. //設(shè)備名
  13. #defineIO_DEVICE_NAME"my_io"
  14. //主設(shè)備號
  15. #defineIO_DEVICE_MAJOR240
  16. //次設(shè)備號
  17. #defineIO_DEVICE_SECONDARY32
  18. //返回一個數(shù)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;//中斷轉(zhuǎn)換標志
  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)//打開設(shè)備函數(shù)
  80. {
  81. intret;
  82. set_irq_type(IRQ_EINT0,EXT_FALLING_EDGE);//設(shè)置中斷0觸發(fā)方式
  83. set_irq_type(IRQ_EINT2,EXT_FALLING_EDGE);//設(shè)置中斷2觸發(fā)方式
  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)//設(shè)備關(guān)閉函數(shù)
  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加載驅(qū)動時執(zhí)行
  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卸載驅(qū)動時執(zhí)行
  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

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

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

驅(qū)動修改版

  1. #include
  2. #include
  3. #include
  4. #include
  5. #include
  6. #include/*設(shè)置中斷方式*/
  7. #include
  8. #include
  9. #include
  10. #include
  11. #include
  12. //設(shè)備名
  13. #defineIO_DEVICE_NAME"my_io"
  14. //主設(shè)備號
  15. #defineIO_DEVICE_MAJOR240
  16. //次設(shè)備號
  17. #defineIO_DEVICE_SECONDARY32
  18. //返回一個數(shù)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;//中斷轉(zhuǎn)換標志
  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)//打開設(shè)備函數(shù)
  80. {
  81. intret;
  82. set_irq_type(IRQ_EINT0,EXT_FALLING_EDGE);//設(shè)置中斷0觸發(fā)方式
  83. set_irq_type(IRQ_EINT2,EXT_FALLING_EDGE);//設(shè)置中斷2觸發(fā)方式
  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)//設(shè)備關(guān)閉函數(shù)
  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加載驅(qū)動時執(zhí)行
  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卸載驅(qū)動時執(zhí)行
  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");

這個驅(qū)動實際上是通過紅外傳感器檢測電平變化,來實現(xiàn)人數(shù)的統(tǒng)計,改進后能夠?qū)崿F(xiàn)正確的通過中斷先后來識別方向,還排除了單一中斷的

抖動干擾。



關(guān)鍵詞: 控制IO端口s3c241

評論


技術(shù)專區(qū)

關(guān)閉