Go Down

Topic: error after changing the I2C bus speed (Read 51 times) previous topic - next topic

janjan210

Nov 08, 2014, 01:22 pm Last Edit: Nov 08, 2014, 03:27 pm by janjan210
Hello,
I have a question concerning "change of the I2c speed"

For my project i wired up a ADXL345 acc. sensor with an arduino Uno and an ethernet shield.
I use the SD card slot of the Ethernet shield to write the sensor data (xyz) to an SD card.

Unfortunately the sampling rate is to slow and i only achieve around 250 hz sampling rate.
I need around 1khz for dynamic measures.

I read about the possibility of changing the I2c speed from 100khz up to 400khz by changing

\Arduino\libraries\Wire\utility\twi.h

from

Code: [Select]
#ifndef TWI_FREQ
 #define TWI_FREQ 100000L
 #endif


to

Code: [Select]
#ifndef TWI_FREQ
 #define TWI_FREQ 400000L
 #endif


I did this, saved the file and restarted the Arduino IDE and did an upload of the code to my arduino.

Since i did this, the program stops in line

Serial.println("initializing the SD card..."); almost at the beginning of the setup part.


Does anyone know, if i have do change something else, or if I have to recompile the library?

I use a 2 m cable to connect the ADXL345 to the arduino

After changing the parameter back to 100khz everything is fine again.

In http://forum.arduino.cc/index.php/topic,16793.0.html the author says, you have
to delete
hardware/libraries/Wire/Wire.o
hardware/libraries/Wire/utility/twi.o

because the library must be re-compiled before it uses the new speed.
(This is done automaticaly when you open the Arduino-IDE)

but in my case, these files do not exist.


The code of my project:


Code: [Select]
#include <Wire.h>
#include <Adafruit_Sensor.h>
#include <Adafruit_ADXL345_U.h>
#include <SD.h>

unsigned long time;
File myFile;

/* Assign a unique ID to this sensor at the same time */
Adafruit_ADXL345_Unified accel = Adafruit_ADXL345_Unified(12345);

//void setDataRate(ADXL345_DATARATE_800HZ);

void displaySensorDetails(void)
{
 sensor_t sensor;
 accel.getSensor(&sensor);
 Serial.println("------------------------------------");
 Serial.print  ("Sensor:       ");
 Serial.println(sensor.name);
 Serial.print  ("Driver Ver:   ");
 Serial.println(sensor.version);
 Serial.print  ("Unique ID:    ");
 Serial.println(sensor.sensor_id);
 Serial.print  ("Max Value:    ");
 Serial.print(sensor.max_value);
 Serial.println(" m/s^2");
 Serial.print  ("Min Value:    ");
 Serial.print(sensor.min_value);
 Serial.println(" m/s^2");
 Serial.print  ("Resolution:   ");
 Serial.print(sensor.resolution);
 Serial.println(" m/s^2");  
 Serial.println("------------------------------------");
 Serial.println("");
 delay(500);
}

void displayDataRate(void)
{
 Serial.print  ("Data Rate:    ");

 switch(accel.getDataRate())
 {
 case ADXL345_DATARATE_3200_HZ:
   Serial.print  ("3200 ");
   break;
 case ADXL345_DATARATE_1600_HZ:
   Serial.print  ("1600 ");
   break;
 case ADXL345_DATARATE_800_HZ:
   Serial.print  ("800 ");
   break;
 case ADXL345_DATARATE_400_HZ:
   Serial.print  ("400 ");
   break;
 case ADXL345_DATARATE_200_HZ:
   Serial.print  ("200 ");
   break;
 case ADXL345_DATARATE_100_HZ:
   Serial.print  ("100 ");
   break;
 case ADXL345_DATARATE_50_HZ:
   Serial.print  ("50 ");
   break;
 case ADXL345_DATARATE_25_HZ:
   Serial.print  ("25 ");
   break;
 case ADXL345_DATARATE_12_5_HZ:
   Serial.print  ("12.5 ");
   break;
 case ADXL345_DATARATE_6_25HZ:
   Serial.print  ("6.25 ");
   break;
 case ADXL345_DATARATE_3_13_HZ:
   Serial.print  ("3.13 ");
   break;
 case ADXL345_DATARATE_1_56_HZ:
   Serial.print  ("1.56 ");
   break;
 case ADXL345_DATARATE_0_78_HZ:
   Serial.print  ("0.78 ");
   break;
 case ADXL345_DATARATE_0_39_HZ:
   Serial.print  ("0.39 ");
   break;
 case ADXL345_DATARATE_0_20_HZ:
   Serial.print  ("0.20 ");
   break;
 case ADXL345_DATARATE_0_10_HZ:
   Serial.print  ("0.10 ");
   break;
 default:
   Serial.print  ("???? ");
   break;
 }  
 Serial.println(" Hz");  
}

