17 de maio de 2021

Do bit Ao Byte

Embarcados, Linux e programação

Como usar ADC no Raspberry Pi Pico

ADC no Raspberry Pi

Ao que parece, usar ADC no Raspberry Pi Pico pode ser mais preciso do que no ESP32 e, certamente, do que no ESP8266. O ADC da RP2040 tem uma surpresa agradável, acompanhe a leitura para ver o que mais ela oferece além da mera leitura analógica.

O ADC no Raspberry Pi Pico, claro, é melhor que o do Arduino também, no que se refere à resolução. Ele tem 12 bits, dando uma escala de 0 à 4095. Não me pergunte o porquê; o MicroPython transforma isso em uma range de 16 bits, onde teremos valores de 0 à 65.535. Provavelmente é para manter a compatibilidade com o comportamento em outras microcontroladoras, porque se fisicamente temos 12 bits, são 12 bits de resolução. O resto é “zoom digital”.

O RP2040 tem 5 canais, 4 estão disponíveis através dos GPIO 26 ao 29. O GPIO29 pode ser usado para medir a tensão VSYS e o quinto, adivinha? Ele é conectado a um sensor de temperatura interno da RP2040!

Como usar o ADC no Raspberry Pi

Como sempre, invés de importarmos tudo o que tem na machine, importando apenas o que será usado nos propiciará economia de memória.

from machine import ADC
adc = ADC(26) #canal 0, indicando GPIO26
adc = ADC(0)  # canal 0 direto
adc = ADC(4)  # sensor de temperatura

Repare que podemos passar tanto o GPIO como o canal diretamente. Também, não é necessário usar Pin() juntamente ao ADC.

Para fazer uma leitura do canal 0, basta algo como:

from machine import ADC
from time import sleep_ms as delay
ad_ch0_gp26 = ADC(26)

while True:
    delay(1500)
    print("ADC 0: ", ad_ch0_gp26.read_u16())

Esse foi fácil, hum? A leitura devolve um unsigned de 2 bytes. O objeto ADC só tem mais uma coisa, que é a definição do pino de leitura da temperatura. Se esquecer qual é o pino, basta usar help(ADC). A macro é ADC.CORE_TEMP, que referencia o quinto canal.

Para converter a leitura para tensão, devemos usar um fator de conversão, explicado mais abaixo

Como usar o sensor de temperatura da RP2040

Falar do ADC no Raspberry Pi é empolgante, mas nada melhor do que usar, certo? Vamos fazer a leitura do sensor de temperatura interno, mas precisamos levar em conta alguns conceitos.

Fator de conversão

A primeira coisa que devemos ter em mente é a leitura. A leitura é como acima, mas lendo o canal 4. A tensão de referência 3v3 e a “pseudo-resolução” do MicroPython é 2 bytes, portanto devemos definir o fator de conversão para dimensionar a leitura. O fator de conversão é fundamental para converter a leitura em tensão de referência, sendo as primeiras duas linhas do código disposto abaixo:

conversion_factor = 3.3 / (65535)
pre_temp = adc.read_u16() * conversion_factor

Pronto. Já sabemos fazer a leitura do ADC, reconhecemos os canais e suas atribuições e sabemos converter a leitura em tensão. Para a leitura de temperatura tem mais um fator a considerar: A conversão da tensão para graus Celsius.

Tensão para graus Celsius

No datasheet estão dispostas todas as informações necessárias, mas de uma maneira bem mais amarga para quem está iniciando. Eu havia estudado e anotado, mas esqueci e perdi a anotação. Faz parte. Só que o fator de conversão era uma anotação à parte, encontrada tanto no livro que recomendo no vídeo da playlist de RPi Pico como em alguns dos artigos relacionados. Enfim, o código completo para leitura da temperatura, dentro de uma função, tudo organizadinho, fica desse jeito:

from machine import ADC
from time import sleep_ms as delay

def temperature():
    adc_temp          = ADC(4)
    readings          = 0
    conversion_factor = 0
    
    for _ in range(4):
        readings += adc_temp.read_u16()
    
    conversion_factor = 3.3 / (65535)
    voltage = (readings/4) * conversion_factor
    
    temperature_now = 21 - (voltage - 0.706) / 0.001721
    
    print("Temperatura: ",temperature_now)
    
if __name__ == '__main__':
    temperature()


Mas vamos lá; no livro está descrito 27 – (voltage – 0.706) / 0.00172121 – (voltage – 0.706) / 0.001721 , mas aqui tive que colocar 21 para bater a temperatura. Depois, colocando o dedo sobre a MCU a temperatura subiu gradativamente. Com esse valor, deu menos de 1 grau de diferença, o que é ótimo, já que a temperatura tem influência da própria MCU. Mas isso também é mal. Se a temperatura estiver calibrada para referenciar o ambiente e houver processamento o suficiente para aquecer a MCU, haverá discrepância. Já se estiver medindo o core, pode ser uma boa referência para saber se a MCU está trabalhando demais, se pode estar havendo algum consumo excessivo etc. Portanto, usando a fórmula original trará a temperatura de operação e ponto.

ADC no Raspberry Pi

A linha 19 é pra executar a função se o programa for chamado diretamente. Se for incluído em outro programa, a função só executará se for chamada explicitamente. Devo fazer um vídeo explicando um pouco mais nessa série sobre MicroPython dessa playlist.

Quer uma Pico?

Aproveite, pois a Robocore está nas últimas peças. Se perder, vai ter que esperar. O link da Pico é esse.