int main() { //create i2c bus. the 0 indicates pull up resistors are present on the i2c line DofBus = i2c_newbus(DofSCL, DofSDA, 0); unsigned char ID = 2; int val = i2c_in(DofBus, GyroAddr, 0x00, 1, (unsigned char*)ID, 1); //get device ID with i2c read print("ID readback: 0x%x", ID); char temp[5]; pause(100); //allow gyro clocks to stabalise //start hyperterminal menu hyperterminal(); while(1) { } return 0; }
short ee_readShort(int addr) { while(lockset(eei2cLock)); int value; i2c_in(st_eeprom, 0x50, addr, 2, (unsigned char*) &value, 2); lockclr(eei2cLock); return value; }
unsigned char* ee_get_str(unsigned char *s, int n, int addr) { if(!st_eeInitFlag) ee_init(); // const unsigned char addrArray[] = {(char)(addr >> 8), (char)(addr&0xFF)}; // i2c_in(st_eeprom, 0xA0, addrArray, 2, s, n); i2c_in(st_eeprom, 0x50, addr, 2, s, n); return s; }
int ee_getInt(int addr) { if(!st_eeInitFlag) ee_init(); //unsigned char val[4] = {0, 0, 0, 0}; int value; // const unsigned char addrArray[] = {(char)(addr >> 8), (char)(addr&0xFF)}; // i2c_in(st_eeprom, 0xA0, addrArray, 2, val, 4); i2c_in(st_eeprom, 0x50, addr, 2, (unsigned char*) &value, 4); // int value = (int)((int)(val[0]) | (int)(val[1] << 8) | (int)(val[2] << 16) | (int)(val[3] << 24)); return value; }
float ee_get_float32(int addr) { if(!eeInitFlag) ee_init(); //int value = 0; unsigned char value[4] = {0, 0, 0, 0}; unsigned char addrArray[] = {(char)(addr >> 8), (char)(addr & 0xFF)}; i2c_in(eeprom, 0xA0, addrArray, 2, value, 4); float fpVal; memcpy(&fpVal, &value, sizeof value); return fpVal; }
int accel(int axis) { if(!st_eeInitFlag) ee_init(); unsigned char val = 0; while(lockset(eei2cLock)); i2c_in (st_eeprom, MMA7660_I2C, axis, 1, &val, 1); i2c_stop(st_eeprom); lockclr(eei2cLock); int g100 = raw2g100(val); if(axis == AY) g100 = -g100; return g100; }
void I2C_ByteRead(I2C_ADDR_t slaveAddress, uint8_t reg, uint8_t* data) { uint8_t num_bytes; uint8_t size = 0; if (reg > 0) { size = sizeof(reg); } lockset(lock); while (i2c_busy(i2c_bus, slaveAddress)) { ; } num_bytes = i2c_in(i2c_bus, slaveAddress, reg, size, data, 1); lockclr(lock); print("\t\tRead addr %02x, reg %02x, data %02x, total %d\n", slaveAddress, reg, *data, num_bytes); }
int main() // Main function { eeBus = i2c_newbus(28, 29, 0); // Set up I2C bus, get bus ID // Use eeBus to write to device i2c_out(eeBus, 0b1010000, // with I2C address 0b1010000, 32768, 2, "abcdefg", 8); // send address 32768 (2 bytes) // and "abc..." data (8 bytes) while(i2c_busy(eeBus, 0b1010000)); // Wait for EEPROM to finish char testStr[] = {0, 0, 0, 0, 0, 0, 0, 0}; // Set up test string // Use eeBus to read from device i2c_in(eeBus, 0b1010000, // with I2C address 0b1010000, 32768, 2, testStr, 8); // send address 32768 (2 bytes) // data in to testStr (8 bytes) print("testStr = %s \n", testStr); // Display result }
void hyperterminal(void) { int menu_no; //hyperterminal switch variable char reg_in[1]; //char to store single byte read in by I2C char reg_out[1]; //char to store single byte to be written to part with I2C int x, y, z; //Stores XYZ output after conversion from reister values int dt, t; //stores timing values: t holds a clock value, dt is compared to it char buffer[6]; //buffer which stores 56 register read backs from a multibyte i2c readback int tic = CNT; float temp = 0; float sum = 0; float xsum = 0; float ysum = 0; float zsum = 0; float prev = 0; float current = 0; while(1) { //menu options print("\n\nSelect a menu option with a number, followed by enter\n"); print("1. Exit hyperterminal \n"); print("2. Read back ID register\n"); print("3. Setup: set clock to Xgyro, sample rate div to 9 (100Hz output), filter 98Hz\n"); print("4. Stream 5 seconds of data\n"); print("5. Stream 30 seconds of data \n"); print("6. 2 second bias calculation\n"); print("7. 10 second cumulative angle calculation\n"); print("8. Timing readout debugger\n"); //get user input. Must be a number! follow with enter scanf("%d", &menu_no); switch(menu_no) { case 1: return; //Exit hyperterminal break; case 2: //dev ID readback i2c_in(DofBus, GyroAddr, 0x00, 1, (unsigned char*)reg_in, 1); print("ID readback: 0x%x\n\n", reg_in[0]); break; case 3: //see ITG3200 data sheet reg_out[0] = 0x01; //Power control: Set clk to xGyro, all gyros on i2c_out(DofBus, GyroAddr, 0x3E, 1, (unsigned char*)reg_out, 1); i2c_in(DofBus, GyroAddr, 0x3E, 1, (unsigned char*)reg_in, 1); print("Power control: 0x%x\n", reg_in[0]); reg_out[0] = 0x09; //Sample rate divider: set to 9, gives x/10 = sample output rate, where x is internal rate i2c_out(DofBus, GyroAddr, 0x15, 1, (unsigned char*)reg_out, 1); i2c_in(DofBus, GyroAddr, 0x15, 1, (unsigned char*)reg_in, 1); print("Rate divider: 0x%x\n", reg_in[0]); reg_out[0] = 0x1A; //scale selection and digital filter: bits 4&5: = 0b11: full scale. bits 2 10: i2c_out(DofBus, GyroAddr, 0x16, 1, (unsigned char*)reg_out, 1); i2c_in(DofBus, GyroAddr, 0x16, 1, (unsigned char*)reg_in, 1); print("Digital Filter: 0x%x\n", reg_in[0]); break; case 4: dt = CLKFREQ*5; // 5 second timeout //CLKFREQ contains the number of ticks in one second, CNT returns current tick no t = CNT; // Mark current time by storing in t while(CNT - t < dt) // Repeat until timeout { i2c_in(DofBus, GyroAddr, 0x1D, 1, (unsigned char*)buffer, 6); //read 6 registers starting at 0x1D - data registers x = twos2signed(buffer[0], buffer[1]) - xGyroDrift; //convert 2s compliment split into 2 registers into signed y = twos2signed(buffer[2], buffer[3]) - yGyroDrift; //and subtract gyro drift z = twos2signed(buffer[4], buffer[5]) - zGyroDrift; print("\nX: %d Y: %d Z: %d\n", x, y, z); pause(500); } break; case 5: dt = CLKFREQ*30; // 30 second timeout t = CNT; // Mark current time by storing in t while(CNT - t < dt) // Repeat until timeout { i2c_in(DofBus, GyroAddr, 0x1D, 1, (unsigned char*)buffer, 6); x = twos2signed(buffer[0], buffer[1]) - xGyroDrift; y = twos2signed(buffer[2], buffer[3]) - yGyroDrift; z = twos2signed(buffer[4], buffer[5]) - zGyroDrift; print("\nX: %d Y: %d Z: %d\n", x, y, z); pause(500); } break; case 6: tic = CNT; dt = CLKFREQ/100; //100HZ cycle NB. integer math xsum = 0; ysum = 0; zsum = 0; for (int i = 0; i < 400; i++) // 4 seconds { t = CNT; // Mark current time by storing in t i2c_in(DofBus, GyroAddr, 0x1D, 1, (unsigned char*)buffer, 6); xsum += ((float)twos2signed(buffer[0], buffer[1])) / 400; //running 400 piece average ysum += ((float)twos2signed(buffer[2], buffer[3])) / 400; zsum += ((float)twos2signed(buffer[4], buffer[5])) / 400; while(CNT - t < dt){} } print("\nelapsed time: %f\n", ((float)(CNT-tic))/CLKFREQ ); print("xdrift: %f, ydrift: %f, zdrift: %f\n", xsum, ysum, zsum); break; case 7: //currently set up for y axis //by taking the variance over a known total rotation (ie rotating exactly 90 degrees, and reading 93 degrees) //a variance in the Gyro scaling factor can be estimated as (93-90)/90 = 3.33% //print("\nGyro conversion factor: %f\n", GyroConv); dt = CLKFREQ/100; //200HZ cycle NB integer math here prev = 0; current = 0; sum = 0; //aqquire first sample t = CNT; // Mark current time by storing in t i2c_in(DofBus, GyroAddr, 0x1D, 1, (unsigned char*)buffer, 6); prev= ( (float)twos2signed(buffer[2], buffer[3]) -yGyroDrift) * yGyroConv; while(CNT - t < dt); //calculate angle over time by taking consecutive values, and using tustins approximation to integration (check name?) //sum this angle over consecutive points for (int i = 0; i < 1000; i++) // 1000 samples/100HZ = 10 seconds. { t = CNT; // Mark current time by storing in t i2c_in(DofBus, GyroAddr, 0x1D, 1, (unsigned char*)buffer, 6); current= ( (float)twos2signed(buffer[2], buffer[3]) -yGyroDrift) * yGyroConv; sum += (current +prev) * 0.01/2; //Tustins approximation to integration prev = current; while(CNT - t < dt){} } print("\nFinal Rotation: %f\n", sum); break; case 8: //debugging case - replace code with whatever suits print("\n\nCLKFREQ: %d\n", CLKFREQ); tic = CNT; dt = CLKFREQ/2; //2HZ cycle NB. integer math sum = 0; for (int i = 0; i < 10; i++) // 5 seconds { t = CNT; // Mark current time by storing in t pause(1); //print("Reading: %f sum: %f\n", temp, sum); while(CNT - t < dt){} } print("\nCNT-tic: %d\n", CNT-tic); print("elapsed time: %f\n", ((float)(CNT-tic))/CLKFREQ ); break; default: //code break; } } }
/** * @brief Interrupt service routine for i2c-1 * @param[in] None * @return None */ static void i2c1ISR(void) { int32_t csr, val; i2c_dev *dev; dev = (i2c_dev *) ( (uint32_t)&i2c_device[1] ); csr = i2c_in(dev, I2C_CSR); csr |= 0x04; i2c_out(dev, csr, I2C_CSR); /* clear interrupt flag */ if(dev->state == I2C_STATE_NOP) return; if((csr & 0x800) && bNackValid) /* NACK only valid in WRITE */ { dev->last_error = I2C_ERR_NACK; _i2cCommand(dev, I2C_CMD_STOP); dev->state = I2C_STATE_NOP; } else if(csr & 0x200) /* Arbitration lost */ { sysprintf("Arbitration lost\n"); dev->last_error = I2C_ERR_LOSTARBITRATION; dev->state = I2C_STATE_NOP; } else if(!(csr & 0x100)) /* transmit complete */ { if(dev->pos < dev->subaddr_len + 1) /* send address state */ { val = dev->buffer[dev->pos++] & 0xff; i2c_out(dev, val, I2C_TxR); _i2cCommand(dev, I2C_CMD_WRITE); } else if(dev->state == I2C_STATE_READ) { /* sub address send over , begin restart a read command */ if(dev->pos == dev->subaddr_len + 1) { val = dev->buffer[dev->pos++]; i2c_out(dev, val, I2C_TxR); _i2cCommand(dev, I2C_CMD_START | I2C_CMD_WRITE); } else { dev->buffer[dev->pos++] = i2c_in(dev, I2C_RxR) & 0xff; if( dev->pos < dev->len) { if(dev->pos == dev->len -1 ) /* last character */ _i2cCommand(dev, I2C_CMD_READ | I2C_CMD_STOP | I2C_CMD_NACK); else _i2cCommand(dev, I2C_CMD_READ); } else { dev->state = I2C_STATE_NOP; } } } else if(dev->state == I2C_STATE_WRITE) /* write data */ { if( dev->pos < dev->len) { val = dev->buffer[dev->pos]; i2c_out(dev, val, I2C_TxR); if(dev->pos == dev->len -1 ) /* last character */ _i2cCommand(dev, I2C_CMD_WRITE| I2C_CMD_STOP); else _i2cCommand(dev, I2C_CMD_WRITE); dev->pos ++; } else { dev->state = I2C_STATE_NOP; } } } }