Newsgroup: it.hobby.elettronica.digitale
Titolo: watch dofg

Salve!
Vorrei usare anche il watch dog, ma la cosa mi risulta difficile nel senso 
che se conosco bene il programma posso fare dei calcoli e capire come fare, 
ma nel caso si usino funzioni di libreria o di terze parti come si fa a 
sapere se c'e' un loop che possa far scaricare il timer del watch dog? ed 
acneh volendo studiarle nei dettagli devono essere tutte modificate tenendo 
conto del watch-dog? 

 tenendo conto del watch-dog?
c'� la possibilit� di resettare il watchdog automaticamente nel caso delle 
varie funzioni delay_ms(), delay_us(), ...
poi cmq se metti il wtd a 2 secondi la vedo dura che una function possa 
richiedere tanto...
di norma non c'� bisogno di modifiacare le funzioni di libreria ma 
semplicemente sapere che cosa fanno e perch�
esempio:
anzich� usare statements bloccanti del tipo while (!ide_cf_ready());
si potrebbe pensare a qualosa tipo:
int timeout;
timeout=0;
while ((!ide_cf_ready())&&(timeout<100)) { timeout++; delay_ms(1); }
- durante la delay_ms() resetti il wdt
- anche se la funzione ide_cf_ready() � codificata e non modificabile (ti 
viene fornita come oggetto da linkare) tu hai lo stesso il controllo del wdt
-ice-

 -ice-
Ho capito quello che vuoi dire, l'esempio e' lampante della tecnica da 
usare, nel mio caso ecco la funzione che .....:
void get_string(char* s, unsigned int8 max) {
   unsigned int8 len;
   char c;
   --max;
   len=0;
   do {
     c=getc();
     if(c==8) {  // Backspace
        if(len>0) {
          len--;
          putc(c);
          putc(' ');
          putc(c);
        }
     } else if ((c>=' ')&&(c<='~'))
       if(len<=max) {
         s[len++]=c;
         putc(c);
       }
   } while(c!=13);
   s[len]=0;
}
questa fa parte della libreria del CCS input.C  alla fine c'e' un ciclo che 
aspetta il carattere carriage return per uscire, in questi casi si deve 
modificare forzatamente la funzione mettendo direttamente l'istruzione 
relativa al watch-dog oppure far richiamare una apposita funzione di 
watch-dog? per me il problema e' proprio non modificare le librerie 
standard, quello che ricordo ora non lo ricordero' certamente fra 1 mese. 

 standard, quello che ricordo ora non lo ricordero' certamente fra 1 mese.
appunto!
nel tuo caso � semplice: se decidi di aspettare tutto il tempo necessario 
all'utente per immetere la stringa (da tastiera? da terminale rs232?) allora 
disabiliti il wdt prima di chiamare la get_string() e lo riabiliti dopo;
se invece decidi di aggiungere un time-out devi disabilitare il wdt ed usare 
un timer (anche il timer0 stesso volendo, per non sprecare risorse) e dopo 
un tot tempo ti scatta la tua bella isr che pu� dare un messaggio all'utente 
e/o resettare il micro, ecc... hai un controllo maggiore
alla peggio ti fai la tua libreria e crei una get_string_wdt_alive() che 
resetta il wdt mentre aspetta che l'utente inserisca i dati
considera che:
- il wdt pu� essere acceso/spento via fw o via fuses... dipende dal micro
- se disabiliti il wdt eventuali isr che scattano si spera siano debuggate a 
dovere
IMHO il wdt � per situazioni disperate... codice complesso o sistemi 
operativi implementati a bordo di un pic (s�, si pu� fare) in target in cui 
non � ammissibile che il micro abbia blocchi;
considera poi bisogna anche pensare che il codice possa essere ok ma per 
qualche evento sfortunato il uC (� un discorso in generale non solo i pic) 
possa trovarsi con dati corrotti e piantarsi perch� finisce in un punto 
casuale del codice (es: si sporca lo stack o cambia il valore di ritorno per 
una iret)
cosa succede ad un missile in aria?
cosa succede ad un'automobile in corsa?
serve il wdt per limitare i danni, per quanto possibile...
poi il discorso � lungo... nelle missioni spaziali ad esempio si va di norma 
in teconologia anti-fuses
-ice- 