void displayRange(void)
{
 Serial.print  ("Range:         +/- ");

 switch(accel.getRange())
 {
 case ADXL345_RANGE_16_G:
   Serial.print  ("16 ");
   break;
 case ADXL345_RANGE_8_G:
   Serial.print  ("8 ");
   break;
 case ADXL345_RANGE_4_G:
   Serial.print  ("4 ");
   break;
 case ADXL345_RANGE_2_G:
   Serial.print  ("2 ");
   break;
 default:
   Serial.print  ("?? ");
   break;
 }  
 Serial.println(" g");  
}


void setup(void)
{
 Serial.begin(9600);

 Serial.println("initializing the SD card...");

 if (!SD.begin(4)) //selbstcheck aufruf SD.beginn i2c pin4
 {
   Serial.println("Initializing failed!!");
   return;
 }
 Serial.println("Initializing completed");
 Serial.println("Accelerometer Test");
 Serial.println("");
 
 /* Initialise the sensor */
 if(!accel.begin())
 {
   /* There was a problem detecting the ADXL345 ... check your connections */
   Serial.println("Ooops, no ADXL345 detected ... Check your wiring!");
   while(1);
 }

 /* Set the range to whatever is appropriate for your project */
 accel.setRange(ADXL345_RANGE_16_G);
 // displaySetRange(ADXL345_RANGE_8_G);
 // displaySetRange(ADXL345_RANGE_4_G);
 // displaySetRange(ADXL345_RANGE_2_G);

 accel.setDataRate(ADXL345_DATARATE_1600_HZ);
 
 /* Display some basic information on this sensor */
 displaySensorDetails();

 /* Display additional settings (outside the scope of sensor_t) */
 displayDataRate();
 displayRange();
 Serial.println("");
}


 
void loop(void)
{
 unsigned long start=millis();
 myFile = SD.open("logtest.csv", FILE_WRITE);
 while (millis()-start<1000L)
 {
   /* Get a new sensor event */
   sensors_event_t event;
   accel.getEvent(&event);
   time = millis();

   /* write action to sd card, */
   myFile.print(time);
   myFile.print(" , ");
   myFile.print(event.acceleration.x);
   myFile.print(" , ");
   myFile.print(event.acceleration.y);
   myFile.print(" , ");
   myFile.print(event.acceleration.z);
   myFile.println(" ");
 }
 myFile.close();
}

 

Thanks a lot!

robtillaart

#1
Nov 08, 2014, 02:09 pm Last Edit: Nov 08, 2014, 02:10 pm by robtillaart
please use code tags - second icon from the right.

The problem is that the SD apparently does not support the fast mode

The solution is to patch the ADXL345 library in the following way (I don't have the lib so it is approx).

Code: [Select]
int ADXL345.read()
{
   wire.begin...

   wire.End...
}


==>

Code: [Select]
int ADXL345.read()
{
   uint8_t OLDTWWBR = TWBR;  // remember
   TWBR = 12; // this register effectively sets 400KHz
   wire.begin...

   wire.End...
   TWBR = OLDTWBR; // set back
}


and that for all the methods that do wire calls.

check my multispeed I2C scanner - http://forum.arduino.cc/index.php?topic=197360.0 -
Rob Tillaart

Nederlandse sectie - http://arduino.cc/forum/index.php/board,77.0.html -
(Please do not PM for private consultancy)

janjan210

#2
Nov 08, 2014, 03:25 pm Last Edit: Nov 08, 2014, 03:26 pm by janjan210
ok, i will check

Go Up