Alors grande première, mon premier µP embarqué en stand alone!
J'ai utilisé un 328P qui est alimenté quand on met le contact. de là, il récupère l'état de la LED antidémarrage, puis si elle clignote rapidement (< 2Hz), il fait le code de 4 chiffres en "appuyant" via un relai sur le bouton de fermeture centralisée et en comptant les impulsions de la LED (le nombre de clignotement indique à combien on est rendu quand on fait un chiffre). Si tout s'est bien passé, le système est alors dévérouillé et on peut démarrer.
Jusque là, fallait le faire à la main, et c'était bien chi**t. maintenant, on met le contact, et pendant les 30 secondes de la manip, on peut attacher la petite à l'arrière, ranger les courses dans le coffre...
C'est toujours ça de gagné, mais le problème n'est pas pour autant réglé. Place aux photos :
le circuit (50 x 65mm, c'est raisonnable) :

Une fois la planche de bord remontée, les deux leds qui dépassent (pas bien prévu le coup, j'ai du découper un peu le plastique pour les voir...)

On notera le connecteur vert qui permet de relier le circuit au FTDI arduino pour le reprogrammer si besoin...
Côté code, rien de bien méchant :
/*********************************************************
DEVEROUILLEUR
MEGANE I essence
**********************************************************
branchement :
- Détection led TDB : ICP1 (PB0)
- Led rouge : OC2A (PB3)
- Led verte : OC2B (PD3)
- Relais CPE : (PB2)
*/
#define T1_stop TCCR1B=0x40 // arrête le timer
#define LED_v_on PORTD|=0x08
#define LED_v_off PORTD&=0xF7
#define LED_r_on PORTB|=0x08
#define LED_r_off PORTB&=0xF7
const volatile byte code[4] = {1, 2, 3, 4}; // code de déverrouillage (spécifique à chaque voiture)
volatile byte T1_count; // compteur d'impulsions
volatile word T1_max, T1_min; // plage de mesure
byte dumy;
void T1_start(word capture_min, word capture_max){ // démarre le timer1 à 15625Hz et les interruptions IPC1 et TOVF1
T1_stop; // arrêter le timer
TCNT1 = 0; // reset timer
T1_count = 0;
T1_min = capture_min; // définition de la plage de capture
T1_max = capture_max;
TIMSK1 = 0x21; // autoriser les int TOVF et ICP
TCCR1B = 0x45; // démarrer le timer
}
void mkcode(){ // fait le code
byte i;
for (i=0; i<4; i++){ // 4 chiffres
PORTB |= 0x04; // alimenter le relai
LED_v_on;
T1_start(18000, 30000); // prend en compte les impulsions entre 1,152 et 1,92 secondes, normalement, l'impulsion fait 1,5s.
while (T1_count < code[i]){
dumy++;
}
T1_stop;
LED_v_off;
if (T1_count != code[i]) { // erreur dans la procédure
i = 250; // arrêter la procédure
}
delay (400);
PORTB &= 0xFB; // couper le relais
delay (400);
}
if (i == 4) { // procédure OK
LED_v_on;
LED_r_off;
delay (10000);
LED_v_off;
} else { // procédure foirée
while(1){ // clignottement des deux leds
LED_v_on;
LED_r_on;
delay(500);
LED_v_off;
LED_r_off;
delay(500);
}
}
}
void setup() {
// configuration des entrées / sorties
DDRB = 0x0C;
DDRD = 0x0A;
LED_v_on;
LED_r_on;
// config timer 1 / ICP
TIMSK1 = 0;
TCCR1A = 0;
TCCR1B = 0;
//TCCR1B = 0x05; // démarre compteur @15625Hz
TCCR1C = 0;
// vérification du vérouillage
T1_start(2500, 9375); // prend en compte les impulsions entre 160 et 600 ms, normalement, l'impulsion fait 300ms.
while (T1_count < 10){ // on en copmte 10 pour être sûr
dumy++;
} // attendre 10 clignottements
T1_stop;
LED_v_off;
if (T1_count != 10){ // erreur ou déjà dévérouillé. dans ce cas, les deux leds sont restées allumées 4,2 secondes
LED_r_off;
LED_v_on;
delay(2500);
LED_v_off;
} else { // vérouillage OK
mkcode(); // on fait le code
}
}
void loop() { // ben oui, on n'a plus rien à faire une fois le code rentré...
}
ISR(TIMER1_OVF_vect){ // débordement timer (au bout de 4,192 secondes sans impulsion sur ICP1)
T1_stop; // arrêter le timer
T1_count = 250; // indiquer le débordement
}
ISR(TIMER1_CAPT_vect){ // capture event
TCNT1 = 0; // reset timer
if ((ICR1 < T1_max) && (ICR1 > T1_min)) { // vérification "dans les clous"
T1_count++;
// } else { // on a reçu une impulsion en dehors de la plage valide
// T1_count = 0; // sinon, reset compteur
}
}
J'ai remarqué qu'un while(qqchose); n'était pas compilé, du coup, mes boucles d'attentes ne marchaient pas... c'est pourquoi j'incrémente dumy, histoire de compiler quelque chose... peut-être qu'une paire d'accolades auraient suffit...
Sinon, le code a marché du premier coup, j'ai eu un début d'érection!