Linux Power Management development
 help / color / mirror / Atom feed
* [PATCH v8] bq27xxx: support interchangeable OnePlus 6/6T fuel gauges
@ 2026-10-19 19:08 Rinat Muhamedgaliev via B4 Relay
  2026-10-19 19:08 ` [PATCH v8] power: supply: bq27xxx: detect bq27541 behind bq27411 compatible Rinat Muhamedgaliev via B4 Relay
  0 siblings, 1 reply; 2+ messages in thread
From: Rinat Muhamedgaliev via B4 Relay @ 2026-10-19 19:08 UTC (permalink / raw)
  To: linux-pm
  Cc: pali, sre, afd, konrad.dybcio, david, krzk, linux-arm-msm,
	linux-kernel, Rinat Muhamedgaliev

OnePlus 6 and 6T battery packs can contain either a bq27411 or a bq27541
fuel gauge. The two chips require different register maps.

The DeviceType check now lives in the bus-neutral battery core, where it
uses the existing register-map and control-register helpers. For bq27411
and bq27541, it compares the type selected by the compatible with the
reported type and chooses the detected profile.

Tested on a OnePlus 6T with DeviceType 0x0541 (bq27541): 4.338 V, 100%
capacity, 27.8 C, and Full/Good status. Testing on DeviceType 0x0421
(bq27411) hardware would be appreciated.

Changes in v8:
- Move DeviceType detection to the bus-neutral battery core.
- Use the existing register map and control-command definitions.
- Link to v7: https://patch.msgid.link/20261019-master-v7-0-a1fc488d9c77@gmail.com

Changes in v7:
- Determine the expected DeviceType through an extensible chip switch.
- Mark the probe-time list for extension with DeviceType-capable fuel gauges.
- Link to v6: https://patch.msgid.link/20261019-master-v6-0-c4b36129721e@gmail.com

Changes in v6:
- Compare the detected model with the compatible-selected model.
- Support both BQ27411-to-BQ27541 and BQ27541-to-BQ27411 detection.

Changes in v5:
- Report detected and expected DeviceType values instead of hard-coding chip names.
- Describe an unknown DeviceType as unrecognized.

Changes in v4:
- Drop the generic compatible and binding update.
- Keep the established OnePlus DTS unchanged.

---
Rinat Muhamedgaliev (1):
      power: supply: bq27xxx: detect bq27541 behind bq27411 compatible

 drivers/power/supply/bq27xxx_battery.c | 61 ++++++++++++++++++++++++++++++++++
 1 file changed, 61 insertions(+)
---
base-commit: 830b3c68c1fb1e9176028d02ef86f3cf76aa2476
change-id: 20260927-master-bd0afd9696ef

Best regards,
--  
Rinat Muhamedgaliev <rinat.muhamedgaliev@gmail.com>



^ permalink raw reply	[flat|nested] 2+ messages in thread

* [PATCH v8] power: supply: bq27xxx: detect bq27541 behind bq27411 compatible
  2026-10-19 19:08 [PATCH v8] bq27xxx: support interchangeable OnePlus 6/6T fuel gauges Rinat Muhamedgaliev via B4 Relay
@ 2026-10-19 19:08 ` Rinat Muhamedgaliev via B4 Relay
  0 siblings, 0 replies; 2+ messages in thread
From: Rinat Muhamedgaliev via B4 Relay @ 2026-10-19 19:08 UTC (permalink / raw)
  To: linux-pm
  Cc: pali, sre, afd, konrad.dybcio, david, krzk, linux-arm-msm,
	linux-kernel, Rinat Muhamedgaliev

From: Rinat Muhamedgaliev <rinat.muhamedgaliev@gmail.com>

OnePlus 6 and 6T replacement battery packs may contain either a bq27411
or a bq27541 fuel gauge at I2C address 0x55. The device tree currently
identifies the gauge as bq27411, but a bq27541 uses a different register
map and then reports invalid battery values.

During setup, query the DeviceType control subcommand for bq27411 and
bq27541. Keep the profile whose DeviceType matches the compatible, or
switch to the profile returned by the fuel gauge. This retains the
established DT ABI and supports replacement packs without introducing a
generic compatible.

Keep this logic in the bus-neutral core so it uses the existing register
maps and control-register access helpers.

Tested on OnePlus 6T (fajita) with DeviceType 0x0541: voltage, state of
charge, and temperature were reported correctly. Testing on hardware with
DeviceType 0x0421 would be appreciated.

