Olá, já estou a algum tempo em um projeto que não está andando.
Preciso ler a informação que chega em um display lcd 20x4 (barramento paralelo 8 pinos de comunicação) e envia-la para um planilha google.
o display lcd recebe os dados de um PLC de uma maquina injetora de plástico. Porem não consegui informações do PLC para retirar esses dados diretamente del, pois o PLC e de fabricação propria da empresa que fez a maquina, e não disponibiliza esses dados. Empresa que já não existe mais.
Atualmente estou tentando fazer isso ligando os pinos de comunicação do lcd nas portas de um esp32, que enviaria esses dados para a planilha. O código que estou usando para isso está a baixo, porem não funciona.
Gostaria de sugestões de como prosseguir, se existe uma forma mais simples de ter as informações que a máquina plota no display, como algum analisador logico que funcione como um display lcd que não plota os dados, mas mande ele via serial ou algo assim.
Não e possível fazer muitos testes na máquina, pois ela roda 24 por 7, só posso testar em paradas para manutenção.
Se alguém puder me dar uma luz eu agradeço.
/* Ativa debug pela porta serial, para ser utlizado com serial monitor */
#define DEBUG 1
/* Tamanho do buffer para armazenamento dos bytes lidos do LCD */
#define BUFFER_LEN 250
/* Pinos do LCD */
#define PINO_EN 21 //Ativo em HIGH
#define PINO_RS 22 //LOW comando, HIGH Caractere
#define PINO_RW 23 //LOW write, HIGH read
#define PINO_BIT7 19 //Bit de dados
#define PINO_BIT6 18 //Bit de dados
#define PINO_BIT5 25 //Bit de dados
#define PINO_BIT4 26 //Bit de dados
#define PINO_BIT3 27 //Bit de dados
#define PINO_BIT2 14 //Bit de dados
#define PINO_BIT1 12 //Bit de dados
#define PINO_BIT0 13 //Bit de dados
/* Ativa modo de comunicação seria utlizando apenas 4 pinos/bits de dados,
se estiver comentado ativa modo 8pinos bits de dados */
#define BITS_8
/* Variável que contem os pinos do LCD a serem lidos */
#ifdef BITS_4
#define ULTIMO_BIT 3
uint8_t pinosPorta[4] = {PINO_BIT7, PINO_BIT6, PINO_BIT5, PINO_BIT4};
#else
#define ULTIMO_BIT 7
uint8_t pinosPorta[8] = {PINO_BIT7, PINO_BIT6, PINO_BIT5, PINO_BIT4, PINO_BIT3, PINO_BIT2, PINO_BIT1, PINO_BIT0};
#endif
void IRAM_ATTR isr();
/* Variável que contem os bytes lidos */
uint8_t bytesLidos[BUFFER_LEN];
/* Variável que contem se o byte é um comando ou caractere */
uint8_t comandosLidos[BUFFER_LEN];
uint8_t RW_Lidos[BUFFER_LEN];
/* Variável para controle da posição atual do byte no buffer rotativo */
uint8_t posicaoByteLido = 0;
/* Variável para controle da quantidade de bytes lidos e disponiveis */
uint8_t BytesDisponiveis = 0;
/* Variável para quebra de linha do debug */
#ifdef DEBUG
int cc = 0;
#endif
/* Função setup, configuração do dispositivo, executa apenas uma vez quando ligado */
void setup() {
/* Inicia portas */
pinMode(PINO_EN, INPUT);
pinMode(PINO_RS, INPUT);
pinMode(PINO_RW, INPUT);
for ( uint8_t i = 0; i < ULTIMO_BIT+1; i++ ) {
pinMode( pinosPorta[i], INPUT );
digitalRead(pinosPorta[i]);
}
/* Ativa interrupção externa no PINO_EN */
//attachInterrupt(PINO_EN, isr, FALLING); //HIGH para LOW
attachInterrupt(PINO_EN, isr, RISING); //LOW para HIGH
/* Inicia comunicação serial para debug */
#ifdef DEBUG
Serial.begin(115200);
delay(300);
Serial.flush();
Serial.println();
Serial.println("Iniciando leitura");
#endif
}
/* Função loop, executa continuamente enquanto ligado */
void loop() {
if (BytesDisponiveis > 0 ) {
/* Pega um byte lido */
uint8_t cbyte = bytesLidos[posicaoByteLido];
/* Paga informação se é comando ou não */
uint8_t ccomm = comandosLidos[posicaoByteLido];
uint8_t cRW = RW_Lidos[posicaoByteLido];
/* Decrementa quantidade de bytes disponiveis */
BytesDisponiveis--;
/* Incrementa posição atual no buffer rotativo */
posicaoByteLido++;
/* Se chegou no final do buffer volta para o inicio */
if ( posicaoByteLido >= BUFFER_LEN ) {
posicaoByteLido = 0;
}
/* Envia dados lidos para debug serial monitor */
#ifdef DEBUG
if (ccomm) {
Serial.print( " " );
} else {
Serial.print( "*" );
}
if (cRW) {
Serial.print( " " );
} else {
Serial.print( "W" );
}
if ( cbyte < 16 )
Serial.print( "0" );
Serial.print( cbyte, HEX );
cc++;
if ( cc > 20 ) {
cc = 0;
Serial.println();
} else {
Serial.print( " " );
}
#endif
}
}
/* Função que efetura a leitura digital da porta/pino que corresponde a 1bit */
uint8_t lerPorta( uint8_t p ) {
return ((GPIO.in >> p) & 0x1);
}
/* Função ativada pelo interruptor externo, FALLING = HIGH para LOW */
void IRAM_ATTR isr() {
static uint8_t posicaoByte = 0;
/* Efetua leitura a porta RS que indica se o byte a ser lido é comando ou caractere */
comandosLidos[posicaoByte] = lerPorta(PINO_RS);
RW_Lidos[posicaoByte] = lerPorta(PINO_RW);
/* Efetua leitura dos bits disponiveis e converte em um byte "byteLido" */
uint8_t byteLido = 0;
for ( uint8_t i = 0; i < ULTIMO_BIT; i++ ) {
byteLido += lerPorta(pinosPorta[i]);
byteLido = byteLido << 1;
}
byteLido += lerPorta(pinosPorta[ULTIMO_BIT]);
/* Adiciona o byte lido ao buffer */
bytesLidos[posicaoByte] = byteLido;
/* Incrementa a quantidade de bytes lidos disponiveis */
BytesDisponiveis++;
/* Incrementa a posição no buffer rotativo */
posicaoByte++;
if ( posicaoByte >= BUFFER_LEN ) {
posicaoByte = 0;
}
}