Pages: [1]   Go Down
Author Topic: should I upgrade to the SD library ? ( from the wavehc )  (Read 2119 times)
0 Members and 1 Guest are viewing this topic.
Cape Town South Africa
Offline Offline
Edison Member
*
Karma: 19
Posts: 1217
A newbie with loads of posts, and still so much to learn !
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

I have been busy on several projects at once, and havn't checked on playing audio files from an SD card for a while.
I made my project that announces a message, controlled from another arduino chip that does the video side, using the wavehc library, which I copied and pasted , but never really understood.

I had one problem when trying to queue the messages ( done on the video chip ) but I got round that by removing the "if playing STOP"  part.

I did have hassles with some makes of SD card ( 2Gb) not working, but I used 4 of the same Kingston cards that seemed OK.

2 of these units have had the card fail, one which is a real failure, and the other I can still see the wav files on it, but it doesn't work.

I remember there was some talk about it being fussy with which cards are used.

Will the new SD library overcome this problem ?  I am using the 328 chips programmed from a Duemilanove board.

My existing code for the sound chip is below, would it be easy to update?
Code:
#include <ArduinoPins.h>
#include <FatReader.h>
#include <FatStructs.h>
#include <mcpDac.h>
#include <SdInfo.h>
#include <SdReader.h>
#include <WaveHC.h>
#include <Wavemainpage.h>
#include <WavePinDefs.h>
#include <WaveUtil.h>


#include <FatReader.h>
#include <SdReader.h>
#include <avr/pgmspace.h>
#include "WaveUtil.h"
#include "WaveHC.h"


SdReader card;    // This object holds the information for the card
FatVolume vol;    // This holds the information for the partition on the card
FatReader root;   // This holds the information for the filesystem on the card
FatReader f; // This holds the information for the file we're play

WaveHC wave; // This is the only wave (audio) object, since we will only play one at a time

#define DEBOUNCE 100  // button debouncer

// testing bcd conversion

int talkingPin = 19;  // high while audio playing to video chip to keep number on.
int aPin =18; //define pin numbers for bcd inputs from dequeued  HT12D
int bPin =17;
int cPin =15;
int dPin =16;
int vtPin = 14; // define pin numbers for valid transmission input from HT12D
int track ; // define audio track number
int bcda ; // define bcd digitalreads for BCD/dec conversion
int bcdb;
int bcdc;
int bcdd;
int valid ;  // to be set high if vt in

// this handy function will return the number of bytes currently free in RAM, great for debugging!
int freeRam(void)
{
  extern int  __bss_end;
  extern int  *__brkval;
  int free_memory;
  if((int)__brkval == 0) {
    free_memory = ((int)&free_memory) - ((int)&__bss_end);
  }
  else {
    free_memory = ((int)&free_memory) - ((int)__brkval);
  }
  return free_memory;
}

void sdErrorCheck(void)
{
  if (!card.errorCode()) return;
  putstring("\n\rSD I/O error: ");
  Serial.print(card.errorCode(), HEX);
  putstring(", ");
  Serial.println(card.errorData(), HEX);
  while(1);

}

void setup() {
  // set up serial port
  Serial.begin(9600);

  pinMode (aPin,INPUT);  //bcd inputs from HT12
  pinMode (bPin,INPUT);
  pinMode (cPin,INPUT);
  pinMode (dPin,INPUT);
  pinMode (vtPin,INPUT);  // valid trasnmission input
  pinMode (talkingPin,OUTPUT); // display enable to vga chip




  putstring_nl("WaveHC with 9 inputs");

  putstring("Free RAM: "); // This can help with debugging, running out of RAM is bad
  Serial.println(freeRam()); // if this is under 150 bytes it may spell trouble!

  // Set the output pins for the DAC control. This pins are defined in the library
  pinMode(2, OUTPUT);
  pinMode(3, OUTPUT);
  pinMode(4, OUTPUT);
  pinMode(5, OUTPUT);

  // pin13 LED
  pinMode(13, OUTPUT);

  // enable pull-up resistors on switch pins (analog inputs)
  // digitalWrite(14, HIGH);
  //digitalWrite(15, HIGH);
  // digitalWrite(16, HIGH);
  //digitalWrite(17, HIGH);
  // digitalWrite(18, HIGH);
  // digitalWrite(19, HIGH);

  //  if (!card.init(true)) { //play with 4 MHz spi if 8MHz isn't working for you
  if (!card.init()) {   //play with 8 MHz spi (default faster!)
    putstring_nl("Card init. failed!");  // Something went wrong, lets print out why
    sdErrorCheck();
    while(1);    // then 'halt' - do nothing!
  }

  // enable optimize read - some cards may timeout. Disable if you're having problems
  card.partialBlockRead(true);

  // Now we will look for a FAT partition!
  uint8_t part;
  for (part = 0; part < 5; part++) {     // we have up to 5 slots to look in
    if (vol.init(card, part))
      break;     // we found one, lets bail
  }
  if (part == 5) {     // if we ended up not finding one  :(
    putstring_nl("No valid FAT partition!");
    sdErrorCheck(); // Something went wrong, lets print out why
    while(1);    // then 'halt' - do nothing!
  }

  // Lets tell the user about what we found
  putstring("Using partition ");
  Serial.print(part, DEC);
  putstring(", type is FAT");
  Serial.println(vol.fatType(),DEC);     // FAT16 or FAT32?

  // Try to open the root directory
  if (!root.openRoot(vol)) {
    putstring_nl("Can't open root dir!"); // Something went wrong,
    while(1);     // then 'halt' - do nothing!
  }

  // Whew! We got past the tough parts.
  putstring_nl("Ready!");
}