Signed-off-by: Rinat Muhamedgaliev <rinat.muhamedgaliev@gmail.com>
---
 drivers/power/supply/bq27xxx_battery.c | 61 ++++++++++++++++++++++++++++++++++
 1 file changed, 61 insertions(+)

diff --git a/drivers/power/supply/bq27xxx_battery.c b/drivers/power/supply/bq27xxx_battery.c
index 8bf048fbd36a..57b51348ff2b 100644
--- a/drivers/power/supply/bq27xxx_battery.c
+++ b/drivers/power/supply/bq27xxx_battery.c
@@ -86,6 +86,10 @@
 #define BQ27XXX_SET_CFGUPDATE		0x13
 #define BQ27XXX_SOFT_RESET		0x42
 #define BQ27XXX_RESET			0x41
+#define BQ27XXX_DEVICE_TYPE		0x0001
+
+#define BQ27411_DEVICE_TYPE		0x0421
+#define BQ27541_DEVICE_TYPE		0x0541
 
 #define BQ27XXX_RS			(20) /* Resistor sense mOhm */
 #define BQ27XXX_POWER_CONSTANT		(29200) /* 29.2 µV^2 * 1000 */
@@ -1141,6 +1145,56 @@ static inline int bq27xxx_write(struct bq27xxx_device_info *di, int reg_index,
 	return ret;
 }
 
+static int bq27xxx_battery_check_device_type(struct bq27xxx_device_info *di)
+{
+	enum bq27xxx_chip detected_chip;
+	int expected_type;
+	int ret;
+
+	/* Add fuel gauges with supported DeviceType reporting to this list. */
+	switch (di->chip) {
+	case BQ27411:
+		expected_type = BQ27411_DEVICE_TYPE;
+		break;
+	case BQ27541:
+		expected_type = BQ27541_DEVICE_TYPE;
+		break;
+	default:
+		return 0;
+	}
+
+	ret = bq27xxx_write(di, BQ27XXX_REG_CTRL, BQ27XXX_DEVICE_TYPE,
+			    false);
+	if (ret < 0)
+		return ret;
+
+	ret = bq27xxx_read(di, BQ27XXX_REG_CTRL, false);
+	if (ret < 0)
+		return ret;
+
+	switch (ret) {
+	case BQ27411_DEVICE_TYPE:
+		detected_chip = BQ27411;
+		break;
+	case BQ27541_DEVICE_TYPE:
+		detected_chip = BQ27541;
+		break;
+	default:
+		dev_err(di->dev, "unrecognized DeviceType 0x%04x\n", ret);
+		return -ENODEV;
+	}
+
+	if (detected_chip == di->chip)
+		return 0;
+
+	dev_warn(di->dev,
+		 "detected DeviceType 0x%04x instead of expected 0x%04x\n",
+		 ret, expected_type);
+	di->chip = detected_chip;
+
+	return 0;
+}
+
 static inline int bq27xxx_read_block(struct bq27xxx_device_info *di, int reg_index,
 				     u8 *data, int len)
 {
@@ -2089,10 +2143,17 @@ int bq27xxx_battery_setup(struct bq27xxx_device_info *di)
 		.of_node = di->dev->of_node,
 		.drv_data = di,
 	};
+	int ret;
 
 	INIT_DELAYED_WORK(&di->work, bq27xxx_battery_poll);
 	mutex_init(&di->lock);
 
+	di->regs       = bq27xxx_chip_data[di->chip].regs;
+
+	ret = bq27xxx_battery_check_device_type(di);
+	if (ret)
+		return ret;
+
 	di->regs       = bq27xxx_chip_data[di->chip].regs;
 	di->unseal_key = bq27xxx_chip_data[di->chip].unseal_key;
 	di->dm_regs    = bq27xxx_chip_data[di->chip].dm_regs;

-- 
2.56.0



^ permalink raw reply related	[flat|nested] 2+ messages in thread

end of thread, other threads:[~2026-10-19 19:08 UTC | newest]

Thread overview: 2+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-10-19 19:08 [PATCH v8] bq27xxx: support interchangeable OnePlus 6/6T fuel gauges Rinat Muhamedgaliev via B4 Relay
2026-10-19 19:08 ` [PATCH v8] power: supply: bq27xxx: detect bq27541 behind bq27411 compatible Rinat Muhamedgaliev via B4 Relay

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox