Voir les contributions

Cette section vous permet de consulter les contributions (messages, sujets et fichiers joints) d'un utilisateur. Vous ne pourrez voir que les contributions des zones auxquelles vous avez accès.


Messages - Loco28

Pages: 1 [2]
16
Ci-joint mon sketch

17
Bon, c'est fait. j'ai ajouté un "noInterrupts()" juste avant le dépilage des fichiers (.shift) et j'ai mis un "interrupts()" après.
Malheureusement cela n'a rien changé.
J'ai évidemment supprimé le "Serial.print" dans le Handler DCC.

J'ai eu l'idée de supprimer les 3 lignes "shiftout" et là, cela marche, du moins en affichage car du coup je n'ai plus la commande de mes aiguilles.
Après j'ai remis 1 ligne "shiftout", OK puis 2, OK et à 3 NOK.
J'ai aussi essayé en mettant "noInterrupts()" et "interrupts()" de chaque côté des lignes "shiftout" mais sans succès.
Là, j'avoue que je suis un peu "sec" sur la suite.

18
Donc, si j'ai bien compris, j'ajoute une ligne "nointerrupts() avant mes 2 lignes ".shift" et j'ajoute une ligne "interrupts()" juste après?

19
D'accord mais qu'est ce qui se passe si des données DCC arrivent pendant cet instant de blocage?

Et, question d'un néophyte dans le domaine des IT: comment bloque-t-on une IT et comment on la réactive?



20
OK pour enlever les "serial.print". C'était mon intention mais j'avais le problème sans ça.

Par contre, tu peux m'expliquer la "concurrence" entre les buffers?

21
J'aurais besoin que quelques spécialistes (plus que moi) regardent mon code.
Ce code fonctionne bien dans 95% des cas (sous CDM-Rail). par contre, dans le cas de commande d'itinéraires, quand, par exemple, 3 aiguillages doivent être commandés en même temps, et malgré le fait que CDM temporise les envois (0,5s), je loupe des commandes.
Il me semblait, qu'à partir du moment où je remplis un fichier FIFO dans le cadre de la routine d'interruption et que je le traite en dehors de cette routine (dans la LOOP) je ne pouvais rien rater.
Est-ce que j'ai bien compris? et est-ce que mon code est correct?
Une petite indication, en m'aidant des Serial.print (qui ne sont là que pour la mise au point), j'ai constaté qu'en supprimant les SHIFOUT je ne loupais plus de commandes DCC.

Ci-dessous mon code.

//Programme de gestion des aiguillages de la zone Bréauté
#include <DCC_Decoder.h>
#define kDCC_INTERRUPT    0    // pin 2 for UNO
#include <CircularBuffer.h>

CircularBuffer <int, 100> storadresse;
CircularBuffer <byte, 100> storaction;

int add = 0;
int act = 0;
int old_add = 0;
int old_act = 0;
int action = 0;

const int LATCH1 = 6;
const int CLOCK1 = 7;
const int DATA1 = 5;

int OUT1[8];
int OUT2[8];
int OUT3[8];

int CDE1 = 0;
int CDE2 = 0;
int CDE3 = 0;


//Handler DCC
void BasicAccDecoderPacket_Handler(int address, boolean activate, byte data){
  storadresse.push (address);
  storaction.push (data);
  Serial.print(address);
  Serial.print("   ");
  Serial.println(data);
}

void setup() {
  DCC.SetBasicAccessoryDecoderPacketHandler(BasicAccDecoderPacket_Handler, true);
  DCC.SetupDecoder( 0x00, 0x00, kDCC_INTERRUPT );
  Serial.begin (115200);

  Serial.println(" DCC brut          ADRESSE   ACTION");
 
  pinMode(LATCH1, OUTPUT);
  pinMode(CLOCK1, OUTPUT);
  pinMode(DATA1, OUTPUT);

}

void loop() {
  DCC.loop();

   while(!storadresse.isEmpty()) {
   add = storadresse.shift();
   act = storaction.shift();

 if ((add != old_add) || (act != old_act)){
    old_add = add;
    old_act = act;
   
  // Conversion de l'adresse NMRA en adresse decodeur d'accessoire
  add -= 1;
  add *= 4;
  add += 1;
  add += (act & 0x06) >> 1;
  action = (act & 0x01);
  Serial.print("                        ");
    Serial.print(add);
    Serial.print("    ");
    Serial.println(action);
   
//Gestion aiguillages
 
//registre à décalage OUT1
  if((add >= 1) && (add <= 8)) {
    if (action == 1) {
      OUT1[add-1] = bit(add - 1);
    }
    else {
      OUT1[add-1] = 0;
    }
  } //fin OUT1

//registre à décalage OUT2
  if((add >= 9) && (add <= 16)) {
    if (action == 1) {
      OUT2[add-9] = bit(add - 9);
    }
    else {
      OUT2[add-9] = 0;
    }
  } //fin OUT2

  //registre à décalage OUT3
    if((add >= 17) && (add <= 24)) {
    if (action == 1) {
      OUT3[add-17] = bit(add - 17);
    }
    else {
      OUT3[add-17] = 0;
    }
  } //fin OUT3
 
//envoi des commandes

  CDE1 = OUT1[0]+OUT1[1]+OUT1[2]+OUT1[3]+OUT1[4]+OUT1[5]+OUT1[6]+OUT1[7];
  CDE2 = OUT2[0]+OUT2[1]+OUT2[2]+OUT2[3]+OUT2[4]+OUT2[5]+OUT2[6]+OUT2[7];
  CDE3 = OUT3[0]+OUT3[1]+OUT3[2]+OUT3[3]+OUT3[4]+OUT3[5]+OUT3[6]+OUT3[7];
 
  digitalWrite(LATCH1, LOW);
  shiftOut(DATA1, CLOCK1, LSBFIRST, CDE3);
  shiftOut(DATA1, CLOCK1, LSBFIRST, CDE2);
  shiftOut(DATA1, CLOCK1, LSBFIRST, CDE1);       
  digitalWrite(LATCH1, HIGH);
 
     }//fin boucle si nouveaux data
   }//fin while   
  }//fin programme principal

