I am using SPI to communicate with a IMU device which is working perfectly, except the SPISpeed which is not being altered as it should:
unsigned int m_SPISpeed = 400000;
SPI.begin();
pinMode(m_SPISelect, OUTPUT);
m_SPISettings = SPISettings(m_SPISpeed, MSBFIRST, SPI_MODE0);
...
SPI.beginTransaction(m_SPISettings);
digitalWrite(m_SPISelect, LOW);
SPI.transfer(regAddr | 0x80);
Where m_SPISpeed
is 400000. No matter what i set this value to it is always operating at 125000Hz
.
1 Answer 1
As was pointed out in the question comments, your use of unsigned int is the problem. The prototype for SPISettings is:
SPISettings(uint32_t clock, uint8_t bitOrder, uint8_t dataMode) {
The comments in spi.h say:
// We find the fastest clock that is less than or equal to the
// given clock rate. The clock divider that results in clock_setting
// is 2 ^^ (clock_div + 1). If nothing is slow enough, we'll use the
// slowest (128 == 2 ^^ 7, so clock_div = 6).
So your SPI speed will be the processor speed divided by 128, which is 16 MHz divided by 128, being 125000 Hz, which is your observed result (since unsigned int cannot possibly hold more than 65535 on this platform).
unsigned int
4000000L
, looking at the source code for the new SPI library, it applies a simple algorithm to get a clock divider, so unless you're spot on with a multiple, you get the next lowest.