Hi all,
I was trying to adapt the "Arduino as ISP" sketch to use software (bit-bang) SPI rather than hardware SPI so that I could use either an Uno or Mega 2560 board to burn bootloaders and other code.
I wrote a very simple SPI driver and it works just fine on the Uno:
spi.cpp
#include "spi.h"
void spi::init(uint8_t sck, uint8_t miso, uint8_t mosi, uint8_t mode)
{
_sck_pin = sck;
_miso_pin = miso;
_mosi_pin = mosi;
_spi_mode = mode;
digitalWrite(_sck_pin, (_spi_mode % 2) ? HIGH : LOW);
pinMode(_sck_pin, OUTPUT);
pinMode(_miso_pin, INPUT);
pinMode(_mosi_pin, OUTPUT);
}
uint8_t spi::transfer(uint8_t data)
{
uint8_t n = 0x80;
do {
digitalWrite(_mosi_pin, data & n);
digitalWrite(_sck_pin, (_spi_mode % 2) ? LOW : HIGH);
if (digitalRead(_miso_pin)) {
data |= n;
} else {
data &= ~n;
}
digitalWrite(_sck_pin, (_spi_mode % 2) ? HIGH : LOW);
} while (n /= 2);
return data;
}
spi.h
#ifndef _SOFTWARE_SPI
#define _SOFTWARE_SPI
#if ARDUINO >= 100
#include "Arduino.h"
#else
#include "WProgram.h"
#endif
class spi {
public:
void init(uint8_t, uint8_t, uint8_t, uint8_t);
uint8_t transfer(uint8_t);
private:
uint8_t _sck_pin;
uint8_t _miso_pin;
uint8_t _mosi_pin;
uint8_t _spi_mode;
};
#endif
To use it, all you do it create an spi object, then init() the code, then use the spi object:
#define sck 13
#define miso 12
#define mosi 11
#define ss 10
#define mode 0
static spi spi; // spi object
pinMode(ss, OUTPUT);
spi.init(sck, miso, mosi, mode);
digitalWrite(ss, HIGH);
returncode = spi.transfer(0x??); // write
digitalWrite(ss, LOW);
As simple as can be. Works great on the Uno R3 board.
But if I try to use the same code on a Mega 2560 R3 board, it doesn't work!
Now I know that the 2560 HARDWARE SPI pins are different numbers, but I am not using that. I am using plain old "digitalRead" and "digitalWrite".
If I write to, say, pin 10, it shouldn't matter which board I'm using. 10 is 10. Right?
Anyone have an idea what the problem could be?
Thanks.
-- Roger