新聞中心

EEPW首頁 > 嵌入式系統(tǒng) > 設(shè)計應(yīng)用 > 嵌入式Linux設(shè)備驅(qū)動開發(fā)之:GPIO驅(qū)動程序?qū)嵗?/p>

嵌入式Linux設(shè)備驅(qū)動開發(fā)之:GPIO驅(qū)動程序?qū)嵗?/h1>
作者: 時間:2013-09-13 來源:網(wǎng)絡(luò) 收藏

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

11.3.2

代碼如下所示:

/*gpio_drv.h*/

#ifndefFS2410_GPIO_SET_H

#defineFS2410_GPIO_SET_H

#includelinux/ioctl.h>

#defineGPIO_DEVICE_NAMEgpio

#defineGPIO_DEVICE_FILENAME/dev/gpio

#defineLED_NUM4

#defineGPIO_IOCTL_MAGIC'G'

#defineLED_D09_SWT_IOW(GPIO_IOCTL_MAGIC,0,unsignedint)

#defineLED_D10_SWT_IOW(GPIO_IOCTL_MAGIC,1,unsignedint)

#defineLED_D11_SWT_IOW(GPIO_IOCTL_MAGIC,2,unsignedint)

#defineLED_D12_SWT_IOW(GPIO_IOCTL_MAGIC,3,unsignedint)

#defineBEEP_SWT_IOW(GPIO_IOCTL_MAGIC,4,unsignedint)

#defineLED_SWT_ON0

#defineLED_SWT_OFF1

#defineBEEP_SWT_ON1

#defineBEEP_SWT_OFF0

#endif/*FS2410_GPIO_SET_H*/

/*gpio_drv.c*/

#includelinux/config.h>

#includelinux/module.h>

#includelinux/moduleparam.h>

#includelinux/init.h>

#includelinux/kernel.h>/*printk()*/

#includelinux/slab.h>/*kmalloc()*/

#includelinux/fs.h>/*everything...*/

#includelinux/errno.h>/*errorcodes*/

#includelinux/types.h>/*size_t*/

#includelinux/mm.h>

#includelinux/kdev_t.h>

#includelinux/cdev.h>

#includelinux/delay.h>

#includelinux/device.h>

#includeasm/io.h>

#includeasm/uaccess.h>

#includeasm/arch-s3c2410/regs-gpio.h>

#includegpio_drv.h

staticintmajor=0;/*采用字符設(shè)備號的動態(tài)分配*/

module_param(major,int,0);/*以參數(shù)的方式可以指定設(shè)備的主設(shè)備號*/

voids3c2410_gpio_cfgpin(unsignedintpin,unsignedintfunction)

{/*對某個管腳進(jìn)行配置(輸入/輸出/其他功能)*/

unsignedlongbase=S3C2410_GPIO_BASE(pin);/*獲得端口的組基地址*/

unsignedlongshift=1;

unsignedlongmask=0x03;/*通常用配置寄存器的兩位表示一個端口*/

unsignedlongcon;

unsignedlongflags;

if(pinS3C2410_GPIO_BANKB)

{

shift=0;

mask=0x01;/*在GPA端口中用配置寄存器的一位表示一個端口*/

}

mask=(S3C2410_GPIO_OFFSET(pin)shift);

local_irq_save(flags);/*保存現(xiàn)場,保證下面一段是原子操作*/

con=__raw_readl(base+0x00);

con=~mask;

con|=function;

__raw_writel(con,base+0x00);/*向配置寄存器寫入新配置數(shù)據(jù)*/

local_irq_restore(flags);/*恢復(fù)現(xiàn)場*/

}

voids3c2410_gpio_pullup(unsignedintpin,unsignedintto)

{/*配置上拉功能*/

unsignedlongbase=S3C2410_GPIO_BASE(pin);/*獲得端口的組基地址*/

unsignedlongoffs=S3C2410_GPIO_OFFSET(pin);/*獲得端口的組內(nèi)偏移地址*/

unsignedlongflags;

unsignedlongup;

if(pinS3C2410_GPIO_BANKB)

{

return;

}

local_irq_save(flags);

up=__raw_readl(base+0x08);

up=~(1offs);

up|=tooffs;

__raw_writel(up,base+0x08);/*向上拉功能寄存器寫入新配置數(shù)據(jù)*/

local_irq_restore(flags);

}

voids3c2410_gpio_setpin(unsignedintpin,unsignedintto)

{/*向某個管腳進(jìn)行輸出*/

unsignedlongbase=S3C2410_GPIO_BASE(pin);

unsignedlongoffs=S3C2410_GPIO_OFFSET(pin);

unsignedlongflags;

unsignedlongdat;

local_irq_save(flags);

dat=__raw_readl(base+0x04);

dat=~(1offs);

dat|=tooffs;

__raw_writel(dat,base+0x04);/*向數(shù)據(jù)寄存器寫入新數(shù)據(jù)*/

local_irq_restore(flags);

}

intgpio_open(structinode*inode,structfile*filp)

{/*open操作函數(shù):進(jìn)行寄存器配置*/

s3c2410_gpio_pullup(S3C2410_GPB0,1);/*BEEP*/

s3c2410_gpio_pullup(S3C2410_GPF4,1);/*LEDD12*/

s3c2410_gpio_pullup(S3C2410_GPF5,1);/*LEDD11*/

s3c2410_gpio_pullup(S3C2410_GPF6,1);/*LEDD10*/

s3c2410_gpio_pullup(S3C2410_GPF7,1);/*LEDD9*/

s3c2410_gpio_cfgpin(S3C2410_GPB0,S3C2410_GPB0_OUTP);

s3c2410_gpio_cfgpin(S3C2410_GPF4,S3C2410_GPF4_OUTP);

s3c2410_gpio_cfgpin(S3C2410_GPF4,S3C2410_GPF5_OUTP);

s3c2410_gpio_cfgpin(S3C2410_GPF4,S3C2410_GPF6_OUTP);

s3c2410_gpio_cfgpin(S3C2410_GPF4,S3C2410_GPF7_OUTP);

return0;

}

ssize_tgpio_read(structfile*file,char__user*buff,

size_tcount,loff_t*offp)

{/*read操作函數(shù):沒有實際功能*/

return0;

}

ssize_tgpio_write(structfile*file,constchar__user*buff,

size_tcount,loff_t*offp)

{/*write操作函數(shù):沒有實際功能*/

return0;

}

intswitch_gpio(unsignedintpin,unsignedintswt)

{/*向5個端口中的一個輸出ON/OFF值*/

if(!((pin=S3C2410_GPF7)(pin>=S3C2410_GPF4))

(pin!=S3C2410_GPB0))

{

printk(Unsupportedpin);

return1;

}

s3c2410_gpio_setpin(pin,swt);

return0;

}

linux操作系統(tǒng)文章專題:linux操作系統(tǒng)詳解(linux不再難懂)

linux相關(guān)文章:linux教程


蜂鳴器相關(guān)文章:蜂鳴器原理


評論


相關(guān)推薦

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

關(guān)閉