Closed felixlindemann closed 1 year ago
Thanks for reporting this issue. As my agenda is rather full it might take several days before I have time to investigate. Furthermore I do not have the hardware to test, i assume you have?
Found a moment to write (copy/paste) a sketch that uses two devices with an Arduino UNO. It uses software SPI so you can adjust pins if you want to. Note that the only difference in the parameters is the SELECT pin. Although the devices share the SWSPI bus, only one will be addressed by means of the SELECT pin.
Not tested with hardware!
//
// FILE: MCP23S17_two.ino
// AUTHOR: Rob Tillaart
// PUPROSE: demo two MCP23017 devices
//
// see issue #19 library
#include "MCP23S17.h"
#include "SPI.h"
MCP23S17 MCP_A(10, 12, 11, 13); // SW SPI
MCP23S17 MCP_B(9 , 12, 11, 13); // SW SPI, different select pin!
// MCP23S17 MCP_A(10); // HW SPI
// MCP23S17 MCP_B(9); // HW SPI, different select pin!
void setup()
{
Serial.begin(115200);
Serial.println();
Serial.print("MCP23S17_LIB_VERSION: ");
Serial.println(MCP23S17_LIB_VERSION);
Serial.println();
delay(100);
SPI.begin();
MCP_A.begin();
MCP_B.begin();
// test connected
int c = testConnection(MCP_A);
Serial.print("Connect A: ");
Serial.println(c);
c = testConnection(MCP_B);
Serial.print("Connect B: ");
Serial.println(c);
// all pins OUTPUT LOW
MCP_A.pinMode16(0);
MCP_A.write16(0x0000);
MCP_B.pinMode16(0);
MCP_B.write16(0x0000);
}
void loop()
{
int x = random(32);
if (x < 16)
{
MCP_A.digitalWrite(x, HIGH);
delay(100);
MCP_A.digitalWrite(x, LOW);
}
else
{
x -= 16;
MCP_B.digitalWrite(x, HIGH);
delay(100);
MCP_B.digitalWrite(x, LOW);
}
}
//
// the connection test tries to write a magic number to a register
// and read it back. If it is the same it is assumed to be connected
//
int testConnection(MCP23S17 & mcp)
{
uint16_t magic_test_number = 0xABCD;
// Read the current polarity config to restore later
uint16_t old_value;
if (! mcp.getPolarity16(old_value)) return -1;
// Write the magic number to polarity register
if (! mcp.setPolarity16(magic_test_number)) return -2;
// Read back the magic number from polarity register
uint16_t temp;
if (! mcp.getPolarity16(temp)) return -3;
// Write old config to polarity register
if (! mcp.setPolarity16(old_value)) return -4;
// Check the magic connection test
if (temp != magic_test_number) return -5;
return 0; // OK
}
// -- END OF FILE --
There should be another way to use multiple devices, by assigning them different addresses. Then in theory they could use even the same SELECT pin. I have never tried this, but given the chip has address pins I expect it to work.
Note, for using the HW address pins, one should enable them - IOCON.HAEN See 3.3.2 datasheet. (need to check library for that)
(checked) This should enable hardware addresses.
MCP.enableControlRegister(0x08);
Created a develop branch which should improve the support for multiple devices.
This branch includes the example above + an example to use the hardware address to operate multiple devices.
Please give it a try and let me know the results.
Wow, That is a fast response. I’ll Check it tonight! Thanks in advance. Felix
hello Rob, I will have to check it on the weekend. I won't make tonight. Thanks for your very fast response I'll get back to you asap.
@felixlindemann Any progress ?
Hi @RobTillaart sorry I am not able to get it to run. In my setup up I want to be flexible according to the wiring - (in my final design I use a canbus board and some pwm servos as well.) for that reason i use the software spi.
The yellow LED on the left flashes randomly the blue in the middle is permanently on. both leds of the second chip are permanently off
here is my Sketch.
here the breedboard
Here is the SoftwareSPI
//
// AUTHOR: Rob Tillaart / Felix Lindemann
// PUPROSE: demo two MCP23017 devices
//
// see issue #19 library
#include "MCP23S17.h"
#include "SPI.h"
const int wCS = 9;
const int wCLK = 13;
const int wSI = 11;
const int wSO = 12;
MCP23S17 MCP_A(wCS,wSI, wSO, wCLK, 0x00 );
MCP23S17 MCP_B(wCS,wSI, wSO, wCLK, 0x01 );
void setup()
{
Serial.begin(115200);
Serial.println();
Serial.print("MCP23S17_LIB_VERSION: ");
Serial.println(MCP23S17_LIB_VERSION);
Serial.println();
delay(500);
SPI.begin();
MCP_A.begin();
MCP_B.begin();
MCP_A.enableHardwareAddress();
MCP_B.enableHardwareAddress();
// all pins OUTPUT LOW
MCP_A.pinMode16(0);
MCP_A.write16(0x0000);
MCP_B.pinMode16(0);
MCP_B.write16(0x0000);
}
void loop()
{
int x= 1;
int y= 8;
Serial.println("8/1");
MCP_A.digitalWrite(x, LOW);
MCP_A.digitalWrite(y, HIGH);
MCP_B.digitalWrite(x, HIGH);
MCP_B.digitalWrite(y, LOW);
delay(1000);
Serial.println("1/8");
MCP_A.digitalWrite(x, HIGH);
MCP_A.digitalWrite(y, LOW);
MCP_B.digitalWrite(x, LOW);
MCP_B.digitalWrite(y, HIGH);
delay(1000);
}
// -- END OF FILE --
int x= 1; int y= 8;
Please try to use x = 0;
and y = 7;
, as pin numbering is 0 based, 0 .. 15
void loop()
{
int x= 0;
int y= 7;
Serial.println("8/1");
MCP_A.digitalWrite(x, LOW);
MCP_A.digitalWrite(y, HIGH);
MCP_B.digitalWrite(x, HIGH);
MCP_B.digitalWrite(y, LOW);
delay(1000);
Serial.println("1/8");
MCP_A.digitalWrite(x, HIGH);
MCP_A.digitalWrite(y, LOW);
MCP_B.digitalWrite(x, LOW);
MCP_B.digitalWrite(y, HIGH);
delay(1000);
}
^ | |____ don't code while tired
obiviously... it works
thanks a lot 👍
I will merge the PR to support the multi device / address code into master asap.
@felixlindemann
What board are you using? I have prototype code for AVR software SPI transfer for the MCP23S17. If you are interested to test it I can send it, it will be part of a - not planned - future release.
Thank you for the Library. With one Chip(=mcp23s17) at a Time, i could get to run. When i tried to Add a Second or Third Chip, the adressing didn’t work. Could you please Provide an example with 2+ Chips- maybe a copy from Chip 1 to Chip 2? Thank you very much Felix