22
Vos projets / Re : Récupération données DCC: CircularBuffer et ShiftOut
« le: décembre 08, 2017, 11:56:05 pm »
Effectivement il y avait une grossière erreur (suite à un effacement malheureux ou un copier/coller raté)) que je ne voyais pas, d'où l'intérêt de faire appel à d'autres paires d'yeux.
Tout est rentré dans l'ordre.
J'ai encore du boulot pour finaliser mon projet mais j'ai commencé à écrire un document pour rassembler tout ça (schémas, programme, photos de cartes, ...).
En attendant, ci-dessous le programme, sûrement perfectible, qui me permet de piloter 12 signaux, au travers de 3 registres à décalage
-------------------------------------------------------------------------------------------------------------
#include <DCC_Decoder.h>
#define kDCC_INTERRUPT    0    // pin 2 for UNO

#include <CircularBuffer.h>

CircularBuffer <int, 100> storadresse;
CircularBuffer <byte, 100> storaction;
int add = 0;
int act = 0;
int old_add = 0;
int old_act = 0;
int action = 0;

//pour les 595
const int CLOCK1 = 4;
const int LATCH1 = 5;
const int DATA1 = 6;

int OUT5[8];
int OUT6[8];
int OUT7[8];

int CDE5 = 0;
int CDE6 = 0;
int CDE7 = 0;

//Handler DCC

void BasicAccDecoderPacket_Handler(int address, boolean activate, byte data){
 storadresse.push (address);
 storaction.push (data);
}
void setup() {
  DCC.SetBasicAccessoryDecoderPacketHandler(BasicAccDecoderPacket_Handler, true);
  DCC.SetupDecoder( 0x00, 0x00, kDCC_INTERRUPT );
  Serial.begin(115200);
  Serial.println("ADRESSE      ACTION");
 
  pinMode(LATCH1, OUTPUT);
  pinMode(CLOCK1, OUTPUT);
  pinMode(DATA1, OUTPUT);

//mise à zéro OUT5, OUT6, et OUT7
   digitalWrite(LATCH1, LOW);
  shiftOut(DATA1, CLOCK1, MSBFIRST, 0);
  shiftOut(DATA1, CLOCK1, MSBFIRST, 0);
  shiftOut(DATA1, CLOCK1, MSBFIRST, 0);
  digitalWrite(LATCH1, HIGH); 
}

void loop() { 
  DCC.loop();

  while(!storadresse.isEmpty()) {
   add = storadresse.shift();
   act = storaction.shift();

 if ((add != old_add) || (act != old_act)){
    old_add = add;
    old_act = act;

// Conversion de l'adresse NMRA en adresse decodeur d'accessoire
   add -= 1;
   add *= 4;
   add += 1;
   add += (act & 0x06) >> 1;
   act =(act & 0x01);
   Serial.print(add);
   Serial.print("   ");
   Serial.println(act);
 
 //Gestion des signaux
  if((add >=151) && (add <= 174)) { //boucle adresse feux
   
 //Registre à décalage OUT5
  if((add >=151) && (add <= 158)) {
    if(act == 1){
    OUT5[add - 151] = bit(add - 151);
    }
    else{
    OUT5[add - 151] = 0;
    }
  }//fin boucle OUT5
 
   //Registre à décalage OUT6
  if((add >=159) && (add <= 166)) {
    if(act == 1){
    OUT5[add - 159] = bit(add - 159);
    }
    else{
    OUT5[add - 159] = 0;
    }
  }//fin boucle OUT6
 
   //Registre à décalage OUT7
  if((add >=167) && (add <= 174)) {
    if(act == 1){
    OUT5[add - 167] = bit(add - 167);
    }
    else{
    OUT5[add - 167] = 0;
    }
  }//fin boucle OUT7
   
//envoi data vers OUT5, OUT6 et OUT7

    CDE5 = OUT5[0]+OUT5[1]+OUT5[2]+OUT5[3]+OUT5[4]+OUT5[5]+OUT5[6]+OUT5[7];
    CDE6 = OUT6[0]+OUT6[1]+OUT6[2]+OUT6[3]+OUT6[4]+OUT6[5]+OUT6[6]+OUT6[7];
    CDE7 = OUT7[0]+OUT7[1]+OUT7[2]+OUT7[3]+OUT7[4]+OUT7[5]+OUT7[6]+OUT7[7];

    digitalWrite(LATCH1, LOW);
    shiftOut(DATA1, CLOCK1, LSBFIRST, CDE7);
    shiftOut(DATA1, CLOCK1, LSBFIRST, CDE6);
    shiftOut(DATA1, CLOCK1, LSBFIRST, CDE5);           
    digitalWrite(LATCH1, HIGH);
     
         }//fin boucle adresse feux
      }//fin boucle si nouveaux data   
  }//fin while
}//fin loop
----------------------------------------------------------------------------------------------------------------------

