Programação GPIO

De Caninos Loucos
Ir para navegação Ir para pesquisar

Esta página explica como programar as saídas GPIO (General Purpose Input/Output) da Labrador, que são basicamente pinos nos quais você pode enviar e receber dados. Para facilitar a programação, a placa Labrador segue a interface padrão para userspace para Linux embarcado. O tutorial desta página funciona tanto com a Labrador 32 quanto 64-bits.

Além disso, a placa Labrador 32-bits é compatível com o formato da Raspberry Pi, e possui a biblioteca wiringK9, baseada na wiringPi, também da Raspberry Pi. Mais detalhes desta biblioteca pode ser encontrado nessa página Wiring K9.

Configuração dos pinos

A configuração de pinos para o cabeçalho de GPIO é a seguinte:

caption Mapeamento do header de 40 pinos.

Interface GPIO do Linux

O kernel Linux implementa em si uma solução de acesso à GPIO atraves de um modelo de criação e consumo de GPIO. Os drivers de criação são drivers como o controlador de GPIO que será detalhado nesta página, os consumidores são os drivers como sensores que utilizam estas linhas GPIO. Dentro do kernel Linux existe uma estrutura de alocação e registradores dos pinos GPIO chamado gpiolib, esta estrutura cobre os drivers em nível de kernel e userspace. As bibliotecas de espaço de usuário são, até a versão 4.7 do Kernel Linux a sysfs e a partir da versao 4.8 a chardev. Embora a placa Labrador esteja atualmente no Kernel 4.19, ambas ainda são compatíveis e cobriremos o uso das duas interfaces de espaço de usuário.

Interface sysfs

Na interface sysfs o usuário tem acesso às GPIO através de arquivos exportados em /sys/class/gpio. Para isso é necessário exportar um arquivo para cada GPIO, configurar a porta e escrever na mesma.

Identificando o número da GPIO

No método sysfs utiliza-se o número absoluto das GPIO para exportá-las individualmente. A Labrador possui 5 grupos de GPIO (A, B, C, D e E). Cada um desses possui 32 pinos agrupados, portanto para indicar o valor absoluto do pino temos um offset dado pelo grupo mais o valor do pino, este offset seguem a lógica a seguir:

  • A: 0
  • B: 32
  • C: 64
  • D: 96
  • E: 128

Portanto se quisermos acessar o pino 3 do header GPIO, no caso seria GPIOE3, portanto devemos exportar o pino GPIO 128+3=131. Isto seria feito com a seguinte linha de terminal:

$ echo 131 > /sys/class/gpio/export

Configurando a direção do pino

Após exportado o pino devemos configurar a direção do mesmo entre input (in) ou output (out). Para isto basta escrever no GPIO exportado o valor requerido. No nosso exemplo colocaremos como output:

$ echo out > /sys/class/gpio/gpio131/direction

Escrevendo ou lendo no pino

Para escrever no pino configurado como output basta enviar o valor para o parâmetro value do pino. No nosso exemplo colocaremos o valor 1 no pino:

$ echo 1 > /sys/class/gpio/gpio131/value

Caso o pino seja definido como input basta ler este mesmo arquivo.

$ cat /sys/class/gpio/gpio131/value

Lendo um parâmetro

O comando cat pode ser usado nestes arquivos de parâmetros para ler o que já foi configurado dos pinos ficamos então com os seguinte exemplo completos para configuração do pino GPIOE3 como output em alta e GPIOE2 como input:

$ echo 131 > /sys/class/gpio/export #Exportando GPIOE3
$ echo out > /sys/class/gpio/gpio131/direction #Definindo como output
$ echo 1 > /sys/class/gpio/gpio131/value #Escrevendo o valor 1
$ cat /sys/class/gpio/gpio131/direction #Lendo a direção do pino
out
$ cat /sys/class/gpio/gpio131/value #Lendo o valor do pino
1
$ echo 130 > /sys/class/gpio/export #Exportando GPIOE2
$ echo in > /sys/class/gpio/gpio130/direction #Definindo como input
$ cat /sys/class/gpio/gpio130/value #Lendo o valor do pino
0
$ cat /sys/class/gpio/gpio130/direction #Lendo a direção do pino
in

Interface chardev

A interface chardev é a interface padrão do kernel Linux a partir do kernel 4.8, apesar de esta solução não permitir o uso de comandos padrão do terminal linux para controle da gpio como echo e cat usados anteriormente, esta API utiliza a biblioteca libgpiod que provê uma série de ferramentas para uso em terminal e também para uso em C, com bibliotecas de vinculações disponíveis em C++ e Python. A solução chardev é mais simples, elegante e robusta que a sysfs.

Identificando o número da GPIO

Para o chardev os diferentes controladores de GPIO possuem pastas diferentes, chamados gpiochip. No caso temos A=0, B=1, C=2, D=3, E=4. Portanto, os pinos agora serão definidos pelo controlador e pela linha dentro do mesmo.

libgpiod no terminal

gpiodetect

Os controladores podem ser identificados com o comando gpiodetect disponível pelo libgpiod

$ gpiodetect
gpiochip0 [209c000.gpio] (32 lines)
gpiochip1 [20a0000.gpio] (32 lines)
gpiochip2 [20a4000.gpio] (32 lines)
gpiochip3 [20a8000.gpio] (32 lines)
gpiochip4 [20ac000.gpio] (32 lines)

gpioinfo

O comando gpioinfo fornece as informações dos pinos de cada controlador, por exemplo para exemplos dos pinos do controlador E:

$ gpioinfo 0
        line   0:      unnamed       unused   input  active-high
        line   1:      unnamed       unused   input  active-high
        line   2:      unnamed       unused   input  active-high

No caso, nenhum destes pinos está em utilização.

gpioget

Os pinos estão configurados como entrada por padrão, para acessar os valores de entrada dos pinos basta utilizar o comando gpioget, no exemplo o pino GPIOE3 (controlador 4, pino 3)

$ gpioget 4 3
0

gpioset

O comando gpioset muda a direção para output e define o valor do mesmo, no exemplo definiremos o GPIOE3 para alto:

$ gpioset 4 3=1
1

gpiomon

Este comando é utilizado para interrupções e eventos, ele monitorará o pino para mudanças e retornará as mudanças encontradas.

$gpiomon 4 3
event:  RISING EDGE offset: 3 timestamp: [    322.073816438]
event: FALLING EDGE offset: 3 timestamp: [    323.467289198]
event:  RISING EDGE offset: 3 timestamp: [    324.245127683]

Utilizando chardev em C

A API chardev facilita o uso em programas em C, alguns exemplos podem ser encontrados com facilidade, como estes.