This class provides APIs to all of the registers of the TI BQ27441 battery gauge, as used on the u-blox C030 board. The caller should instantiate an I2C interface and pass this to init(), which will initialise the chip and place it into its lowest power state. When battery gauging is enabled, the getRemainingCapacity()/getRemainingPercentage() API calls may be used; otherwise the chip will be maintained in its lowest power state until a voltage/current/temperature reading is requested.

Dependents:   example-battery-gauge-bq27441

Revision:
5:63b325f2c21a
Parent:
3:ebd56471d57c
Child:
6:998cc334f8f2
--- a/bq27441.cpp	Wed Jun 07 10:32:54 2017 +0000
+++ b/bq27441.cpp	Wed Jun 14 17:11:40 2017 +0100
@@ -137,7 +137,7 @@
         if (offset / 32 == (offset + length - 1) / 32) {
         
 #ifdef DEBUG_BQ27441
-            printf("BatteryGaugeBq27441 (I2C 0x%02x): preparing to read %d byte(s) from offset %d of sub-class %d.\n", gAddress >> 1, length, offset, subClassId);
+            printf("BatteryGaugeBq27441 (I2C 0x%02x): preparing to read %d byte(s) from offset %d of sub-class %d.\n", gAddress >> 1, (int) length, (int) offset, subClassId);
 #endif
             // Handle unsealing
             wasSealed = isSealed();
@@ -182,7 +182,7 @@
 #endif
                                     } else {
 #ifdef DEBUG_BQ27441
-                                        printf("BatteryGaugeBq27441 (I2C 0x%02x): couldn't read all %d bytes of config.\r", gAddress >> 1, length);
+                                        printf("BatteryGaugeBq27441 (I2C 0x%02x): couldn't read all %d bytes of config.\r", gAddress >> 1, (int) length);
 #endif
                                     }
                                 } else {
@@ -217,7 +217,7 @@
             }
         } else {
 #ifdef DEBUG_BQ27441
-            printf("BatteryGaugeBq27441 (I2C 0x%02x): offset (%d) is in different 32 byte block to offset + length (%d) [length is %d].\n", gAddress >> 1, offset, offset + length, length);
+            printf("BatteryGaugeBq27441 (I2C 0x%02x): offset (%d) is in different 32 byte block to offset + length (%d) [length is %d].\n", gAddress >> 1, (int) offset, (int) (offset + length), (int) length);
 #endif
         }
     }
@@ -250,7 +250,7 @@
         // The offset + length combination must not cross a 32-byte boundary
         if (offset / 32 == (offset + length - 1) / 32) {        
 #ifdef DEBUG_BQ27441
-            printf("BatteryGaugeBq27441 (I2C 0x%02x): preparing to write %d byte(s) to offset %d of sub-class %d.\n", gAddress >> 1, length, offset, subClassId);
+            printf("BatteryGaugeBq27441 (I2C 0x%02x): preparing to write %d byte(s) to offset %d of sub-class %d.\n", gAddress >> 1, (int) length, (int) offset, subClassId);
 #endif
             // Handle unsealing
             wasSealed = isSealed();
@@ -361,7 +361,7 @@
                                                 }
                                             } else {
 #ifdef DEBUG_BQ27441
-                                                printf("BatteryGaugeBq27441 (I2C 0x%02x): couldn't write all %d bytes during config update.\n", gAddress >> 1, length);
+                                                printf("BatteryGaugeBq27441 (I2C 0x%02x): couldn't write all %d bytes during config update.\n", gAddress >> 1, (int) length);
 #endif
                                             }
                                         } else {
@@ -406,7 +406,7 @@
             }
         } else {
 #ifdef DEBUG_BQ27441
-            printf("BatteryGaugeBq27441 (I2C 0x%02x): offset (%d) is in different 32 byte block to offset + length (%d) [length is %d].\n", gAddress >> 1, offset, offset + length, length);
+            printf("BatteryGaugeBq27441 (I2C 0x%02x): offset (%d) is in different 32 byte block to offset + length (%d) [length is %d].\n", gAddress >> 1, (int) offset, (int) (offset + length), (int) length);
 #endif
         }
     }
@@ -736,6 +736,96 @@
     return gGaugeOn;
 }
 