Mi e' venuta una idea forse malsana :-) se usassi un interrupt con un timer 
per ricaricare il watch-dog? 

 per ricaricare il watch-dog? 
Per esperienza personale, scarterei subito questa ipotesi!
Mentre e' semplice entrare in loop nel programma, e' molto 
difficile farlo con gli interrupt che, in effetti, sono 
gestiti da una periferica a se stante.
Questo per dire che non e' raro che capiti che funziona solo 
la parte di programma gestita a interrupt mentre la parte 
gestita dalle altre "normali" funzioni non da' segni di 
vita; in pratica, il watch dog non resetterebbe.
ciao
Angelo

 ciao
Vabbe' l'avevo detto che era malsana come idea :-) comunque ho visto che il 
compilatore della CCS gestisce anche queste situazioni di loop bloccanti, il 
caso piu' eclatante sarebbe di usare un ritardo con l'istruzione delay_ms, 
se mettiamo 10 secondi oppure 30 secondi il watch-dog sarebbe ingestibile in 
queste situazioni, lo so si potrebbe fare un ciclo da 100ms e farlo ripetere 
per il ritardo voluto, ma il mio e' un esempio in questi casi il compilatore 
prevede di usare #use delay(clock=20000000, restart_wdt) 


Evidentemente non mi sono spiegato bene, dicevo che ci sono alcune funzioni 
non so se tecnicamente si possano definire bloccanti che creano problemi 
all' azzeramento del watch-dog
se uso la funzione delay_ms (20000); //ritardo di 20 secondi e sto usando il 
watch dog come faccio a non far resettare durante questo ritardo? il 
compilatopre ccs fa in modo che si dichiara insieme al quarzo che si sta 
usando anche restart_wdt  permettera' al compilatore di far  ricaricare il 
watch-dog durante questi ritardi prolungati, la stessa cosa succede per 
delle funzioni tipo:
void get_string(char* s, unsigned int8 max) {
   unsigned int8 len;
   char c;
   --max;
   len=0;
   do {
     c=getc();
     if(c==8) {  // Backspace
        if(len>0) {
          len--;
          putc(c);
          putc(' ');
          putc(c);
        }
     } else if ((c>=' ')&&(c<='~'))
       if(len<=max) {
         s[len++]=c;
         putc(c);
       }
   } while(c!=13);
   s[len]=0;
}
questa funzione sta nel header input.c, ora la possibilita' sta nel copiare 
questa funzione nel mio programma modificando ed adattando la watch-dog 
oppure come per delay_ms(); si aggiunge restart_wdt cioe' da  #use 
rs232(baud=9600, xmit=PIN_C6, rcv=PIN_C7) a #use rs232(baud=9600, 
xmit=PIN_C6, rcv=PIN_C7,restart_wdt) 

 
funzioni bloccanti e watch-dog non vanno d'accordo, o le prime o il 
secondo, ovvero in alternativa ti riscrivi le funzioni bloccanti in modo 
da includere al loro interno il reset del watchdog

si ma quel "restart_wdt" cosa fa ?
ti leggi la documentazione del compilatore e capisci come si comporta in 
presenza di watchdog abilitato e uso della delay/getc ( magari il 
compilatore non prevede la possibilita' di un uso contemporaneo delle 
due funzionalita' ) e ti regoli di conseguenza
se come dici il compilatore provvede ad inserire nei delay e nella getc 
i reset del watchdog non ti devi preoccupare
per la getc ( e' quella la funzione bloccante ). in alternativa, fai in 
modi di chiamarla solo quando sei sicuro che c'e' un carattere "in attesa"
una cosa del tipo :
while(1) {
   if (char_available() ) {
	c = getc();
  	....
   }
   watchdog_reset();
}
la funzione char_available() puo' essere gia' fornita dal compilatore ( 
magari con altro nome ) o te la scrivi tu