1 // SPDX-License-Identifier: GPL-2.0-only 2 /* 3 * Driver for Texas Instruments INA238 power monitor chip 4 * Datasheet: https://www.ti.com/product/ina238 5 * 6 * Copyright (C) 2021 Nathan Rossi <nathan.rossi@digi.com> 7 */ 8 9 #include <linux/bitops.h> 10 #include <linux/err.h> 11 #include <linux/hwmon.h> 12 #include <linux/i2c.h> 13 #include <linux/init.h> 14 #include <linux/kernel.h> 15 #include <linux/module.h> 16 #include <linux/of.h> 17 #include <linux/regmap.h> 18 19 /* INA238 register definitions */ 20 #define INA238_CONFIG 0x0 21 #define INA238_ADC_CONFIG 0x1 22 #define INA238_SHUNT_CALIBRATION 0x2 23 #define SQ52206_SHUNT_TEMPCO 0x3 24 #define INA238_SHUNT_VOLTAGE 0x4 25 #define INA238_BUS_VOLTAGE 0x5 26 #define INA238_DIE_TEMP 0x6 27 #define INA238_CURRENT 0x7 28 #define INA238_POWER 0x8 29 #define SQ52206_ENERGY 0x9 30 #define SQ52206_CHARGE 0xa 31 #define INA238_DIAG_ALERT 0xb 32 #define INA238_SHUNT_OVER_VOLTAGE 0xc 33 #define INA238_SHUNT_UNDER_VOLTAGE 0xd 34 #define INA238_BUS_OVER_VOLTAGE 0xe 35 #define INA238_BUS_UNDER_VOLTAGE 0xf 36 #define INA238_TEMP_LIMIT 0x10 37 #define INA238_POWER_LIMIT 0x11 38 #define SQ52206_POWER_PEAK 0x20 39 #define INA238_DEVICE_ID 0x3f /* not available on INA237 */ 40 41 #define INA238_CONFIG_ADCRANGE BIT(4) 42 #define SQ52206_CONFIG_ADCRANGE_HIGH BIT(4) 43 #define SQ52206_CONFIG_ADCRANGE_LOW BIT(3) 44 45 #define INA238_DIAG_ALERT_TMPOL BIT(7) 46 #define INA238_DIAG_ALERT_SHNTOL BIT(6) 47 #define INA238_DIAG_ALERT_SHNTUL BIT(5) 48 #define INA238_DIAG_ALERT_BUSOL BIT(4) 49 #define INA238_DIAG_ALERT_BUSUL BIT(3) 50 #define INA238_DIAG_ALERT_POL BIT(2) 51 52 #define INA238_REGISTERS 0x20 53 54 #define INA238_RSHUNT_DEFAULT 2500 /* uOhm */ 55 56 /* Default configuration of device on reset. */ 57 #define INA238_CONFIG_DEFAULT 0 58 #define SQ52206_CONFIG_DEFAULT 0x0005 59 /* 16 sample averaging, 1052us conversion time, continuous mode */ 60 #define INA238_ADC_CONFIG_DEFAULT 0xfb6a 61 /* Configure alerts to be based on averaged value (SLOWALERT) */ 62 #define INA238_DIAG_ALERT_DEFAULT 0x2000 63 #define INA238_DIAG_ALERT_APOL BIT(12) 64 /* 65 * This driver uses a fixed calibration value in order to scale current/power 66 * based on a fixed shunt resistor value. This allows for conversion within the 67 * device to avoid integer limits whilst current/power accuracy is scaled 68 * relative to the shunt resistor value within the driver. This is similar to 69 * how the ina2xx driver handles current/power scaling. 70 * 71 * To achieve the best possible dynamic range, the value of the shunt voltage 72 * register should match the value of the current register. With that, the shunt 73 * voltage of 0x7fff = 32,767 uV = 163,785 uV matches the maximum current, 74 * and no accuracy is lost. Experiments with a real chip show that this is 75 * achieved by setting the SHUNT_CAL register to a value of 0x1000 = 4,096. 76 * Per datasheet, 77 * SHUNT_CAL = 819.2 x 10^6 x CURRENT_LSB x Rshunt 78 * = 819,200,000 x CURRENT_LSB x Rshunt 79 * With SHUNT_CAL set to 4,096, we get 80 * CURRENT_LSB = 4,096 / (819,200,000 x Rshunt) 81 * Assuming an Rshunt value of 5 mOhm, we get 82 * CURRENT_LSB = 4,096 / (819,200,000 x 0.005) = 1mA 83 * and thus a dynamic range of 1mA ... 32,767mA, which is sufficient for most 84 * applications. The actual dynamic range is of course determined by the actual 85 * shunt resistor value. 86 * 87 * Power and energy values are scaled accordingly. 88 */ 89 #define INA238_CALIBRATION_VALUE 4096 90 #define INA238_FIXED_SHUNT 5000 91 92 #define INA238_SHUNT_VOLTAGE_LSB 5000 /* 5 uV/lsb, in nV */ 93 #define INA238_BUS_VOLTAGE_LSB 3125000 /* 3.125 mV/lsb, in nV */ 94 #define SQ52206_BUS_VOLTAGE_LSB 3750000 /* 3.75 mV/lsb, in nV */ 95 96 #define NUNIT_PER_MUNIT 1000000 /* n[AV] -> m[AV] */ 97 98 static const struct regmap_config ina238_regmap_config = { 99 .max_register = INA238_REGISTERS, 100 .reg_bits = 8, 101 .val_bits = 16, 102 }; 103 104 enum ina238_ids { ina228, ina237, ina238, ina700, ina780, sq52206 }; 105 106 struct ina238_config { 107 bool has_20bit_voltage_current; /* vshunt, vbus and current are 20-bit fields */ 108 bool has_power_highest; /* chip detection power peak */ 109 bool has_energy; /* chip detection energy */ 110 u8 temp_resolution; /* temperature register resolution in bit */ 111 u16 config_default; /* Power-on default state */ 112 u32 power_calculate_factor; /* fixed parameter for power calculation, from datasheet */ 113 u32 bus_voltage_lsb; /* bus voltage LSB, in nV */ 114 int current_lsb; /* current LSB, in uA */ 115 }; 116 117 struct ina238_data { 118 const struct ina238_config *config; 119 struct i2c_client *client; 120 struct regmap *regmap; 121 u32 rshunt; 122 int gain; 123 u32 voltage_lsb[2]; /* shunt, bus voltage LSB, in nV */ 124 int current_lsb; /* current LSB, in uA */ 125 int power_lsb; /* power LSB, in uW */ 126 int energy_lsb; /* energy LSB, in uJ */ 127 }; 128 129 static const struct ina238_config ina238_config[] = { 130 [ina228] = { 131 .has_20bit_voltage_current = true, 132 .has_energy = true, 133 .has_power_highest = false, 134 .power_calculate_factor = 20, 135 .config_default = INA238_CONFIG_DEFAULT, 136 .bus_voltage_lsb = INA238_BUS_VOLTAGE_LSB, 137 .temp_resolution = 16, 138 }, 139 [ina237] = { 140 .has_20bit_voltage_current = false, 141 .has_energy = false, 142 .has_power_highest = false, 143 .power_calculate_factor = 20, 144 .config_default = INA238_CONFIG_DEFAULT, 145 .bus_voltage_lsb = INA238_BUS_VOLTAGE_LSB, 146 .temp_resolution = 12, 147 }, 148 [ina238] = { 149 .has_20bit_voltage_current = false, 150 .has_energy = false, 151 .has_power_highest = false, 152 .power_calculate_factor = 20, 153 .config_default = INA238_CONFIG_DEFAULT, 154 .bus_voltage_lsb = INA238_BUS_VOLTAGE_LSB, 155 .temp_resolution = 12, 156 }, 157 [ina700] = { 158 .has_20bit_voltage_current = false, 159 .has_energy = true, 160 .has_power_highest = false, 161 .power_calculate_factor = 20, 162 .config_default = INA238_CONFIG_DEFAULT, 163 .bus_voltage_lsb = INA238_BUS_VOLTAGE_LSB, 164 .temp_resolution = 12, 165 .current_lsb = 480, 166 }, 167 [ina780] = { 168 .has_20bit_voltage_current = false, 169 .has_energy = true, 170 .has_power_highest = false, 171 .power_calculate_factor = 20, 172 .config_default = INA238_CONFIG_DEFAULT, 173 .bus_voltage_lsb = INA238_BUS_VOLTAGE_LSB, 174 .temp_resolution = 12, 175 .current_lsb = 2400, 176 }, 177 [sq52206] = { 178 .has_20bit_voltage_current = false, 179 .has_energy = true, 180 .has_power_highest = true, 181 .power_calculate_factor = 24, 182 .config_default = SQ52206_CONFIG_DEFAULT, 183 .bus_voltage_lsb = SQ52206_BUS_VOLTAGE_LSB, 184 .temp_resolution = 16, 185 }, 186 }; 187 188 static int ina238_read_reg24(const struct i2c_client *client, u8 reg, u32 *val) 189 { 190 u8 data[3]; 191 int err; 192 193 /* 24-bit register read */ 194 err = i2c_smbus_read_i2c_block_data(client, reg, 3, data); 195 if (err < 0) 196 return err; 197 if (err != 3) 198 return -EIO; 199 *val = (data[0] << 16) | (data[1] << 8) | data[2]; 200 201 return 0; 202 } 203 204 static int ina238_read_reg40(const struct i2c_client *client, u8 reg, u64 *val) 205 { 206 u8 data[5]; 207 u32 low; 208 int err; 209 210 /* 40-bit register read */ 211 err = i2c_smbus_read_i2c_block_data(client, reg, 5, data); 212 if (err < 0) 213 return err; 214 if (err != 5) 215 return -EIO; 216 low = (data[1] << 24) | (data[2] << 16) | (data[3] << 8) | data[4]; 217 *val = ((long long)data[0] << 32) | low; 218 219 return 0; 220 } 221 222 static int ina238_read_field_s20(const struct i2c_client *client, u8 reg, s32 *val) 223 { 224 u32 regval; 225 int err; 226 227 err = ina238_read_reg24(client, reg, ®val); 228 if (err) 229 return err; 230 231 /* bits 3-0 Reserved, always zero */ 232 regval >>= 4; 233 234 *val = sign_extend32(regval, 19); 235 236 return 0; 237 } 238 239 static int ina228_read_voltage(struct ina238_data *data, int channel, long *val) 240 { 241 int reg = channel ? INA238_BUS_VOLTAGE : INA238_CURRENT; 242 u32 lsb = data->voltage_lsb[channel]; 243 u32 factor = NUNIT_PER_MUNIT; 244 int err, regval; 245 246 if (data->config->has_20bit_voltage_current) { 247 err = ina238_read_field_s20(data->client, reg, ®val); 248 if (err) 249 return err; 250 /* Adjust accuracy: LSB in units of 500 pV */ 251 lsb /= 8; 252 factor *= 2; 253 } else { 254 err = regmap_read(data->regmap, reg, ®val); 255 if (err) 256 return err; 257 regval = (s16)regval; 258 } 259 260 *val = DIV_S64_ROUND_CLOSEST((s64)regval * lsb, factor); 261 return 0; 262 } 263 264 static int ina238_read_in(struct device *dev, u32 attr, int channel, 265 long *val) 266 { 267 struct ina238_data *data = dev_get_drvdata(dev); 268 int reg, mask = 0; 269 int regval; 270 int err; 271 272 if (attr == hwmon_in_input) 273 return ina228_read_voltage(data, channel, val); 274 275 switch (channel) { 276 case 0: 277 switch (attr) { 278 case hwmon_in_max: 279 reg = INA238_SHUNT_OVER_VOLTAGE; 280 break; 281 case hwmon_in_min: 282 reg = INA238_SHUNT_UNDER_VOLTAGE; 283 break; 284 case hwmon_in_max_alarm: 285 reg = INA238_DIAG_ALERT; 286 mask = INA238_DIAG_ALERT_SHNTOL; 287 break; 288 case hwmon_in_min_alarm: 289 reg = INA238_DIAG_ALERT; 290 mask = INA238_DIAG_ALERT_SHNTUL; 291 break; 292 default: 293 return -EOPNOTSUPP; 294 } 295 break; 296 case 1: 297 switch (attr) { 298 case hwmon_in_max: 299 reg = INA238_BUS_OVER_VOLTAGE; 300 break; 301 case hwmon_in_min: 302 reg = INA238_BUS_UNDER_VOLTAGE; 303 break; 304 case hwmon_in_max_alarm: 305 reg = INA238_DIAG_ALERT; 306 mask = INA238_DIAG_ALERT_BUSOL; 307 break; 308 case hwmon_in_min_alarm: 309 reg = INA238_DIAG_ALERT; 310 mask = INA238_DIAG_ALERT_BUSUL; 311 break; 312 default: 313 return -EOPNOTSUPP; 314 } 315 break; 316 default: 317 return -EOPNOTSUPP; 318 } 319 320 err = regmap_read(data->regmap, reg, ®val); 321 if (err < 0) 322 return err; 323 324 if (mask) 325 *val = !!(regval & mask); 326 else 327 *val = DIV_S64_ROUND_CLOSEST((s64)(s16)regval * data->voltage_lsb[channel], 328 NUNIT_PER_MUNIT); 329 330 return 0; 331 } 332 333 static int ina238_write_in(struct device *dev, u32 attr, int channel, long val) 334 { 335 struct ina238_data *data = dev_get_drvdata(dev); 336 static const int low_limits[2] = {-164, 0}; 337 static const int high_limits[2] = {164, 150000}; 338 static const u8 low_regs[2] = {INA238_SHUNT_UNDER_VOLTAGE, INA238_BUS_UNDER_VOLTAGE}; 339 static const u8 high_regs[2] = {INA238_SHUNT_OVER_VOLTAGE, INA238_BUS_OVER_VOLTAGE}; 340 int regval; 341 342 /* Initial clamp to avoid overflows */ 343 val = clamp_val(val, low_limits[channel], high_limits[channel]); 344 val = DIV_S64_ROUND_CLOSEST((s64)val * NUNIT_PER_MUNIT, data->voltage_lsb[channel]); 345 /* Final clamp to register limits */ 346 regval = clamp_val(val, S16_MIN, S16_MAX) & 0xffff; 347 348 switch (attr) { 349 case hwmon_in_min: 350 return regmap_write(data->regmap, low_regs[channel], regval); 351 case hwmon_in_max: 352 return regmap_write(data->regmap, high_regs[channel], regval); 353 default: 354 return -EOPNOTSUPP; 355 } 356 } 357 358 static int __ina238_read_curr(struct ina238_data *data, long *val) 359 { 360 u32 lsb = data->current_lsb; 361 int err, regval; 362 363 if (data->config->has_20bit_voltage_current) { 364 err = ina238_read_field_s20(data->client, INA238_CURRENT, ®val); 365 if (err) 366 return err; 367 lsb /= 16; /* Adjust accuracy */ 368 } else { 369 err = regmap_read(data->regmap, INA238_CURRENT, ®val); 370 if (err) 371 return err; 372 regval = (s16)regval; 373 } 374 375 *val = DIV_S64_ROUND_CLOSEST((s64)regval * lsb, 1000); 376 return 0; 377 } 378 379 static int ina238_read_curr(struct device *dev, u32 attr, long *val) 380 { 381 struct ina238_data *data = dev_get_drvdata(dev); 382 int reg, mask = 0; 383 int regval; 384 int err; 385 386 if (attr == hwmon_curr_input) 387 return __ina238_read_curr(data, val); 388 389 switch (attr) { 390 case hwmon_curr_min: 391 reg = INA238_SHUNT_UNDER_VOLTAGE; 392 break; 393 case hwmon_curr_min_alarm: 394 reg = INA238_DIAG_ALERT; 395 mask = INA238_DIAG_ALERT_SHNTUL; 396 break; 397 case hwmon_curr_max: 398 reg = INA238_SHUNT_OVER_VOLTAGE; 399 break; 400 case hwmon_curr_max_alarm: 401 reg = INA238_DIAG_ALERT; 402 mask = INA238_DIAG_ALERT_SHNTOL; 403 break; 404 default: 405 return -EOPNOTSUPP; 406 } 407 408 err = regmap_read(data->regmap, reg, ®val); 409 if (err < 0) 410 return err; 411 412 if (mask) 413 *val = !!(regval & mask); 414 else 415 *val = DIV_S64_ROUND_CLOSEST((s64)(s16)regval * data->current_lsb, 1000); 416 417 return 0; 418 } 419 420 static int ina238_write_curr(struct device *dev, u32 attr, long val) 421 { 422 struct ina238_data *data = dev_get_drvdata(dev); 423 int regval; 424 425 /* Set baseline range to avoid over/underflows */ 426 val = clamp_val(val, -1000000, 1000000); 427 /* Scale */ 428 val = DIV_ROUND_CLOSEST(val * 1000, data->current_lsb); 429 /* Clamp to register size */ 430 regval = clamp_val(val, S16_MIN, S16_MAX) & 0xffff; 431 432 switch (attr) { 433 case hwmon_curr_min: 434 return regmap_write(data->regmap, INA238_SHUNT_UNDER_VOLTAGE, 435 regval); 436 case hwmon_curr_max: 437 return regmap_write(data->regmap, INA238_SHUNT_OVER_VOLTAGE, 438 regval); 439 default: 440 return -EOPNOTSUPP; 441 } 442 } 443 444 static int ina238_read_power(struct device *dev, u32 attr, long *val) 445 { 446 struct ina238_data *data = dev_get_drvdata(dev); 447 long long power; 448 int regval; 449 int err; 450 451 switch (attr) { 452 case hwmon_power_input: 453 err = ina238_read_reg24(data->client, INA238_POWER, ®val); 454 if (err) 455 return err; 456 457 power = (long long)regval * data->power_lsb; 458 /* Clamp value to maximum value of long */ 459 *val = clamp_val(power, 0, LONG_MAX); 460 break; 461 case hwmon_power_input_highest: 462 err = ina238_read_reg24(data->client, SQ52206_POWER_PEAK, ®val); 463 if (err) 464 return err; 465 466 power = (long long)regval * data->power_lsb; 467 /* Clamp value to maximum value of long */ 468 *val = clamp_val(power, 0, LONG_MAX); 469 break; 470 case hwmon_power_max: 471 err = regmap_read(data->regmap, INA238_POWER_LIMIT, ®val); 472 if (err) 473 return err; 474 475 /* 476 * Truncated 24-bit compare register, lower 8-bits are 477 * truncated. Same conversion to/from uW as POWER register. 478 */ 479 power = ((long long)regval << 8) * data->power_lsb; 480 /* Clamp value to maximum value of long */ 481 *val = clamp_val(power, 0, LONG_MAX); 482 break; 483 case hwmon_power_max_alarm: 484 err = regmap_read(data->regmap, INA238_DIAG_ALERT, ®val); 485 if (err) 486 return err; 487 488 *val = !!(regval & INA238_DIAG_ALERT_POL); 489 break; 490 default: 491 return -EOPNOTSUPP; 492 } 493 494 return 0; 495 } 496 497 static int ina238_write_power_max(struct device *dev, long val) 498 { 499 struct ina238_data *data = dev_get_drvdata(dev); 500 501 /* 502 * Unsigned postive values. Compared against the 24-bit power register, 503 * lower 8-bits are truncated. Same conversion to/from uW as POWER 504 * register. 505 * The first clamp_val() is to establish a baseline to avoid overflows. 506 */ 507 val = clamp_val(val, 0, LONG_MAX / 2); 508 val = DIV_ROUND_CLOSEST(val, data->power_lsb); 509 val = clamp_val(val >> 8, 0, U16_MAX); 510 511 return regmap_write(data->regmap, INA238_POWER_LIMIT, val); 512 } 513 514 static int ina238_temp_from_reg(s16 regval, u8 resolution) 515 { 516 return ((regval >> (16 - resolution)) * 1000) >> (resolution - 9); 517 } 518 519 static int ina238_read_temp(struct device *dev, u32 attr, long *val) 520 { 521 struct ina238_data *data = dev_get_drvdata(dev); 522 int regval; 523 int err; 524 525 switch (attr) { 526 case hwmon_temp_input: 527 err = regmap_read(data->regmap, INA238_DIE_TEMP, ®val); 528 if (err) 529 return err; 530 *val = ina238_temp_from_reg(regval, data->config->temp_resolution); 531 break; 532 case hwmon_temp_max: 533 err = regmap_read(data->regmap, INA238_TEMP_LIMIT, ®val); 534 if (err) 535 return err; 536 /* Signed, result in mC */ 537 *val = ina238_temp_from_reg(regval, data->config->temp_resolution); 538 break; 539 case hwmon_temp_max_alarm: 540 err = regmap_read(data->regmap, INA238_DIAG_ALERT, ®val); 541 if (err) 542 return err; 543 544 *val = !!(regval & INA238_DIAG_ALERT_TMPOL); 545 break; 546 default: 547 return -EOPNOTSUPP; 548 } 549 550 return 0; 551 } 552 553 static u16 ina238_temp_to_reg(long val, u8 resolution) 554 { 555 int fraction = 1000 - DIV_ROUND_CLOSEST(1000, BIT(resolution - 9)); 556 557 val = clamp_val(val, -255000 - fraction, 255000 + fraction); 558 559 return (DIV_ROUND_CLOSEST(val << (resolution - 9), 1000) << (16 - resolution)) & 0xffff; 560 } 561 562 static int ina238_write_temp_max(struct device *dev, long val) 563 { 564 struct ina238_data *data = dev_get_drvdata(dev); 565 int regval; 566 567 regval = ina238_temp_to_reg(val, data->config->temp_resolution); 568 return regmap_write(data->regmap, INA238_TEMP_LIMIT, regval); 569 } 570 571 static int ina238_read_energy(struct device *dev, s64 *energy) 572 { 573 struct ina238_data *data = dev_get_drvdata(dev); 574 u64 regval; 575 int ret; 576 577 ret = ina238_read_reg40(data->client, SQ52206_ENERGY, ®val); 578 if (ret) 579 return ret; 580 581 /* result in uJ */ 582 *energy = regval * data->energy_lsb; 583 return 0; 584 } 585 586 static int ina238_read(struct device *dev, enum hwmon_sensor_types type, 587 u32 attr, int channel, long *val) 588 { 589 switch (type) { 590 case hwmon_in: 591 return ina238_read_in(dev, attr, channel, val); 592 case hwmon_curr: 593 return ina238_read_curr(dev, attr, val); 594 case hwmon_power: 595 return ina238_read_power(dev, attr, val); 596 case hwmon_energy64: 597 return ina238_read_energy(dev, (s64 *)val); 598 case hwmon_temp: 599 return ina238_read_temp(dev, attr, val); 600 default: 601 return -EOPNOTSUPP; 602 } 603 return 0; 604 } 605 606 static int ina238_write(struct device *dev, enum hwmon_sensor_types type, 607 u32 attr, int channel, long val) 608 { 609 switch (type) { 610 case hwmon_in: 611 return ina238_write_in(dev, attr, channel, val); 612 case hwmon_curr: 613 return ina238_write_curr(dev, attr, val); 614 case hwmon_power: 615 return ina238_write_power_max(dev, val); 616 case hwmon_temp: 617 return ina238_write_temp_max(dev, val); 618 default: 619 return -EOPNOTSUPP; 620 } 621 } 622 623 static umode_t ina238_is_visible(const void *drvdata, 624 enum hwmon_sensor_types type, 625 u32 attr, int channel) 626 { 627 const struct ina238_data *data = drvdata; 628 bool has_power_highest = data->config->has_power_highest; 629 bool has_energy = data->config->has_energy; 630 631 switch (type) { 632 case hwmon_in: 633 switch (attr) { 634 case hwmon_in_input: 635 case hwmon_in_max_alarm: 636 case hwmon_in_min_alarm: 637 return 0444; 638 case hwmon_in_max: 639 case hwmon_in_min: 640 return 0644; 641 default: 642 return 0; 643 } 644 case hwmon_curr: 645 switch (attr) { 646 case hwmon_curr_input: 647 case hwmon_curr_max_alarm: 648 case hwmon_curr_min_alarm: 649 return 0444; 650 case hwmon_curr_max: 651 case hwmon_curr_min: 652 return 0644; 653 default: 654 return 0; 655 } 656 case hwmon_power: 657 switch (attr) { 658 case hwmon_power_input: 659 case hwmon_power_max_alarm: 660 return 0444; 661 case hwmon_power_max: 662 return 0644; 663 case hwmon_power_input_highest: 664 if (has_power_highest) 665 return 0444; 666 return 0; 667 default: 668 return 0; 669 } 670 case hwmon_energy64: 671 /* hwmon_energy_input */ 672 if (has_energy) 673 return 0444; 674 return 0; 675 case hwmon_temp: 676 switch (attr) { 677 case hwmon_temp_input: 678 case hwmon_temp_max_alarm: 679 return 0444; 680 case hwmon_temp_max: 681 return 0644; 682 default: 683 return 0; 684 } 685 default: 686 return 0; 687 } 688 } 689 690 #define INA238_HWMON_IN_CONFIG (HWMON_I_INPUT | \ 691 HWMON_I_MAX | HWMON_I_MAX_ALARM | \ 692 HWMON_I_MIN | HWMON_I_MIN_ALARM) 693 694 static const struct hwmon_channel_info * const ina238_info[] = { 695 HWMON_CHANNEL_INFO(in, 696 /* 0: shunt voltage */ 697 INA238_HWMON_IN_CONFIG, 698 /* 1: bus voltage */ 699 INA238_HWMON_IN_CONFIG), 700 HWMON_CHANNEL_INFO(curr, 701 /* 0: current through shunt */ 702 HWMON_C_INPUT | HWMON_C_MIN | HWMON_C_MIN_ALARM | 703 HWMON_C_MAX | HWMON_C_MAX_ALARM), 704 HWMON_CHANNEL_INFO(power, 705 /* 0: power */ 706 HWMON_P_INPUT | HWMON_P_MAX | 707 HWMON_P_MAX_ALARM | HWMON_P_INPUT_HIGHEST), 708 HWMON_CHANNEL_INFO(energy64, 709 HWMON_E_INPUT), 710 HWMON_CHANNEL_INFO(temp, 711 /* 0: die temperature */ 712 HWMON_T_INPUT | HWMON_T_MAX | HWMON_T_MAX_ALARM), 713 NULL 714 }; 715 716 static const struct hwmon_ops ina238_hwmon_ops = { 717 .is_visible = ina238_is_visible, 718 .read = ina238_read, 719 .write = ina238_write, 720 }; 721 722 static const struct hwmon_chip_info ina238_chip_info = { 723 .ops = &ina238_hwmon_ops, 724 .info = ina238_info, 725 }; 726 727 static int ina238_probe(struct i2c_client *client) 728 { 729 struct device *dev = &client->dev; 730 struct device *hwmon_dev; 731 struct ina238_data *data; 732 enum ina238_ids chip; 733 int config; 734 int ret; 735 736 chip = (uintptr_t)i2c_get_match_data(client); 737 738 data = devm_kzalloc(dev, sizeof(*data), GFP_KERNEL); 739 if (!data) 740 return -ENOMEM; 741 742 data->client = client; 743 /* set the device type */ 744 data->config = &ina238_config[chip]; 745 746 data->regmap = devm_regmap_init_i2c(client, &ina238_regmap_config); 747 if (IS_ERR(data->regmap)) { 748 dev_err(dev, "failed to allocate register map\n"); 749 return PTR_ERR(data->regmap); 750 } 751 752 /* Setup CONFIG register */ 753 config = data->config->config_default; 754 if (data->config->current_lsb) { 755 data->voltage_lsb[0] = INA238_SHUNT_VOLTAGE_LSB; 756 data->current_lsb = data->config->current_lsb; 757 } else { 758 /* load shunt value */ 759 if (device_property_read_u32(dev, "shunt-resistor", &data->rshunt) < 0) 760 data->rshunt = INA238_RSHUNT_DEFAULT; 761 if (data->rshunt == 0) { 762 dev_err(dev, "invalid shunt resister value %u\n", data->rshunt); 763 return -EINVAL; 764 } 765 766 /* load shunt gain value */ 767 if (device_property_read_u32(dev, "ti,shunt-gain", &data->gain) < 0) 768 data->gain = 4; /* Default of ADCRANGE = 0 */ 769 if (data->gain != 1 && data->gain != 2 && data->gain != 4) { 770 dev_err(dev, "invalid shunt gain value %u\n", data->gain); 771 return -EINVAL; 772 } 773 774 /* Setup SHUNT_CALIBRATION register with fixed value */ 775 ret = regmap_write(data->regmap, INA238_SHUNT_CALIBRATION, 776 INA238_CALIBRATION_VALUE); 777 if (ret < 0) { 778 dev_err(dev, "error configuring the device: %d\n", ret); 779 return -ENODEV; 780 } 781 if (chip == sq52206) { 782 if (data->gain == 1) /* ADCRANGE = 10/11 is /1 */ 783 config |= SQ52206_CONFIG_ADCRANGE_HIGH; 784 else if (data->gain == 2) /* ADCRANGE = 01 is /2 */ 785 config |= SQ52206_CONFIG_ADCRANGE_LOW; 786 } else if (data->gain == 1) { /* ADCRANGE = 1 is /1 */ 787 config |= INA238_CONFIG_ADCRANGE; 788 } 789 data->voltage_lsb[0] = INA238_SHUNT_VOLTAGE_LSB * data->gain / 4; 790 data->current_lsb = DIV_U64_ROUND_CLOSEST(250ULL * INA238_FIXED_SHUNT * data->gain, 791 data->rshunt); 792 } 793 794 ret = regmap_write(data->regmap, INA238_CONFIG, config); 795 if (ret < 0) { 796 dev_err(dev, "error configuring the device: %d\n", ret); 797 return -ENODEV; 798 } 799 800 /* Setup ADC_CONFIG register */ 801 ret = regmap_write(data->regmap, INA238_ADC_CONFIG, 802 INA238_ADC_CONFIG_DEFAULT); 803 if (ret < 0) { 804 dev_err(dev, "error configuring the device: %d\n", ret); 805 return -ENODEV; 806 } 807 808 /* Setup alert/alarm configuration */ 809 config = INA238_DIAG_ALERT_DEFAULT; 810 if (device_property_read_bool(dev, "ti,alert-polarity-active-high")) 811 config |= INA238_DIAG_ALERT_APOL; 812 813 ret = regmap_write(data->regmap, INA238_DIAG_ALERT, config); 814 if (ret < 0) { 815 dev_err(dev, "error configuring the device: %d\n", ret); 816 return -ENODEV; 817 } 818 819 data->voltage_lsb[1] = data->config->bus_voltage_lsb; 820 821 data->power_lsb = DIV_ROUND_CLOSEST(data->current_lsb * 822 data->config->power_calculate_factor, 823 100); 824 825 data->energy_lsb = data->power_lsb * 16; 826 827 hwmon_dev = devm_hwmon_device_register_with_info(dev, client->name, data, 828 &ina238_chip_info, NULL); 829 if (IS_ERR(hwmon_dev)) 830 return PTR_ERR(hwmon_dev); 831 832 if (data->rshunt) 833 dev_info(dev, "power monitor %s (Rshunt = %u uOhm, gain = %u)\n", 834 client->name, data->rshunt, data->gain); 835 836 return 0; 837 } 838 839 static const struct i2c_device_id ina238_id[] = { 840 { "ina228", ina228 }, 841 { "ina237", ina237 }, 842 { "ina238", ina238 }, 843 { "ina700", ina700 }, 844 { "ina780", ina780 }, 845 { "sq52206", sq52206 }, 846 { } 847 }; 848 MODULE_DEVICE_TABLE(i2c, ina238_id); 849 850 static const struct of_device_id __maybe_unused ina238_of_match[] = { 851 { 852 .compatible = "ti,ina228", 853 .data = (void *)ina228 854 }, 855 { 856 .compatible = "ti,ina237", 857 .data = (void *)ina237 858 }, 859 { 860 .compatible = "ti,ina238", 861 .data = (void *)ina238 862 }, 863 { 864 .compatible = "ti,ina700", 865 .data = (void *)ina700 866 }, 867 { 868 .compatible = "ti,ina780", 869 .data = (void *)ina780 870 }, 871 { 872 .compatible = "silergy,sq52206", 873 .data = (void *)sq52206 874 }, 875 { } 876 }; 877 MODULE_DEVICE_TABLE(of, ina238_of_match); 878 879 static struct i2c_driver ina238_driver = { 880 .driver = { 881 .name = "ina238", 882 .of_match_table = of_match_ptr(ina238_of_match), 883 }, 884 .probe = ina238_probe, 885 .id_table = ina238_id, 886 }; 887 888 module_i2c_driver(ina238_driver); 889 890 MODULE_AUTHOR("Nathan Rossi <nathan.rossi@digi.com>"); 891 MODULE_DESCRIPTION("ina238 driver"); 892 MODULE_LICENSE("GPL"); 893