Vai al contenuto
PLC Forum


Info Su Protocolli Di Comunicazione - connessione PC pic


kucaio

Messaggi consigliati

Buon giorno a tutti,

sono riuscito ad instaurare una comunicazione tra PC e PIC serie 18, il programma viene eseguito sino a che non genero un interrupt sulla porta di comunicazione del PIC

dove passo tramite un programma scritto in vb2008 un byte, che verrà utlizzato dal programma PIC come riferimento di velocità.

void
interrupt isr()
	{


	if (TMR1IF ==1)
  {
	//	TMR1IF=0;
	//	tempo_sleep = durata+1;
  }
	if (TMR2IF ==1)
  {
	//	TMR1IF=0;
	//	tempo_sleep = durata+1;
  }

	if (RCIF ==1)
  {
  valore_gas_pc = getchar();
  ritardo(50);
  printf("\rl_min	-%d\n-",limite_minimo_gas);
  printf("\rl_max	-%d\n-",limite_massimo_gas);
  printf("\rgas	-%d\n-",valore_gas_out);
  printf("\rpr2	-%d\n-",PR2);  
  printf("\rbatt	-%d\n-",valore_batteria_PC);
  printf("\rtemp	-%d\n-",temperatura);
  }
	}

Il programma funziona correttamente la stringa che passa il Pic al pc viene scomposta dal programma VB e vengono ricavati tutti i valori. La mia domande è :

C'è un metodo piu' consono o standard per scrivere il protocollo di comunicazione?

Se io volessi passare un intero ovvero 2 byte dal pc verso il pic come posso fare, ho visto che la funzione getchar() non funziona.

Grazia a tutti

Link al commento
Condividi su altri siti


Dimentica la “getchar”. Gestisci direttamente l’UART del PIC (da interrupt o in polling)

Per il protocollo, la cosa più semplice, è delimitare il buffer che invii con dei caratteri di controllo;

ad esempio STX all’inizio e ETX alla fine: in questo modo ti puoi “sincronizzare” con la ricezione.

Ovviamente devi trasmettere in ASCII e non in binario: potresti confondere l’inizio buffer con un dato binario uguale a STS o ETX all’interno del buffer

trasmesso. Se usi VB non è un problema.

Ti consiglio di aggiungere un CRC di controllo alla fine del buffer se i caratteri che invii sono molti.

Ciao.

Link al commento
Condividi su altri siti

Buongiorno,

Io ti consiglio di leggerti la documentazione del modbus RTU, cosi puoi capire come è stato implementato il protocollo. Al limite potresti implementare tale protocollo nel PIC ... cosi oltre che ai plus tecnici, e quindi le problematiche di comunicazione già implementate ( tipo CRC) , tale applicazione la puoi riutilizzare in altri ambiti , e magari con software commerciali tipo SCADA che supportano tale protocollo.

Tanto per cominciare :

il pacchetto che il Master manda è composta dai seguenti campi:

N° Nodo destinazione - Codice operazione - n Byte con significati diversi a seconda del codice - 2 byte CRC.

Da qua in poi ti lascio camminare da solo.

Link al commento
Condividi su altri siti

non mi sembra una buona idea per uno che è alle prime armi, non credo che sia necessaro un protocollo così complesso... almeno per i primi "esperimenti".

laugh.gif

Un protocollo tipico è come ti hanno già suggerito, un byte di start e un byte di stop (noti, utili per controllare il flusso) e i dati in mezzo. Questo è il minimo sindacale.

Se poi vuoi fare un po meglio puoi mettere un byte per la LEN, così dopo aver letto i primi 2 byte sai già quanti byte devi ancora ricevere e puoi fare la ricezione in un ciclo anche usando la funzione che riceve un solo carattere.

Infine non sarebbe male un CRC, che non deve essere necessariamente complesso, potrebbe essere anche semplicemente un checksum (una somma algebrica di tutti i byte senza riporto) o uno XOR, molto usato in questi casi.

Link al commento
Condividi su altri siti

if (RCIF ==1)

{

buffer_recezione[n_caratteri] = getchar();

n_caratteri=n_caratteri+1;

ritardo(50);

}

function Controllo_Recezione()

{

elabori il tuo buffer ... ad esempio:

if (n_caratteri >= 6)

{

elabori il tuo buffer ... ad esempio:

if buffer_recezione[o] == 2 valore_gas_pc = buffer_recezione[2] ;

}

}

Link al commento
Condividi su altri siti

Ciao a tutti, innanzi tutto vi volevo ringraziare , poi aggiornarvi sugli sviluppi del mio progetto.

ho effettuato le seguenti routine

void
interrupt isr()
	{
	if (RCIF==1)
  {
  while(RCIF==1)
  	{
  	buffer_ricezione[n_caratteri] = getchar;
  	n_caratteri=n_caratteri+1;
  	ritardo(50);
  	}
  controllo_ricezione();
  }
	}
void
controllo_ricezione()  
	{	
	if (n_caratteri >= 2) 
  {
  if (buffer_ricezione[n_caratteri] == 2)
  	{
  	valore_gas_pc = buffer_ricezione[2];
  	}
  }
	controllo_da_pc=1;
	ritardo(50);
	printf("\rl_min-%d\n",limite_minimo_gas);
	printf("\rl_max-%d\n",limite_massimo_gas);
	printf("\rgas-%d\n",valore_gas_out);
	printf("\rpr2-%d\n",PR2);  
	printf("\rbatt-%d\n",valore_batteria_PC);
	printf("\rtemp-%d\n",temperatura);
	n_caratteri=0;
	}
tramite un programma scritto in vb invio il numero 1021
Porta_attiva.Write((1021))

ma leggo tramite getchar solo un byte (buffer_ricezione[0] = "1", come se il buffer di ricezione si "scaricasse alla lettura del primo byte", in quanto il bit RCIF va a 0.

Avete qualche idea? Inoltre è possibile leggere il numero invece che in ascii in intero?

Ciao a tutti

Link al commento
Condividi su altri siti

La routine di interrupt viene chiamata quando un carattere e’ pronto (RCIF=1). Questa routine deve leggere il carattere (quindi RCIF diventa 0), memorizzarlo ed uscire; se fai una chiamata a “ritardo (50)” e‘ ovvio che perdi tutti i caratteri seguenti.

La routine diventa:

void interrupt isr (void)
{
// Se hai un solo interrupt abilitato diventa inutile fare: if (RCIF==1)
if (RCIF == 1)
  {
  // prima di memorizzare il carattere sarebbe saggio controllare se ci sono errori di ricezione...
  buffer_ricezione [n_caratteri++] = getchar ();
  }
}

void main (void)
  {
  //…
  n_caratteri = 0;
  If  (n_caratteri >= 2)
    {
    //…
    }
  }

Alcuni consigli:

1) ci sono dei compilatori la cui “getchar” e’ pesante (in termini di esecuzione) per cui ti consiglio di non usarla.

2) se proprio vuoi usarla, verifica che ritorni anche se non ci sono caratteri presenti

Link al commento
Condividi su altri siti

Crea un account o accedi per commentare

Devi essere un utente per poter lasciare un commento

Crea un account

Registrati per un nuovo account nella nostra comunità. è facile!

Registra un nuovo account

Accedi

Hai già un account? Accedi qui.

Accedi ora
×
×
  • Crea nuovo/a...