0.1.0 MCP23008

This commit is contained in:
rob tillaart 2022-01-10 12:51:36 +01:00
parent d13d98052a
commit bb3cba8cd7
15 changed files with 984 additions and 0 deletions

View File

@ -0,0 +1,11 @@
compile:
# Choosing to run compilation tests on 2 different Arduino platforms
platforms:
- uno
# - due
# - zero
# - leonardo
- m4
- esp32
# - esp8266
# - mega2560

View File

@ -0,0 +1,13 @@
name: Arduino-lint
on: [push, pull_request]
jobs:
lint:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- uses: arduino/arduino-lint-action@v1
with:
library-manager: update
compliance: strict

View File

@ -0,0 +1,17 @@
---
name: Arduino CI
on: [push, pull_request]
jobs:
runTest:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- uses: ruby/setup-ruby@v1
with:
ruby-version: 2.6
- run: |
gem install arduino_ci
arduino_ci.rb

View File

@ -0,0 +1,18 @@
name: JSON check
on:
push:
paths:
- '**.json'
pull_request:
jobs:
test:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- name: json-syntax-check
uses: limitusus/json-syntax-check@v1
with:
pattern: "\\.json$"

View File

@ -0,0 +1,21 @@
MIT License
Copyright (c) 2022-2022 Rob Tillaart
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.

View File

