Этот пример из elinux использует отображенный в память ввод -вывод . Ядро также экспортирует пространство интерфейса пользователя через /sys/class/gpio
, 1 , который также документированной на elinux . Работая в C, вы бы использовали низкий уровень read()
/ write()
вместо echo
, очевидно. Не используйте потоковые функции более высокого уровня.
Некоторые программисты немного расстраиваются, когда им говорят, что нужно использовать файловый интерфейс для вещей, которые, по их мнению, следует делать с помощью системных вызовов. Это чисто вопрос стиля - это одно и то же . В этом случае нет необходимости в «дополнительных затратах на ввод-вывод» и т. Д., Потому что это не настоящий файл, а интерфейс ядра. Точно так же, как любая другая система ABI, которую вы когда-либо использовали, только другая. Разработчики ядра давно предпочитают использовать узлы /proc
и /sys
, но я все еще вижу людей, решивших использовать системные вызовы там, где они могут, например sysfs()
, несмотря на то, man 2 sysfs
что ясно сказано:
Этот производный системный вызов System-V устарел; не используйте это. В системах с / proc ту же информацию можно получить через / proc / filesystems; используйте этот интерфейс вместо.
Это справочная страница библиотеки C, рассказывающая вам об использовании /proc
интерфейса . Если этого недостаточно, чтобы убедить вас, ничего не значит. /sys
это то же самое. Дело в том, что то, что вы используете файловый узел вместо какого-то специфичного для C API, не означает, что вы не занимаетесь реальным программированием, что производительность снижается и т. Д. И т. Д. Некоторые люди могут сказать, что это действительно хорошая функция. Это также метод, рекомендованный людьми, которые написали ядро ОС.
Краткое введение в интерфейс GPIO можно найти в [kernel-src]/Documentation/ABI/testing/sysfs-gpio
:
GPIOs are only made available to userspace by an explicit
"export" operation. If a given GPIO is not claimed for use by
kernel code, it may be exported by userspace (and unexported later).
Kernel code may export it for complete or partial access.
GPIOs are identified as they are inside the kernel, using integers in
the range 0..INT_MAX. See Documentation/gpio.txt for more information.
/sys/class/gpio
/export ... asks the kernel to export a GPIO to userspace
/unexport ... to return a GPIO to the kernel
/gpioN ... for each exported GPIO #N
/value ... always readable, writes fail for input GPIOs
/direction ... r/w as: in, out (default low); write: high, low
/edge ... r/w as: none, falling, rising, both
/gpiochipN ... for each gpiochip; #N is its first GPIO
/base ... (r/o) same as N
/label ... (r/o) descriptive, not necessarily unique
/ngpio ... (r/o) number of GPIOs; numbered N to N + (ngpio - 1)
Там, кажется, различные учебники и такие онлайн, в дополнение к Elinux. Я только использовал I2C, иначе я бы дал вам более прямой ответ.
Если вы заинтересованы в написании кода пространства ядра для доступа к GPIO, вы можете посмотреть здесь , хотя я думаю, что это действительно полезно, только если вы хотите написать драйвер для конкретного устройства и создать свой собственный API пространства пользователя.
1. Поскольку мем-сопоставленный ввод-вывод также должен использовать чтение / запись, я не уверен, что один метод дает здесь существенное преимущество перед другим. Использование /sys
интерфейса, безусловно, будет более переносимым, если вы ищете код, который будет работать не только на Raspberry Pi.