没想到一个小小的GPIO操作函数,竟然写了七篇博客,这应该算是最后一篇了。
1、s3c6410的GPIO操作函数主要涉及到三个文件,如下所示:
arch/arm/plat-s3c64xx/gpiolib.c
linux/arch/arm/plat-s3c/gpio.c
linux/arch/arm/plat-s3c/gpio-config.c
这三个文件中的很多函数都已经讲到了,可以说基本上都讲了,当然,下面这两个函数没讲:
int s3c_gpio_cfgpin(unsigned int pin, unsigned int config)
{
struct s3c_gpio_chip *chip =s3c_gpiolib_getchip(pin);
这个函数根据pin的引脚编号,得到对应的struct s3c_gpio_chip结构体,源码如下:
static inline struct s3c_gpio_chip *s3c_gpiolib_getchip(unsigned int chip)
{
return (chip < S3C_GPIO_END) ? s3c_gpios[chip] : NULL;
}
struct s3c_gpio_chip *s3c_gpios[S3C_GPIO_END];这个数组大家,应该还有印象。
unsigned long flags;
int offset;
int ret;
if (!chip)
return -EINVAL;
offset = pin - chip->chip.base;得到偏移量
local_irq_save(flags);
ret = s3c_gpio_do_setcfg(chip, offset, config);
这函数源码如下:
/* As a note, all gpio configuration functions are entered exclusively, either
* with the relevant lock held or the system prevented from doing anything else
* by disabling interrupts.
*/
static inline int s3c_gpio_do_setcfg(struct s3c_gpio_chip *chip,
unsigned int off, unsigned int config)
{
return (chip->config->set_config)(chip, off, config);
}
通过这调用具体的函数。例如:
static struct s3c_gpio_cfg gpio_4bit_cfg_noint = {
.set_config= s3c_gpio_setcfg_s3c64xx_4bit,
.set_pull = s3c_gpio_setpull_updown,
.get_pull = s3c_gpio_getpull_updown,
};
local_irq_restore(flags);
return ret;
}
2、看另外一个函数,源码如下:
int s3c_gpio_setpull(unsigned int pin, s3c_gpio_pull_t pull)
{
struct s3c_gpio_chip *chip = s3c_gpiolib_getchip(pin);
unsigned long flags;
int offset, ret;
if (!chip)
return -EINVAL;
offset = pin - chip->chip.base;
local_irq_save(flags);
ret = s3c_gpio_do_setpull(chip, offset, pull);
local_irq_restore(flags);
return ret;
}
其他的和前一个函数都很类似,我们只看这部分
static inline int s3c_gpio_do_setpull(struct s3c_gpio_chip *chip,
unsigned int off, s3c_gpio_pull_t pull)
{
return (chip->config->set_pull)(chip, off, pull);
}
也是调用具体的函数,如下
static struct s3c_gpio_cfg gpio_4bit_cfg_noint = {
.set_config = s3c_gpio_setcfg_s3c64xx_4bit,
.set_pull= s3c_gpio_setpull_updown,
.get_pull = s3c_gpio_getpull_updown,
}
EXPORT_SYMBOL(s3c_gpio_cfgpin);
EXPORT_SYMBOL(s3c_gpio_setpull);
终于可以松口气了,GPIO操作函数以及所涉及的文件都已分析完了,可是要告诉大家一个不幸的消息,其实我们费那么多事,其实在实际运用中,也可不用这些函数,只需要下面这些就可以了,究竟是什么呢?其实,大家想一下,不就是对IO寄存器的操作吗?直接对其直接进行不也是一样的吗,何必费那么多事。包装真可怕!
#define __raw_writeb(v,a)(__chk_io_ptr(a), *(volatile unsigned char __force *)(a) = (v))
#define __raw_writew(v,a) (__chk_io_ptr(a), *(volatile unsigned short __force *)(a) = (v))
#define __raw_writel(v,a) (__chk_io_ptr(a), *(volatile unsigned int __force *)(a) = (v))
#define __raw_readb(a) (__chk_io_ptr(a), *(volatile unsigned char __force *)(a))
#define __raw_readw(a) (__chk_io_ptr(a), *(volatile unsigned short __force *)(a))
#define __raw_readl(a) (__chk_io_ptr(a), *(volatile unsigned int __force *)(a))
上一篇:s3c6410的UART设备驱动(4)
下一篇:Linux下s3c6410的GPIO操作(6)
推荐阅读最新更新时间:2024-11-20 10:58
设计资源 培训 开发板 精华推荐
- OP497GSZ-REEL精密运算放大器正峰值检波器典型应用电路
- ADP7104CPZ-REDYKIT、ADP7104CP-EVALZ LFCSP RedyKits 适用于 ADP7104 3V 低压差 (LDO) 线性稳压器
- 3相直流无刷电机驱动IC —— TB67B000FG
- 4455-915-PDK,用于 Si4455 915-MHz 射频收发器的 EZRadio 双向链路开发套件
- LT6656BCS6-2.048、2.048V 精密电流和升压电压基准的典型应用
- L7905C 负电压稳压器的典型应用
- 基于VNI8200XP-32的八通道高端驱动器
- RGB耳环 V1.0
- 用于街道和室内 LED 照明的大电流 LED 驱动器
- 基带AGC