This is a library for the MAX17055 Li+ Battery Fuel Gauge.

Dependents:   Low_Power_Long_Distance_IR_Vision_Robot MAX17055_EZconfig MAX17055_EZconfig_Sample Low_Power_Long_Distance_IR_Vision_Robot

Fork of max17055 by Maxim Integrated

Revision:
9:f29d5e49b190
Parent:
8:ca8765c30ed2
Child:
11:bdbd3104995b
--- a/max17055.cpp	Thu Nov 02 18:11:16 2017 +0000
+++ b/max17055.cpp	Tue Feb 06 21:10:30 2018 +0000
@@ -3,16 +3,17 @@
 *
 * @author Felipe Neira - Maxim Integrated - TTS
 *
-* @version 1.0
+* @version 1.2
 *
-* Started: 11SEP17
+* Started: 9JAN18
 *
-* Updated:
+* Updated: 
+* New functions improved for continious display. Change copyright notice for 2018.
+* 
+* 
 *
-* @brief Source file for MAX31855 class
-*
-********************************************************************************
-* Copyright (C) 2017 Maxim Integrated Products, Inc., All Rights Reserved.
+/*******************************************************************************
+* Copyright (C) 2018 Maxim Integrated Products, Inc., All Rights Reserved.
 *
 * Permission is hereby granted, free of charge, to any person obtaining a
 * copy of this software and associated documentation files (the "Software"),
@@ -41,8 +42,8 @@
 * trademarks, maskwork rights, or any other form of intellectual
 * property whatsoever. Maxim Integrated Products, Inc. retains all
 * ownership rights.
-*
-******************************************************************************/
+*******************************************************************************
+*/
 
 #include "mbed.h"
 #include "max17055.h"
@@ -57,6 +58,9 @@
 #define MAX17055_STATUS_BST             (1 << 3)
 #define MAX17055_STATUS_POR             (1 << 1)
 
+/* POR Mask */
+#define MAX17055_POR_MASK               (0xFFFD)
+
 /* MODELCFG register bits */
 #define MAX17055_MODELCFG_REFRESH       (1 << 15)
 
@@ -213,6 +217,7 @@
 * \retval       1 on success
 *               0 if device is not present
 *              -1 if errors exist
+*              -2 if POR is not set
 */
 
 
@@ -220,6 +225,7 @@
 {
 
     int status, ret;
+    int time_out = 10;
     uint16_t read_data, hibcfg_value, reg;
 
 
@@ -230,26 +236,21 @@
     /* Step 0: Check for POR */
     /* Skip load model if POR bit is cleared */
 
-    readReg(STATUS_REG, read_data);
-
-    if (!(read_data & MAX17055_STATUS_POR ) )
-        return -1;  //POR is not set. Skip Initialization.
+    if (check_POR_func() == -1)
+        return -2;  //POR is not set. Skip Initialization.
 
     /* Step 1: Check if FStat.DNR == 0 */
     // Do not continue until FSTAT.DNR == 0
-    printf("step 0 check \r\n");
-
-    int time_out = 500;
     ret = poll_flag_clear(FSTAT_REG, MAX17055_FSTAT_DNR, time_out);
     if (ret < 0) {
-        printf("Unsuccessful init: Data Not Ready!\n");
+        //printf("Unsuccessful init: Data Not Ready!\n");
         return ret;
     }
 
     /* Force exit from hibernate */
     hibcfg_value = forcedExitHyberMode();
 
-    printf("step 1 check \r\n");
+    //printf("step 1 check \r\n");
 
     /* Step 2: Initialize configuration */
     switch (1) {
@@ -258,30 +259,78 @@
             EZconfig_init(des_data);
 
             /* Poll ModelCFG.ModelRefresh bit for clear */
-            int time_out = 500; //msec
             ret = poll_flag_clear(MODELCFG_REG, MAX17055_MODELCFG_REFRESH, time_out);
             if(ret < 0) {
                 //dev_err(priv->dev, "Option1 model refresh not completed!\n");
                 return ret;
             }
 
-            break;
+            break; 
     }
     /* Restore original HibCfg */
     writeReg(HIBCFG_REG, hibcfg_value);
-    printf("Last section check \r\n");
+    //printf("Last section check \r\n");
 
 
     /* Optional step - alert threshold initialization */
     //set_alert_thresholds(priv);
 
     /* Clear Status.POR */
-    readReg(STATUS_REG, reg);
-    write_and_verify_reg(STATUS_REG, (reg & ~MAX17055_STATUS_POR));
-
+    ret = clear_POR_bit();
+    if (ret == -1)
+        return ret;    
     return 1;
 }
 
+////////////////////////////////////////////////////////////////////////////////
+
+/**
+* \brief        Check POR function
+* \par          Details
+*               This function check is there was a power on reset event for the MAX17055
+*
+* \retval       1 for no POR detected
+*              -1 for POR detected
+*/
+int MAX17055::check_POR_func()
+{
+    uint16_t read_data;
+    
+    readReg(STATUS_REG, read_data);
+
+    if (!(read_data & MAX17055_STATUS_POR ) )
+        return -1;  //POR is not set.
+    else 
+        return 1;
+}
+
+////////////////////////////////////////////////////////////////////////////////
+
+/**
+* \brief        clear POR bit function
+* \par          Details
+*               This function clear the idicating bit for POR - MAX17055
+*
+* \retval       1 for Success
+*              -1 for errors
+*/
+int MAX17055::clear_POR_bit()
+{
+    int status, ret;
+    uint16_t read_data, hibcfg_value, reg;
+
+
+    status = readReg(STATUS_REG, read_data);
+    if (status != 1)
+        return -1;  //Device is not present in the i2c Bus
+    status = write_and_verify_reg(STATUS_REG, (read_data & MAX17055_POR_MASK));
+    if (status != 1)
+        return -1;
+    else 
+        return 1;
+
+
+}
 
 ///////////////////////////////////////////////////////////////////////////////
 
@@ -303,8 +352,9 @@
     uint16_t data;
     int ret;
 
+
     do {
-        wait_ms(10);
+        wait_ms(1);
         ret = readReg(reg_addr, data);
         if(ret < 0)
             return ret;
@@ -312,7 +362,7 @@
         if(!(data & mask))
             return 1;
 
-        timeout -= 10;
+        timeout -= 1;
     } while(timeout > 0);
 
     return -1;
@@ -396,7 +446,7 @@
 * \par          Details
 *               This function implements the steps for the EZ confing m5 FuelGauge
 *
-* \retval       returns TBD
+* \retval       1 on success
 *
 */
 
@@ -412,19 +462,19 @@
 
 
     /* Step 2.1: Option 1 EZ Config */
-    writeReg(DESIGNCAP_REG, des_data.designcap);
-    writeReg(DQACC_REG, des_data.designcap >> 5);
-    writeReg(ICHGTERM_REG, des_data.ichgterm);
-    writeReg(VEMPTY_REG, des_data.vempty);
+    ret = writeReg(DESIGNCAP_REG, des_data.designcap);
+    ret = writeReg(DQACC_REG, des_data.designcap >> 5);  //DesignCap divide by 32
+    ret = writeReg(ICHGTERM_REG, des_data.ichgterm);
+    ret = writeReg(VEMPTY_REG, des_data.vempty);
 
     if (des_data.vcharge > charger_th) {
         dpacc = (des_data.designcap >> 5) * chg_V_high / des_data.designcap;
-        writeReg(DPACC_REG, dpacc);
-        writeReg(MODELCFG_REG, param_EZ_FG1); //Why 0x8400
+        ret = writeReg(DPACC_REG, dpacc);
+        ret = writeReg(MODELCFG_REG, param_EZ_FG1); //Why 0x8400??
     } else {
         dpacc = (des_data.designcap >> 5) * chg_V_low / des_data.designcap;
-        writeReg(DPACC_REG, dpacc);
-        writeReg(MODELCFG_REG, param_EZ_FG2);
+        ret = writeReg(DPACC_REG, dpacc);
+        ret = writeReg(MODELCFG_REG, param_EZ_FG2);
     }
 
 
@@ -494,6 +544,36 @@
     return data;
 }
 