@ -0,0 +1,405 @@
//
// FILE: MCP23008.cpp
// AUTHOR: Rob Tillaart
// VERSION: 0.1.0
// PURPOSE: Arduino library for I2C MCP23008 8 channel port expander
// DATE: 2019-10-12
// URL: https://github.com/RobTillaart/MCP23008
//
// HISTORY:
// 0.1.0 2022-01-10 initial version
#include "MCP23008.h"
// Registers // description datasheet
#define MCP23008_DDR_A 0x00 // Data Direction Register A P
#define MCP23008_POL_A 0x01 // Input Polarity A P
#define MCP23008_GPINTEN_A 0x02 // NOT USED interrupt enable P
#define MCP23008_DEFVAL_A 0x03 // NOT USED interrupt def P
#define MCP23008_INTCON_A 0x04 // NOT USED interrupt control P
#define MCP23008_IOCR 0x05 // IO control register P
#define MCP23008_PUR_A 0x06 // Pull Up Resistors A P
#define MCP23008_INTF_A 0x07 // NOT USED interrupt flag P
#define MCP23008_INTCAP_A 0x08 // NOT USED interrupt capture P
#define MCP23008_GPIO_A 0x09 // General Purpose IO A P
#define MCP23008_OLAT_A 0x0A // NOT USED output latch P
MCP23008::MCP23008(uint8_t address, TwoWire *wire)
{
_address = address;
_wire = wire;
_error = MCP23008_OK;
}
#if defined(ESP8266) || defined(ESP32)
bool MCP23008::begin(const uint8_t dataPin, const uint8_t clockPin)
{
_wire = &Wire;
_wire->begin(dataPin, clockPin);
// check connected
if (! isConnected()) return false;
// disable address increment (datasheet)
if (! writeReg(MCP23008_IOCR, 0b00100000)) return false;
// Force INPUT_PULLUP
if (! writeReg(MCP23008_PUR_A, 0xFF)) return false;
return true;
}
#endif
bool MCP23008::begin()
{
_wire->begin();
// check connected
if (! isConnected()) return false;
// disable address increment (datasheet)
if (! writeReg(MCP23008_IOCR, 0b00100000)) return false;
// Force INPUT_PULLUP
if (! writeReg(MCP23008_PUR_A, 0xFF)) return false;
return true;
}
bool MCP23008::isConnected()
{
_wire->beginTransmission(_address);
if (_wire->endTransmission() != 0)
{
_error = MCP23008_I2C_ERROR;
return false;
}
_error = MCP23008_OK;
return true;
}
// single pin interface
// pin = 0..7
// mode = INPUT, OUTPUT, INPUT_PULLUP (= same as INPUT)
bool MCP23008::pinMode(uint8_t pin, uint8_t mode)
{
if (pin > 7)
{
_error = MCP23008_PIN_ERROR;
return false;
}
if ((mode != INPUT) && (mode != INPUT_PULLUP) && (mode != OUTPUT))
{
_error = MCP23008_VALUE_ERROR;
return false;
}
uint8_t dataDirectionRegister = MCP23008_DDR_A;
uint8_t val = readReg(dataDirectionRegister);
if (_error != MCP23008_OK)
{
return false;
}
uint8_t mask = 1 << pin;
// only work with valid
if ((mode == INPUT) || (mode == INPUT_PULLUP))
{
val |= mask;
}
else if (mode == OUTPUT)
{
val &= ~mask;
}
// other values won't change val ....
writeReg(dataDirectionRegister, val);
if (_error != MCP23008_OK)
{
return false;
}
return true;
}
// pin = 0..7
// value = LOW, HIGH
bool MCP23008::digitalWrite(uint8_t pin, uint8_t value)
{
if (pin > 7)
{
_error = MCP23008_PIN_ERROR;
return false;
}
uint8_t IOR = MCP23008_GPIO_A;
uint8_t val = readReg(IOR);
if (_error != MCP23008_OK)
{
return false;
}
uint8_t mask = 1 << pin;
if (value)
{
val |= mask;
}
else
{
val &= ~mask;
}
writeReg(IOR, val);
if (_error != MCP23008_OK)
{
return false;
}
return true;
}
uint8_t MCP23008::digitalRead(uint8_t pin)
{
if (pin > 7)
{
_error = MCP23008_PIN_ERROR;
return MCP23008_INVALID_READ;
}
uint8_t IOR = MCP23008_GPIO_A;
uint8_t val = readReg(IOR);
if (_error != MCP23008_OK)
{
return MCP23008_INVALID_READ;
}
uint8_t mask = 1 << pin;
if (val & mask) return HIGH;
return LOW;
}
// pin = 0..7
// reverse = true or false
bool MCP23008::setPolarity(uint8_t pin, bool reversed)
{
if (pin > 7)
{
_error = MCP23008_PIN_ERROR;
return false;
}
uint8_t inputPolarityRegister = MCP23008_POL_A;
uint8_t val = readReg(inputPolarityRegister);
if (_error != MCP23008_OK)
{
return false;
}
uint8_t mask = 1 << pin;
if (reversed)
{
val |= mask;
}
else
{
val &= ~mask;
}
writeReg(inputPolarityRegister, val);
if (_error != MCP23008_OK)
{
return false;
}
return true;
}
bool MCP23008::getPolarity(uint8_t pin, bool &reversed)
{
if (pin > 7)
{
_error = MCP23008_PIN_ERROR;
return false;
}
uint8_t inputPolarityRegister = MCP23008_POL_A;
uint8_t val = readReg(inputPolarityRegister);
if (_error != MCP23008_OK)
{
return false;
}
uint8_t mask = 1 << pin;
reversed = (val & mask) > 0;
return true;
}
// pin = 0..7
// reverse = true or false
bool MCP23008::setPullup(uint8_t pin, bool pullup)
{
if (pin > 7)
{
_error = MCP23008_PIN_ERROR;
return false;
}
uint8_t inputPullupRegister = MCP23008_PUR_A;
uint8_t val = readReg(inputPullupRegister);
if (_error != MCP23008_OK)
{
return false;
}
uint8_t mask = 1 << pin;
if (pullup)
{
val |= mask;
}
else
{
val &= ~mask;
}
writeReg(inputPullupRegister, val);
if (_error != MCP23008_OK)
{
return false;
}
return true;
}
bool MCP23008::getPullup(uint8_t pin, bool &pullup)
{
if (pin > 7)
{
_error = MCP23008_PIN_ERROR;
return false;
}
uint8_t inputPullupRegister = MCP23008_PUR_A;
uint8_t val = readReg(inputPullupRegister);
if (_error != MCP23008_OK)
{
return false;
}
uint8_t mask = 1 << pin;
pullup = (val & mask) > 0;
return true;
}
///////////////////////////////////////////////////////////////////////
// 8 pins interface
// whole register at once
// value = 0..0xFF bit pattern
bool MCP23008::pinMode8(uint8_t value)
{
writeReg(MCP23008_DDR_A, value);
_error = MCP23008_OK;
return true;
}
bool MCP23008::write8(uint8_t value)
{
writeReg(MCP23008_GPIO_A, value);
_error = MCP23008_OK;
return true;
}
int MCP23008::read8()
{
_error = MCP23008_OK;
return readReg(MCP23008_GPIO_A);
}
// mask = 0..0xFF bit pattern
bool MCP23008::setPolarity8(uint8_t mask)
{
writeReg(MCP23008_POL_A, mask);
if (_error != MCP23008_OK)
{
return false;
}
return true;
}
bool MCP23008::getPolarity8(uint8_t &mask)
{
mask = readReg(MCP23008_POL_A);
if (_error != MCP23008_OK)
{
return false;
}
return true;
}
// mask = 0..0xFF bit pattern
bool MCP23008::setPullup8(uint8_t mask)
{
writeReg(MCP23008_PUR_A, mask);
if (_error != MCP23008_OK)
{
return false;
}
return true;
}
bool MCP23008::getPullup8(uint8_t &mask)
{
mask = readReg(MCP23008_PUR_A);
if (_error != MCP23008_OK)
{
return false;
}
return true;
}
int MCP23008::lastError()
{
int e = _error;
_error = MCP23008_OK; // reset error after read.
return e;
}
////////////////////////////////////////////////////
//
// PRIVATE
//
bool MCP23008::writeReg(uint8_t reg, uint8_t value)
{
_wire->beginTransmission(_address);
_wire->write(reg);
_wire->write(value);
if (_wire->endTransmission() != 0)
{
_error = MCP23008_I2C_ERROR;
return false;
}
_error = MCP23008_OK;
return true;
}
uint8_t MCP23008::readReg(uint8_t reg)
{
_wire->beginTransmission(_address);
_wire->write(reg);
if (_wire->endTransmission() != 0)
{
_error = MCP23008_I2C_ERROR;
return 0;
}
else
{
_error = MCP23008_OK;
}
uint8_t n = _wire->requestFrom(_address, (uint8_t)1);
if (n != 1)
{
_error = MCP23008_I2C_ERROR;
return 0;
}
return _wire->read();
}
// -- END OF FILE --

