This class provides APIs to all of the registers of the TI BQ35100 battery gauge, as used on the u-blox C030 primary battery shield.

Dependents:   example-battery-gauge-bq35100

Revision:
1:ee7cc8d75283
Parent:
0:cec745c014b7
Child:
2:4c699a813451
--- a/TESTS/unit_tests/default/main.cpp	Mon Jul 03 16:12:22 2017 +0000
+++ b/TESTS/unit_tests/default/main.cpp	Thu Nov 09 22:55:13 2017 +0000
@@ -10,6 +10,20 @@
 // COMPILE-TIME MACROS
 // ----------------------------------------------------------------
 
+// The gauge enable pin
+#define GAUGE_ENABLE_PIN D4
+
+// Pick some sensible minimum and maximum numbers
+#define MAX_TEMPERATURE_READING_C  80
+#define MIN_TEMPERATURE_READING_C -20
+#define MIN_VOLTAGE_READING_MV     0
+#define MAX_VOLTAGE_READING_MV     12000
+#define MAX_CURRENT_READING_MA     2000
+#define MIN_CURRENT_READING_MA    -2000
+#define MIN_CAPACITY_READING_UAH   0
+#define MAX_CAPACITY_READING_UAH   30000000
+#define SET_DESIGN_CAPACITY_MAH    32177
+
 // ----------------------------------------------------------------
 // PRIVATE VARIABLES
 // ----------------------------------------------------------------