void loop() {

  bcda = digitalRead ( aPin );  // read the state of the video micro dequeued "decode" data outputs  
  bcdb = digitalRead ( bPin );
  bcdc = digitalRead ( cPin );
  bcdd = digitalRead ( dPin );
  valid = digitalRead ( vtPin );  // check if signal received, set valid high

  if (bcda==1 && bcdb==0 && bcdc == 0 && bcdd == 0 ) { //bcd / dec decoding to give track number to be read
    track = 1;
  }  // convert bcd to dec
  if (bcda==0 && bcdb==1 && bcdc == 0 && bcdd == 0 ) {
    track = 2;
  }
  if (bcda==1 && bcdb==1 && bcdc == 0 && bcdd == 0 ) {
    track = 3;
  }
  if (bcda==0 && bcdb==0 && bcdc == 1 && bcdd == 0 ) {
    track = 4;
  }
  if (bcda==1 && bcdb==0 && bcdc == 1 && bcdd == 0 ) {
    track = 5;
  }
  if (bcda==0 && bcdb==1 && bcdc == 1 && bcdd == 0 ) {
    track = 6;
  }
  if (bcda==1 && bcdb==1 && bcdc == 1 && bcdd == 0 ) {
    track = 7;
  }
  if (bcda==0 && bcdb==0 && bcdc == 0 && bcdd == 1 ) {
    track = 8;
  }
  if (bcda==1 && bcdb==0 && bcdc == 0 && bcdd == 1 ) {
    track = 9;
  }  

  //Serial.print ( track);
  //Serial.print( bcda);
 // Serial.print ( bcdb);
 // Serial.print ( bcdc);
 // Serial.print( bcdd);
 // Serial.println ( valid);




  //putstring("."); // uncomment this to see if the loop isnt running
  if (track==1) {
    playcomplete("doornum1.wav");
  }
  else;
  if (track==2) {
    playcomplete("doornum2.wav");
  }
  else;
  if (track==3) {
    playcomplete("doornum3.wav");
  }
  else;
  if (track==4) {
    playcomplete("doornum4.wav");
  }
  else;
  if (track==5) {
    playcomplete("doornum5.wav");
  }
  else;
  if (track==6) {
    playcomplete("doornum6.wav");
  }
  else;
  if (track==7) {
    playcomplete("doornum7.wav");
  }
  else;
  if (track==8) {
    playcomplete("doornum8.wav");
  }
  else;
  if (track==9) {
    playcomplete("doornum9.wav");
  }

}
// Plays a full file from beginning to end with no pause.
void playcomplete(char *name) {
  // call our helper to find and play this name
  playfile(name);
  if (wave.isplaying) {//   set display enable high to vga chip
    digitalWrite(talkingPin, LOW);
  }
  else
  {  
    digitalWrite(talkingPin, HIGH);
  }
  while (wave.isplaying) {

  }
  // now its done playing
}

void playfile(char *name) {
  // see if the wave object is currently doing something
 //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;
  }
  if (valid == 1){
    // ok time to play! start playback
    wave.play();

  }

}
« Last Edit: April 07, 2011, 06:47:06 am by Boffin1 » Logged

With my mobile phone I can call people and talk to them -  how smart can you get ?

Cape Town South Africa
Offline Offline
Edison Member
*
Karma: 19
Posts: 1217
A newbie with loads of posts, and still so much to learn !
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

 I don't need to record anything, the audio files I record with my PC,  I just need a .wav file reader and DA to get the audio out ( one of 9 files recorded )
« Last Edit: April 07, 2011, 08:21:23 am by Boffin1 » Logged

With my mobile phone I can call people and talk to them -  how smart can you get ?

0
Offline Offline
Edison Member
*
Karma: 67
Posts: 1655
Arduino rocks
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