View File

@ -0,0 +1,76 @@
#pragma once
//
// FILE: MCP23008.h
// AUTHOR: Rob Tillaart
// VERSION: 0.1.0
// PURPOSE: Arduino library for I2C MCP23008 16 channel port expander
// DATE: 2022-01-10
// URL: https://github.com/RobTillaart/MCP23008
#include "Arduino.h"
#include "Wire.h"
#define MCP23008_LIB_VERSION (F("0.1.0"))
#define MCP23008_OK 0x00
#define MCP23008_PIN_ERROR 0x81
#define MCP23008_I2C_ERROR 0x82
#define MCP23008_VALUE_ERROR 0x83
#define MCP23008_PORT_ERROR 0x84
#define MCP23008_INVALID_READ -100
class MCP23008
{
public:
MCP23008(uint8_t address, TwoWire *wire = &Wire);
#if defined(ESP8266) || defined(ESP32)
bool begin(const uint8_t dataPin, const uint8_t clockPin);
#endif
bool begin();
bool isConnected();
// single pin interface
// mode = INPUT, OUTPUT or INPUT_PULLUP (==INPUT)
bool pinMode(uint8_t pin, uint8_t mode);
bool digitalWrite(uint8_t pin, uint8_t value);
uint8_t digitalRead(uint8_t pin);
bool setPolarity(uint8_t pin, bool reversed);
bool getPolarity(uint8_t pin, bool &reversed);
bool setPullup(uint8_t pin, bool pullup);
bool getPullup(uint8_t pin, bool &pullup);
// 8 pins interface
// value = bit pattern
bool pinMode8(uint8_t value);
bool write8(uint8_t value);
int read8();
bool setPolarity8(uint8_t mask);
bool getPolarity8(uint8_t &mask);
bool setPullup8(uint8_t mask);
bool getPullup8(uint8_t &mask);
int lastError();
private:
bool writeReg(uint8_t reg, uint8_t value);
uint8_t readReg(uint8_t reg);
uint8_t _address;
TwoWire* _wire;
uint8_t _error;
};
// -- END OF FILE --

View File