+// Disable the battery detect pin.
+bool BatteryGaugeBq27441::disableBatteryDetect (void)
+{
+    bool success = false;
+    char data[3];
+    
+    if (gReady && (gpI2c != NULL)) {
+        gpI2c->lock();
+        // Read the OpConfig register which is in the Registers sub-class
+        // (64) at offset 0.
+        if (readExtendedData(64, 0, 2, &(data[0]))) {
+#ifdef DEBUG_BQ27441
+            printf("BatteryGaugeBq27441 (I2C 0x%02x): OpConfig is 0x%02x%02x.\r\n", gAddress >> 1, data[0], data[1]);
+#endif                        
+            // Battery Insertion Enabled is bit 5 of the high byte of OpConfig.
+            // 1 means that the battery input pin is enabled
+            if (((data[0] & (1 << 5)) != 0)) {
+                // Clear the BIE bit 'cos it's set and is shouldn't be
+                data[0] &= ~(1 << 5);
+                // Write the new value back
+                if (writeExtendedData(64, 0, 2, &(data[0]))) {
+                    // Send the Battery Inserted message as we can't do gauging otherwise
+                    data[0] = 0x00;  // Set address to first register for control
+                    data[1] = 0x0C;  // First byte of BAT_INSERT sub-command (0x0C)
+                    data[2] = 0x00;  // Second byte of BAT_INSERT sub-command (0x00)
+                    success = gpI2c->write(gAddress, &(data[0]), 3) == 0;
+#ifdef DEBUG_BQ27441
+                    if (success) {
+                        printf("BatteryGaugeBq27441 (I2C 0x%02x): BIE disabled, BAT_INSERT sent, OpConfig becomes 0x%02x%02x.\r\n", gAddress >> 1, data[0], data[1]);
+                    }
+#endif
+                }
+            } else {
+                success = true;
+            }
+        }
+        
+        // Set hibernate again if we are not monitoring
+        if (!gGaugeOn) {
+            setHibernate();
+        }
+
+        gpI2c->unlock();
+    }
+    
+    return success;
+}
+
+// Enable the battery detect pin.
+bool BatteryGaugeBq27441::enableBatteryDetect (void)
+{
+    bool success = false;
+    char data[3];
+    
+    if (gReady && (gpI2c != NULL)) {
+        gpI2c->lock();
+        // Read the OpConfig register which is in the Registers sub-class
+        // (64) at offset 0.
+        if (readExtendedData(64, 0, 2, &(data[0]))) {
+#ifdef DEBUG_BQ27441
+            printf("BatteryGaugeBq27441 (I2C 0x%02x): OpConfig is 0x%02x%02x.\r\n", gAddress >> 1, data[0], data[1]);
+#endif                        
+            // Battery Insertion Enabled is bit 5 of the high byte of OpConfig.
+            // 1 means that the battery input pin is enabled
+            if (((data[0] & (1 << 5)) == 0)) {
+                // Set the BIE bit 'cos it's not set and needs to be
+                data[0] |= 1 << 5;
+                // Write the new value back
+                success = writeExtendedData(64, 0, 2, &(data[0]));
+#ifdef DEBUG_BQ27441
+                if (success) {
+                    printf("BatteryGaugeBq27441 (I2C 0x%02x): BIE enabled, OpConfig becomes 0x%02x%02x.\r\n", gAddress >> 1, data[0], data[1]);
+                }
+#endif                        
+            } else {
+                success = true;
+            }
+        }
+        
+        // Set hibernate again if we are not monitoring
+        if (!gGaugeOn) {
+            setHibernate();
+        }
+
+        gpI2c->unlock();
+    }
+    
+    return success;
+}
+
 // Check whether a battery has been detected or not.
 bool BatteryGaugeBq27441::isBatteryDetected (void)
 {
@@ -799,7 +889,7 @@
                 }
 
 #ifdef DEBUG_BQ27441
-                printf("BatteryGaugeBq27441 (I2C 0x%02x): chip temperature %.1f K, so %d C.\n", gAddress >> 1, ((float) data) / 10, temperatureC);
+                printf("BatteryGaugeBq27441 (I2C 0x%02x): chip temperature %.1f K, so %d C.\n", gAddress >> 1, ((float) data) / 10, (int) temperatureC);
 #endif
             }
         
@@ -871,7 +961,7 @@
                 }
 
 #ifdef DEBUG_BQ27441
-                printf("BatteryGaugeBq27441 (I2C 0x%02x): current %d mA.\n", gAddress >> 1, currentMA);
+                printf("BatteryGaugeBq27441 (I2C 0x%02x): current %d mA.\n", gAddress >> 1, (int) currentMA);
 #endif
             }
 
@@ -976,7 +1066,7 @@
         success = readExtendedData(subClassId, offset, length, pData);
 #ifdef DEBUG_BQ27441
         if (success) {
-            printf("BatteryGaugeBq27441 (I2C 0x%02x): read extended data with subClassId %d from offset %d.\n", gAddress >> 1, subClassId, offset);
+            printf("BatteryGaugeBq27441 (I2C 0x%02x): read extended data with subClassId %d from offset %d.\n", gAddress >> 1, subClassId, (int) offset);
         }
 #endif
 
@@ -1002,7 +1092,7 @@
         success = writeExtendedData(subClassId, offset, length, pData);
 #ifdef DEBUG_BQ27441
         if (success) {
-            printf("BatteryGaugeBq27441 (I2C 0x%02x): written %d byte(s) of extended data with subClassId %d from offset %d.\n", gAddress >> 1, length, subClassId, offset);
+            printf("BatteryGaugeBq27441 (I2C 0x%02x): written %d byte(s) of extended data with subClassId %d from offset %d.\n", gAddress >> 1, (int) length, subClassId, (int) offset);
         }
 #endif