+////////////////////////////////////////////////////////////////////////////////
+
+/**
+* \brief        Get State Of Charge(SOC) Function for MAX17055
+* \par          Details
+*               This function sends a request to access the internal
+*               of the MAX17055
+*
+* \param[in]    reg_addr     - register address
+* \param[out]   reg_data     - SOC data from the REPSOC_REG register
+* \retval       1 on success
+*
+*              -1 if errors exist
+*/
+
+
+int MAX17055::get_mixSOC()
+{
+
+    int ret;
+    uint16_t data;
+
+    ret = readReg(MIXSOC_REG, data);
+    if (ret < 0)
+        return ret;
+
+    data = data >> 8; /* RepSOC LSB: 1/256 % */
+
+    return data;
+}
 ///////////////////////////////////////////////////////////////////////////////
 
 /**
@@ -507,13 +587,13 @@
 *              -1 if errors exist
 */
 
-int MAX17055::get_TTE()
+int MAX17055::get_atTTE()
 {
 
     int ret;
     uint16_t data;
 
-    ret = readReg(TTE_REG, data);
+    ret = readReg(ATTTE_REG, data);
     if (ret < 0)
         return ret;
     else
@@ -689,4 +769,109 @@
         res *= 1562500 /(rsense_value * 1000); //Change to interact with the rsense of customer
     }
     return res;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+
+/**
+* \brief        Save Learned Parameters Function
+* \par          Details
+*               It is recommended to save the learned capacity parameters every
+*               time bit 2 of the Cycles register toggles
+*               (so that it is saved every 64% change in the battery) 
+*               so that if power is lost the values can easily be restored.
+*
+* \retval      ret int -1 if fail
+*
+*/
+
+int MAX17055::save_Params(saved_FG_params_t FG_params)
+{
+    int ret;
+    uint16_t data[5];
+    ret = readReg(RCOMP0_REG, data[0]);
+    if (ret < 0)
+        return ret;
+    else
+        FG_params.rcomp0 = data[0];
+
+    ret = readReg(TEMPCO_REG, data[1]);
+    if (ret < 0)
+        return ret;
+    else
+        FG_params.temp_co = data[1];
+
+    ret = readReg(FULLCAPREP_REG, data[2]);
+    if (ret < 0)
+        return ret;
+    else
+        FG_params.full_cap_rep = data[2];
+
+    ret = readReg(CYCLES_REG, data[3]);
+    if (ret < 0)
+        return ret;
+    else
+        FG_params.cycles = data[3];
+
+    ret = readReg(FULLCAPNOM_REG, data[4]);
+    if (ret < 0)
+        return ret;
+    else
+        FG_params.full_cap_nom = data[4];
+    return ret;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+
+/**
+* \brief        Resotore Parameters Function
+* \par          Details
+*               If power is lost, then the capacity information 
+*               can be easily restored with this function
+*
+* \param[in]   struct saved_FG_params_t 
+* \retval      void
+*
+*/
+
+int MAX17055::restore_Params(saved_FG_params_t FG_params)
+{
+    int ret;
+    uint16_t temp_data, fullcapnom_data, mixCap_calc, dQacc_calc;
+    uint16_t dPacc_value = 0x0C80;//Why this vcalue?
+
+    //Restoring capacity parameters 
+    write_and_verify_reg(RCOMP0_REG, FG_params.rcomp0);
+    write_and_verify_reg(TEMPCO_REG, FG_params.temp_co);
+    write_and_verify_reg(FULLCAPNOM_REG, FG_params.full_cap_nom);
+    
+    wait_ms(350);
+    //Restore FullCap
+
+    ret = readReg(FULLCAPNOM_REG, fullcapnom_data);
+    if (ret < 0)
+        return ret;
+
+    ret = readReg(MIXSOC_REG, temp_data); //check if Error in sofware guide register incorrect
+    if (ret < 0)
+        return ret;
+    
+    mixCap_calc = (temp_data*fullcapnom_data)/25600;
+
+    write_and_verify_reg(MIXCAP_REG, mixCap_calc);
+    write_and_verify_reg(FULLCAPREP_REG, FG_params.full_cap_rep);
+    
+    //Write DQACC to 200% of Capacity and DPACC to 200%
+    dQacc_calc = (FG_params.full_cap_nom/ 16) ;
+
+    write_and_verify_reg(DPACC_REG, dPacc_value);
+    write_and_verify_reg(DQACC_REG, dQacc_calc);
+
+    wait_ms(350);
+
+    //Restore Cycles register
+    ret = write_and_verify_reg(CYCLES_REG, FG_params.cycles);
+    if (ret < 0)
+        return ret;
+return ret;
 }
\ No newline at end of file