我正在使用AT91SAM9G25板,它有4个PIO控制器,可管理多达32个可编程I / O线。每个引脚都可配置为通用I / O线 仅作为I / O线路或多路复用两个外围I / O.因此,例如,根据文档(SAM9G25,第14页),信号PC0可以复用为通用I / O线或VIDEO_ATMEL_ISI(图像传感器接口的ISI)的ISI_D0线。
╔════════════╦════════════╦════════════╦════════════╦════════════╗
║ Primary ║ Alternates ║ PeripA ║ PeripB ║ PeripC ║
╠════════════╬════════════╬════════════╬════════════╬════════════╣
║ Signal/Dir ║ Signal/Dir ║ Signal/Dir ║ Signal/Dir ║ Signal/Dir ║
║ --------- ║ --------- ║ --------- ║ --------- ║ --------- ║
║ PC0 / I/O ║ ║ ║ ISI_D0 / I ║ ║
╚════════════╩════════════╩════════════╩════════════╩════════════╝
所有GPIO线的复位状态为方向IN和上拉启用。当我通过sysfs使用GPIOLIB时,由于上拉,我在几个GPIO中读取“1”值作为INPUT。当它们可以与其他外设复用时,这是GPIO(带上拉电阻的INPUT)复位时的正常安全状态吗?我不知道如何通过GPIOLIB通过用户空间禁用上拉。例如,我看到当内核启动时,它检查是否在内核或作为模块启用了图像传感器外设,如果是,则将PC0设置为外设B.这是在/ arch / arm / mach的内核源代码中-at91 / at91sam9x5_devices.c
#if defined(CONFIG_VIDEO_ATMEL_ISI) || defined(CONFIG_VIDEO_ATMEL_ISI_MODULE)
....
at91_set_B_periph(AT91_PIN_PC0, 0); /* ISI_D0 */
...
#endif
然后,如果我不在内核中启用ISI支持,我可以将PC0信号用作GPIO线。这是/ sys / kernel / debug / gpio:
# cat /sys/kernel/debug/gpio
GPIOs 32-63, A:
GPIOs 64-95, B:
[atmel_usba_udc] GPIOB16: [gpio] set
[d1] GPIOB18: [gpio] clear
GPIOs 96-127, C:
GPIOs 128-159, D:
[ohci_vbus] GPIOD19: [gpio] clear
[ohci_vbus] GPIOD20: [gpio] clear
[d2] GPIOD21: [gpio] set
这是/ sys / kernel / debug / at91_gpio
# cat /sys/kernel/debug/at91_gpio
Pin PIOA PIOB PIOC PIOD
0: A A GPIO:1 A
1: A A GPIO:1 A
2: GPIO:1 A GPIO:1 A
3: GPIO:1 A GPIO:1 A
4: GPIO:1 A GPIO:1 GPIO:1
5: GPIO:1 A GPIO:1 GPIO:1
6: GPIO:1 A GPIO:1 A
7: B A GPIO:1 A
8: GPIO:1 GPIO:1 GPIO:1 A
9: A A GPIO:1 A
10: A A GPIO:1 A
11: A GPIO:1 GPIO:1 A
12: A GPIO:1 GPIO:1 A
13: A GPIO:1 GPIO:1 A
14: A GPIO:1 GPIO:1 GPIO:1
15: GPIO:1 GPIO:1 GPIO:1 A
16: GPIO:1 GPIO:1 GPIO:0 A
17: GPIO:1 GPIO:1 GPIO:1 A
18: GPIO:1 GPIO:1 GPIO:1 A
19: GPIO:1 A GPIO:1 GPIO:0
20: GPIO:1 A GPIO:0 GPIO:0
21: GPIO:1 A GPIO:0 GPIO:1
22: GPIO:1 A GPIO:1 A
23: GPIO:1 A GPIO:1 A
24: GPIO:1 A GPIO:1 A
25: GPIO:1 A GPIO:1 A
26: GPIO:1 A GPIO:1 A
27: GPIO:0 A GPIO:1 A
28: GPIO:1 A GPIO:0 A
29: GPIO:1 A GPIO:0 A
30: GPIO:1 A GPIO:1 A
31: GPIO:1 A GPIO:1 A
上面的输出显示PIOA0多路复用到外设A(TXD0 UART线),例如PIOC20被清零,但是文档说所有处于复位状态的GPIO线路都是带有上拉的INPUTS而且我找不到内核或者u -boot禁用此GPIO的上拉(如果没有触及其寄存器,GPIO可能会保持其状态吗?)
但他主要的问题是,如何清除GPIO线路的上拉寄存器?我在内核源代码中发现/arch/arm/mach-at91/at91sam9x5_devices.c使用linux-2.6.39 / arch / arm / mach-at91 / gpio.c中实现的这个函数。
/*
* enable/disable the pull-down.
* If pull-up already enabled while calling the function, we disable it.
*/
int __init_or_module at91_set_pulldown(unsigned pin, int is_on)
{
void __iomem *pio = pin_to_controller(pin);
unsigned mask = pin_to_mask(pin);
if (!pio || !cpu_has_pio3())
return -EINVAL;
/* Disable pull-up anyway */
__raw_writel(mask, pio + PIO_PUDR);
__raw_writel(mask, pio + (is_on ? PIO_PPDER : PIO_PPDDR));
return 0;
}
EXPORT_SYMBOL(at91_set_pulldown);
标题拱/ arm / mach-at91 / include / mach / gpio.h
#ifndef __ASSEMBLY__
/* setup setup routines, called from board init or driver probe() */
.....
extern int __init_or_module at91_set_pulldown(unsigned pin, int is_on);
.....
#endif /* __ASSEMBLY__ */
如何在我的工具链中使用此功能,还是应该创建内核模块?
由于
PD:对不起我的英文错误,我知道我需要改进它。答案 0 :(得分:2)
也许你可以单独留下上拉。我在OMAP SoC上使用了GPIO,在最低级别有类似的引脚复用器选项,但没有必要担心上拉。通常无论驱动它,它都可以吸收足够的电流(这是EE /电路的观点,如果您不熟悉,请不要担心)。浮动输入可能是随机的,也很麻烦;拉高应该没问题。
我认为您不应该制作内核模块。我建议您使用现有的用户模式界面进行实验。您的内核应该已经连接了低级驱动程序以通过sysfs提供访问。请参阅sysfs,omap gpio。我不认为我在sysfs中看到了pullup选项。如果你有一些工作并且需要从C代码调用它,那么你可以查找API,或者只使用system()。
答案 1 :(得分:0)
在使用设备树的较新内核上,您可以通过重新编译设备“blob”来控制它,而不需要更改内核或编写内核驱动程序。
但如果pinctrl具有像gpio这样的用户空间接口,那将是非常可爱的,因此控制引脚的完整解决方案是用户空间控制。