Import initial du projet shipheart_appli
This commit is contained in:
@@ -0,0 +1,747 @@
|
||||
//**********************************************************************************************************************************************************************************
|
||||
// Fichier CAPTEURS.C
|
||||
//
|
||||
// Contient toutes les fonctions liées aux capteurs, associé à la table TB_Capteurs de la BDD (créé en janvier 2017)
|
||||
//**********************************************************************************************************************************************************************************
|
||||
|
||||
//#define __DEBUG_CAPTEURS // Décommenter cette ligne pour que les infos de debug soient affichées
|
||||
//#define __DEBUG_CAPTEURS_CALCULES // Décommenter cette ligne pour que les infos de debug soient affichées
|
||||
//#define __DEBUG_CAPTEURS_ALERTES_ALARMES // Décommenter cette ligne pour que les infos de debug soient affichées
|
||||
|
||||
// Include :
|
||||
#include "main.h"
|
||||
|
||||
// Prototypes :
|
||||
void gestion_capteurs(void);
|
||||
int8_t init_capteurs(void);
|
||||
bool test_condition_capteur_booleen(uint16_t no_capteur, uint16_t no_condition);
|
||||
bool valeur_neutre_operation_booleene(uint8_t operation);
|
||||
int16_t capteur_cle_primaire(uint16_t cle_primaire);
|
||||
int16_t variable_capteur_cle_primaire(uint16_t cle_primaire);
|
||||
|
||||
// Variables globales :
|
||||
struct Struct_capteurs capteurs;
|
||||
|
||||
|
||||
|
||||
|
||||
//**********************************************************************************************************************************************************************************
|
||||
// Fonction INIT_CAPTEURS
|
||||
//
|
||||
//**********************************************************************************************************************************************************************************
|
||||
int8_t init_capteurs(void)
|
||||
{
|
||||
|
||||
capteurs.sequenceur.etat = ETAT_SEQUENCEUR_CAPTEURS_INIT;
|
||||
capteurs.sequenceur.compteur = CAPTEURS_TEMPO_INIT;
|
||||
|
||||
// Affichage du message de débug :
|
||||
affichage_debug(__FILE__, __LINE__, "Initialisation des capteurs\t\t: OK", TYPE_MESSAGE_DEBUG_OK);
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
||||
//**********************************************************************************************************************************************************************************
|
||||
// Fonction GESTION_CAPTEURS
|
||||
//
|
||||
//**********************************************************************************************************************************************************************************
|
||||
void gestion_capteurs(void)
|
||||
{
|
||||
uint16_t i, j;
|
||||
float val;
|
||||
int16_t no;
|
||||
bool flag_erreur;
|
||||
char tmp[MAX_LONGUEUR_BUFFER_TEMPORAIRE_DEBUG];
|
||||
|
||||
|
||||
if (!systeme.flag_cm3p_ready) return; // Evite que le traitement soit fait au milieu d'une reconfiguration...
|
||||
|
||||
switch(capteurs.sequenceur.etat)
|
||||
{
|
||||
//--------------------------------------------------------------------------------------------------------------
|
||||
case ETAT_SEQUENCEUR_CAPTEURS_INIT :
|
||||
//--------------------------------------------------------------------------------------------------------------
|
||||
{
|
||||
if ((systeme.flag_cm3p_ready) && // Permet de s'assurer que le cycle d'init système est terminé. En particulier, on est sûr que 'init_bdd()' puis 'annuaire_k_bus()' ont été traités.
|
||||
(capteurs.sequenceur.compteur == 0))
|
||||
{
|
||||
|
||||
affichage_debug(__FILE__, __LINE__, "------------------CAPTEURS INIT", TYPE_MESSAGE_DEBUG_WARNING);
|
||||
|
||||
for (i=0; i<capteurs.nb; i++)
|
||||
{
|
||||
if (capteurs.capteurs[i].flag_validite == FALSE) continue;
|
||||
|
||||
// Mise à jour de valeurs de démarrage des entrées prédéfinies à partir des valeurs de capteurs stockés dans la BDD.
|
||||
|
||||
// Correction de l'offset et du gain :
|
||||
if (capteurs.capteurs[i].gain != 0) // Le cas d'un gain=0 ne doit pas arriver car cela est vérifié au chargement, dans bdd_init.c. Mais on ne sait jamais...
|
||||
{
|
||||
val = (capteurs.capteurs[i].variables[CAPTEUR_VARIABLE_VALEUR].valeur_courante - capteurs.capteurs[i].offset) / capteurs.capteurs[i].gain;
|
||||
}
|
||||
else val = capteurs.capteurs[i].variables[CAPTEUR_VARIABLE_VALEUR].valeur_courante - capteurs.capteurs[i].offset;
|
||||
|
||||
|
||||
no = capteurs.capteurs[i].no_entrees[0]; // Facilite le traitement et la lecture ensuite. ATTENTION : Uniquement pour les types n'ayant qu'UNE entrée par capteur !!!!
|
||||
|
||||
switch(capteurs.capteurs[i].type_entrees)
|
||||
{
|
||||
//==================================
|
||||
case TYPE_ENTREES_AUXILIAIRES :
|
||||
{
|
||||
uint32_t val_u32 = (uint32_t) val;
|
||||
for (j = 0; j < capteurs.capteurs[i].nb_entrees; j ++)
|
||||
{
|
||||
entrees.aux.entrees[capteurs.capteurs[i].no_entrees[j]].valeur = (uint8_t) (val_u32 & 0x00000001);
|
||||
val_u32 >>= 1;
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
//==================================
|
||||
case TYPE_ENTREES_LEVEL_SENSOR :
|
||||
{
|
||||
entrees.level_sensor.entrees[no].valeur = val; // NB : si le capteur est valide, l'entrée correspondante l'est aussi (traité dans 'enregistrement_annuaire_k_bus()')
|
||||
break;
|
||||
}
|
||||
|
||||
//==================================
|
||||
case TYPE_ENTREES_VOLTAGE :
|
||||
{
|
||||
entrees.volt.entrees[no].valeur = val; // NB : si le capteur est valide, l'entrée correspondante l'est aussi (traité dans 'enregistrement_annuaire_k_bus()')
|
||||
break;
|
||||
}
|
||||
|
||||
//==================================
|
||||
case TYPE_ENTREES_OW :
|
||||
{
|
||||
// L'init se fait dans 'c_bus_down_reponse_annuaire_ow()' car on n'est pas sûr d'avoir l'annuaire OW disponible à ce stade.
|
||||
break;
|
||||
}
|
||||
|
||||
//==================================
|
||||
case TYPE_ENTREES_PREDEFINIES :
|
||||
{
|
||||
entrees.predefinies.entrees[no].valeur = val; // NB : si le capteur est valide, l'entrée correspondante l'est aussi (traité dans 'enregistrement_annuaire_k_bus()')
|
||||
break;
|
||||
}
|
||||
|
||||
/* //==================================
|
||||
case TYPE_ENTREES_IBS :
|
||||
{
|
||||
break;
|
||||
}
|
||||
*/
|
||||
//==================================
|
||||
case TYPE_ENTREES_NMEA :
|
||||
{
|
||||
entrees.nmea.entrees[no].valeur = val; // NB : si le capteur est valide, l'entrée correspondante l'est aussi (traité dans 'enregistrement_annuaire_k_bus()')
|
||||
break;
|
||||
}
|
||||
|
||||
//==================================
|
||||
/* case TYPE_ENTREES_CAN :
|
||||
{
|
||||
break;
|
||||
}
|
||||
*/
|
||||
//==================================
|
||||
case TYPE_ENTREES_CALCULEE_BOOLEEN :
|
||||
{
|
||||
for (j = 0; j < capteurs.capteurs[i].nb_entrees; j ++)
|
||||
{
|
||||
if (capteurs.capteurs[i].conditions.conditions[j].type_condition == CAPTEUR_CONDITION_GROUPE_NORMAL)
|
||||
{
|
||||
// Mise à jour du n° de source à partir de l'ID_Source :
|
||||
// Mise à jour du n° de variable à partir de l'ID_Variable :
|
||||
int16_t no_source;
|
||||
int16_t no_variable;
|
||||
switch(capteurs.capteurs[i].conditions.conditions[j].type_source)
|
||||
{
|
||||
case SOURCE_MESURE_CIRCUIT:
|
||||
{
|
||||
no_source = circuit_cle_primaire(capteurs.capteurs[i].conditions.conditions[j].id_source);
|
||||
no_variable = variable_circuit_cle_primaire(capteurs.capteurs[i].conditions.conditions[j].id_variable);
|
||||
break;
|
||||
}
|
||||
case SOURCE_MESURE_CAPTEUR:
|
||||
{
|
||||
no_source = capteur_cle_primaire(capteurs.capteurs[i].conditions.conditions[j].id_source);
|
||||
no_variable = 0; // Un capteur n'a qu'un n° de variable...
|
||||
break;
|
||||
}
|
||||
case SOURCE_MESURE_RESERVOIR:
|
||||
{
|
||||
no_source = reservoir_cle_primaire(capteurs.capteurs[i].conditions.conditions[j].id_source);
|
||||
no_variable = variable_reservoir_cle_primaire(capteurs.capteurs[i].conditions.conditions[j].id_variable);
|
||||
break;
|
||||
}
|
||||
case SOURCE_MESURE_BATTERIE:
|
||||
{
|
||||
no_source = batterie_cle_primaire(capteurs.capteurs[i].conditions.conditions[j].id_source);
|
||||
no_variable = variable_batterie_cle_primaire(capteurs.capteurs[i].conditions.conditions[j].id_variable);
|
||||
break;
|
||||
}
|
||||
default:
|
||||
{
|
||||
no_source = -1;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (no_source < 0) // Si on n'a pas trouvé d'équipement valide correspondant à l'ID reçu, on est obligé de dévalider complètement de capteur car l'équation peut ne plus rien vouloir dire...
|
||||
{
|
||||
sprintf(tmp, "L'ID_Source de la condition #%i du capteur #%i (clé primaire = %i) est invalide [%i]. Le capteur est dévalidé complètement car l'équation pourrait devenir instable", j, i, capteurs.capteurs[i].cle_primaire, capteurs.capteurs[i].conditions.conditions[j].id_source);
|
||||
affichage_debug(__FILE__, __LINE__, tmp, TYPE_MESSAGE_DEBUG_ERREUR);
|
||||
capteurs.capteurs[i].flag_validite = FALSE;
|
||||
break;
|
||||
}
|
||||
else capteurs.capteurs[i].conditions.conditions[j].no_source = no_source;
|
||||
|
||||
if (no_variable < 0) // Si on n'a pas trouvé de variable valide correspondant à l'ID reçu, on est obligé de dévalider complètement de capteur car l'équation peut ne plus rien vouloir dire...
|
||||
{
|
||||
sprintf(tmp, "L'ID_Variable de la condition #%i du capteur #%i (clé primaire = %i) est invalide [%i]. Le capteur est dévalidé complètement car l'équation pourrait devenir instable", j, i, capteurs.capteurs[i].cle_primaire, capteurs.capteurs[i].conditions.conditions[j].id_variable);
|
||||
affichage_debug(__FILE__, __LINE__, tmp, TYPE_MESSAGE_DEBUG_ERREUR);
|
||||
capteurs.capteurs[i].flag_validite = FALSE;
|
||||
break;
|
||||
}
|
||||
else capteurs.capteurs[i].conditions.conditions[j].no_variable = no_variable;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
/* //==================================
|
||||
case TYPE_ENTREES_CALCULEE_NUMERIQUE :
|
||||
{
|
||||
break;
|
||||
}
|
||||
*/
|
||||
|
||||
//==================================
|
||||
default:
|
||||
{
|
||||
sprintf(tmp, "Le 'Type_entrées' du capteur #%i est invalide [%i]. Le capteur est dévalidé", i, capteurs.capteurs[i].type_entrees);
|
||||
affichage_debug(__FILE__, __LINE__, tmp, TYPE_MESSAGE_DEBUG_ERREUR);
|
||||
capteurs.capteurs[i].flag_validite = FALSE;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
capteurs.sequenceur.etat = ETAT_SEQUENCEUR_CAPTEURS_REPOS;
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
//--------------------------------------------------------------------------------------------------------------
|
||||
case ETAT_SEQUENCEUR_CAPTEURS_REPOS :
|
||||
//--------------------------------------------------------------------------------------------------------------
|
||||
{
|
||||
if (capteurs.sequenceur.compteur == 0)
|
||||
{
|
||||
capteurs.sequenceur.compteur = CAPTEURS_PERIODE_INTEGRATION_VALEUR;
|
||||
|
||||
for (i = 0; i < capteurs.nb; i ++)
|
||||
{
|
||||
if (capteurs.capteurs[i].flag_validite == FALSE) continue;
|
||||
|
||||
flag_erreur = FALSE;
|
||||
val = 0;
|
||||
|
||||
//-------------------------------------
|
||||
// Recherche de la valeur du capteur :
|
||||
//-------------------------------------
|
||||
|
||||
// ATTENTION : ne doit pas fonctionner si le nb d'entrées est > 1 !!!!
|
||||
no = capteurs.capteurs[i].no_entrees[0]; // Facilite le traitement et la lecture ensuite.
|
||||
|
||||
switch(capteurs.capteurs[i].type_entrees)
|
||||
{
|
||||
//==================================
|
||||
case TYPE_ENTREES_AUXILIAIRES :
|
||||
{
|
||||
uint32_t val_u32 = 0;
|
||||
for (j = 0; j < capteurs.capteurs[i].nb_entrees; j ++)
|
||||
{
|
||||
val_u32 |= ((uint32_t)(entrees.aux.entrees[capteurs.capteurs[i].no_entrees[j]].valeur) ) << j;
|
||||
}
|
||||
|
||||
val = (float) val_u32;
|
||||
capteurs.capteurs[i].valeur_brute = val; // SDIR #135
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
//==================================
|
||||
case TYPE_ENTREES_LEVEL_SENSOR :
|
||||
{
|
||||
switch(entrees.level_sensor.entrees[no].mode)
|
||||
{
|
||||
case ENTREE_LEVEL_SENSOR_MODE_FONCTIONNEMENT_DEFAUT_ISOLEMENT_MASSE :
|
||||
case ENTREE_LEVEL_SENSOR_MODE_FONCTIONNEMENT_DEFAUT_ISOLEMENT_PLUS :
|
||||
case ENTREE_LEVEL_SENSOR_MODE_FONCTIONNEMENT_DEFAUT_ISOLEMENT_FULL :
|
||||
{
|
||||
val = entrees.level_sensor.entrees[no].valeur;
|
||||
if (fabs(val) < 0.8) val = 0; // Seuil (en valeur absolue), en-dessous duquel on considère la valeur comme non significative donc nulle. Evite les questions...!
|
||||
// if (val < -99.9) val = -99.9; // Il est inutile d'afficher des valeurs supérieures qui risquent d'affoler pour rien puisque c'est une projection qui est faite et pas un courant réel.
|
||||
//printf("Valeur lue sur détection de courant de défaut = %.3f\n", val);
|
||||
break;
|
||||
}
|
||||
|
||||
case ENTREE_LEVEL_SENSOR_MODE_FONCTIONNEMENT_NON_DEFINI :
|
||||
case ENTREE_LEVEL_SENSOR_MODE_FONCTIONNEMENT_0_10V :
|
||||
case ENTREE_LEVEL_SENSOR_MODE_FONCTIONNEMENT_500R :
|
||||
case ENTREE_LEVEL_SENSOR_MODE_FONCTIONNEMENT_4_20MA :
|
||||
case ENTREE_LEVEL_SENSOR_MODE_FONCTIONNEMENT_AUTO_TEST :
|
||||
default :
|
||||
{
|
||||
val = entrees.level_sensor.entrees[no].valeur;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
capteurs.capteurs[i].valeur_brute = val; // SDIR #135
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
//==================================
|
||||
case TYPE_ENTREES_VOLTAGE :
|
||||
{
|
||||
val = entrees.volt.entrees[no].valeur;
|
||||
capteurs.capteurs[i].valeur_brute = val; // SDIR #135
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
//==================================
|
||||
case TYPE_ENTREES_OW :
|
||||
{
|
||||
// NB : on sait que l'entrée est valide car le test a été fait dans 'enregistrement_annuaire_ow()'... Inutile de retester à chaque boucle.
|
||||
|
||||
// Vérification qu'on a déjà reçu des valeurs OW depuis le Companon :
|
||||
if (!entrees.ow.flag_premieres_valeurs_recues)
|
||||
{
|
||||
flag_erreur = TRUE;
|
||||
break;
|
||||
}
|
||||
|
||||
// SDIR # 176 :
|
||||
val = entrees.ow.entrees[no].valeur;
|
||||
capteurs.capteurs[i].valeur_brute = val; // SDIR #135
|
||||
|
||||
// SDIR #178 [début] :
|
||||
if (entrees.ow.entrees[no].etat != OW_ETAT_DEVICE_OK) // Si le capteur OW est NOK :
|
||||
{
|
||||
flag_erreur = TRUE; // Il est inutile de traiter de nouvelles valeurs de capteurs si le capteur est défaillant.
|
||||
|
||||
if (capteurs.capteurs[i].etat != CAPTEUR_ETAT_ALARME) // Détection d'un changement d'état.
|
||||
{
|
||||
capteurs.capteurs[i].etat = CAPTEUR_ETAT_ALARME; // Mise à jour du nouvel état du capteur
|
||||
capteurs.capteurs[i].flag_dde_maj_bdd = TRUE;
|
||||
|
||||
if (entrees.ow.entrees[no].etat == OW_ETAT_BUS_NOK) // Différentiation entre erreur globale du bus OW :
|
||||
{
|
||||
enregistrement_historique(TYPE_SOURCE_HISTORIQUE_CAPTEURS, CAPTEUR_OW_BUS_NOK, capteurs.capteurs[i].cle_primaire, 0, entrees.ow.entrees[no].rom_code);
|
||||
}
|
||||
else // ... et erreur du capteur seulement :
|
||||
{
|
||||
enregistrement_historique(TYPE_SOURCE_HISTORIQUE_CAPTEURS, CAPTEUR_OW_DEVICE_NOK, capteurs.capteurs[i].cle_primaire, 0, entrees.ow.entrees[no].rom_code);
|
||||
}
|
||||
}
|
||||
}
|
||||
else // Si le capteur OW est Ok :
|
||||
{
|
||||
if (capteurs.capteurs[i].etat != CAPTEUR_ETAT_NORMAL) // Détection d'un changement d'état
|
||||
{
|
||||
capteurs.capteurs[i].etat = CAPTEUR_ETAT_NORMAL; // Mise à jour du nouvel état du capteur (il sera peut-être modifié ensuite si une alerte ou une alarme est détectée)
|
||||
capteurs.capteurs[i].flag_dde_maj_bdd = TRUE;
|
||||
|
||||
enregistrement_historique(TYPE_SOURCE_HISTORIQUE_CAPTEURS, CAPTEUR_OW_DEVICE_OK, capteurs.capteurs[i].cle_primaire, 0, entrees.ow.entrees[no].rom_code);
|
||||
}
|
||||
}
|
||||
// SDIR #178 [fin]
|
||||
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
//==================================
|
||||
case TYPE_ENTREES_PREDEFINIES :
|
||||
{
|
||||
val = entrees.predefinies.entrees[no].valeur;
|
||||
capteurs.capteurs[i].valeur_brute = val; // SDIR #135
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
/* //==================================
|
||||
case TYPE_ENTREES_IBS :
|
||||
{
|
||||
break;
|
||||
}
|
||||
*/
|
||||
//==================================
|
||||
case TYPE_ENTREES_NMEA :
|
||||
{
|
||||
val = entrees.nmea.entrees[no].valeur;
|
||||
capteurs.capteurs[i].valeur_brute = val; // SDIR #135
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
//==================================
|
||||
/* case TYPE_ENTREES_CAN :
|
||||
{
|
||||
break;
|
||||
}
|
||||
*/
|
||||
//==================================
|
||||
case TYPE_ENTREES_CALCULEE_BOOLEEN :
|
||||
{
|
||||
struct Struct_calcul_capteur_booleen calcul_booleen;
|
||||
calcul_booleen.niveau = -1;
|
||||
|
||||
|
||||
#ifdef __DEBUG_CAPTEURS_CALCULES
|
||||
sprintf(tmp, "Capteur calculé #%i : ---------------------------------", i);
|
||||
affichage_debug(__FILE__, __LINE__, tmp, TYPE_MESSAGE_DEBUG_PAR_DEFAUT);
|
||||
#endif
|
||||
|
||||
for (j = 0; j < capteurs.capteurs[i].nb_entrees; j ++)
|
||||
{
|
||||
//----------------------------------------------------------------------------------------
|
||||
// Condition de début de groupe '[' :
|
||||
if (capteurs.capteurs[i].conditions.conditions[j].type_condition > CAPTEUR_CONDITION_GROUPE_NORMAL)
|
||||
{
|
||||
calcul_booleen.niveau ++;
|
||||
|
||||
calcul_booleen.parentheses[calcul_booleen.niveau].operation = capteurs.capteurs[i].conditions.conditions[j].type_condition;
|
||||
calcul_booleen.parentheses[calcul_booleen.niveau].resultat = valeur_neutre_operation_booleene(calcul_booleen.parentheses[calcul_booleen.niveau].operation);
|
||||
#ifdef __DEBUG_CAPTEURS_CALCULES
|
||||
char ch[100] = "";
|
||||
uint8_t k;
|
||||
|
||||
for (k=0; k<calcul_booleen.niveau; k++) strcat(ch, "\t");
|
||||
sprintf(tmp, "#%i : %s[",
|
||||
j, ch );
|
||||
affichage_debug(__FILE__, __LINE__, tmp, TYPE_MESSAGE_DEBUG_PAR_DEFAUT);
|
||||
#endif
|
||||
continue;
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------------------
|
||||
// Condition normale :
|
||||
if (capteurs.capteurs[i].conditions.conditions[j].type_condition == CAPTEUR_CONDITION_GROUPE_NORMAL)
|
||||
{
|
||||
bool val_bool;
|
||||
|
||||
if (capteurs.capteurs[i].conditions.conditions[j].flag_validite) val_bool = test_condition_capteur_booleen(i, j);
|
||||
else val_bool = valeur_neutre_operation_booleene(calcul_booleen.parentheses[calcul_booleen.niveau].operation);
|
||||
|
||||
if (calcul_booleen.parentheses[calcul_booleen.niveau].operation == CAPTEUR_CONDITION_GROUPE_OU)
|
||||
{
|
||||
calcul_booleen.parentheses[calcul_booleen.niveau].resultat |= val_bool;
|
||||
}
|
||||
else
|
||||
{
|
||||
calcul_booleen.parentheses[calcul_booleen.niveau].resultat &= val_bool;
|
||||
}
|
||||
#ifdef __DEBUG_CAPTEURS_CALCULES
|
||||
char ch[100] = "";
|
||||
uint8_t k;
|
||||
|
||||
for (k=0; k<(calcul_booleen.niveau+1); k++) strcat(ch, "\t");
|
||||
sprintf(tmp, "#%i : %s%s (%s) %s",
|
||||
j, ch,
|
||||
(calcul_booleen.parentheses[calcul_booleen.niveau].operation == CAPTEUR_CONDITION_GROUPE_OU) ? "OU" : "ET",
|
||||
(val_bool) ? "TRUE" : "FALSE",
|
||||
(capteurs.capteurs[i].conditions.conditions[j].flag_validite) ? "" : "[condition dévalidée]" );
|
||||
affichage_debug(__FILE__, __LINE__, tmp, TYPE_MESSAGE_DEBUG_PAR_DEFAUT);
|
||||
#endif
|
||||
continue;
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------------------
|
||||
// Condition de fin de groupe ']' :
|
||||
if (capteurs.capteurs[i].conditions.conditions[j].type_condition < CAPTEUR_CONDITION_GROUPE_NORMAL)
|
||||
{
|
||||
if (calcul_booleen.niveau > 0)
|
||||
{
|
||||
calcul_booleen.niveau --;
|
||||
|
||||
if (calcul_booleen.parentheses[calcul_booleen.niveau].operation == CAPTEUR_CONDITION_GROUPE_OU)
|
||||
{
|
||||
calcul_booleen.parentheses[calcul_booleen.niveau].resultat |= calcul_booleen.parentheses[calcul_booleen.niveau + 1].resultat;
|
||||
}
|
||||
else
|
||||
{
|
||||
calcul_booleen.parentheses[calcul_booleen.niveau].resultat &= calcul_booleen.parentheses[calcul_booleen.niveau + 1].resultat;
|
||||
}
|
||||
#ifdef __DEBUG_CAPTEURS_CALCULES
|
||||
char ch[100] = "";
|
||||
uint8_t k;
|
||||
|
||||
for (k=0; k<(calcul_booleen.niveau+1); k++) strcat(ch, "\t");
|
||||
sprintf(tmp, "#%i : %s] %s (%s)",
|
||||
j, ch,
|
||||
(calcul_booleen.parentheses[calcul_booleen.niveau].operation == CAPTEUR_CONDITION_GROUPE_OU) ? "OU" : "ET",
|
||||
(calcul_booleen.parentheses[calcul_booleen.niveau + 1].resultat) ? "TRUE" : "FALSE");
|
||||
affichage_debug(__FILE__, __LINE__, tmp, TYPE_MESSAGE_DEBUG_PAR_DEFAUT);
|
||||
#endif
|
||||
}
|
||||
else
|
||||
{
|
||||
val = (float) calcul_booleen.parentheses[calcul_booleen.niveau].resultat;
|
||||
capteurs.capteurs[i].valeur_brute = val; // SDIR #135
|
||||
#ifdef __DEBUG_CAPTEURS_CALCULES
|
||||
sprintf(tmp, "#%i : ] Résultat = %s", j, (val == 0) ? "FALSE" : "TRUE");
|
||||
affichage_debug(__FILE__, __LINE__, tmp, TYPE_MESSAGE_DEBUG_PAR_DEFAUT);
|
||||
#endif
|
||||
break;
|
||||
}
|
||||
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
/* //==================================
|
||||
case TYPE_ENTREES_CALCULEE_NUMERIQUE :
|
||||
{
|
||||
break;
|
||||
}
|
||||
*/
|
||||
|
||||
//==================================
|
||||
default: flag_erreur = TRUE; // A priori, pas possible car testé au moment de l'init...
|
||||
}
|
||||
|
||||
|
||||
//------------------------------------
|
||||
// Traitement de la valeur récupérée :
|
||||
//------------------------------------
|
||||
if (flag_erreur == FALSE)
|
||||
{
|
||||
// Correction :
|
||||
val = (val * capteurs.capteurs[i].gain) + capteurs.capteurs[i].offset ;
|
||||
|
||||
// Calcul de la nouvelle moyenne de valeur courante à partir de l'ancienne et de la valeur lue :
|
||||
capteurs.capteurs[i].variables[CAPTEUR_VARIABLE_VALEUR].valeur_courante = (((capteurs.capteurs[i].variables[CAPTEUR_VARIABLE_VALEUR].valeur_courante * (capteurs.capteurs[i].valeur_coeff_filtrage - 1))) + val) / capteurs.capteurs[i].valeur_coeff_filtrage;
|
||||
|
||||
// Mise à jour du cumul :
|
||||
capteurs.capteurs[i].variables[CAPTEUR_VARIABLE_VALEUR].cumul += capteurs.capteurs[i].variables[CAPTEUR_VARIABLE_VALEUR].valeur_courante;
|
||||
capteurs.capteurs[i].cumuls_nb_val ++; // MàJ du nombre d'échantillons dans le cumul
|
||||
|
||||
// Traitement si la valeur a suffisemment évolué :
|
||||
// if (fabs(capteurs.capteurs[i].variables[CAPTEUR_VARIABLE_VALEUR].valeur_bdd - capteurs.capteurs[i].variables[CAPTEUR_VARIABLE_VALEUR].valeur_courante) >= capteurs.variables[capteurs.capteurs[i].no_variable].marge)
|
||||
if (fabs(capteurs.capteurs[i].variables[CAPTEUR_VARIABLE_VALEUR].valeur_bdd - capteurs.capteurs[i].variables[CAPTEUR_VARIABLE_VALEUR].valeur_courante) > 0)
|
||||
{
|
||||
#ifdef __DEBUG_CAPTEURS
|
||||
sprintf(tmp, "Capteur #%i (cle primaire = %i) : changement détecté avec valeur_courante=%.3f et valeur_bdd=%.3f - Marge=%.3f ", i, capteurs.capteurs[i].cle_primaire, capteurs.capteurs[i].variables[CAPTEUR_VARIABLE_VALEUR].valeur_courante, capteurs.capteurs[i].variables[CAPTEUR_VARIABLE_VALEUR].valeur_bdd, capteurs.variables[capteurs.capteurs[i].no_variable].marge);
|
||||
affichage_debug(__FILE__, __LINE__, tmp, TYPE_MESSAGE_DEBUG_WARNING);
|
||||
#endif
|
||||
capteurs.capteurs[i].flag_dde_maj_bdd = TRUE; // Flag pour mise à jour dans la BDD
|
||||
|
||||
|
||||
// Enregistrement de la mesure si le capteur est configuré en mode MODE_ENREGISTREMENT_MESURES_CHANGEMENT_ETAT :
|
||||
if (capteurs.capteurs[i].mode_enregistrement_mesures == MODE_ENREGISTREMENT_MESURES_CHANGEMENT_ETAT)
|
||||
{
|
||||
char date_vide[MAX_LONGUEUR_DATE_COURANTE] = ""; // Evite un warning depuis GCC14
|
||||
enregistrement_mesure(SOURCE_MESURE_CAPTEUR, i, capteurs.capteurs[i].no_variable, date_vide, BDD_ENREGISTREMENT_MESURE_PONCTUEL);
|
||||
}
|
||||
|
||||
} // Fin de traitement si la valeur a évolué.
|
||||
|
||||
#ifdef __DEBUG_CAPTEURS
|
||||
sprintf(tmp, "Capteur #%i : Valeur=%.3f ", i, capteurs.capteurs[i].variables[CAPTEUR_VARIABLE_VALEUR].valeur_courante);
|
||||
affichage_debug(__FILE__, __LINE__, tmp, TYPE_MESSAGE_DEBUG_PAR_DEFAUT);
|
||||
#endif
|
||||
// Mise à jour des valeurs BDD des variables :
|
||||
if (capteurs.capteurs[i].flag_dde_maj_bdd)
|
||||
{
|
||||
for (j = 0; j < MAX_NOMBRE_VARIABLES_PAR_CAPTEUR; j ++) capteurs.capteurs[i].variables[j].valeur_bdd = capteurs.capteurs[i].variables[j].valeur_courante;
|
||||
}
|
||||
} // Fin du traitement sans erreur.
|
||||
}
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
//--------------------------------------------------------------------------------------------------------------
|
||||
default :
|
||||
//--------------------------------------------------------------------------------------------------------------
|
||||
{
|
||||
sprintf(tmp, "L'état du séquenceur Capteurs est inconnu [%i]. Il est repositionné au REPOS", capteurs.sequenceur.etat);
|
||||
affichage_debug(__FILE__, __LINE__, tmp, TYPE_MESSAGE_DEBUG_ERREUR);
|
||||
capteurs.sequenceur.etat = ETAT_SEQUENCEUR_CAPTEURS_REPOS;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
//**********************************************************************************************************************************************************************************
|
||||
// Fonction : Teste si la condition d'un capteur calculé booléen est vraie ou fausse
|
||||
// Reçoit : Le numéro du capteur et le numéro de la condition du capteur
|
||||
// Retourne : Vrai ou Faux
|
||||
//**********************************************************************************************************************************************************************************
|
||||
bool test_condition_capteur_booleen(uint16_t no_capteur, uint16_t no_condition)
|
||||
{
|
||||
float valeur;
|
||||
|
||||
|
||||
// Si la condition n'est pas une condition normale, on retourne directement FALSE :
|
||||
if (capteurs.capteurs[no_capteur].conditions.conditions[no_condition].type_condition != CAPTEUR_CONDITION_GROUPE_NORMAL) return(false);
|
||||
|
||||
//==================================================
|
||||
// Recherche de la valeur en cours de la source :
|
||||
switch(capteurs.capteurs[no_capteur].conditions.conditions[no_condition].type_source)
|
||||
{
|
||||
case SOURCE_MESURE_CIRCUIT:
|
||||
{
|
||||
valeur = circuits.circuits[capteurs.capteurs[no_capteur].conditions.conditions[no_condition].no_source].variables[capteurs.capteurs[no_capteur].conditions.conditions[no_condition].no_variable].valeur_courante;
|
||||
break;
|
||||
}
|
||||
case SOURCE_MESURE_CAPTEUR:
|
||||
{
|
||||
valeur = capteurs.capteurs[capteurs.capteurs[no_capteur].conditions.conditions[no_condition].no_source].variables[capteurs.capteurs[no_capteur].conditions.conditions[no_condition].no_variable].valeur_courante;
|
||||
break;
|
||||
}
|
||||
case SOURCE_MESURE_RESERVOIR:
|
||||
{
|
||||
valeur = reservoirs.reservoirs[capteurs.capteurs[no_capteur].conditions.conditions[no_condition].no_source].variables[capteurs.capteurs[no_capteur].conditions.conditions[no_condition].no_variable].valeur_courante;
|
||||
break;
|
||||
}
|
||||
case SOURCE_MESURE_BATTERIE:
|
||||
{
|
||||
valeur = batteries.batteries[capteurs.capteurs[no_capteur].conditions.conditions[no_condition].no_source].variables[capteurs.capteurs[no_capteur].conditions.conditions[no_condition].no_variable].valeur_courante;
|
||||
break;
|
||||
}
|
||||
default: return(false); // Ne devrait pas arriver puisque testé à l'init...
|
||||
}
|
||||
#ifdef __DEBUG_CAPTEURS_CALCULES
|
||||
/*char tmp[MAX_LONGUEUR_BUFFER_TEMPORAIRE_DEBUG];
|
||||
sprintf(tmp, "Test de la condition #%i du capteur #%i : Type_source=%i, N° source=%i, N° de variable=%i, Valeur= %.2f, Condition de test=%i",
|
||||
no_condition, no_capteur,
|
||||
capteurs.capteurs[no_capteur].conditions.conditions[no_condition].type_source,
|
||||
capteurs.capteurs[no_capteur].conditions.conditions[no_condition].no_source,
|
||||
capteurs.capteurs[no_capteur].conditions.conditions[no_condition].no_variable,
|
||||
valeur,
|
||||
capteurs.capteurs[no_capteur].conditions.conditions[no_condition].test);
|
||||
affichage_debug(__FILE__, __LINE__, tmp, TYPE_MESSAGE_DEBUG_PAR_DEFAUT);
|
||||
*/
|
||||
#endif
|
||||
|
||||
//==================================================
|
||||
// Test selon le type de test de l'évènement :
|
||||
switch(capteurs.capteurs[no_capteur].conditions.conditions[no_condition].test)
|
||||
{
|
||||
//-------------------------------------
|
||||
case EVENTS_TYPE_TEST_STRICT_INFERIEUR:
|
||||
{
|
||||
return (valeur < capteurs.capteurs[no_capteur].conditions.conditions[no_condition].seuil);
|
||||
break;
|
||||
}
|
||||
|
||||
//-------------------------------------
|
||||
case EVENTS_TYPE_TEST_INFERIEUR_OU_EGAL:
|
||||
{
|
||||
return (valeur <= capteurs.capteurs[no_capteur].conditions.conditions[no_condition].seuil);
|
||||
break;
|
||||
}
|
||||
|
||||
//-------------------------------------
|
||||
case EVENTS_TYPE_TEST_EGAL:
|
||||
{
|
||||
return (fabs(valeur - capteurs.capteurs[no_capteur].conditions.conditions[no_condition].seuil) < FLT_MIN);
|
||||
break;
|
||||
}
|
||||
|
||||
//-------------------------------------
|
||||
case EVENTS_TYPE_TEST_SUPERIEUR_OU_EGAL:
|
||||
{
|
||||
return (valeur >= capteurs.capteurs[no_capteur].conditions.conditions[no_condition].seuil);
|
||||
break;
|
||||
}
|
||||
|
||||
//-------------------------------------
|
||||
case EVENTS_TYPE_TEST_STRICT_SUPERIEUR:
|
||||
{
|
||||
return (valeur > capteurs.capteurs[no_capteur].conditions.conditions[no_condition].seuil);
|
||||
break;
|
||||
}
|
||||
|
||||
//-------------------------------------
|
||||
default:
|
||||
case EVENTS_TYPE_TEST_NON_DEFINI :
|
||||
{
|
||||
return (false);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//**********************************************************************************************************************************************************************************
|
||||
// Fonction : Renvoit une valeur booléenne neutre par rapport à une opération (0 si OU , 1 si ET)
|
||||
// Reçoit : l'opération concernée
|
||||
// Retourne : Vrai ou Faux
|
||||
//**********************************************************************************************************************************************************************************
|
||||
bool valeur_neutre_operation_booleene(uint8_t operation)
|
||||
{
|
||||
|
||||
if (operation == CAPTEUR_CONDITION_GROUPE_ET) return(true);
|
||||
else return(false);
|
||||
}
|
||||
|
||||
|
||||
//**********************************************************************************************************************************************************************************
|
||||
// Fonction CAPTEUR_CLE_PRIMAIRE
|
||||
// Reçoit en paramètre :
|
||||
// - La Cle_primaire du capteur à rechercher
|
||||
// Retourne :
|
||||
// - le numéro de capteur correspondant (ou -1 si aucun capteur valide ne correspond). La numérotation allant de 0 à MAX_NOMBRE_CAPTEURS-1.
|
||||
//**********************************************************************************************************************************************************************************
|
||||
int16_t capteur_cle_primaire(uint16_t cle_primaire)
|
||||
{
|
||||
uint16_t i;
|
||||
|
||||
for (i=0; i<capteurs.nb; i++)
|
||||
{
|
||||
if ((capteurs.capteurs[i].cle_primaire == cle_primaire) && (capteurs.capteurs[i].flag_validite)) return(i);
|
||||
|
||||
}
|
||||
return (-1); // Si on est arrivé au bout de la boucle, on renvoi le code de 'non trouvé'.
|
||||
}
|
||||
|
||||
|
||||
//**********************************************************************************************************************************************************************************
|
||||
// Fonction VARIABLE_CAPTEUR_CLE_PRIMAIRE
|
||||
// Reçoit en paramètre :
|
||||
// - La Cle_primaire de la variable à rechercher
|
||||
// Retourne :
|
||||
// - le numéro de variable correspondant (ou -1 si aucune variable valide ne correspond). La numérotation allant de 0 à MAX_NOMBRE_VARIABLES_CAPTEURS-1.
|
||||
//**********************************************************************************************************************************************************************************
|
||||
int16_t variable_capteur_cle_primaire(uint16_t cle_primaire)
|
||||
{
|
||||
uint16_t i;
|
||||
|
||||
for (i=0; i<MAX_NOMBRE_VARIABLES_CAPTEURS; i++)
|
||||
{
|
||||
if (capteurs.variables[i].cle_primaire == cle_primaire) return(i);
|
||||
|
||||
}
|
||||
return (-1); // Si on est arrivé au bout de la boucle, on renvoi le code de 'non trouvé'.
|
||||
}
|
||||
Reference in New Issue
Block a user