/
ina260.go
112 lines (90 loc) · 2.58 KB
/
ina260.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
package ina260
import "tinygo.org/x/drivers"
// Device wraps an I2C connection to an INA260 device.
type Device struct {
bus drivers.I2C
Address uint16
}
// Config holds the configuration of the INA260 device.
type Config struct {
// One of AVGMODE_XXX
AverageMode byte
// One of CONVTIME_XXXXUSEC
VoltConvTime byte
// One of CONVTIME_XXXXUSEC
CurrentConvTime byte
// Multiple of MODE_XXXX
Mode byte
}
// New creates a new INA260 connection. The I2C bus must already be
// configured.
//
// This function only creates the Device object, it does not touch the device.
func New(bus drivers.I2C) Device {
return Device{
bus: bus,
Address: Address,
}
}
// Configure sets up the device.
//
// This only needs to be called to override built-in defaults. By default,
// the device starts with:
//
// * AverageMode = AVGMODE_1
// * VoltConvTime = CONVTIME_1100USEC
// * CurrentConvTime = CONVTIME_1100USEC
// * Mode = MODE_CONTINUOUS | MODE_VOLTAGE | MODE_CURRENT
//
func (d *Device) Configure(cfg Config) {
var val uint16
val = uint16(cfg.AverageMode&0x7) << 9
val |= uint16(cfg.VoltConvTime&0x7) << 6
val |= uint16(cfg.CurrentConvTime&0x7) << 3
val |= uint16(cfg.Mode & 0x7)
d.WriteRegister(REG_CONFIG, val)
}
// Resets the device, setting all registers to default values
func (d *Device) Reset() {
d.WriteRegister(REG_CONFIG, 0x8000)
}
// Connected returns whether an INA260 has been found.
func (d *Device) Connected() bool {
return d.ReadRegister(REG_MANF_ID) == MANF_ID &&
(d.ReadRegister(REG_DIE_ID)&DEVICE_ID_MASK) == DEVICE_ID
}
// Gets the measured current in µA (max resolution 1.25mA)
func (d *Device) Current() int32 {
val := d.ReadRegister(REG_CURRENT)
if val&0x8000 == 0 {
return int32(val) * 1250
}
// Two's complement, convert to signed int
return -(int32(^val) + 1) * 1250
}
// Gets the measured voltage in µV (max resolution 1.25mV)
func (d *Device) Voltage() int32 {
val := d.ReadRegister(REG_BUSVOLTAGE)
if val&0x8000 == 0 {
return int32(val) * 1250
}
// Two's complement, convert to signed int
return -(int32(^val) + 1) * 1250
}
// Gets the measured power in µW (max resolution 10mW)
func (d *Device) Power() int32 {
return int32(d.ReadRegister(REG_POWER)) * 10000
}
// Read a register
func (d *Device) ReadRegister(reg uint8) uint16 {
data := []byte{0, 0}
d.bus.ReadRegister(uint8(d.Address), reg, data)
return (uint16(data[0]) << 8) | uint16(data[1])
}
// Write to a register
func (d *Device) WriteRegister(reg uint8, v uint16) {
data := []byte{0, 0}
data[0] = byte(v >> 8)
data[1] = byte(v & 0xff)
d.bus.WriteRegister(uint8(d.Address), reg, data)
}