Go Down

Topic: faire fonctionner 2 attach interrupt à la fois (Read 3782 times) previous topic - next topic

inryjo

Bonjour à tous,
Je galère un peu sur mon projet de tableau de bord moto avec le traitement des impulsions de ma vitesse de roue et des impulsons de l'allumage.
J'arrive à avoir soit l'un soit l'autre mais pas les 2 en même temps ou alors avec des affichages farfelus.
Il semblerait que ce soit un problème récurrent d'après mes multiples recherches sur le forum.
Vu les prises de tête successives de ceux qui ont essayé, j'envisage d'ajouter un arduino mini pro et le dédier à l'une des deux tâches pour renvoyer les données à mon arduino principal.
Dans ce cas-là conseillerez-vous de lui attribuer la lecture de la vitesse ou du régime moteur ?
Etant donné que dans mon loop principal j'ai 0.2 secondes de delay pour un attachinterrupt, il me semble plus approprié de le dédier au régime moteur, qui donnera forcément beaucoup plus d'impulsions dans ce laps de temps.
A moins que quelqu'un ait déjà essayé et réussi à faire sans...

dfgh

hello
intéressant
quel est le régime maxi moteur et la fréquence maxi pour le capteur roue?

inryjo

Salut,
Régime maxi environ 470 Hz (moteur 2 temps à 2 étincelles par tour).
Capteur roue maxi 16Hz.
Je n'ai encore pas testé en vrai.
J'utilise un bouton poussoir pour tester pour l'instant (et oui j'ai bien pensé à faire un front montant).

dfgh

hello
explique

470*60=28200 étincelles pour un bicylindres cela nous ramène à 14100 tr/mn

tu confirmes?

tu ne peux pas prélever les étincelles pour un seul cylindre?


pour la roue tu simules avec un BP, et tu as déjà des problème alors que tu n'arrive pas à la fréquence réelle de la roue!!!

ton afficheur, c'est quoi ?


kamill

Bonjour,

Personnellement je ne comprends pas le problème et en particulier ça:
Quote
Etant donné que dans mon loop principal j'ai 0.2 secondes de delay pour un attachinterrupt

inryjo

hello
explique

470*60=28200 étincelles pour un bicylindres cela nous ramène à 14100 tr/mn

tu confirmes?

tu ne peux pas prélever les étincelles pour un seul cylindre?


pour la roue tu simules avec un BP, et tu as déjà des problème alors que tu n'arrive pas à la fréquence réelle de la roue!!!

ton afficheur, c'est quoi ?


Monocylindre qui prend 14000 rpm oui c'est une 80cc de course donc forcément ça prend un peu plus de tours qu'une moto classique...

Afficheur classique 2x16 utilisé partout.

Bonjour,

Personnellement je ne comprends pas le problème et en particulier ça:
Je précise que je suis débutant dans le domaine, d'après mes lectures, pour pouvoir faire deux choses à la fois il faut utiliser la fonction attachinterrupt. D'après ce que j'ai compris, on laisse un certain laps de temps pour lire le nombre d'impulsions, non ?
Dans tout les cas, avec ou sans ce delay, ça ne fonctionne pas et c'est un problème que d'autres ont rencontré, malgré les très nombreux exemples dispos sur le web, je n'ai encore rien trouvé avec une mesure de fréquence qui fonctionne pour 2 entrées simultanées.

kamill

Plutôt que de nous forcer à spéculer, si tu mettais ton code.

akuma8

Bonjour,

Je rejoins _pepe_ sur ça :
A priori, pour mesurer et afficher plusieurs fréquences inférieures au kilohertz, les petits Arduinos sont déjà largement surdimensionnés. Si cela ne paraît pas possible, c'est sûrement qu'on doit mal s'y prendre.

Si l'on n'utilise pas de périphérique susceptible de bloquer durablement l'exécution du programme, alors les fréquences en jeu sont tellement faibles qu'on pourrait le faire sans recourir aux interruptions.
Les uC des Arduino sont très largement surdimensionnés pour ces types de fréquences (16MHz vs quelques KHz)

Personnellement dans mes différents projets où je lis 4 codeurs différents, je le fais sans utiliser les interruptions et tout se passe très bien.

C'est vrai que attachInterrupt() donne une facilité en programmation et demande moins de lignes de codes mais perso je pense qu'on maitrise plus ce qu'on fait en le codant soi-même.



inryjo

#8
Feb 19, 2016, 05:56 pm Last Edit: Feb 19, 2016, 07:14 pm by inryjo
Merci beaucoup pour vos réponses, pour être franc, je n'ai pas tout à fait le principe du attach interrupt (c'est pourtant pas faute d'avoir lu des cours dessus)...
Si par exemple on utilise (comme je l'ai déjà vu) les fonctions attachInterrupt()/detachInterrupt() pour traiter les rebonds des signaux d'entrée, je pense qu'on frise l'erreur de conception.
effectivement, ça frise l'erreur de conception  :)

voilà pour mon code:

Code: [Select]

#include <Wire.h>
#include "Sodaq_DS3231.h"
#include <LiquidCrystal.h>
#include <OneWire.h>
#include <DallasTemperature.h>


#define ONE_WIRE_BUS 10


volatile byte rpmcount;
unsigned int rpm;
unsigned int rpmroue;
unsigned long timeold;
volatile byte kmhcount;
unsigned int kmh;
unsigned int kmh1;
unsigned long kmhtimeold;
const int potar = 0;
int valeurLue;
float tension;
float temp;
uint32_t old_ts;

LiquidCrystal lcd(12,11,9,8,7,6);
OneWire oneWire(ONE_WIRE_BUS);
DallasTemperature sensors(&oneWire);


void LCDPrint();
 
void setup()
{
Serial.begin(115200);
while (!Serial);
lcd.begin(16,2);
sensors.begin();
Wire.begin();
rtc.begin();
attachInterrupt(1, rpm_pulse, FALLING);
attachInterrupt(0, kmh_pulse, FALLING);
digitalWrite(2,HIGH);/*pullup interne*/
digitalWrite(3,HIGH);/*pullup interne*/
}

void loop()
{
detachInterrupt(1);
rpm = (60*1000ul)/(millis() - timeold)*rpmcount;
timeold = millis();
rpmcount = 0;
attachInterrupt(1, rpm_pulse, FALLING);
Serial.print("Compte-tours:");
Serial.println(rpm);
delay(200); 

detachInterrupt(0);
kmh = (60*1000ul)/(millis() - kmhtimeold)*kmhcount;
kmh = kmh*0.0017*3600ul;
kmhtimeold = millis();
kmhcount = 0;
attachInterrupt(0, kmh_pulse, FALLING);
Serial.print("Vitesse");
Serial.println(kmh);
delay(200);

valeurLue = analogRead(potar);
tension = valeurLue * 5.0 / 1023;
Serial.print("Tension = ");
Serial.println(tension,2);

sensors.requestTemperatures();
float temp = sensors.getTempCByIndex(0);
Serial.print("Temperature de la sonde: ");
Serial.println(temp);


DateTime now = rtc.now(); //get the current date-time   
Serial.print(now.hour(), DEC);
Serial.print(':');
Serial.print(now.minute(), DEC);
Serial.println();

LCDPrint();
}

void rpm_pulse()
{
  rpmcount++;
}

void kmh_pulse()
{
  kmhcount++;
}

void LCDPrint()
{
lcd.clear();
lcd.setCursor(0,0);
lcd.print(kmh);
lcd.setCursor(2,0);
lcd.print("kmh");
lcd.setCursor(0,1);
lcd.print(rpm);
lcd.setCursor(5,1);
lcd.print("RPM");
lcd.setCursor(11,0);
lcd.print(tension);
lcd.setCursor(15,0);
lcd.print("V");
lcd.setCursor(10,1);
float temp = sensors.getTempCByIndex(0);
lcd.print(temp,1);
lcd.setCursor(15,1);
lcd.print((char)223);
lcd.setCursor(5,0);
lcd.print("16");
lcd.setCursor(7,0);
lcd.print(":");
lcd.setCursor(8,0);
lcd.print("23");

return;
}

kamill

Pourquoi les detachInterrupt attachInterrupt dans la loop?

marcus_95

Bonjour, a ta place j'utiliserais une interruption pour le RPM et la vitesse dans le loop, le LCD est très lent 1/2 seconde.
Le dallas temperature ralenti le programme.
Cdt.
Marcus.

marcus_95

Va voir la: http://www.mon-club-elec.fr/pmwiki_mon_club_elec/pmwiki.php?n=MAIN.ArduinoInitiationEntreesOnOffOptoFourcheCompteTourTerminal

inryjo

#12
Feb 19, 2016, 06:34 pm Last Edit: Feb 19, 2016, 06:44 pm by inryjo
Pourquoi les detachInterrupt attachInterrupt dans la loop?
parce que j'ai trouvé un programme de simple mesure rpm de ventilateur et que j'ai bêtement recopié :)

Je les retire tout simplement ?

J'imagine que les initiés doivent voir de nombreuses aberrations dans mon code...
Bonjour, a ta place j'utiliserais une interruption pour le RPM et la vitesse dans le loop, le LCD est très lent 1/2 seconde.
Le dallas temperature ralenti le programme.
Cdt.
Marcus.
Pour le dallas oui il ralentit le programme ça ne fait aucun doute (ça avait fait l'objet de l'un de mes autres topics). Pour la latence du lcd, on ne peut rien y faire, non ? en tout cas un refresh de vitesse et rpm tous les 0.5 sec maxi me va tres bien.

kamill

Oui, tu enlève simplement les attach/detach Interrupt dans la loop

Supprime aussi les delay(200), la loop est déjà assez longue

marcus_95

pour les interruption un peut de lecture et très bien fait.
http://forum.arduino.cc/index.php?topic=100906.0

Go Up