gobot.io/x/gobot/v2@v2.1.0/drivers/i2c/ads1x15_driver_1115_test.go (about) 1 package i2c 2 3 import ( 4 "errors" 5 "strings" 6 "testing" 7 8 "gobot.io/x/gobot/v2/gobottest" 9 ) 10 11 func initTestADS1115DriverWithStubbedAdaptor() (*ADS1x15Driver, *i2cTestAdaptor) { 12 a := newI2cTestAdaptor() 13 d := NewADS1115Driver(a) 14 if err := d.Start(); err != nil { 15 panic(err) 16 } 17 return d, a 18 } 19 20 func TestNewADS1115Driver(t *testing.T) { 21 var di interface{} = NewADS1115Driver(newI2cTestAdaptor()) 22 d, ok := di.(*ADS1x15Driver) 23 if !ok { 24 t.Errorf("NewADS1115Driver() should have returned a *ADS1x15Driver") 25 } 26 gobottest.Refute(t, d.Driver, nil) 27 gobottest.Assert(t, strings.HasPrefix(d.Name(), "ADS1115"), true) 28 for i := 0; i <= 3; i++ { 29 gobottest.Assert(t, d.channelCfgs[i].gain, 1) 30 gobottest.Assert(t, d.channelCfgs[i].dataRate, 128) 31 } 32 } 33 34 func TestADS1115Options(t *testing.T) { 35 // This is a general test, that options are applied in constructor by using the common WithBus() option and 36 // least one of this driver. Further tests for options can also be done by call of "WithOption(val)(d)". 37 d := NewADS1115Driver(newI2cTestAdaptor(), WithBus(2), WithADS1x15Gain(2), WithADS1x15DataRate(860)) 38 gobottest.Assert(t, d.GetBusOrDefault(1), 2) 39 for i := 0; i <= 3; i++ { 40 gobottest.Assert(t, d.channelCfgs[i].gain, 2) 41 gobottest.Assert(t, d.channelCfgs[i].dataRate, 860) 42 } 43 } 44 45 func TestADS1115WithADS1x15BestGainForVoltage(t *testing.T) { 46 d, _ := initTestADS1115DriverWithStubbedAdaptor() 47 WithADS1x15BestGainForVoltage(1.01)(d) 48 for i := 0; i <= 3; i++ { 49 gobottest.Assert(t, d.channelCfgs[i].gain, 3) 50 } 51 } 52 53 func TestADS1115WithADS1x15ChannelBestGainForVoltage(t *testing.T) { 54 d, _ := initTestADS1115DriverWithStubbedAdaptor() 55 WithADS1x15ChannelBestGainForVoltage(0, 1.0)(d) 56 WithADS1x15ChannelBestGainForVoltage(1, 2.5)(d) 57 WithADS1x15ChannelBestGainForVoltage(2, 3.3)(d) 58 WithADS1x15ChannelBestGainForVoltage(3, 5.0)(d) 59 gobottest.Assert(t, d.channelCfgs[0].gain, 3) 60 gobottest.Assert(t, d.channelCfgs[1].gain, 1) 61 gobottest.Assert(t, d.channelCfgs[2].gain, 1) 62 gobottest.Assert(t, d.channelCfgs[3].gain, 0) 63 } 64 65 func TestADS1115AnalogRead(t *testing.T) { 66 d, a := initTestADS1115DriverWithStubbedAdaptor() 67 WithADS1x15WaitSingleCycle()(d) 68 69 a.i2cReadImpl = func(b []byte) (int, error) { 70 copy(b, []byte{0x7F, 0xFF}) 71 return 2, nil 72 } 73 74 val, err := d.AnalogRead("0") 75 gobottest.Assert(t, val, 32767) 76 gobottest.Assert(t, err, nil) 77 78 val, err = d.AnalogRead("1") 79 gobottest.Assert(t, val, 32767) 80 gobottest.Assert(t, err, nil) 81 82 val, err = d.AnalogRead("2") 83 gobottest.Assert(t, val, 32767) 84 gobottest.Assert(t, err, nil) 85 86 val, err = d.AnalogRead("3") 87 gobottest.Assert(t, val, 32767) 88 gobottest.Assert(t, err, nil) 89 90 val, err = d.AnalogRead("0-1") 91 gobottest.Assert(t, val, 32767) 92 gobottest.Assert(t, err, nil) 93 94 val, err = d.AnalogRead("0-3") 95 gobottest.Assert(t, val, 32767) 96 gobottest.Assert(t, err, nil) 97 98 val, err = d.AnalogRead("1-3") 99 gobottest.Assert(t, val, 32767) 100 gobottest.Assert(t, err, nil) 101 102 val, err = d.AnalogRead("2-3") 103 gobottest.Assert(t, val, 32767) 104 gobottest.Assert(t, err, nil) 105 106 _, err = d.AnalogRead("3-2") 107 gobottest.Refute(t, err.Error(), nil) 108 } 109 110 func TestADS1115AnalogReadError(t *testing.T) { 111 d, a := initTestADS1115DriverWithStubbedAdaptor() 112 113 a.i2cReadImpl = func(b []byte) (int, error) { 114 return 0, errors.New("read error") 115 } 116 117 _, err := d.AnalogRead("0") 118 gobottest.Assert(t, err, errors.New("read error")) 119 } 120 121 func TestADS1115AnalogReadInvalidPin(t *testing.T) { 122 d, _ := initTestADS1115DriverWithStubbedAdaptor() 123 124 _, err := d.AnalogRead("98") 125 gobottest.Assert(t, err, errors.New("Invalid channel (98), must be between 0 and 3")) 126 } 127 128 func TestADS1115AnalogReadWriteError(t *testing.T) { 129 d, a := initTestADS1115DriverWithStubbedAdaptor() 130 131 a.i2cWriteImpl = func([]byte) (int, error) { 132 return 0, errors.New("write error") 133 } 134 135 _, err := d.AnalogRead("0") 136 gobottest.Assert(t, err, errors.New("write error")) 137 138 _, err = d.AnalogRead("0-1") 139 gobottest.Assert(t, err, errors.New("write error")) 140 141 _, err = d.AnalogRead("2-3") 142 gobottest.Assert(t, err, errors.New("write error")) 143 } 144 145 func TestADS1115ReadInvalidChannel(t *testing.T) { 146 d, _ := initTestADS1115DriverWithStubbedAdaptor() 147 148 _, err := d.Read(7, 1, 1600) 149 gobottest.Assert(t, err, errors.New("Invalid channel (7), must be between 0 and 3")) 150 } 151 152 func TestADS1115ReadInvalidGain(t *testing.T) { 153 d, _ := initTestADS1115DriverWithStubbedAdaptor() 154 155 _, err := d.Read(0, 21, 1600) 156 gobottest.Assert(t, err, errors.New("Gain (21) must be one of: [0 1 2 3 4 5 6 7]")) 157 } 158 159 func TestADS1115ReadInvalidDataRate(t *testing.T) { 160 d, _ := initTestADS1115DriverWithStubbedAdaptor() 161 162 _, err := d.Read(0, 1, 678) 163 gobottest.Assert(t, err, errors.New("Invalid data rate (678). Accepted values: [8 16 32 64 128 250 475 860]")) 164 } 165 166 func TestADS1115ReadDifferenceInvalidChannel(t *testing.T) { 167 d, _ := initTestADS1115DriverWithStubbedAdaptor() 168 169 _, err := d.ReadDifference(5, 1, 1600) 170 gobottest.Assert(t, err, errors.New("Invalid channel (5), must be between 0 and 3")) 171 } 172 173 func TestADS1115_rawRead(t *testing.T) { 174 // sequence to read: 175 // * prepare config register content (mode, input, gain, data rate, comparator) 176 // * write config register (16 bit, MSByte first) 177 // * read config register (16 bit, MSByte first) and wait for bit 15 is set 178 // * read conversion register (16 bit, MSByte first) for the value 179 // * apply two's complement converter, relates to one digit resolution (1/2^15), voltage multiplier 180 var tests = map[string]struct { 181 input []uint8 182 gain int 183 dataRate int 184 want int 185 wantConfig []uint8 186 }{ 187 "+FS": { 188 input: []uint8{0x7F, 0xFF}, 189 gain: 0, 190 dataRate: 8, 191 want: (1<<15 - 1), 192 wantConfig: []uint8{0x91, 0x03}, 193 }, 194 "+1": { 195 input: []uint8{0x00, 0x01}, 196 gain: 0, 197 dataRate: 16, 198 want: 1, 199 wantConfig: []uint8{0x91, 0x23}, 200 }, 201 "+-0": { 202 input: []uint8{0x00, 0x00}, 203 gain: 0, 204 dataRate: 32, 205 want: 0, 206 wantConfig: []uint8{0x91, 0x43}, 207 }, 208 "-1": { 209 input: []uint8{0xFF, 0xFF}, 210 gain: 0, 211 dataRate: 64, 212 want: -1, 213 wantConfig: []uint8{0x91, 0x63}, 214 }, 215 "-FS": { 216 input: []uint8{0x80, 0x00}, 217 gain: 0, 218 dataRate: 128, 219 want: -(1 << 15), 220 wantConfig: []uint8{0x91, 0x83}, 221 }, 222 "+FS gain 1": { 223 input: []uint8{0x7F, 0xFF}, 224 gain: 1, 225 dataRate: 250, 226 want: (1<<15 - 1), 227 wantConfig: []uint8{0x93, 0xA3}, 228 }, 229 "+FS gain 3": { 230 input: []uint8{0x7F, 0xFF}, 231 gain: 3, 232 dataRate: 475, 233 want: (1<<15 - 1), 234 wantConfig: []uint8{0x97, 0xC3}, 235 }, 236 "+FS gain 5": { 237 input: []uint8{0x7F, 0xFF}, 238 gain: 5, 239 dataRate: 860, 240 want: (1<<15 - 1), 241 wantConfig: []uint8{0x9B, 0xE3}, 242 }, 243 "+FS gain 7": { 244 input: []uint8{0x7F, 0xFF}, 245 gain: 7, 246 dataRate: 128, 247 want: (1<<15 - 1), 248 wantConfig: []uint8{0x9F, 0x83}, 249 }, 250 } 251 d, a := initTestADS1115DriverWithStubbedAdaptor() 252 // arrange 253 channel := 0 254 channelOffset := 1 255 for name, tt := range tests { 256 t.Run(name, func(t *testing.T) { 257 a.written = []byte{} // reset writes of Start() and former test 258 // arrange reads 259 conversion := []uint8{0x00, 0x00} // a conversion is in progress 260 noConversion := []uint8{0x80, 0x00} // no conversion in progress 261 returnRead := [3][]uint8{conversion, noConversion, tt.input} 262 numCallsRead := 0 263 a.i2cReadImpl = func(b []byte) (int, error) { 264 numCallsRead++ 265 retRead := returnRead[numCallsRead-1] 266 copy(b, retRead) 267 return len(b), nil 268 } 269 // act 270 got, err := d.rawRead(channel, channelOffset, tt.gain, tt.dataRate) 271 // assert 272 gobottest.Assert(t, err, nil) 273 gobottest.Assert(t, got, tt.want) 274 gobottest.Assert(t, numCallsRead, 3) 275 gobottest.Assert(t, len(a.written), 6) 276 gobottest.Assert(t, a.written[0], uint8(ads1x15PointerConfig)) 277 gobottest.Assert(t, a.written[1], tt.wantConfig[0]) // MSByte: OS, MUX, PGA, MODE 278 gobottest.Assert(t, a.written[2], tt.wantConfig[1]) // LSByte: DR, COMP_* 279 gobottest.Assert(t, a.written[3], uint8(ads1x15PointerConfig)) // first check for no conversion 280 gobottest.Assert(t, a.written[4], uint8(ads1x15PointerConfig)) // second check for no conversion 281 gobottest.Assert(t, a.written[5], uint8(ads1x15PointerConversion)) 282 }) 283 } 284 }