Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Revision 0:d801ad2b1422, committed 2022-03-06
- Comitter:
- snec_student
- Date:
- Sun Mar 06 14:21:57 2022 +0000
- Commit message:
- fonctionne depart arret HTR; ;
Changed in this revision
| DS_3231.cpp | Show annotated file Show diff for this revision Revisions of this file |
| DS_3231.h | Show annotated file Show diff for this revision Revisions of this file |
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/DS_3231.cpp Sun Mar 06 14:21:57 2022 +0000
@@ -0,0 +1,314 @@
+#include "DS_3231.h"
+
+//Constructeur avec 2 broches i2c
+DS_3231::DS_3231(PinName SDA, PinName SCL): i2c(SDA,SCL)
+{
+ w_adrs = ((DS3231_I2C_ADRS << 1) | I2C_WRITE);
+ r_adrs = ((DS3231_I2C_ADRS << 1) | I2C_READ);
+}
+
+// ecrire l'horaire dans le composant
+// arguments : structure de type horaire
+// cette fonction renvoie 0 si opération OK,1 si capteur absent
+/*
+* Example:
+* @code
+*
+* //instantiate rtc object
+* DS_3231 horloge(D14, D15);
+*
+* //time = 12:00:00 AM 12hr mode
+* ds3231_time_t time = {12, 0, 0, 0, 1}
+* uint16_t rtn_val;
+*
+* rtn_val = rtc.set_time(time);
+*
+* @endcode
+**************************************************************/
+uint16_t DS_3231::set_time(DS_3231_time_t time)
+{
+ uint8_t data[] = {0,0,0,0};
+ uint8_t data_length = 0;
+ uint8_t max_hour = 24;
+
+ data[data_length++] = SECONDS;
+ data[data_length++] = uchar_2_bcd(time.seconds);
+ data[data_length++] = uchar_2_bcd(time.minutes);
+
+ //format Hours register
+ data[data_length] = uchar_2_bcd(time.hours);
+ if(time.mode) {
+ max_hour = max_hour/2;
+
+ data[data_length] |= MODE;
+ if(time.am_pm) {
+ data[data_length] |= AM_PM;
+ }
+
+ } else {
+ max_hour = max_hour - 1;
+ }
+ data_length++;
+
+ //Make sure data is within range.
+ if((time.seconds > 59) || (time.minutes > 59) || (time.hours > max_hour)) {
+ return(1);
+ } else {
+ return(i2c.write(w_adrs,(const char*) data, data_length));
+ }
+}
+
+
+
+/**********************************************************//**
+* Lire l'horaire sur l'horloge
+*
+// arguments : pointeur vers une structure de type horaire
+// cette fonction renvoie 0 si opération OK,1 si capteur absent
+
+* Example:
+* @code
+*
+* //instantiate rtc object
+* Ds3231 rtc(D14, D15);
+*
+* //time = 12:00:00 AM 12hr mode
+* ds3231_time_t time = {12, 0, 0, 0, 1}
+* uint16_t rtn_val;
+*
+* rtn_val = rtc.get_time(&time);
+*
+* @endcode
+**************************************************************/
+uint16_t DS_3231::get_time(DS_3231_time_t* time)
+{
+ uint16_t rtn_val = 1;
+ uint8_t data[3];
+ data[0] = SECONDS;
+ rtn_val = i2c.write(w_adrs, (const char*) data, 1);
+ if(!rtn_val) {
+ rtn_val = i2c.read(r_adrs,(char *) data, 3);
+ time->seconds = bcd_2_uchar(data[0]);
+ time->minutes = bcd_2_uchar(data[1]);
+ time->am_pm = (data[2]&AM_PM);
+ time->mode = (data[2]&MODE);
+ if(time->mode) {
+ time->hours = bcd_2_uchar((data[2]&0x1F));
+ } else {
+ time->hours = bcd_2_uchar((data[2]&0x3F));
+ }
+ }
+ return(rtn_val);
+}
+
+// programmer une alarme sur l'horloge
+// arguments : structure de type alarme, numero de la voie alarme 0/1 pour alrm1/2
+// cette fonction renvoie 0 si opération OK,1 si capteur absent
+uint16_t DS_3231::set_alarm(DS_3231_alrm_t alarm, bool one_r_two)
+{
+ uint8_t data[] = {0,0,0,0,0};
+ uint8_t data_length = 0;
+ uint8_t max_hour = 24;
+ uint8_t mask_var = 0;
+
+ //setting alarm 1 or 2?
+ if(one_r_two)
+ {
+ data[data_length++] = ALRM1_SECONDS;
+
+ //config seconds register
+ if(alarm.am1)
+ {
+ mask_var |= ALRM_MASK;
+ }
+ data[data_length++] = (mask_var | uchar_2_bcd(alarm.seconds));
+ mask_var = 0;
+
+ //config minutes register
+ if(alarm.am2)
+ {
+ mask_var |= ALRM_MASK;
+ }
+ data[data_length++] = (mask_var | uchar_2_bcd(alarm.minutes));
+ mask_var = 0;
+
+ //config hours register
+ if(alarm.am3)
+ {
+ mask_var |= ALRM_MASK;
+ }
+ if(alarm.mode)
+ {
+ max_hour = max_hour/2;
+ mask_var |= MODE;
+ if(alarm.am_pm)
+ {
+ mask_var |= AM_PM;
+ }
+ }
+ else
+ {
+ max_hour = max_hour - 1;
+ }
+ data[data_length++] = (mask_var | uchar_2_bcd(alarm.hours));
+ mask_var = 0;
+
+ //config day/date register
+ if(alarm.am4)
+ {
+ mask_var |= ALRM_MASK;
+ }
+ if(alarm.dy_dt)
+ {
+ mask_var |= DY_DT;
+ data[data_length++] = (mask_var | uchar_2_bcd(alarm.day));
+ }
+ else
+ {
+ data[data_length++] = (mask_var | uchar_2_bcd(alarm.date));
+ }
+ mask_var = 0;
+ }
+ else
+ {
+ data[data_length++] = ALRM2_MINUTES;
+
+ //config minutes register
+ if(alarm.am2)
+ {
+ mask_var |= ALRM_MASK;
+ }
+ data[data_length++] = (mask_var | uchar_2_bcd(alarm.minutes));
+ mask_var = 0;
+
+ //config hours register
+ if(alarm.am3)
+ {
+ mask_var |= ALRM_MASK;
+ }
+ if(alarm.mode)
+ {
+ max_hour = max_hour/2;
+ mask_var |= MODE;
+ if(alarm.am_pm)
+ {
+ mask_var |= AM_PM;
+ }
+ }
+ else
+ {
+ max_hour = max_hour - 1;
+ }
+ data[data_length++] = (mask_var | uchar_2_bcd(alarm.hours));
+ mask_var = 0;
+
+ //config day/date register
+ if(alarm.am4)
+ {
+ mask_var |= ALRM_MASK;
+ }
+ if(alarm.dy_dt)
+ {
+ mask_var |= DY_DT;
+ data[data_length++] = (mask_var | uchar_2_bcd(alarm.day));
+ }
+ else
+ {
+ data[data_length++] = (mask_var | uchar_2_bcd(alarm.date));
+ }
+ mask_var = 0;
+ }
+
+ //Make sure data is within range.
+ if((alarm.seconds > 59) || (alarm.minutes > 59) || (alarm.hours > max_hour) ||
+ ((alarm.day < 1) || (alarm.day > 7)) ||
+ ((alarm.date < 1) || (alarm.date > 31)))
+ {
+ return(1);
+ }
+ else
+ {
+ return(i2c.write(w_adrs,(const char*) data, data_length));
+ }
+ }
+
+// programmer les registres d'etat et de controle sur l'horloge
+// arguments : structure de type registre de controle/etat
+// cette fonction renvoie 0 si opération OK,1 si pb
+// Example:
+ /* //do not use 0xAA, see datasheet for appropriate data
+ * ds3231_cntl_stat_t data = {0xAA, 0xAA};
+ *
+ * rtn_val = rtc.set_cntl_stat_reg(data);
+ *
+ * @endcode
+ **************************************************************/
+uint16_t DS_3231::set_cntl_stat_reg(DS_3231_cntl_stat_t data)
+{
+ uint8_t local_data[] = {0,0,0};
+ uint8_t data_length = 0;
+
+ local_data[data_length++] = CONTROL;
+ local_data[data_length++] = data.control;
+ local_data[data_length++] = data.status;
+
+ //users responsibility to make sure data is logical
+ return(i2c.write(w_adrs,(const char*) local_data, data_length));
+}
+
+// raz flag alarme
+
+char DS_3231::raz_alm1()
+ {
+ char buffer_envoi[2]={0x0F,0x00};
+ char data;
+ char test = i2c.write(w_adrs,buffer_envoi,1);
+ test = i2c.read(r_adrs,&data,1);
+ data=data&&0xFE;
+ buffer_envoi[1]=data;
+ test = i2c.write(w_adrs,buffer_envoi,2);
+ return test;
+ }
+
+
+
+
+
+/**********************************************************//**
+* Conversion d'un uint8_t en bcd
+* argument: valeur de la valeur à convertir en BDC (0 à 255)
+* valeur retournée : = valeur convertie en BCD
+* par exemple unint16_t toto = uchar_2_bcd(323); => toto = 0x323
+**************************************************************/
+uint16_t DS_3231::uchar_2_bcd(uint8_t data)
+{
+ uint16_t bcd_result = 0;
+
+ //Obtention des centaines
+ bcd_result |= ((data/100) << 8);
+ data = (data - (data/100)*100);
+
+ //Obtention des dizaines
+ bcd_result |= ((data/10) << 4);
+ data = (data - (data/10)*10);
+
+ //Obtention des unites
+ bcd_result |= data;
+ return(bcd_result);
+}
+
+/**********************************************************//**
+* Conversion d'un bcd en uint8_t
+* argument: valeur de la valeur à convertir en BCD
+* valeur retournée : = valeur convertie en uint8
+* par exemple :
+**************************************************************/
+uint8_t DS_3231::bcd_2_uchar(uint8_t bcd)
+{
+ uint8_t rtn_val = 0;
+
+ rtn_val += ((bcd&0xf0)>>4)*10;
+ rtn_val += (bcd&0x000f);
+
+ return rtn_val;
+}
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/DS_3231.h Sun Mar 06 14:21:57 2022 +0000
@@ -0,0 +1,167 @@
+#include "mbed.h"
+
+#ifndef DS_3231_H
+#define DS_3211_H
+
+
+
+#define DS3231_I2C_ADRS 0x68
+#define I2C_WRITE 0
+#define I2C_READ 1
+
+#define AM_PM (1 << 5)
+#define MODE (1 << 6)
+#define DY_DT (1 << 6)
+#define ALRM_MASK (1 << 7)
+
+/** definition d'une structure de type temps
+* DS_3231_time_t - Structure permettant de cntenir un temps
+* Membres:
+* - uint32_t seconds - Use decimal value. Member fx's convert to BCD
+* - uint32_t minutes - Use decimal value. Member fx's convert to BCD
+* - uint32_t hours - Use decimal value. Member fx's convert to BCD
+* - bool am_pm - TRUE for PM, same logic as datashee
+* - bool mode - TRUE for 12 hour, same logic as datasheet */
+typedef struct { //
+ uint32_t seconds; //valeur des secondes
+ uint32_t minutes; //valeur des minutes
+ uint32_t hours; //valeur des heures
+ bool am_pm; // 0 pour AM, 1 pour PM
+ bool mode; // 0 pour format 24 heures, 1 pour format 12 heures
+} DS_3231_time_t;
+
+/**definition d'une structure de type alarme
+* Members:
+* - uint32_t seconds - Use decimal value. Member fx's convert to BCD
+* - uint32_t minutes - Use decimal value. Member fx's convert to BCD
+* - uint32_t hours - Use decimal value. Member fx's convert to BCD
+* - uint32_t day - Use decimal value. Member fx's convert to BCD
+* - uint32_t date - Use decimal value. Member fx's convert to BCD
+* - bool am1 - Flag for setting alarm rate
+* - bool am2 - Flag for setting alarm rate
+* - bool am3 - Flag for setting alarm rate
+* - bool am4 - Flag for setting alarm rate
+* - bool am_pm - TRUE for PM, same logic as datasheet
+* - bool mode - TRUE for 12 hour, same logic as datasheet
+* - bool dy_dt - TRUE for Day, same logic as datasheet
+*/
+typedef struct
+{
+ //Seconds and am1 not used for alarm2
+ uint32_t seconds;
+ uint32_t minutes;
+ uint32_t hours;
+ uint32_t day;
+ uint32_t date;
+ bool am1;
+ bool am2;
+ bool am3;
+ bool am4;
+ bool am_pm;
+ bool mode;
+ bool dy_dt;
+}DS_3231_alrm_t;
+
+/**Definition des registres de configuration et d'etat
+* Members:
+* - uint8_t control - Binary data for read/write of control register
+* - uint8_t status - Binary data for read/write of status register
+*/
+typedef struct
+{
+ uint8_t control;
+ uint8_t status;
+}DS_3231_cntl_stat_t;
+
+
+/******************************************************************//**
+* Ds3231 Class
+**********************************************************************/
+class DS_3231
+{
+ uint8_t w_adrs, r_adrs; // declaration des adresses I2C en ecriture et en lecture
+public :
+
+ /**
+ * ds3231_regs_t - enumerated DS3231 registers
+ */
+ typedef enum {
+ SECONDS,
+ MINUTES,
+ HOURS,
+ DAY,
+ DATE,
+ MONTH,
+ YEAR,
+ ALRM1_SECONDS,
+ ALRM1_MINUTES,
+ ALRM1_HOURS,
+ ALRM1_DAY_DATE,
+ ALRM2_MINUTES,
+ ALRM2_HOURS,
+ ALRM2_DAY_DATE,
+ CONTROL,
+ STATUS,
+ AGING_OFFSET, //don't touch this register
+ MSB_TEMP,
+ LSB_TEMP
+ } DS3231_regs_t;
+
+// constructeur avec 2 broches I2C
+ DS_3231 (PinName SDA, PinName SCL);
+
+// ecrire l'horaire sur l'horloge
+// arguments : structure de type horaire
+// cette fonction renvoie 0 si opération OK,1 si capteur absent
+ uint16_t set_time(DS_3231_time_t time);
+
+// Lire l'horaire sur l'horloge
+// arguments : pointeur vers une structure de type horaire
+// cette fonction renvoie 0 si opération OK,1 si capteur absent
+ uint16_t get_time(DS_3231_time_t* time);
+
+// programmer une alarme sur l'horloge
+// arguments : structure de type alarme, numero de la voie alarme 0/1 pour alrm1/2
+// cette fonction renvoie 0 si opération OK,1 si capteur absent
+ uint16_t set_alarm(DS_3231_alrm_t alarm, bool one_r_two);
+
+// programmer les registres d'etat et de controle sur l'horloge
+// arguments : structure de type registre de controle/etat
+// cette fonction renvoie 0 si opération OK,1 si pb
+// Example:
+ /* //do not use 0xAA, see datasheet for appropriate data
+ * ds3231_cntl_stat_t data = {0xAA, 0xAA};
+ *
+ * rtn_val = rtc.set_cntl_stat_reg(data);
+ *
+ * @endcode
+ **************************************************************/
+ uint16_t set_cntl_stat_reg(DS_3231_cntl_stat_t data);
+
+// raz flag alarme
+
+ char raz_alm1();
+
+
+private :
+ /**********************************************************//**
+ * Conversion d'un uint8_t en bcd
+ * argument: valeur de la valeur à convertir en BDC (0 à 255)
+ * valeur retournée : = valeur convertie en BCD
+ * par exemple unint16_t toto = uchar_2_bcd(323); => toto = 0x323
+ **************************************************************/
+ uint16_t uchar_2_bcd(uint8_t data);
+ // la classe possede en interne :
+ I2C i2c; // un composant I2C que l'on nommera i2c
+ // unsigned char adr_I2C=0x32; // une adresse I2C
+
+
+/**********************************************************//**
+* Conversion d'un bcd en uint8_t
+* argument: valeur de la valeur à convertir en BCD
+* valeur retournée : = valeur convertie en uint8
+* par exemple :
+**************************************************************/
+uint8_t bcd_2_uchar(uint8_t bcd);
+};
+#endif