The "native library" is thin wrapper for SdFat, a library I wrote.  i also wrote WaveHC.  You will never get saisfactory performance from SD.h to play audio on an Adafruit Wave Shield.

WaveHC is highly optimized to play audio.

It is possible to play Audio with SdFat but SD.h does not export the part of SdFat's API that is required to do raw I/O to the SD card.  WaveRP is a library based on SdFat that can record an play audio using the Adafruit Wave Shield.
Logged

Cape Town South Africa
Offline Offline
Edison Member
*
Karma: 19
Posts: 1217
A newbie with loads of posts, and still so much to learn !
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Thanks,  so do you have any advice about which cards to use with the waveHC library,? or how I should format them perhaps ?
Logged

With my mobile phone I can call people and talk to them -  how smart can you get ?

0
Offline Offline
Edison Member
*
Karma: 67
Posts: 1655
Arduino rocks
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Do you have version 1.0 of the Wave Shield?  Version 1.0 of the Wave Shield was fussy about SD cards.  It had resistor based level shifters to convert the Arduino 5V SPI to 3.3V for the SD.  Not much can be done to fix it with out major mods, see this post http://forums.adafruit.com/viewtopic.php?f=31&t=8738&p=43796&hilit=wave+shield+1+0+resistor+level+shifter#p43796.

In general the best way to format an SD card is to use the SD association's formatter here http://www.sdcard.org/consumers/formatter_3/.

I am including a sketch in the new version of SdFat that formats SD cards to the SD association's specification.  The new SdFat is in beta here http://code.google.com/p/beta-lib/downloads/list
Logged

Cape Town South Africa
Offline Offline
Edison Member
*
Karma: 19
Posts: 1217
A newbie with loads of posts, and still so much to learn !
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Theres some things to go on now, this afternoon the card that wasn't working, started working again...  so it must be something working near the limits somewhere.

I am not using a shield, the chips are in sockets on a pcb, and I am using the buffer to convert the levels to 3v3.

I will try the associations formatter tonight, thanks
Logged

With my mobile phone I can call people and talk to them -  how smart can you get ?

Cape Town South Africa
Offline Offline
Edison Member
*
Karma: 19
Posts: 1217
A newbie with loads of posts, and still so much to learn !
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

The plot thickens :-)

I had 4 "Kingston" cards, one of which had "failed" ( though I could still read the files on my PC ),

and 2  traxdata  cards, neither of which worked from the start.

I downloaded the formatter3 and started with a FULL OVERWRITE format ( over half an hour ! ) of one of the nonworking traxdata cards.

I copied the audio files on to it, and it worked 100 %  !

I thought I had hit gold, and decided to reformat all the cards like this, however I got the 2 traxdata cards mixed up, and to see which one had been properly formatted, I tested to see which one worked - and they both did !!

So I have no idea what is going on.   I am formatting all the cards anyway,

Should I slow something down in the card reading to help matters?  I think I saw a choice of some speed..
Logged

With my mobile phone I can call people and talk to them -  how smart can you get ?

0
Offline Offline
Edison Member
*
Karma: 67
Posts: 1655
Arduino rocks
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

You could try running the SPI bus at half speed.  That is 4 MHz.

Change your card.init() to card.init(1).  That will reduce the SPI bus from 8 MHz to 4 MHz.

If it works something is marginal at full speed.

You may not be able to play 16-bit 44.1 ksps files at half speed.
Logged

Cape Town South Africa
Offline Offline
Edison Member
*
Karma: 19
Posts: 1217
A newbie with loads of posts, and still so much to learn !
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

thanks, that was what I saw.
I cant remember at what speed/bits I recorded the wav files, but its only a voice announcement so if I reduce it it shouldnt notice ( I used to use the ISD chips which were pretty slow and acceptable )
Logged

With my mobile phone I can call people and talk to them -  how smart can you get ?

Cape Town South Africa
Offline Offline
Edison Member
*
Karma: 19
Posts: 1217
A newbie with loads of posts, and still so much to learn !
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

That seems to be working fine.

With the full SD format and the half speed I hope its all OK now, thanks for your help.
Logged

With my mobile phone I can call people and talk to them -  how smart can you get ?

Netherlands
Offline Offline
Sr. Member
****
Karma: 1
Posts: 290
(:-)
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Do you have decoupling capacitors near your ic's? If not that might be a good thing to add.
Logged

Cape Town South Africa
Offline Offline
Edison Member
*
Karma: 19
Posts: 1217
A newbie with loads of posts, and still so much to learn !
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Yes I have one on top of the chips Vcc to GND, it looks scruffy but old habits die hard, if I use double sided board they go on the board/groundplane.

Logged

With my mobile phone I can call people and talk to them -  how smart can you get ?

Pages: [1]   Go Up
Jump to: