Read data from an ADIS16355 IMU and write it to the USB port.

Dependencies:   mbed

Revision:
0:c6ee363ac724
diff -r 000000000000 -r c6ee363ac724 imu-spi.cpp
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/imu-spi.cpp	Wed Aug 10 21:50:36 2011 +0000
@@ -0,0 +1,98 @@
+//
+// imu-spi.cpp
+//
+// copyright 2010 Hugh Shane
+//
+#include "mbed.h"
+#include "imu-spi.h"
+
+ImuSpi::ImuSpi(void) :
+    spi(p5, p6, p7), // mosi, miso, sclk
+    cs(p8), // IMU chip select
+    reset(p8), // IMU reset. CAUTION! This also resets the altimeter.
+    diag(p21), // diagnostic output
+    imuDataReady(p11) // interrupt on IMU data-ready
+{
+    // Setup the spi for 16 bit data, high steady state clock,
+    // second edge capture, with a 1 MHz clock rate
+    spi.format(16,3);
+    spi.frequency(1000000);
+    
+    // init the pingpong buffer
+    pingpong = 0;
+    
+    // init the interrupt semaphore
+    dataReady = false;    
+    
+    // interrupt on the falling edge of the IMU data-ready signal
+    diag = 0;
+    imuDataReady.fall(this, &ImuSpi::DataReadyISR);
+    
+    // init the IMU
+    InitImu();
+
+}
+
+void  ImuSpi::reinitInterrupts(void) {
+    imuDataReady.fall(this, &ImuSpi::DataReadyISR);
+}
+
+// initialize the IMU
+void ImuSpi::InitImu(void) {
+    // deselect the IMU
+    cs = 1;
+    reset = 1;
+    // perform a hard reset
+    reset = 0; wait(.1); reset = 1;    
+    // send initialization commands
+    Write(0x34, 0x04); // enable active low data ready on DIO1
+    Write(0x38, 0x00); // Set the FIR filter to its widest possible bandwidth
+}
+
+// read the IMU accelerometer and gyro registers into the pingpong buffer
+void ImuSpi::BurstRead(void) {
+    static int16_t imuRegs[] = {0x04,0x06,0x08,0x0A,0x0C,0x0E,0x3C};
+    int16_t* wp = GetBufferWritePtr();
+    Read(imuRegs[0]); // set up the first register read operation
+    wait(0.000024); // required to meet IMU t(datarate) spec
+    
+    // send register read commands & read the registers
+    for (int i = 1; i <= 6; i++) {
+        *wp++ = Read(imuRegs[i]);
+        wait(0.000024);
+    }
+    *wp = Read(0); // read the last register output
+}
+
+int16_t ImuSpi::Read(char adr) {
+    int16_t cmd = 0x3f00 & (adr << 8);
+    int16_t response;
+    cs = 0;
+    response = spi.write(cmd);
+    cs = 1;
+    return response;
+}
+
+
+void ImuSpi::Write(char adr, char data) {
+    int16_t cmd = 0x8000 | (adr << 8) | data;
+    cs = 0;
+    spi.write(cmd);
+    cs = 1;
+}
+
+bool ImuSpi::IsDataReady(void) {
+    if (dataReady == true) {
+        dataReady = false;
+        return true;
+    } else {
+        return false;
+    }
+}
+
+void ImuSpi::DataReadyISR(void) {
+diag = 1;
+    TogglePingpong();
+    dataReady = true;
+diag = 0;
+}