mirror of
https://github.com/tinygo-org/drivers.git
synced 2026-07-26 02:28:41 +00:00
@@ -0,0 +1,29 @@
|
||||
package main
|
||||
|
||||
import (
|
||||
"machine"
|
||||
"time"
|
||||
|
||||
"tinygo.org/x/drivers/ina219"
|
||||
)
|
||||
|
||||
func main() {
|
||||
machine.I2C0.Configure(machine.I2CConfig{})
|
||||
|
||||
dev := ina219.New(machine.I2C0)
|
||||
dev.Configure()
|
||||
|
||||
for {
|
||||
busVoltage, shuntVoltage, current, power, err := dev.Measurements()
|
||||
if err != nil {
|
||||
println("Error reading measurements", err)
|
||||
}
|
||||
|
||||
println("Bus Voltage:", busVoltage, "V")
|
||||
println("Shunt Voltage:", shuntVoltage/100, "mV")
|
||||
println("Current:", current, "mA")
|
||||
println("Power:", power, "mW")
|
||||
|
||||
time.Sleep(10 * time.Millisecond)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,183 @@
|
||||
package ina219
|
||||
|
||||
type Config struct {
|
||||
// BusVoltageRange sets the bus voltage range.
|
||||
BusVoltageRange BusVoltageRange
|
||||
|
||||
// PGA sets the programmable gain amplifier.
|
||||
PGA PGA
|
||||
|
||||
// BusADC sets the bus ADC resolution.
|
||||
BusADC BusADC
|
||||
|
||||
// ShuntADC sets the shunt ADC resolution.
|
||||
ShuntADC ShuntADC
|
||||
|
||||
// Mode sets the operating mode.
|
||||
Mode Mode
|
||||
|
||||
// Calibration sets the calibration value for the expected
|
||||
// voltage and current values.
|
||||
Calibration Calibration
|
||||
|
||||
// 1000 / uA per bit
|
||||
CurrentDivider float32
|
||||
|
||||
// 1mW per bit
|
||||
PowerMultiplier float32
|
||||
}
|
||||
|
||||
// RegisterValue returns the register value of the configuration.
|
||||
func (c *Config) RegisterValue() uint16 {
|
||||
return c.BusVoltageRange.RegisterValue() |
|
||||
c.PGA.RegisterValue() |
|
||||
c.BusADC.RegisterValue() |
|
||||
c.ShuntADC.RegisterValue() |
|
||||
c.Mode.RegisterValue()
|
||||
}
|
||||
|
||||
// Generate a new configuration from a register value.
|
||||
func NewConfig(config int16, calibration int16) Config {
|
||||
return Config{
|
||||
BusVoltageRange: BusVoltageRange(config >> 13 & 0x1),
|
||||
PGA: PGA(config >> 11 & 0x3),
|
||||
BusADC: BusADC(config >> 7 & 0xF),
|
||||
ShuntADC: ShuntADC(config >> 3 & 0xF),
|
||||
Mode: Mode(config & 0x7),
|
||||
Calibration: Calibration(calibration),
|
||||
}
|
||||
}
|
||||
|
||||
// Configurations from
|
||||
// https://github.com/adafruit/Adafruit_INA219/blob/master/Adafruit_INA219.cpp
|
||||
var (
|
||||
// Config32V2A is a configuration for a 32V 2A range.
|
||||
Config32V2A = Config{
|
||||
BusVoltageRange: Range32V,
|
||||
PGA: PGA8,
|
||||
BusADC: ADC12,
|
||||
ShuntADC: SADC12,
|
||||
Mode: ModeContShuntBus,
|
||||
Calibration: Calibration16V400mA,
|
||||
CurrentDivider: 10.0,
|
||||
PowerMultiplier: 2.0,
|
||||
}
|
||||
|
||||
// Config32V1A is a configuration for a 32V 1A range.
|
||||
Config32V1A = Config{
|
||||
BusVoltageRange: Range32V,
|
||||
PGA: PGA8,
|
||||
BusADC: ADC12,
|
||||
ShuntADC: SADC12,
|
||||
Mode: ModeContShuntBus,
|
||||
Calibration: Calibration32V1A,
|
||||
CurrentDivider: 25.0,
|
||||
PowerMultiplier: 0.8,
|
||||
}
|
||||
|
||||
// Config16V400mA is a configuration for a 16V 400mA range.
|
||||
Config16V400mA = Config{
|
||||
BusVoltageRange: Range16V,
|
||||
PGA: PGA1,
|
||||
BusADC: ADC12,
|
||||
ShuntADC: SADC12,
|
||||
Mode: ModeContShuntBus,
|
||||
Calibration: Calibration16V400mA,
|
||||
CurrentDivider: 20.0,
|
||||
PowerMultiplier: 1.0,
|
||||
}
|
||||
)
|
||||
|
||||
// BusVoltageRange is the bus voltage range.
|
||||
type BusVoltageRange int8
|
||||
|
||||
const (
|
||||
Range16V BusVoltageRange = 0 // 0-16V
|
||||
Range32V BusVoltageRange = 1 // 0-32V
|
||||
)
|
||||
|
||||
func (r BusVoltageRange) RegisterValue() uint16 {
|
||||
return uint16(r) << 13
|
||||
}
|
||||
|
||||
// PGA is the programmable gain amplifier.
|
||||
type PGA int8
|
||||
|
||||
const (
|
||||
PGA1 PGA = 0 // 40mV
|
||||
PGA2 PGA = 1 // 80mV
|
||||
PGA4 PGA = 2 // 160mV
|
||||
PGA8 PGA = 3 // 320mV
|
||||
)
|
||||
|
||||
func (p PGA) RegisterValue() uint16 {
|
||||
return uint16(p) << 11
|
||||
}
|
||||
|
||||
// BusADC is the bus ADC resolution.
|
||||
type BusADC int8
|
||||
|
||||
const (
|
||||
ADC9 BusADC = 0 // 9-bit
|
||||
ADC10 BusADC = 1 // 10-bit
|
||||
ADC11 BusADC = 2 // 11-bit
|
||||
ADC12 BusADC = 3 // 12-bit
|
||||
)
|
||||
|
||||
func (b BusADC) RegisterValue() uint16 {
|
||||
return uint16(b) << 7
|
||||
}
|
||||
|
||||
// ShuntADC is the shunt ADC resolution.
|
||||
type ShuntADC int8
|
||||
|
||||
const (
|
||||
SADC9 ShuntADC = 0 // 9-bit
|
||||
SADC10 ShuntADC = 1 // 10-bit
|
||||
SADC11 ShuntADC = 2 // 11-bit
|
||||
SADC12 ShuntADC = 3 // 12-bit
|
||||
)
|
||||
|
||||
func (s ShuntADC) RegisterValue() uint16 {
|
||||
return uint16(s) << 3
|
||||
}
|
||||
|
||||
// Mode is the operating mode.
|
||||
type Mode int8
|
||||
|
||||
const (
|
||||
ModePowerDown Mode = 0 // power-down
|
||||
ModeTrigShunt Mode = 1 // triggered shunt voltage
|
||||
ModeTrigBus Mode = 2 // triggered bus voltage
|
||||
ModeTrigShuntBus Mode = 3 // triggered shunt and bus voltage
|
||||
ModeADCOff Mode = 4 // ADC off
|
||||
ModeContShunt Mode = 5 // continuous shunt voltage
|
||||
ModeContBus Mode = 6 // continuous bus voltage
|
||||
ModeContShuntBus Mode = 7 // continuous shunt and bus voltage
|
||||
)
|
||||
|
||||
// ModeTriggered is a mask for triggered modes.
|
||||
const ModeTriggeredMask Mode = 0x4
|
||||
|
||||
// ModeTriggered returns true if the mode is a triggered mode.
|
||||
func ModeTriggered(m Mode) bool {
|
||||
return m != ModePowerDown && m&ModeTriggeredMask == 0
|
||||
}
|
||||
|
||||
func (m Mode) RegisterValue() uint16 {
|
||||
return uint16(m)
|
||||
}
|
||||
|
||||
// Calibration is the calibration register for the INA219. Values from:
|
||||
// https://github.com/adafruit/Adafruit_INA219/blob/master/Adafruit_INA219.cpp
|
||||
type Calibration uint16
|
||||
|
||||
const (
|
||||
Calibration32V2A Calibration = 4096
|
||||
Calibration32V1A Calibration = 10240
|
||||
Calibration16V400mA Calibration = 8192
|
||||
)
|
||||
|
||||
func (c Calibration) RegisterValue() uint16 {
|
||||
return uint16(c)
|
||||
}
|
||||
@@ -0,0 +1,13 @@
|
||||
package ina219
|
||||
|
||||
type ErrOverflow struct{}
|
||||
|
||||
func (e ErrOverflow) Error() string { return "overflow" }
|
||||
|
||||
type ErrNotReady struct{}
|
||||
|
||||
func (e ErrNotReady) Error() string { return "not ready" }
|
||||
|
||||
type ErrConfigMismatch struct{}
|
||||
|
||||
func (e ErrConfigMismatch) Error() string { return "config mismatch" }
|
||||
@@ -0,0 +1,202 @@
|
||||
package ina219
|
||||
|
||||
import (
|
||||
"tinygo.org/x/drivers"
|
||||
"tinygo.org/x/drivers/internal/legacy"
|
||||
)
|
||||
|
||||
// An INA219 device.
|
||||
type Device struct {
|
||||
bus drivers.I2C
|
||||
Address uint16
|
||||
config Config
|
||||
}
|
||||
|
||||
// Create a new INA219 device with the default configuration
|
||||
// and the given I2C bus at the default address.
|
||||
//
|
||||
// Set Address after New to change the address.
|
||||
//
|
||||
// Call Configure after New to write the configuration to the
|
||||
// device. If you don't call Configure, the device may have a
|
||||
// different configuration and the power divider and current
|
||||
// multiplier are probably wrong.
|
||||
func New(bus drivers.I2C) Device {
|
||||
return Device{
|
||||
bus: bus,
|
||||
Address: Address,
|
||||
config: Config32V2A,
|
||||
}
|
||||
}
|
||||
|
||||
// Set the configuration for the device. This only changes the
|
||||
// configuration in memory, not on the device. Call Configure
|
||||
// to write the configuration to the device.
|
||||
func (d *Device) SetConfig(config Config) {
|
||||
d.config = config
|
||||
}
|
||||
|
||||
// Write the current configuration to the device.
|
||||
func (d *Device) Configure() (err error) {
|
||||
if err = d.WriteRegister(
|
||||
RegConfig,
|
||||
d.config.RegisterValue(),
|
||||
); err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
if err = d.WriteRegister(
|
||||
RegCalibration,
|
||||
d.config.Calibration.RegisterValue(),
|
||||
); err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
var readConfig Config
|
||||
// make sure the configuration is read back correctly
|
||||
if readConfig, err = d.ReadConfig(); err != nil {
|
||||
return
|
||||
} else if readConfig.RegisterValue() != d.config.RegisterValue() {
|
||||
err = ErrConfigMismatch{}
|
||||
} else if readConfig.Calibration.RegisterValue() != d.config.Calibration.RegisterValue() {
|
||||
err = ErrConfigMismatch{}
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
// Trigger a conversion. This is only necessary if the device is in
|
||||
// trigger mode. In continuous mode (the default), the device will
|
||||
// automatically trigger conversions and this has no effect. See
|
||||
// config.go.
|
||||
//
|
||||
// Triggering a conversion or reading the "power" register resets
|
||||
// the conversion ready bit.
|
||||
func (d *Device) Trigger() (err error) {
|
||||
// Only trigger if the mode is one of the triggered modes.
|
||||
if ModeTriggered(d.config.Mode) {
|
||||
err = d.WriteRegister(RegConfig, d.config.RegisterValue())
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
// Measurements reads the bus voltage, shunt voltage, current, and power
|
||||
// from the device.
|
||||
func (d *Device) Measurements() (
|
||||
busVoltage int16,
|
||||
shuntVoltage int16,
|
||||
current float32,
|
||||
power float32,
|
||||
err error,
|
||||
) {
|
||||
// Attempt to read bus voltage first, so we can check for overflow
|
||||
// or conversion not ready.
|
||||
if busVoltage, err = d.BusVoltage(); err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
// Read the rest of the values, reading Power last, which resets
|
||||
// the conversion ready bit (relevant for triggered modes).
|
||||
if shuntVoltage, err = d.ShuntVoltage(); err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
if current, err = d.Current(); err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
if power, err = d.Power(); err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
// BusVoltage reads the "bus" voltage in millivolts.
|
||||
//
|
||||
// It returns an error if the value is invalid due to overflow
|
||||
// or if the conversion is not ready yet. In a continuous mode
|
||||
// there should always be a measurement available after the
|
||||
// device is ready. See above notes on Trigger.
|
||||
func (d *Device) BusVoltage() (voltage int16, err error) {
|
||||
val, err := d.ReadRegister(RegBusVoltage)
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
// The overflow bit is set, so the values are invalid.
|
||||
if val&(1<<0) != 0 {
|
||||
err = ErrOverflow{}
|
||||
return
|
||||
}
|
||||
|
||||
// The conversion is not ready yet.
|
||||
if ModeTriggered(d.config.Mode) && val&(1<<1) != 0 {
|
||||
err = ErrNotReady{}
|
||||
return
|
||||
}
|
||||
|
||||
voltage = (int16(val) >> 3) * 4
|
||||
return
|
||||
}
|
||||
|
||||
// ShuntVoltage reads the "shunt" voltage in 100ths of a millivolt.
|
||||
func (d *Device) ShuntVoltage() (voltage int16, err error) {
|
||||
return d.ReadRegister(RegShuntVoltage)
|
||||
}
|
||||
|
||||
// Current reads the current in milliamps.
|
||||
func (d *Device) Current() (current float32, err error) {
|
||||
val, err := d.ReadRegister(RegCurrent)
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
current = float32(val) / d.config.CurrentDivider
|
||||
return
|
||||
}
|
||||
|
||||
// Power reads the power in milliwatts.
|
||||
func (d *Device) Power() (power float32, err error) {
|
||||
val, err := d.ReadRegister(RegPower)
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
power = float32(val) * d.config.PowerMultiplier
|
||||
return
|
||||
}
|
||||
|
||||
// Read the configuration from the device.
|
||||
func (d *Device) ReadConfig() (config Config, err error) {
|
||||
var cfg, cal int16
|
||||
if cfg, err = d.ReadRegister(RegConfig); err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
if cal, err = d.ReadRegister(RegCalibration); err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
config = NewConfig(cfg, cal)
|
||||
return
|
||||
}
|
||||
|
||||
// Read a register from the device.
|
||||
func (d *Device) ReadRegister(reg uint8) (val int16, err error) {
|
||||
buf := make([]byte, 2)
|
||||
|
||||
err = legacy.ReadRegister(d.bus, uint8(d.Address), reg, buf)
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
val = int16(buf[0])<<8 | int16(buf[1]&0xff)
|
||||
return
|
||||
}
|
||||
|
||||
// Write to a register on the device.
|
||||
func (d *Device) WriteRegister(reg uint8, val uint16) error {
|
||||
buf := []byte{byte(val >> 8), byte(val & 0xff)}
|
||||
return legacy.WriteRegister(d.bus, uint8(d.Address), reg, buf)
|
||||
}
|
||||
@@ -0,0 +1,232 @@
|
||||
package ina219
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"testing"
|
||||
|
||||
qt "github.com/frankban/quicktest"
|
||||
"tinygo.org/x/drivers/tester"
|
||||
)
|
||||
|
||||
func TestDefaultAddress(t *testing.T) {
|
||||
c := qt.New(t)
|
||||
bus := tester.NewI2CBus(c)
|
||||
dev := New(bus)
|
||||
c.Assert(dev.Address, qt.Equals, uint16(Address))
|
||||
}
|
||||
|
||||
func TestBusVoltage(t *testing.T) {
|
||||
t.Run("valid", func(t *testing.T) {
|
||||
c := qt.New(t)
|
||||
bus := tester.NewI2CBus(c)
|
||||
fake := tester.NewI2CDevice16(c, Address)
|
||||
fake.Registers = map[uint8]uint16{
|
||||
RegBusVoltage: (4200 << 3) / 4, // 4.2V
|
||||
}
|
||||
bus.AddDevice(fake)
|
||||
|
||||
dev := New(bus)
|
||||
voltage, err := dev.BusVoltage()
|
||||
c.Assert(err, qt.IsNil)
|
||||
c.Assert(voltage, qt.Equals, int16(4200))
|
||||
})
|
||||
|
||||
t.Run("overflow", func(t *testing.T) {
|
||||
c := qt.New(t)
|
||||
bus := tester.NewI2CBus(c)
|
||||
fake := tester.NewI2CDevice16(c, Address)
|
||||
fake.Registers = map[uint8]uint16{
|
||||
RegBusVoltage: (1 >> 0), // overflow
|
||||
}
|
||||
bus.AddDevice(fake)
|
||||
|
||||
dev := New(bus)
|
||||
_, err := dev.BusVoltage()
|
||||
c.Assert(err, qt.Not(qt.IsNil))
|
||||
c.Assert(err, qt.ErrorMatches, ErrOverflow{}.Error())
|
||||
})
|
||||
|
||||
t.Run("not ready", func(t *testing.T) {
|
||||
c := qt.New(t)
|
||||
bus := tester.NewI2CBus(c)
|
||||
fake := tester.NewI2CDevice16(c, Address)
|
||||
fake.Registers = map[uint8]uint16{
|
||||
RegBusVoltage: ((4200 << 3) / 4) | (1 << 1), // not ready
|
||||
}
|
||||
bus.AddDevice(fake)
|
||||
|
||||
dev := New(bus)
|
||||
dev.config.Mode = ModeTrigBus
|
||||
_, err := dev.BusVoltage()
|
||||
c.Assert(err, qt.Not(qt.IsNil))
|
||||
c.Assert(err, qt.ErrorMatches, ErrNotReady{}.Error())
|
||||
})
|
||||
}
|
||||
|
||||
func TestShuntVoltage(t *testing.T) {
|
||||
c := qt.New(t)
|
||||
bus := tester.NewI2CBus(c)
|
||||
fake := tester.NewI2CDevice16(c, Address)
|
||||
fake.Registers = map[uint8]uint16{
|
||||
RegShuntVoltage: 0x1234,
|
||||
}
|
||||
bus.AddDevice(fake)
|
||||
|
||||
dev := New(bus)
|
||||
voltage, err := dev.ShuntVoltage()
|
||||
c.Assert(err, qt.IsNil)
|
||||
c.Assert(voltage, qt.Equals, int16(0x1234))
|
||||
}
|
||||
|
||||
func TestCurrent(t *testing.T) {
|
||||
c := qt.New(t)
|
||||
bus := tester.NewI2CBus(c)
|
||||
fake := tester.NewI2CDevice16(c, Address)
|
||||
fake.Registers = map[uint8]uint16{
|
||||
RegCurrent: 420 * 6.9, // 420mA
|
||||
}
|
||||
bus.AddDevice(fake)
|
||||
|
||||
dev := New(bus)
|
||||
dev.config.CurrentDivider = 6.9
|
||||
current, err := dev.Current()
|
||||
c.Assert(err, qt.IsNil)
|
||||
c.Assert(current, qt.Equals, float32(420))
|
||||
}
|
||||
|
||||
func TestPower(t *testing.T) {
|
||||
c := qt.New(t)
|
||||
bus := tester.NewI2CBus(c)
|
||||
fake := tester.NewI2CDevice16(c, Address)
|
||||
fake.Registers = map[uint8]uint16{
|
||||
RegPower: 420 / 0.8, // 420mW
|
||||
}
|
||||
bus.AddDevice(fake)
|
||||
|
||||
dev := New(bus)
|
||||
dev.config.PowerMultiplier = 0.8
|
||||
power, err := dev.Power()
|
||||
c.Assert(err, qt.IsNil)
|
||||
c.Assert(power, qt.Equals, float32(420))
|
||||
}
|
||||
|
||||
func TestReadConfig(t *testing.T) {
|
||||
// use the default configurations
|
||||
for _, tc := range []Config{
|
||||
Config16V400mA,
|
||||
Config32V2A,
|
||||
Config32V1A,
|
||||
} {
|
||||
n := fmt.Sprintf("%x/%x", tc.RegisterValue(), tc.Calibration.RegisterValue())
|
||||
t.Run(n, func(t *testing.T) {
|
||||
c := qt.New(t)
|
||||
bus := tester.NewI2CBus(c)
|
||||
fake := tester.NewI2CDevice16(c, Address)
|
||||
fake.Registers = map[uint8]uint16{
|
||||
RegConfig: tc.RegisterValue(),
|
||||
RegCalibration: tc.Calibration.RegisterValue(),
|
||||
}
|
||||
bus.AddDevice(fake)
|
||||
|
||||
dev := New(bus)
|
||||
config, err := dev.ReadConfig()
|
||||
c.Assert(err, qt.IsNil)
|
||||
c.Assert(config.BusADC, qt.Equals, tc.BusADC)
|
||||
c.Assert(config.BusVoltageRange, qt.Equals, tc.BusVoltageRange)
|
||||
c.Assert(config.Calibration, qt.Equals, tc.Calibration)
|
||||
c.Assert(config.Mode, qt.Equals, tc.Mode)
|
||||
c.Assert(config.PGA, qt.Equals, tc.PGA)
|
||||
c.Assert(config.ShuntADC, qt.Equals, tc.ShuntADC)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestWriteConfig(t *testing.T) {
|
||||
// use the default configurations
|
||||
for _, tc := range []Config{
|
||||
Config16V400mA,
|
||||
Config32V2A,
|
||||
Config32V1A,
|
||||
} {
|
||||
n := fmt.Sprintf("%x/%x", tc.RegisterValue(), tc.Calibration.RegisterValue())
|
||||
t.Run(n, func(t *testing.T) {
|
||||
c := qt.New(t)
|
||||
bus := tester.NewI2CBus(c)
|
||||
fake := tester.NewI2CDevice16(c, Address)
|
||||
bus.AddDevice(fake)
|
||||
fake.Registers = map[uint8]uint16{
|
||||
RegConfig: 0,
|
||||
RegCalibration: 0,
|
||||
}
|
||||
|
||||
dev := New(bus)
|
||||
dev.config = tc
|
||||
err := dev.Configure()
|
||||
c.Assert(err, qt.IsNil)
|
||||
c.Assert(fake.Registers[RegConfig], qt.Equals, tc.RegisterValue())
|
||||
c.Assert(fake.Registers[RegCalibration], qt.Equals, tc.Calibration.RegisterValue())
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestSetConfig(t *testing.T) {
|
||||
for _, tc := range []Config{
|
||||
Config16V400mA,
|
||||
Config32V2A,
|
||||
Config32V1A,
|
||||
} {
|
||||
n := fmt.Sprintf("%x/%x", tc.RegisterValue(), tc.Calibration.RegisterValue())
|
||||
t.Run(n, func(t *testing.T) {
|
||||
c := qt.New(t)
|
||||
bus := tester.NewI2CBus(c)
|
||||
dev := New(bus)
|
||||
dev.SetConfig(tc)
|
||||
c.Assert(dev.config, qt.Equals, tc)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestTrigger(t *testing.T) {
|
||||
c := qt.New(t)
|
||||
bus := tester.NewI2CBus(c)
|
||||
fake := tester.NewI2CDevice16(c, Address)
|
||||
bus.AddDevice(fake)
|
||||
fake.Registers = map[uint8]uint16{
|
||||
RegConfig: Config32V2A.RegisterValue(),
|
||||
}
|
||||
|
||||
dev := New(bus)
|
||||
dev.config = Config32V2A
|
||||
dev.config.Mode = ModeTrigBus
|
||||
err := dev.Trigger()
|
||||
c.Assert(err, qt.IsNil)
|
||||
c.Assert(fake.Registers[RegConfig], qt.Equals, dev.config.RegisterValue())
|
||||
}
|
||||
|
||||
func TestMeasurements(t *testing.T) {
|
||||
bvVal := int16(4200)
|
||||
svVal := int16(1234)
|
||||
iVal := float32(420)
|
||||
pVal := float32(420)
|
||||
|
||||
c := qt.New(t)
|
||||
bus := tester.NewI2CBus(c)
|
||||
fake := tester.NewI2CDevice16(c, Address)
|
||||
bus.AddDevice(fake)
|
||||
fake.Registers = map[uint8]uint16{
|
||||
RegBusVoltage: uint16(((4200 << 3) / 4) | (1 << 1)),
|
||||
RegShuntVoltage: uint16(svVal),
|
||||
RegCurrent: uint16(iVal * Config16V400mA.CurrentDivider),
|
||||
RegPower: uint16(pVal / Config16V400mA.PowerMultiplier),
|
||||
}
|
||||
|
||||
dev := New(bus)
|
||||
dev.config = Config16V400mA
|
||||
bv, sv, i, p, err := dev.Measurements()
|
||||
c.Assert(err, qt.IsNil)
|
||||
c.Assert(bv, qt.Equals, bvVal)
|
||||
c.Assert(sv, qt.Equals, svVal)
|
||||
c.Assert(i, qt.Equals, iVal)
|
||||
c.Assert(p, qt.Equals, pVal)
|
||||
|
||||
}
|
||||
@@ -0,0 +1,13 @@
|
||||
package ina219
|
||||
|
||||
// The default I2C address for this device.
|
||||
const Address = 0x40
|
||||
|
||||
const (
|
||||
RegConfig uint8 = 0x0
|
||||
RegShuntVoltage uint8 = 0x1
|
||||
RegBusVoltage uint8 = 0x2
|
||||
RegPower uint8 = 0x3
|
||||
RegCurrent uint8 = 0x4
|
||||
RegCalibration uint8 = 0x5
|
||||
)
|
||||
@@ -109,6 +109,7 @@ tinygo build -size short -o ./build/test.hex -target=xiao ./examples/pcf8563/tim
|
||||
tinygo build -size short -o ./build/test.hex -target=pico ./examples/qmi8658c/main.go
|
||||
tinygo build -size short -o ./build/test.hex -target=feather-rp2040 ./examples/pcf8591/
|
||||
tinygo build -size short -o ./build/test.hex -target=feather-m0 ./examples/ina260/main.go
|
||||
tinygo build -size short -o ./build/test.hex -target=feather-m0 ./examples/ina219/main.go
|
||||
tinygo build -size short -o ./build/test.hex -target=nucleo-l432kc ./examples/aht20/main.go
|
||||
tinygo build -size short -o ./build/test.hex -target=feather-m4 ./examples/sdcard/console/
|
||||
tinygo build -size short -o ./build/test.hex -target=feather-m4 ./examples/i2csoft/adt7410/
|
||||
|
||||
Reference in New Issue
Block a user