ScadaBr - Arduinos - Influência entre as portas analógicas

Amigos,

trago aqui uma discussão, baseada na observação de slaves (escravos) que tenho instalados em uma rede de automação. O mestre dessa rede é o software chamado ScadaBR, bem discutido nos posts do LDG.

Acontece que estou procurando melhorar a exatidão dos valores obtidos para me garantir que as leituras realmente são as reais.

Observem a leitura de uma porta analógica que possui um potenciômetro ligado a ela. Durante 24h, não foi feito nenhum ajuste no potenciômetro.

Fiquei muito intrigado por essa variação. Por coincidência fui olhar a variação da leitura de um sensor de iluminação que tenho no mesmo arduino. Observem o gráfico.

Para mim ficou claro que existe uma relação. Checando no código observei que as leituras são feitas em sequência, sem intervalo. Dai fui pensar se é necessário a colocação de um delay, ou se possível, outra alternativa.

Em um outro escravo da mesma rede estou monitorando uma porta analógica ligada ao GND. Para minha surpresa o valor não ficou zerado. Observem que até caiu com o tempo. O que acontece no arduino?

Alguém tem algo a contribuir com esse assunto?

Exibições: 2991

Responder esta

Respostas a este tópico

Olá Sidney,

Este problema já foi discutido algumas vezes no forum do LDG, uma pesquisa no google pode ajudar.

O problema se deve ao fato do hardware do AVR ter apenas um conversor ADC alimentado por um MUX onde estão ligadas as diversas portas analógicas do chip. Esta configuração é muito comum em outras famílias de microcontroladores como por exemplo na maioria dos PIC.

O ADC trabalha da seguinte forma, quando no programa escrevemos 

valor = analogRead(A0);

O microcontrolador seta o MUX de forma a  selecionar a entrada ADC0 na entrada Uin do ADC, onde existe um circuito que pega a uma amostra da tensão na entrada Uin e congela a mesma para que o ADC possa fazer as devidas comparações entre a amostra e a tensão de referência do ADC (circuito sampling and holding, amostra e retém), salvando o resultado nos registradores ADCH e ADCL (10bits) que então será salvo na variável valor.

No próximo ciclo de execução do programa (void main), ou seja na próxima vez que for feita outra leitura da entrada analógica uma nova amostra  Uin será captura e comparada resultando em uma nova leitura em valor.

A questão é que o circuito do ADC leva um certo tempo para capturar uma amostra, então se houver variações abruptas entre uma leitura e outra o circuito pode não conseguir capturar uma amostra de valor correto.

Uma analogia muito próxima é a carga e descarga de um capacitor em um circuito RC.

Se aplicarmos uma tensão contínua em um capacitor não obteremos a leitura da tensão aplicada no instante inicial, mas apenas após algum tempo depois, devido a carga do capacitor. Se em um momento o capacitor estiver carregado e no seguinte ligarmos o mesmo ao 0V a tensão do capacitor também levará um certo tempo para atingir o novo potencial, este tempo será proporcional a constante RC do circuito.

A mesma coisa ocorre no circuito de amostragem  do ADC, e no datasheet do microcontrolador está descrito o tempo de amostragem.

Quando usamos apenas um sensor ligado a uma entrada analógica do arduino isso tudo passa desapercebido, mas quando usamos dois ou mais sensores podem ocorrer os problemas registrados no seu gráfico. Porque no caso as entradas estão com valores bem diferentes uma da outra e o ADC não está conseguindo tomar uma amostra com valor real.

Existem duas soluções para resolver o problema:

1 - Diminuir a impedância dos sensores, assim o tempo de carga/descarga do ADC diminui. O problema é que nem sempre isso é possível.

2 - Selecionar a entrada a ser medida, aguardar um tempo para que o circuito estabilize a leitura e então fazer a leitura do sensor.

Para o caso 2 o código ficaria assim: 

analogRead(A0);

delay(10);

valor1 = analogRead(A0);

analogRead(A1);

delay(10);

valor2 = analogRead(A1);

Normalmente isso resolve o problema, se persistir, tem que verificar a existência de captação de ruídos e interferências nos cabos e falhas de aterramento na sua montagem.

Abraço.

Oi sidney de acordo, com o que o Wiechert falou, de repente o modbus RTU, não aceitaria bem a questão do DElay, poderia ser interessante ver a questão do uso do Modbus ASCII, que em outro post o wiechert já havia dado essa ideia pora poder usar Delay.

O vitor Rocha tinha publicado esta biblioteca do modbus ASCII na area jurassica dos nossos trabalhos pode te servir para trabalhar com delay aqui o post 

http://labdegaragem.com/forum/topics/scadabr?id=6223006%3ATopic%3A1...

Pode trabalhar com modbus-RTU também, substituindo o delay por um contador de tempo baseado na função millis.

Permalink Responder até Luciano Bellarmino 2 minutos atrás

Wiechert, mas isto não justifica a enorme variação na leitura apresentada em 24h acredito eu, justificaria oscilações nas medições apenas. Ou estou errado?

Se eu não estiver errado na afirmação anterior, o AVR utiliza como tensão de referencia para o AD a própria alimentação do CI? Se sim, uma variação na alimentação (sem variar a entrada analógica) justificaria o erro na leitura.

Luciano,

Observe as linhas vermelha (iluminação) e azul (potenciômetro) do gráfico.

Perceba que a linha vermelha vem de um sensor de iluminação do ambiente, se me recordo bem é um LDR, o Sidney pode confirmar. E a linha reflete o ciclo de um dia, mostrando a iluminação diminuindo com o anoitecer, os momentos que havia lâmpadas acesas, o amanhecer do dia, e até as variações mínimas que provavelmente são devidas a passagem de nuvens, animais ou pessoas perto do sensor.

A linha azul que era pra ser uma reta horizontal, pois o potenciômetro não está sendo movimentado e portanto deveria estar entregando sempre o mesmo nível de tensão a entrada analógica onde está ligado, e provavelmente está. Mas como podemos ver a linha azul acompanha a linha vermelha durante todo o período de tempo. 

A tensão de referência do ADC no AVR (como na maioria dos controladores que tem ADC interno) pode ser selecionado via registradores para usar fonte externa ou interna que vem da alimentação de 5V do arduino, e passa por um regulador interno do AVR para então servir de referência.  E realmente uma variação na tensão de referência irá causar erros na leitura. Mas se realmente a causa do erro fosse uma variação na referência a linha azul iria ser uma somatória da tensão do potenciômetro mais a variação na referência (que provavelmente seria algo com componentes de 60Hz ou 120Hz no caso de fontes lineares ou com componentes de alguns kHz nos casos onde o circuito é alimentado por fontes chaveadas. Mas o que é visto na linha azul é a somatória da linha vermelha com a linha do potenciômetro.

Pela análise dos gráficos, o mais provável é que o ADC não está bem configurado, está pegando o sinal de amostragem por tempo menor que o suficiente para estabilizar o circuito, gerando os erros. Este problema não gera erro quando se usa uma única entrada analógica.

E como a IDE do arduino não disponibiliza  nenhum comando para setar os parâmetros do AD a saída é comandar diretamente os registradores via comandos assembly ou então fazer os ajustes como mostrei na minha resposta anterior, acho que esta é a saída mais fácil pra quem não quer se dedicar a estudar o microcontrolador mais profundamente, como é o caso da maioria dos usuários do arduino. Este é o preço que se paga pelas facilidades da IDE do arduino.

Abraço.

Então... logo após postar meu comentário me liguei que a grande variação na segunda entrada analógica era devida, por se tratar de um sensor de iluminação (até então estava considerando aquela variação como um erro também o que me fez entender que as duas leituras estavam sendo afetadas pelo mesmo problema. Erro de interpretação meu hehe). Assim, concordo plenamente com o que você comentou anteriormente.

Até tentei apagar meu comentário afim de evitar confundir outras pessoas que visualizassem este tópico, mas você foi mais rápido. Hahahaha.

Peço desculpas pelo equivoco.

Abraço

Não tem problema, acho que a indagação acabou por deixar a explicação mais detalhada, melhorando ainda mais o tópico.

Amigos,

entendi bem a explicação. Agradeço ao wiechert pela resposta tão completa.

Eu até tinha colocado o delay, e era de 200ms, mas não fiz como no exemplo. Vou fazer uma leitura, esperar um tempo e repetir a leitura.

Sobre o modbus ASCII, vou fazer o teste, mas por outros objetivos.

Se alguem souber de algo que possa ser feito fisicamente, também ajuda.

Vou mudar o código rapidamente e subir. Mostrarei os mesmos gráficos para entendermos o que acontece.

Sobre delay eu já estou usando o milis, faço uma leitura a cada segundo.

Então, ficará assim. A cada segundo faço uma leitura de uma porta, dou uns 50 microsegundos e repito a leitura. Dai passo para a outra porta, e vou seguir até o fim.

Amigos,

realmente a afirmação do Luciano serviu esclarecer mais o tópico. É essa ideia mesmo. Quando só acendemos led com arduino não nos deparamos com esses desafios.

Mas a partir do momento que temos um supervisório, 24h por dia, monitorando sensores ligados ao arduino, observamos fenômenos e todo bom cientísta vai buscar respostas.

Estou alterando o código, incluindo uma melhora na biblioteca.

Não sei se o wiechert sabe, mas a biblioteca do JPMZometa foi alterada pelo professor André, que segundo consta acrescentou funções modbus para melhorar a biblioteca.

Não havia me atentado para essa melhoria. Vou estudar agora os códigos, e talvez mudar todos os slaves.

Já penso realmente em aplicações críticas buscar um CLP que fale modbus rtu para salvar a lavoura. Quem souber de equipamentos assim, favor indicar os nomes para estudarmos.

Eu vou colocar os resultados dos testes e fecharemos o tópico com chave de ouro.

Sim.
Conheço bem as modificações feitas pelo André. .Ele acrescentou os outros comandos do protocolo Modbus, que foram feitos originalmente pela Modicom para facilitar que os seus PLC controlasem um módulo remoto de I/O. Mas sinceramente não vejo muita utilidade nestes comandos, ja que os comandos do grupo dos registradores holding ja fazem tudo que precisamos, que é ler/escrever em variáveis digitais (booleanas) e analógicas.
Quando a idéia de partir para o uso de PLC industrial saiba que os custos irão subir muito em relação ao sistema com o arduino, , tanto em termos do hardware como do software de programação que não é livre e que deve ser aprendido, coisa que também leva algum tempo. Não sei se é o melhor caso pra sua planta.

Antes de adotar a utilização de um CLP você deve colocar alguns pontos na balança e basicamente compara-los com valores. Como o Wiechert comentou, o custo do hardware irá subir muito, principalmente se você já tem um projeto pronto e já dedicou algum tempo considerável no estudo deste (terá que dedicar mais tempo estudando o CLP que irá utilizar).

O uso do CLP facilitaria caso estivesse iniciando o projeto pois não se preocuparia com algumas programações que não são o foco (modbus, escritas em LCD se for o caso, tratamentos em entradas analógicas, etc...) e ganharia uma certa robustez por ser um equipamento industrial, ja testado. Porém, para tudo existe um preço.

Quanto ao software de programação pago, vai depender do fabricante que você utilizar. Se escolher Rockwell por exemplo, prepare-se para gastar uma grana alta tanto em hardware quanto em software de programação.

Eu particularmente tenho algumas opiniões relacionadas ao uso de CLP x controle dedicado. Acredito não ser o foco do topico!

Amigos,

realmente a análise do custo benefício entre usar um slave desenvolvido com arduino (ou similar) e um CLP profissional deve ser encarada com cuidado.

Por hora, enquanto eu conseguir caminhar com arduinos vai esse mesmo. Adotar um CLP incluindo seus custos só se for um processo muito crítico, que atualmente não tenho.

Falta apresentar para vocês a solução feita no software. Aguardem um pouquinho que vai sair.

RSS

© 2024   Criado por Marcelo Rodrigues.   Ativado por

Badges  |  Relatar um incidente  |  Termos de serviço