Polytech school project. RICM4 students, see http://air.imag.fr/index.php/Projets-2016-2017-Station_de_pompage_connect%C3%A9e for more information

Dependencies:   SX1272Lib mbed WakeUp

Fork of SX1272PingPong by Semtech

Revision:
17:cce0eada6d82
Parent:
16:85fb5e37def7
--- a/main.cpp	Fri Mar 03 13:42:44 2017 +0000
+++ b/main.cpp	Sat Apr 01 12:29:59 2017 +0000
@@ -6,13 +6,15 @@
 #include "ordre.h"
 #include "pompe.h"
 #include "WakeUp.h"
-//#include "niveau.h"
+#include "niveau.h"
 
 /* Set this flag to '1' to display debug messages on the console */
 #define DEBUG_MESSAGE   1
 #define ID_DEVICE 0x24
 #define ID_STATION 0x55
 #define TEMPS_ECOUTE_ORDRE_SECONDE 20.0
+#define TEMPS_ATTENTE_ACK 60.0
+#define SLEEP_TIME 30000 //ms
 
 /* Set this flag to '1' to use the LoRa modulation or to '0' to use FSK modulation */
 #define USE_MODEM_LORA  1
@@ -54,7 +56,7 @@
     #error "Please define a modem in the compiler options."
 #endif
 
-#define RX_TIMEOUT_VALUE                                30000000//3500000   // in us
+#define RX_TIMEOUT_VALUE                                3500000//3500000   // in us
 #define BUFFER_SIZE                                     32        // Define the payload size here
 
 #if( defined ( TARGET_KL25Z ) || defined ( TARGET_LPC11U6X ) )
@@ -94,46 +96,30 @@
  */
 SX1272MB2xAS Radio( NULL );
 
-//const uint8_t PingMsg[] = "PING";
-//const uint8_t PongMsg[] = "PONG";
-
 uint16_t BufferSize = BUFFER_SIZE;
 uint8_t Buffer[BUFFER_SIZE];
 
 int16_t RssiValue = 0.0;
 int8_t SnrValue = 0.0;
 
-/*Ticker flipper;
-
-
-void doNothing(){
-    NULL;
-}*/
-
+//Fonction permettant de faire dormir la carte
+//LE DEEPSLEEP Ne fonctionne pas !
 void dormir(){
-    debug("dodo\r\n");
+    debug_if(DEBUG_MESSAGE,"dodo\r\n");
     Radio.Sleep();
-    //flipper.attach(&doNothing, 20.0);
-    // critical section
-    WakeUp::set_ms(10000);
+    WakeUp::set_ms(SLEEP_TIME);
     sleep();
     
     wait(5);
 }
-/*
-void flip(){
-    debug("flip\r\n");
-    dormir();
-}*/
 
 Timer ecouterOrdre;
 
 int main() 
 {
     uint8_t i;
-    bool isMaster = true;
     
-    debug( "\n\n\r     SX1272 Cuve Demo Application \n\n\r" );
+    debug_if(DEBUG_MESSAGE, "\n\n\r     SX1272 Cuve Demo Application \n\n\r" );
 
     // Initialize Radio driver
     RadioEvents.TxDone = OnTxDone;
@@ -146,10 +132,10 @@
     // verify the connection with the board
     while( Radio.Read( REG_VERSION ) == 0x00  )
     {
-        debug( "Radio could not be detected!\n\r", NULL );
+        debug_if(DEBUG_MESSAGE, "Radio could not be detected!\n\r", NULL );
         wait( 1 );
     }
-            
+    
     debug_if( ( DEBUG_MESSAGE & ( Radio.DetectBoardType( ) == SX1272MB2XAS ) ) , "\n\r > Board Type: SX1272MB2xAS < \n\r" );
   
     Radio.SetChannel( RF_FREQUENCY ); 
@@ -173,7 +159,7 @@
                          
 #elif USE_MODEM_FSK == 1
 
-    debug("\n\n\r              > FSK Mode < \n\n\r");
+    debug_if(DEBUG_MESSAGE,"\n\n\r              > FSK Mode < \n\n\r");
     Radio.SetTxConfig( MODEM_FSK, TX_OUTPUT_POWER, FSK_FDEV, 0,
                          FSK_DATARATE, 0,
                          FSK_PREAMBLE_LENGTH, FSK_FIX_LENGTH_PAYLOAD_ON,
@@ -194,74 +180,79 @@
         
     led = 0;
     
-    DigitalOut pompe(PC_14);
-    
-    //Pompe pompe(PC_14);
+    //Initialisation
+    Pompe pompe(PC_5);
+    pompe.arreterPompe();
+    Niveau cuve(PC_8,PC_3,PC_2,PC_6);
+    TrameData dataPaquet(ID_DEVICE,ID_STATION, 8, pompe.etat(), 0xF, 0xA);
     
-    DigitalIn p1(PC_15);//(PC_15); //Poid fort
-    DigitalIn p2(PH_0);
-    DigitalIn p3(PH_1); //Poid faible
-    
-    //Niveau cuve();
-    //char niveau = (char) ((p1.read()<<2) | (p2.read()<<1) | p3.read());
-    TrameData dataPaquet(ID_DEVICE, 63, (char) pompe.read(), 0x1F, 0xF);
-    
-    bool enAttente = false;
+    bool enAttenteOrdre = false;
+    bool enAttenteAck = false;
     
     //The low-power oscillator can be quite inaccurate on some targets
     //this function calibrates it against the main clock
     WakeUp::calibrate();
     
-    //TODO
-    // Distinguer deux temps. Il faut pouvoir s'endormir une heure, mais aussi écouter pendant 5 minutes
-    Radio.Rx( RX_TIMEOUT_VALUE );
     
+    //Debut programme
     while( 1 )
     {
         switch( State )
         {
         case RX:
-            //If the board is the master, it have the initiative
-            if( enAttente == true )
+            if( enAttenteOrdre || enAttenteAck )
             {
-                debug("1\r\n");
+               
                 if( BufferSize > 0 )
                 {
-                    debug("2\r\n");
-                    debug((const char* )Buffer);
-                    debug(" ");
-                    debug((const char* ) ID_DEVICE);
+                    debug_if( DEBUG_MESSAGE, "2\r\n");
+                    debug_if(DEBUG_MESSAGE,(const char* )Buffer);
+                    debug_if( DEBUG_MESSAGE, " ");
+                    debug_if(DEBUG_MESSAGE,(const char* ) ID_DEVICE);
                     Ordre trameRecue((char*)Buffer);
                     //Si message recu alors trouver ordre correspondant et faire traitement
                     if( trameRecue.getIdRecepteur() == (char) ID_DEVICE )
                     {
-                        debug("ID DEVICE OK\r\n");
+                        debug_if( DEBUG_MESSAGE, "ID DEVICE OK\r\n");
                         if( trameRecue.getIdEmetteur() == (char) ID_STATION ){
-                            debug("ID STATION OK\r\n");
-                            //Ordre pour nous
-                            led = !led;
-                            debug( "...Ordre recu \r\n" );
-                            Ordre o((char *) Buffer);
+                            debug_if( DEBUG_MESSAGE, "ID STATION OK\r\n");
                             
-                            //TODO executer ordre
-                            debug("Executer Ordre\r\n");
-                            
-                            //On attend 10 secondes
-                            debug("Dormir\r\n");
-                            dormir();
-                            
-                            
-                            enAttente = false;
-                            Radio.Rx( RX_TIMEOUT_VALUE );
+                            if(enAttenteOrdre){
+                                //Ordre pour nous
+                                led = !led;
+                                debug_if( DEBUG_MESSAGE,  "...Ordre recu \r\n" );
+                                Ordre o((char *) Buffer);
+                                if(trameRecue.getOrdreAFaire()==1)
+                                    o.executerOrdre(pompe, cuve, o.getNiveauCuve());
+                                
+                                dormir();
+                                enAttenteOrdre = false;
+                                Radio.Rx( RX_TIMEOUT_VALUE );
+                            }
+                            else if(trameRecue.getOrdreAFaire()==0 && enAttenteAck){
+                                debug_if( DEBUG_MESSAGE, "ACK recu\r\n");
+                                enAttenteAck = false;
+                                ecouterOrdre.reset();
+                                enAttenteOrdre = true;
+                                Radio.Rx( RX_TIMEOUT_VALUE );
+                            }
+                            else{
+                                //mauvais ACK on concidère que c'est OK
+                                debug_if( DEBUG_MESSAGE, "mauvais ACK recu\r\n");
+                                enAttenteAck = false;
+                                ecouterOrdre.reset();
+                                enAttenteOrdre = true;
+                                Radio.Rx( RX_TIMEOUT_VALUE );
+                            }
                         }else{
-                            debug("autre station\r\n");
+                            debug_if( DEBUG_MESSAGE, "autre station\r\n");
                             Radio.Rx( RX_TIMEOUT_VALUE );
                         }
                     }
-                    else // valid reception but neither a PING or a PONG message
-                    {    // Set device as master ans start again
-                        debug("Reception message pour quelqu'un d'autre\r\n");
-                        Radio.Rx( RX_TIMEOUT_VALUE ); //La on reattend pour 5 minutes à chaque foi que qq'un envoit un message c'est pas top....
+                    else // valid reception but not for us
+                    {    // Start again
+                        debug_if( DEBUG_MESSAGE, "Reception message pour quelqu'un d'autre\r\n");
+                        Radio.Rx( RX_TIMEOUT_VALUE );
                     }    
                 }
             }
@@ -269,31 +260,20 @@
             break;
         case TX:    
             led = !led; 
-            debug( "Envoi des donnees...\r\n" );
-            debug("En attente ORDRE\r\n");
-            //flipper.attach(&dormir, 40.0); // the address of the function to be attached (flip) and the interval (2 seconds)
+            debug_if( DEBUG_MESSAGE && !enAttenteAck,  "Envoi des donnees...\r\n" );
+            debug_if( DEBUG_MESSAGE && enAttenteAck, "En attente ACK\r\n");
             Radio.Rx( RX_TIMEOUT_VALUE );
             State = LOWPOWER;
             break;
         case RX_TIMEOUT:           
-            //TODO executer ordre
-            /*debug("Pas Ordre\r\n");
-            
-            //On attend 10 secondes
-            debug("Dormir\r\n");
-            dormir();
-            
-            wait(5);
-            enAttente = false; */
             Radio.Rx( RX_TIMEOUT_VALUE );  
             State = LOWPOWER;
             break;
         case RX_ERROR:
             //Erreur CRC, faire une demande de renvoi
             //TODO
-            debug("Erreur CRC \r\n");
+            debug_if( DEBUG_MESSAGE, "Erreur CRC \r\n");
             Radio.Rx( RX_TIMEOUT_VALUE );
-            
             State = LOWPOWER;
             break;
         case TX_TIMEOUT:
@@ -301,35 +281,45 @@
             State = LOWPOWER;
             break;
         case LOWPOWER:
-            if(!enAttente){
+            if(!enAttenteOrdre && !enAttenteAck){
                 //Corps de l'application
                 //On envoie les données
-                debug("envoie3\r\n");
-                dataPaquet.mettreAJourEtatPompe((char) 0);
-                dataPaquet.mettreAJourNiveauCuve((char) 0x1F);
-                dataPaquet.mettreAJourNiveauBatterie((char) 0xF); //TODO
+                debug_if( DEBUG_MESSAGE, "envoie3\r\n");
+                dataPaquet.mettreAJourEtatPompe((char) pompe.etat());
+                dataPaquet.mettreAJourNiveauCuve(cuve.getNiveauCuve());
+                dataPaquet.mettreAJourNiveauBatterie((char) 0xA);
                 
+                // Send the data
                 char * trame = dataPaquet.creerTrame();
-                debug( trame);
                 strcpy( ( char* ) Buffer, trame);
                 for (i = TAILLE_TRAME_DATA; i < BufferSize; i++ )
                 {
                     Buffer[i] = i - 4;
                 }
                 wait_ms( 10 );
-                // Send the data 
-                Radio.Send( Buffer, BufferSize );
-                enAttente = true;
+                
+                //Initialisation des variables de controle
+                enAttenteAck = true;
+                debug_if( DEBUG_MESSAGE,  "Debut timer \r\n");
                 ecouterOrdre.start();
+                Radio.Send( Buffer, BufferSize );
             }else{
-                if(ecouterOrdre.read() > TEMPS_ECOUTE_ORDRE_SECONDE){
-                    debug("delaisAttente depasse. Dormir.\r\n");
+                ecouterOrdre.stop();
+                if(enAttenteAck && (ecouterOrdre.read() > TEMPS_ATTENTE_ACK)){
+                    debug_if( DEBUG_MESSAGE, "delaisAttente ack depasse. Reemission.\r\n");
+                    ecouterOrdre.stop();
+                    ecouterOrdre.reset();
+                    enAttenteAck = false;
+                }else
+                if(enAttenteOrdre && (ecouterOrdre.read() > TEMPS_ECOUTE_ORDRE_SECONDE)){
+                    debug_if( DEBUG_MESSAGE, "delaisAttente depasse. Dormir.\r\n");
                     ecouterOrdre.stop();
                     ecouterOrdre.reset();
                     dormir();
-                    debug("fin dodo\r\n");
-                    enAttente = false;
+                    debug_if( DEBUG_MESSAGE, "fin dodo\r\n");
+                    enAttenteOrdre = false;
                 }
+                else ecouterOrdre.start();
             }
             break;
         default:
@@ -369,7 +359,7 @@
     Radio.Sleep( );
     Buffer[ BufferSize ] = 0;
     State = RX_TIMEOUT;
-    debug_if( DEBUG_MESSAGE, "> OnRxTimeout\n\r" );
+    debug_if( DEBUG_MESSAGE, "." );
 }
 
 void OnRxError( void )