23
Vos projets / Re : Récupération données DCC: CircularBuffer et ShiftOut
« le: décembre 07, 2017, 10:53:10 pm »
Désolé, je clos le post.
le problème est dans le SETUP: il manque la définition en OUTPUT pour CLOCK, LATCH et DATA

24
Vos projets / Récupération données DCC: CircularBuffer et ShiftOut
« le: décembre 07, 2017, 12:05:56 am »
Bonsoir,
J'ai commencé depuis quelques temps la réalisation de décodeurs d'accessoires sur base ARDUINO.
J'utilise la bibliothèque DCC_Decoder. Le système marche très bien pour les aiguillages mais je me suis aperçu récemment que du côté des signaux il y avait des ratés.
Après analyse, tests et interrogations sur les forums, je suis arrivé à la conclusion que le traitement des données, que je faisais à la suite du void BasicAccDecoderPacket_Handler, me faisait louper des données.
j'ai donc inclus une autre bibliothèque, CircularBuffer, pour enregistrer les données immédiatement après le "Handler" puis les récupérer et les traiter, cette fois-ci dans la "loop".
Et là, impeccable, je ne loupais plus de données, au vu du Serial.print.
J'ai donc continué le traitement des données pour activer les sorties: tout est OK jusqu'au calcul de la valeur à envoyer (ici CDE4) mais rien ne se passe avec le ShiftOut (j'utilise des registres à décalage).
J'en viens à me demander si l'instruction ShiftOut ne se percute pas avec la fonction buffer.shift() de CircularBuffer!
Je précise que je travaille avec CDM-Rail et que je ne suis pas un grand spécialiste de la programmation (cela ressemble sûrement à "la programmation pour les nuls")
Ci-dessous une copie de mon code que j'ai allégé pour aller au plus simple, mais avec lequel j'ai bien un problème au moment de l'envoi du ShiftOut.
------------------------------------------------------------------------------------------------------------------------------------

#include <DCC_Decoder.h>
#define kDCC_INTERRUPT    0    // pin 2 for UNO
#include <CircularBuffer.h>

CircularBuffer <int, 100> storadresse;
CircularBuffer <byte, 100> storaction;

int add = 0;
int act = 0;
int old_add = 0;
int old_act = 0;
int action = 0;

const int CLOCK2 = 8;
const int LATCH2 = 9;
const int DATA2 = 10;

int OUT4[8];

int CDE4 = 0;

//Handler DCC
void BasicAccDecoderPacket_Handler(int address, boolean activate, byte data){
  //Serial.print(address);
  //Serial.print("    ");
  //Serial.println(data);
 storadresse.push (address);
 storaction.push (data);
  }
void setup() {     
  DCC.SetBasicAccessoryDecoderPacketHandler(BasicAccDecoderPacket_Handler, true);
  DCC.SetupDecoder( 0x00, 0x00, kDCC_INTERRUPT );
  Serial.begin (115200); 
  Serial.println("Debut test");
}
void loop() {
  DCC.loop();

  while(!storadresse.isEmpty()) {
   add = storadresse.shift();
   act = storaction.shift();

 if ((add != old_add) || (act != old_act)){
    old_add = add;
    old_act = act;
// Conversion de l'adresse NMRA en adresse decodeur d'accessoire
   add -= 1;
   add *= 4;
   add += 1;
   add += (act & 0x06) >> 1;
   action =(act & 0x01);
   Serial.print(add);
   Serial.print("   ");
   Serial.println(action);

  //Gestion des signaux
 
 //Registre à décalage OUT4
  if((add >=127) && (add <= 134)){ 
    if(action = 1){
    OUT4[add - 127] = bit(add - 127);
    }
    else{
    OUT4[add - 127] = 0;
    }
  }//fin boucle OUT4
         
//Envoi OUTT4

    CDE4 = OUT4[0]+OUT4[1]+OUT4[2]+OUT4[3]+OUT4[4]+OUT4[5]+OUT4[6]+OUT4[7];
    Serial.println(CDE4);
   
    digitalWrite(LATCH2, LOW);
    shiftOut(DATA2, CLOCK2, LSBFIRST, CDE4);     
    digitalWrite(LATCH2, HIGH);

   } //fin nouvelle donnée
  } //fin while   
} //fin loop
--------------------------------------------------------------------------------------------------------------------

Merci d'avance à ceux qui pourront m'aider

Pages: 1 [2]