Jump to content
I2Cdevlib Forums

Dealing with FIFO overflow and running in the background


Recommended Posts

Hello,

 

I'm attempting to use the MPU-6050 in conjunction with the Adafruit Wave sheild, seen here: http://www.adafruit.com/product/94

 

The problem occurs whenever a sound file is played, playing the file slows the code down enough that the MPU can't be read fast enough to empty the FIFO buffer and an overflow occurs.

 

When not playing the file, it reads fine, but while playing anything, overflows occur. It is running at 20Hz and this still occurs.

 

Is there any way to just have the DMP calculate the quaternion on its own and output it when asked to?

 

The shield uses SPI communication. Relevant code:

 

/***
 *  FUNCTION:  PlayPhrase
 *
 *  PROGRAMMER:  adafruit, https://learn.adafruit.com/system/assets/assets/000/010/349/original/wavehc_play6.pde.txt
 *
 *  UPDATE:  1-Aug-14
 *
 *  PURPOSE:  Play a .wav file from an sd card, stop the wave if an event has been detected
 *
 *  CALL:  PlayPhrase(char* name,byte type )
 *
 *  WHERE:  name = character array of name of file, must be in 8.3 format with .wav as the last 4 characters
 *          type = byte determining whether to play the full wav file, 0 stops if an event is detected, 1 plays through
 *
 *  INPUTS:  name, type
 *
 *  OUTPUTS:  plays sound
 *
 *  NOTES:  adopted from an adafruit provided code
 ***/
void PlayPhrase(char *name, byte type)
{
  if (wave.isplaying) {                    // already playing something, so stop it!
    wave.stop();                           // stop it
  }


  // look in the root directory and open the file
  if (!f.open(root, name)) {
    putstring("Couldn't open file "); 
    Serial.print(name); 
    return;
  }


  // OK read the file and turn it into a wave object
  if (!wave.create(f)) {
    putstring_nl("Not a valid WAV"); 
    return;
  }


  // ok time to play! start playback
  wave.play();


  //original has nothing in this while loop
  while(wave.isplaying){
    Serial.println(millis());
    if (type<1){
      BaseLineCalc();             //updates the baseline while playing
    }
}

mpuInterrupt is the flag changed in an ISR

/***
 *  FUNCTION:  BaseLineCalc
 *
 *  PROGRAMMER: 
 *
 *  UPDATE:   10/16/14
 *
 *  PURPOSE:  calculates the baseline
 *
 *  CALL: BaseLineCalc()
 *
 *  WHERE: baseLine is a global variable representing the current baseline
 *
 *  INPUTS: 
 *
 *  OUTPUTS: 
 *
 *  NOTES: reads pot then updates the average, which is the output
 ***/
void BaseLineCalc()
{
  int average=0;
  int sensor=GetSensorData();
  if (sensor>=0){
    Serial.print("\t");
    Serial.print(intcounter);
    intcounter=0;
    baseNum++;
    if (baseNum>= BASE_LENGTH ){  //if baseline index is greater than the size of the base
      baseNum=0;                             //reset the index
    }
    base[baseNum]=sensor;            //read the pot value and store it


    for (byte m=0;m<BASE_LENGTH ;m++){
      average=average+base[m];               //sums all the entries in base


    }
    average=(average/BASE_LENGTH);  //takes the average


    baseLine=average;
//    Serial.print("\tBaseline:\t");
//    Serial.print(baseLine);
//    Serial.print("\t");




    //  delay(DELAY_TIME);
  }
  else{
    intcounter++;
  }
}


/***
 *  FUNCTION:  GetSensorData
 *  PROGRAMMER:
 *
 *  UPDATE: 10/16/14
 *
 *  PURPOSE:  reads sensor data and outputs and int scaled from 0 to 1024
 *
 *  CALL:  GetSensorData()
 *
 *  WHERE:  N/A
 *
 *  INPUTS: analog reading from sensor
 *
 *  OUTPUTS: int value from 0 to 1024
 *
 *  NOTES: expand for different sensors
 */
int GetSensorData(){
  int output=2;


  if (mpuInterrupt){        //if the sensor has something ready, read it
    // reset interrupt flag and get INT_STATUS byte
    mpuInterrupt = false;


    mpuIntStatus = mpu.getIntStatus();


    // get current FIFO count
    fifoCount = mpu.getFIFOCount();


    // check for overflow (this should never happen unless our code is too inefficient)
    if ((mpuIntStatus & 0x10) || fifoCount == 1024) {
      // reset so we can continue cleanly
      mpu.resetFIFO();
      Serial.print(F("\tFIFO overflow!"));
      PlayPhrase("900.wav",1);


      // otherwise, check for DMP data ready interrupt (this should happen frequently)
    } 
    if (mpuIntStatus & 0x02) {
      // wait for correct available data length, should be a VERY short wait
      while (fifoCount < packetSize) fifoCount = mpu.getFIFOCount();


      // read a packet from FIFO
      mpu.getFIFOBytes(fifoBuffer, packetSize);


      // track FIFO count here in case there is > 1 packet available
      // (this lets us immediately read more without waiting for an interrupt)
      fifoCount -= packetSize;


      // display quaternion values in easy matrix form: w x y z
      mpu.dmpGetQuaternion(&q, fifoBuffer);
//      Serial.print("\nquat\t");
//      Serial.print(q.w);
//      Serial.print("\t");
//      Serial.print(q.x);
//      Serial.print("\t");
//      Serial.print(q.y);
//      Serial.print("\t");
//      Serial.print(q.z);
//      Serial.print("\ttime\t");
//      Serial.print(millis());
    }


    return output;
  }
  else{
    return -1;
  }
}

Thanks.

Link to comment
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Loading...
×
×
  • Create New...