@@ -29,8 +43,252 @@
 void test_init() {
     BatteryGaugeBq35100 * pBatteryGauge = new BatteryGaugeBq35100();
     
-    TEST_ASSERT_FALSE(pBatteryGauge->init(NULL));
-    TEST_ASSERT(pBatteryGauge->init(gpI2C));
+    TEST_ASSERT_FALSE(pBatteryGauge->init(NULL, GAUGE_ENABLE_PIN));
+    TEST_ASSERT(pBatteryGauge->init(gpI2C, GAUGE_ENABLE_PIN));
+}
+
+// Test that a temperature reading can be performed
+void test_temperature() {
+    BatteryGaugeBq35100 * pBatteryGauge = new BatteryGaugeBq35100();
+    int32_t temperatureC = MIN_TEMPERATURE_READING_C - 1;
+    
+    // Call should fail if the battery gauge has not been initialised
+    TEST_ASSERT_FALSE(pBatteryGauge->getTemperature(&temperatureC));
+    
+    // Normal case
+    TEST_ASSERT(pBatteryGauge->init(gpI2C, GAUGE_ENABLE_PIN));
+    TEST_ASSERT(pBatteryGauge->getTemperature(&temperatureC));
+    printf ("Temperature %d C.\n", (int) temperatureC);
+    // Range check
+    TEST_ASSERT((temperatureC >= MIN_TEMPERATURE_READING_C) && (temperatureC <= MAX_TEMPERATURE_READING_C));
+    
+    // The parameter is allowed to be NULL
+    TEST_ASSERT(pBatteryGauge->getTemperature(NULL));
+}
+
+// Test that a voltage reading can be performed
+void test_voltage() {
+    BatteryGaugeBq35100 * pBatteryGauge = new BatteryGaugeBq35100();
+    int32_t voltageMV = MIN_VOLTAGE_READING_MV - 1;
+    
+    // Call should fail if the battery gauge has not been initialised
+    TEST_ASSERT_FALSE(pBatteryGauge->getVoltage(&voltageMV));
+    
+    // Normal case
+    TEST_ASSERT(pBatteryGauge->init(gpI2C, GAUGE_ENABLE_PIN));
+    TEST_ASSERT(pBatteryGauge->getVoltage(&voltageMV));
+    printf ("Voltage %.3f V.\n", ((float) voltageMV) / 1000);
+    // Range check
+    TEST_ASSERT((voltageMV >= MIN_VOLTAGE_READING_MV) && (voltageMV <= MAX_VOLTAGE_READING_MV));
+    
+    // The parameter is allowed to be NULL
+    TEST_ASSERT(pBatteryGauge->getVoltage(NULL));
+}
+
+// Test that a current reading can be performed
+void test_current() {
+    BatteryGaugeBq35100 * pBatteryGauge = new BatteryGaugeBq35100();
+    int32_t currentMA = MIN_CURRENT_READING_MA - 1;
+    
+    // Call should fail if the battery gauge has not been initialised
+    TEST_ASSERT_FALSE(pBatteryGauge->getCurrent(&currentMA));
+    
+    // Normal case
+    TEST_ASSERT(pBatteryGauge->init(gpI2C, GAUGE_ENABLE_PIN));
+    TEST_ASSERT(pBatteryGauge->getCurrent(&currentMA));
+    printf ("Current %.3f A.\n", ((float) currentMA) / 1000);
+    // Range check
+    TEST_ASSERT((currentMA >= MIN_CURRENT_READING_MA) && (currentMA <= MAX_CURRENT_READING_MA));
+    
+    // The parameter is allowed to be NULL
+    TEST_ASSERT(pBatteryGauge->getCurrent(NULL));
+}
+
+// Test that a capacity used reading can be performed
+void test_used_capacity() {
+    BatteryGaugeBq35100 * pBatteryGauge = new BatteryGaugeBq35100();
+    uint32_t capacityUAh = MIN_CAPACITY_READING_UAH - 1;
+    
+    // Call should fail if the battery gauge has not been initialised
+    TEST_ASSERT_FALSE(pBatteryGauge->getUsedCapacity(&capacityUAh));
+    
+    // Normal case
+    TEST_ASSERT(pBatteryGauge->init(gpI2C, GAUGE_ENABLE_PIN));
+    TEST_ASSERT(pBatteryGauge->getUsedCapacity(&capacityUAh));
+    printf ("Used capacity %.3f mAh.\n", ((float) capacityUAh) / 1000);
+    // Range check
+    TEST_ASSERT((capacityUAh >= MIN_CAPACITY_READING_UAH) && (capacityUAh <= MAX_CAPACITY_READING_UAH));
+
+    // The parameter is allowed to be NULL
+    TEST_ASSERT(pBatteryGauge->getUsedCapacity(NULL));
+}
+
+// Test that the design capacity can be set and read
+void test_design_capacity() {
+    BatteryGaugeBq35100 * pBatteryGauge = new BatteryGaugeBq35100();
+    uint32_t originalDesignCapacity;
+    uint32_t newDesignCapacity = SET_DESIGN_CAPACITY_MAH;
+    uint32_t readDesignCapacity = 0;
+    
+    // Calls should fail if the battery gauge has not been initialised
+    TEST_ASSERT_FALSE(pBatteryGauge->getDesignCapacity(&readDesignCapacity));
+    TEST_ASSERT_FALSE(pBatteryGauge->setDesignCapacity(newDesignCapacity));
+
+    // First get the original design capacity
+    TEST_ASSERT(pBatteryGauge->init(gpI2C, GAUGE_ENABLE_PIN));
+    TEST_ASSERT(pBatteryGauge->getDesignCapacity(&originalDesignCapacity));
+    printf ("Design capacity was originally %d mAh.\n", (unsigned int) originalDesignCapacity);
+
+    // Avoid the old and new values being the same
+    if (originalDesignCapacity == newDesignCapacity) {
+        newDesignCapacity--;
+    }
+
+    // Now set a new value
+    TEST_ASSERT(pBatteryGauge->setDesignCapacity(newDesignCapacity));
+    printf ("Design capacity set to %d mAh.\n", (unsigned int) newDesignCapacity);
+
+    // Read the value back and check that it's been set
+    TEST_ASSERT(pBatteryGauge->getDesignCapacity(&readDesignCapacity));
+    printf ("Design capacity was read as %d mAh.\n", (unsigned int) readDesignCapacity);
+    TEST_ASSERT(readDesignCapacity = newDesignCapacity)
+
+    // The parameter in the get call is allowed to be NULL
+    TEST_ASSERT(pBatteryGauge->getDesignCapacity(NULL));
+
+    // Put the original value back
+    TEST_ASSERT(pBatteryGauge->setDesignCapacity(originalDesignCapacity));
+    printf ("Design capacity returned to %d mAh.\n", (unsigned int) originalDesignCapacity);
+}
+
+// Test that a remaining capacity reading can be performed
+void test_remaining_capacity() {
+    BatteryGaugeBq35100 * pBatteryGauge = new BatteryGaugeBq35100();
+    uint32_t capacityUAh = MIN_CAPACITY_READING_UAH - 1;
+
+    // Call should fail if the battery gauge has not been initialised
+    TEST_ASSERT_FALSE(pBatteryGauge->getRemainingCapacity(&capacityUAh));
+    
+    // Normal case
+    TEST_ASSERT(pBatteryGauge->init(gpI2C, GAUGE_ENABLE_PIN));
+    TEST_ASSERT(pBatteryGauge->getRemainingCapacity(&capacityUAh));
+    printf ("Remaining capacity %.3f mAh.\n", ((float) capacityUAh) / 1000);
+    // Range check
+    TEST_ASSERT((capacityUAh >= MIN_CAPACITY_READING_UAH) && (capacityUAh <= MAX_CAPACITY_READING_UAH));
+
+    // The parameter is allowed to be NULL
+    TEST_ASSERT(pBatteryGauge->getRemainingCapacity(NULL));
+}
+
+// Test that a remaining precentage reading can be performed
+void test_remaining_percentage() {
+    BatteryGaugeBq35100 * pBatteryGauge = new BatteryGaugeBq35100();
+    int32_t percentage = -1;
+
+    // Call should fail if the battery gauge has not been initialised
+    TEST_ASSERT_FALSE(pBatteryGauge->getRemainingPercentage(&percentage));
+    
+    // Normal case
+    TEST_ASSERT(pBatteryGauge->init(gpI2C, GAUGE_ENABLE_PIN));
+    TEST_ASSERT(pBatteryGauge->getRemainingPercentage(&percentage));
+    printf ("Remaining capacity %d%%.\n", (signed int) percentage);
+    // Range check
+    TEST_ASSERT((percentage >= 0) && (percentage <= 100));
+
+    // The parameter is allowed to be NULL
+    TEST_ASSERT(pBatteryGauge->getRemainingPercentage(NULL));
+}
+
+// Test that the security mode of the chip can be changed
+void test_advanced_security_mode() {
+    BatteryGaugeBq35100 * pBatteryGauge = new BatteryGaugeBq35100();
+    BatteryGaugeBq35100::SecurityMode securityMode;
+
+    // Get the existing device mode and then set it to sealed
+    TEST_ASSERT(pBatteryGauge->init(gpI2C, GAUGE_ENABLE_PIN));
+    printf ("Calling advancedGetSecurityMode()...\n");
+    securityMode = pBatteryGauge->advancedGetSecurityMode();
+    printf ("Calling advancedSetSecurityMode(SECURITY_MODE_SEALED)...\n");
+    TEST_ASSERT(pBatteryGauge->advancedSetSecurityMode(BatteryGaugeBq35100::SECURITY_MODE_SEALED));
+
+    delete pBatteryGauge;
+    pBatteryGauge = new BatteryGaugeBq35100();
+    // Calls should fail if the battery gauge has not been initialised
+    printf ("Calling advancedGetSecurityMode()...\n");
+    TEST_ASSERT(pBatteryGauge->advancedGetSecurityMode() == BatteryGaugeBq35100::SECURITY_MODE_UNKNOWN);
+    printf ("Calling advancedSetSecurityMode(SECURITY_MODE_UNSEALED)...\n");
+    TEST_ASSERT_FALSE(pBatteryGauge->advancedSetSecurityMode(BatteryGaugeBq35100::SECURITY_MODE_UNSEALED));
+    
+    // Normal case
+    printf ("Calling init()...\n");
+    TEST_ASSERT(pBatteryGauge->init(gpI2C, GAUGE_ENABLE_PIN));
+    printf ("Calling advancedGetSecurityMode()...\n");
+    TEST_ASSERT(pBatteryGauge->advancedGetSecurityMode() == BatteryGaugeBq35100::SECURITY_MODE_SEALED);
+    
+    // These calls should fail
+    // TODO do a thing that only works when unsealed
+    // TODO do a thing that only works when full access
+
+    // Now unseal it
+    printf ("Calling advancedSetSecurityMode(SECURITY_MODE_UNSEALED)...\n");
+    TEST_ASSERT(pBatteryGauge->advancedSetSecurityMode(BatteryGaugeBq35100::SECURITY_MODE_UNSEALED));
+    
+    // This call should now pass
+    // TODO do a thing that only works when unsealed
+    
+    // But this should still fail
+    // TODO do a thing that only works when full access
+
+    // Seal it again
+    printf ("Calling advancedSetSecurityMode(SECURITY_MODE_SEALED)...\n");
+    TEST_ASSERT(pBatteryGauge->advancedSetSecurityMode(BatteryGaugeBq35100::SECURITY_MODE_SEALED));
+
+    // Now allow full access, which should fail as you can't get there from SEALED
+    printf ("Calling advancedSetSecurityMode(SECURITY_MODE_FULL_ACCESS)...\n");
+    TEST_ASSERT_FALSE(pBatteryGauge->advancedSetSecurityMode(BatteryGaugeBq35100::SECURITY_MODE_FULL_ACCESS));
+    
+    // Now unseal it
+    printf ("Calling advancedSetSecurityMode(SECURITY_MODE_UNSEALED)...\n");
+    TEST_ASSERT(pBatteryGauge->advancedSetSecurityMode(BatteryGaugeBq35100::SECURITY_MODE_UNSEALED));
+    
+    // *Now* allow full access, which should succeed
+    printf ("Calling advancedSetSecurityMode(SECURITY_MODE_FULL_ACCESS)...\n");
+    TEST_ASSERT(pBatteryGauge->advancedSetSecurityMode(BatteryGaugeBq35100::SECURITY_MODE_FULL_ACCESS));
+    
+    // These calls should now both pass
+    // TODO do a thing that only works when unsealed
+    // TODO do a thing that only works when full access
+
+    // Put the device back the way it was
+    TEST_ASSERT(pBatteryGauge->advancedSetSecurityMode(securityMode));
+}
+
+// Reset the BQ35100 battery gauge chip at the outset
+void test_advanced_reset() {
+    BatteryGaugeBq35100 * pBatteryGauge = new BatteryGaugeBq35100();
+    BatteryGaugeBq35100::SecurityMode securityMode;
+
+    // Call should fail if the battery gauge has not been initialised
+    TEST_ASSERT_FALSE(pBatteryGauge->advancedReset());
+
+    // Get the existing security mode and then set it to unsealed
+    TEST_ASSERT(pBatteryGauge->init(gpI2C, GAUGE_ENABLE_PIN));
+
+    printf ("Calling advancedGetSecurityMode()...\n");
+    securityMode = pBatteryGauge->advancedGetSecurityMode();
+    printf ("Calling advancedSetSecurityMode(SECURITY_MODE_UNSEALED)...\n");
+    TEST_ASSERT(pBatteryGauge->advancedSetSecurityMode(BatteryGaugeBq35100::SECURITY_MODE_UNSEALED));
+   
+    // TODO: modify a thing that will later be reset
+    
+    // Now reset the chip
+    printf ("Calling advancedReset()...\n");
+    TEST_ASSERT(pBatteryGauge->advancedReset());
+    
+    // TODO check that the thing has been reset
+
+    // Put the security mode back to what it was
+    TEST_ASSERT(pBatteryGauge->advancedSetSecurityMode(securityMode));
 }
 
 // ----------------------------------------------------------------
@@ -47,7 +305,16 @@
 
 // Test cases
 Case cases[] = {
-    Case("Initialisation", test_init)
+    Case("Initialisation", test_init),
+    Case("Temperature read", test_temperature),
+    Case("Voltage read", test_voltage),
+    Case("Current read", test_current),
+    Case("Used capacity read", test_used_capacity),
+    Case("Design capacity read/set", test_design_capacity),
+    Case("Remaining capacity read", test_remaining_capacity),
+    Case("Remaining precentage read", test_remaining_percentage),
+    Case("Advanced security mode", test_advanced_security_mode),
+    Case("Advanced reset", test_advanced_reset)
 };
 
 Specification specification(test_setup, cases);