I'm trying to interface with a BNO055 breakout board from a Teensy 2.0, but I'm having trouble reading from the BNO055. It has different registers that you can access to read data from the chip. To start, I'm just trying to read the IDs of some internal parts. No matter what I do, I seem to only get the last value that I put in TWDR
. Trying to do a read doesn't seem to populate it. This is what I have in my main:
void main(void) {
CPU_PRESCALE(CPU_16MHz);
init_sensor();
char buffer[50];
sprintf(buffer, "Chip ID: %X\n", read_address(0x00));
while(1) {
_delay_ms(20);
}
}
This is my BNO055.c:
#include "BNO055.h"
#include <avr/io.h>
// The breakout board pulls COM3_state low internally
#define DEVICE_ADDR 0x29
#define READ 0
#define WRITE 1
#define F_CPU 16000000UL
#define SCL_CLOCK 400000L
inline void start(void) {
TWCR = (1<<TWINT) | (1<<TWSTA) | (1<<TWEN);
while ( !(TWCR & (1<<TWINT)));
}
inline void stop(void) {
TWCR = (1 << TWINT) | (1 << TWSTO) | (1 << TWEN);
while(TWCR & (1 << TWSTO));
}
void send_address(uint8_t w) {
TWDR = (DEVICE_ADDR<<1) | w ;
TWCR = (1 << TWINT) | (1<<TWEN);
while(!(TWCR & (1 << TWINT)));
}
uint8_t read(void) {
TWCR = (1 << TWINT) | (1 << TWEN);
while(!(TWCR & (1 << TWINT)));
return TWDR;
}
void write(uint8_t data) {
TWDR = data;
TWCR = (1 << TWINT) | (1<<TWEN);
while(!(TWCR & (1 << TWINT)));
}
uint8_t read_address(uint8_t addr) {
start();
send_address(WRITE);
write(addr);
stop();
start();
send_address(READ);
const uint8_t value = read();
stop();
return value;
}
void write_address(uint8_t addr, uint8_t value) {
start();
send_address(WRITE);
write(addr);
write(value);
stop();
}
uint8_t status(void) {
return TWSR & 0xF8;
}
void init_sensor(void) {
// Setup I2C
DDRD &= ~((1 << 0) | (1 << 1));
PORTD |= ((1 << 0) | (1 << 1));
TWBR = ((( F_CPU / SCL_CLOCK ) - 16) / 2);
TWSR = 0;
TWCR = ((1 << TWEN) | (1 << TWIE) | (1 << TWEA));
}