@ -0,0 +1,77 @@
[![Arduino CI](https://github.com/RobTillaart/MCP23008/workflows/Arduino%20CI/badge.svg)](https://github.com/marketplace/actions/arduino_ci)
[![Arduino-lint](https://github.com/RobTillaart/MCP23008/actions/workflows/arduino-lint.yml/badge.svg)](https://github.com/RobTillaart/MCP23008/actions/workflows/arduino-lint.yml)
[![JSON check](https://github.com/RobTillaart/MCP23008/actions/workflows/jsoncheck.yml/badge.svg)](https://github.com/RobTillaart/MCP23008/actions/workflows/jsoncheck.yml)
[![License: MIT](https://img.shields.io/badge/license-MIT-green.svg)](https://github.com/RobTillaart/MCP23008/blob/master/LICENSE)
[![GitHub release](https://img.shields.io/github/release/RobTillaart/MCP23008.svg?maxAge=3600)](https://github.com/RobTillaart/MCP23008/releases)
# MCP23008
Arduino library for MCP23008 8 channel I2C port expander.
## Description
This library gives easy control over the 8 pins of a (I2C) MCP23008 chip.
This IC is strongly related tot the MCP23017 I2C port expander - https://github.com/RobTillaart/MCP23017_RT
Programming Interface is kept the same as much as possible.
## Interface
### Constructor
- **MCP23008(uint8_t address, TwoWire \*wire = &Wire)** constructor, with default Wire interface.
Can be overruled with Wire0..WireN.
- **bool begin()** for UNO, returns true if successful.
- **bool begin(uint8_t sda, uint8_t scl)** for ESP32, returns true if successful.
- **bool isConnected()** returns true if connected, false otherwise.
### Single pin interface
- **bool pinMode(uint8_t pin, uint8_t mode)** pin = 0..7, mode = INPUT, OUTPUT, returns true if successful.
- **bool digitalWrite(uint8_t pin, uint8_t value)** pin = 0..7, value = LOW(0) HIGH (!0), returns true if successful.
- **uint8_t digitalRead(uint8_t pin)** pin = 0..7, returns LOW or HIGH, might set the lastError();
- **bool setPolarity(uint8_t pin, bool reversed)** pin = 0..7, set reversed flag, returns true if successful.
- **bool getPolarity(uint8_t pin, bool &reversed)** pin = 0..7, reads reversed flag, returns true if successful.
- **bool setPullup(uint8_t pin, bool pullup)** pin = 0..7, set pull-up flag, returns true if successful.
- **bool getPullup(uint8_t pin, bool &pullup)** pin = 0..7, reads pull-up flag, returns true if successful.
### 8 pins interface
- **bool pinMode8(uint8_t value)** value = 0..255, returns true if successful.
- **bool write8(uint8_t value)** value = 0..255, returns true if successful.
- **uint8_t read8()** reads 8 pins into one byte.
- **bool setPolarity8(uint8_t mask)** sets polarity for 8 channels at once.
- **bool getPolarity8(uint8_t &mask)** reads polarity of 8 channels at once.
- **bool setPullup8(uint8_t mask)** sets pull-up for 8 channels at once.
- **bool getPullup8(uint8_t &mask)** reads pull-up for 8 channels at once.
### Error codes
- **int lastError()** Above functions set an error flag that can be read with this function.
Reading it will reset the flag to **MCP23008_OK**.
| DESCRIPTION | VALUE |
|:----------------------|:-----:|
| MCP23008_OK | 0x00 |
| MCP23008_PIN_ERROR | 0x81 |
| MCP23008_I2C_ERROR | 0x82 |
| MCP23008_VALUE_ERROR | 0x83 |
| MCP23008_PORT_ERROR | 0x84 |
## Operation
See examples.
## Future
- keep in sync with MCP23017

View File

@ -0,0 +1,40 @@
//
// FILE: MCP23008_digitalRead.ino
// AUTHOR: Rob Tillaart
// DATE: 2019-10-14
// PUPROSE: test MCP23008 library
#include "MCP23008.h"
#include "Wire.h"
MCP23008 MCP(0x27);
void setup()
{
Serial.begin(230400);
Serial.print("MCP23008_test version: ");
Serial.println(MCP23008_LIB_VERSION);
Wire.begin();
MCP.begin();
MCP.pinMode8(0x00);
Serial.println("TEST digitalRead(pin)");
for (int pin = 0; pin < 8; pin++)
{
int val = MCP.digitalRead(pin);
Serial.print(val);
Serial.print('\t');
}
Serial.println();
}
void loop()
{
}
// -- END OF FILE --

View File

@ -0,0 +1,68 @@
//
// FILE: MCP23008_digitalWrite.ino
// AUTHOR: Rob Tillaart
// DATE: 2019-10-14
// PUPROSE: test MCP23008 library
#include "MCP23008.h"
#include "Wire.h"
MCP23008 MCP(0x27);
void setup()
{
Serial.begin(230400);
Serial.print("MCP23008_test version: ");
Serial.println(MCP23008_LIB_VERSION);
Wire.begin();
MCP.begin();
MCP.pinMode8(0x00); // 0 = output , 1 = input
Wire.setClock(100000);
Serial.println("TEST digitalWrite(0)");
for (int i = 0; i < 8; i++)
{
MCP.digitalWrite(0, i % 2); // alternating HIGH/LOW
Serial.print(i % 2);
Serial.print('\t');
delay(250);
}
Serial.println();
Serial.println();
Serial.println("TEST digitalWrite(pin)");
for (int pin = 0; pin < 8; pin++)
{
MCP.digitalWrite(pin, 1 - pin % 2); // alternating HIGH/LOW
Serial.print(1 - pin % 2);
Serial.print('\t');
}
Serial.println();
Serial.println();
Serial.println("TEST read back");
for (int pin = 0; pin < 8; pin++)
{
int val = MCP.digitalRead(pin);
Serial.print(val);
Serial.print('\t');
}
Serial.println();
Serial.println();
}
void loop()
{
}
// -- END OF FILE --

View File

@ -0,0 +1,97 @@
//
// FILE: MCP23008_performance.ino
// AUTHOR: Rob Tillaart
// DATE: 2022-01-09
// PUPROSE: test MCP23008 library
#include "MCP23008.h"
#include "Wire.h"
MCP23008 MCP(0x27);
uint32_t start, stop;
void setup()
{
Serial.begin(115200);
Serial.println();
Serial.print("MCP23008_LIB_VERSION: ");
Serial.println(MCP23008_LIB_VERSION);
Serial.println();
delay(100);
Wire.begin();
bool b = MCP.begin();
MCP.pinMode8(0x00); // 0 = output , 1 = input
Serial.println("\ntime in microseconds\n");
delay(100);
Serial.print("TEST digitalWrite(0, value):\t");
delay(100);
start = micros();
for (int i = 0; i < 8; i++)
{
MCP.digitalWrite(i, i & 0x01); // alternating HIGH/LOW
}
stop = micros();
Serial.println((stop - start) / 8.0);
Serial.print("TEST digitalWrite(pin, value):\t");
delay(100);
start = micros();
for (int pin = 0; pin < 8; pin++)
{
MCP.digitalWrite(pin, 1 - pin % 2); // alternating HIGH/LOW
}
stop = micros();
Serial.println((stop - start) / 8.0);
Serial.print("TEST digitalRead(pin):\t");
delay(100);
start = micros();
for (int pin = 0; pin < 8; pin++)
{
volatile int val = MCP.digitalRead(pin);
}
stop = micros();
Serial.println((stop - start) / 8.0);
Serial.println();
//////////////////////////////////////////////////
//
// write8 read8 interface
//
Serial.print("TEST write8(mask):\t");
delay(100);
start = micros();
MCP.write8(0xAA); // alternating HIGH/LOW
stop = micros();
Serial.println(stop - start);
Serial.print("TEST read8():\t");
delay(100);
start = micros();
volatile int val8 = MCP.read8();
stop = micros();
Serial.println(stop - start);
Serial.println();
Serial.println("\ndone...");
}
void loop()
{
}
// -- END OF FILE --

View File

@ -0,0 +1,23 @@
{
"name": "MCP23008",
"keywords": "MCP23008,I2C, 8 IO, polarity, pullup",
"description": "Arduino library for I2C MCP23008 8 channel port expander",
"authors":
[
{
"name": "Rob Tillaart",
"email": "Rob.Tillaart@gmail.com",
"maintainer": true
}
],
"repository":
{
"type": "git",
"url": "https://github.com/RobTillaart/MCP23008.git"
},
"version": "0.1.0",
"license": "MIT",
"frameworks": "arduino",
"platforms": "*",
"headers": "MCP23008.h"
}

View File

@ -0,0 +1,11 @@
name=MCP23008
version=0.1.0
author=Rob Tillaart <rob.tillaart@gmail.com>
maintainer=Rob Tillaart <rob.tillaart@gmail.com>
sentence=Arduino library for I2C MCP23008 8 channel port expander 8 IO-lines
paragraph= setPolarity, setPullup
category=Signal Input/Output
url=https://github.com/RobTillaart/MCP23008
architectures=*
includes=MCP23008.h
depends=

View File

@ -0,0 +1,107 @@
//
// FILE: unit_test_001.cpp
// AUTHOR: Rob Tillaart
// DATE: 2022-01-10
// PURPOSE: unit tests for the MCP23008
// https://github.com/RobTillaart/MCP23008
// https://github.com/Arduino-CI/arduino_ci/blob/master/REFERENCE.md
//
// supported assertions
// ----------------------------
// assertEqual(expected, actual); // a == b
// assertNotEqual(unwanted, actual); // a != b
// assertComparativeEquivalent(expected, actual); // abs(a - b) == 0 or (!(a > b) && !(a < b))
// assertComparativeNotEquivalent(unwanted, actual); // abs(a - b) > 0 or ((a > b) || (a < b))
// assertLess(upperBound, actual); // a < b
// assertMore(lowerBound, actual); // a > b
// assertLessOrEqual(upperBound, actual); // a <= b
// assertMoreOrEqual(lowerBound, actual); // a >= b
// assertTrue(actual);
// assertFalse(actual);
// assertNull(actual);
// // special cases for floats
// assertEqualFloat(expected, actual, epsilon); // fabs(a - b) <= epsilon
// assertNotEqualFloat(unwanted, actual, epsilon); // fabs(a - b) >= epsilon
// assertInfinity(actual); // isinf(a)
// assertNotInfinity(actual); // !isinf(a)
// assertNAN(arg); // isnan(a)
// assertNotNAN(arg); // !isnan(a)
#include <ArduinoUnitTests.h>
#include "Arduino.h"
#include "MCP23008.h"
unittest_setup()
{
fprintf(stderr, "MCP23008_LIB_VERSION: %s\n", (char *) MCP23008_LIB_VERSION);
}
unittest_teardown()
{
}
unittest(test_constants)
{
assertEqual(MCP23008_OK , 0x00);
assertEqual(MCP23008_PIN_ERROR , 0x81);
assertEqual(MCP23008_I2C_ERROR , 0x82);
assertEqual(MCP23008_VALUE_ERROR , 0x83);
assertEqual(MCP23008_PORT_ERROR , 0x84);
assertEqual(MCP23008_INVALID_READ, -100);
}
// TODO more tests if godmode->wire works
unittest(test_constructor)
{
Wire.resetMocks();
MCP23008 MCP(0x27);
assertFalse(Wire.didBegin());
MCP.begin();
// in fact invalid ...
assertTrue(Wire.didBegin());
assertTrue(MCP.isConnected());
}
unittest(test_lastError)
{
Wire.resetMocks();
MCP23008 MCP(0x27);
MCP.begin();
assertEqual(MCP23008_OK, MCP.lastError());
// MCP23008_PIN_ERROR
MCP.pinMode(8, INPUT);
assertEqual(MCP23008_PIN_ERROR, MCP.lastError());
assertEqual(MCP23008_OK, MCP.lastError());
MCP.digitalWrite(8, 1);
assertEqual(MCP23008_PIN_ERROR, MCP.lastError());
assertEqual(MCP23008_OK, MCP.lastError());
uint8_t y = MCP.digitalRead(8);
assertEqual(MCP23008_PIN_ERROR, MCP.lastError());
assertEqual(MCP23008_OK, MCP.lastError());
// MCP23008_VALUE_ERROR - 3 is not INPUT, INPUT_PULLUP, OUTPUT)
MCP.pinMode(0, 3);
assertEqual(MCP23008_VALUE_ERROR, MCP.lastError());
assertEqual(MCP23008_OK, MCP.lastError());
}
unittest_main()
// --------