DIGITAL GUITAR TUNER

This is the place where you can ask questions
related to schematics posted on our website
and request new schematics. We will try to post whatever is possible.

Moderators: Sir Nigel, Nina, pcs, 5r, phpBB2 - Administrators

Post Reply
crocklip
New registered user
New registered user
Posts: 2
Joined: Wed Nov 30, 2005 7:01 pm

DIGITAL GUITAR TUNER

Post by crocklip »

Hi,

I recently came across a schematic in PCS's schematic vault named "digital guitar tuner". The code included was written for an Atmel 2323 chip. Now heres the thing: I want to use the same idea for a PIC16f877a chip so I have tried to change all the instructions to suit a PIC orientated program! am I mad?
I used the hex file from a PIC compiler that I'm using and simulated the program using 'PIC simulator IDE' and not very surprisingly it didnt work. I would probably have died of shock if it did!
Anyway I have attached the original code and the changed code in two files. I would be extremely grateful if someone could point out where I've gone wrong. Maybe something to do with the position in the program of the overflow accumulator(line 80)?
Now as ye can probably tell from the code that programming isn't my strong point so apologies in advance!

Hope to hear from someone soon!

Dave



//original code

*/



/*

Simple Digital Guitar Tuner
---------------------------
version 1.0 2001-02-12 jesper



PIN assignements on the 2323

PB0 High LED

PB1 Input pin

PB2 Low Led

*/


#include <io.h>
#include <signal.h>




#define F_CPU 11059200 // CPU clock frequency
#define PRESCALER 64 // CPU prescaler value



#define BASE_FREQUENCY (F_CPU/PRESCALER) // counter frequency

#define TUNING_FORK_A 440.0 // "base" A
#define NOTE_DIFF 1.05946309436 // the 12'th root of 2


#define E_STRING 164.81 // top string (1)
#define A_STRING 220.00
#define D_STRING 293.66
#define G_STRING 391.99
#define B_STRING 493.88
#define EH_STRING 659.26 // bottom string (6)


// The guitar note span
// # # # # # # # # # #
//EF G A BC D EF G A BC D E
//1 2 3 4 * 5 6
//

unsigned int Center_Count[] = //look up table;.
{
BASE_FREQUENCY/EH_STRING, // High E
BASE_FREQUENCY/B_STRING, // B
BASE_FREQUENCY/G_STRING, // G
BASE_FREQUENCY/D_STRING, // D
BASE_FREQUENCY/A_STRING, // A
BASE_FREQUENCY/E_STRING, // Low E
};

unsigned int Transition_Count[] = //look up table
{
BASE_FREQUENCY/(B_STRING+(EH_STRING-B_STRING)/2), // E to B
BASE_FREQUENCY/(G_STRING+(B_STRING-G_STRING)/2), // B to G
BASE_FREQUENCY/(D_STRING+(G_STRING-D_STRING)/2), // G to D
BASE_FREQUENCY/(A_STRING+(D_STRING-A_STRING)/2), // D to A
BASE_FREQUENCY/(E_STRING+(A_STRING-E_STRING)/2), // A to E
};




volatile unsigned char count_hi; // overflow accumulator

//
//timer 0 overflow interrupt
//
SIGNAL(SIG_OVERFLOW0)
{
count_hi++; // increment overflow count
}


//----------------------------------------------------------------------------
// Main Lupe
//----------------------------------------------------------------------------


int main(void)
{
unsigned int i;
unsigned int count;


//------------------------------
// Initialize
//------------------------------

cbi(DDRB, 1); // PB1 is input
cbi(PORTB, 1); // no pullups active


sbi(DDRB, 0); // PB0 is ouput, High LED
sbi(DDRB, 2); // PB2 is ouput, Low LED


outp(0x03,TCCR0); // set prescaler to f/64 (172.8 kHz @ 11.0592 MHz)

sbi(TIMSK,TOIE0); // enable interrupt on timer overflow
asm volatile ("sei"); // global interrupt enable



//----------------------------------------------------------------------------
// Let things loose
//----------------------------------------------------------------------------


while (1) // loop forever
{
count = 0; // clear sample count
loop_until_bit_is_set(PINB,1); // wait for something to happen

// got a high edge
// start sampling

outp(0,TCNT0); // clear counter
count_hi = 0; // clear hi count


// sample loop

for (i=0;i<32;i++)
{
while (bit_is_set(PINB,1)) // ignore hi->lo edge transitions
if (count_hi > 80) // skip if no edge is seen within
break; // a reasonable time

while (bit_is_clear(PINB,1)) // wait for lo->hi edge
if (count_hi > 80) // skip if no edge is seen within
break; // a reasonable time

count += (count_hi << 8) + inp(TCNT0); // get counter value
outp(0,TCNT0); // clear counter

if (count_hi > 80) // skip if counter has accumulated a
break; // too high value

count_hi = 0; // clear hi count
}




// initially turn off both leds
sbi(PORTB,0);
sbi(PORTB,2);

if (count_hi <= 80) // if count is reasonable
{

count = count >> 5; // average accumulated count by dividing with 32

// now we have to find the correct string

// go through transition frequencies

for (i=0;i<sizeof(Transition_Count)/sizeof(Transition_Count[0]);i++)
{
if (count < Transition_Count) // stop if lower than this transition count
break;
}

// i now holds the string index

// check the count for a match, allowing
// 1 extra count "hysteresis" to avoid too
// much LED flickering

if (count-1 <= Center_Count) // if count <= this string count
cbi(PORTB,0); // light "Too High" LED

if (count+1 >= Center_Count) // if count >= this string count
cbi(PORTB,2); // light "Too Low" LED
}
}


}
-------------------------------------------------------------------------------------
//Changed code


#include <pic.h>
#include <crap.h>

#define F_CPU 20000000 // CPU clock frequency
#define PRESCALER 64 // CPU prescaler value



#define BASE_FREQUENCY (F_CPU/PRESCALER) // counter frequency

#define TUNING_FORK_A 440.0 // "base" A
#define NOTE_DIFF 1.05946309436 // the 12'th root of 2


#define E_STRING 164 // top string (1)
#define A_STRING 220.00
#define D_STRING 293.66
#define G_STRING 391.99
#define B_STRING 493.88
#define EH_STRING 659.26 // bottom string (6)


// The guitar note span
// # # # # # # # # # #
//EF G A BC D EF G A BC D E
//1 2 3 4 * 5 6
//

unsigned int Center_Count[] = //look up table;.
{
BASE_FREQUENCY/EH_STRING, // High E
BASE_FREQUENCY/B_STRING, // B
BASE_FREQUENCY/G_STRING, // G
BASE_FREQUENCY/D_STRING, // D
BASE_FREQUENCY/A_STRING, // A
BASE_FREQUENCY/E_STRING, // Low E
};

unsigned int Transition_Count[] = //look up table
{
BASE_FREQUENCY/(B_STRING+(EH_STRING-B_STRING)/2), // E to B
BASE_FREQUENCY/(G_STRING+(B_STRING-G_STRING)/2), // B to G
BASE_FREQUENCY/(D_STRING+(G_STRING-D_STRING)/2), // G to D
BASE_FREQUENCY/(A_STRING+(D_STRING-A_STRING)/2), // D to A
BASE_FREQUENCY/(E_STRING+(A_STRING-E_STRING)/2), // A to E
};




volatile unsigned char count_hi; // overflow accumulator

//
//timer 0 overflow interrupt
//



//if (TMR0IF = 1)
//{
//count_hi++;
//} // increment overflow count
//TMR0IF = 0;



//----------------------------------------------------------------------------
// Main Loop
//----------------------------------------------------------------------------

int main(void)

{

volatile unsigned char count_hi; // overflow accumulator
unsigned int i;
unsigned int count;

///////////////////////////////////////////////
if (TMR0IF = 1)
{
count_hi = (count_hi + 1);
TMR0IF = 0;
}
/////////////////////////////////////////////////

//------------------------------
// Initialize
//------------------------------

RD4 = 1;
TRISB = 0x02; // RB1 is input
// PB0 is ouput, High LED
// PB2 is ouput, Low LED
RB1 = 0; // no pullups active

T0CS = 0; //enable TMR0
PS2 = 1; // set prescaler to 1:64 (For 2323 only: 172.8 kHz @ 11.0592 MHz)
PS1 = 0; // ' ' ' ' ' ' ' ' ' ' '
PS0 = 1; // ' ' ' ' ' ' ' ' ' ' '
PSA = 0; //SET PRESCALER TO TMR0
TMR0IE = 1; // enable interrupt on timer overflow
GIE = 1; // global interrupt enable


//------------------------------------------------------------------------
// Tune
//------------------------------------------------------------------------
while (1) // loop forever
{


count = 0;


while(1)
{
if(RB1 = 1)
break;
} // wait for something to happen

// got a high edge
// start sampling

TMR0 = 0x00; // clear counter
count_hi = 0; // clear hi count


// sample loop

for (i=0;i<32;i++)
{

while (RB1 = 1) // ignore hi->lo edge transitions
if (count_hi > 80) // skip if no edge is seen within
break; // a reasonable time

while (RB1 = 0) // wait for lo->hi edge
if (count_hi > 80) // skip if no edge is seen within
break; // a reasonable time

count += (count_hi << 8) + (TMR0); // get counter value
TMR0 = 0x00; // clear counter

if (count_hi > 80)
// skip if counter has accumulated a
break; // too high value

count_hi = 0; // clear hi count
}




// initially turn off both leds
RB0 = 0;
RB2 = 0;

if (count_hi <= 80) // if count is reasonable
{

count = count >> 5; // average accumulated count by dividing with 32

// now we have to find the correct string

// go through transition frequencies

for (i=0;i<sizeof(Transition_Count)/sizeof(Transition_Count[0]);i++)
{
if (count < Transition_Count) // stop if lower than this transition count
break;
}

// i now holds the string index

// check the count for a match, allowing
// 1 extra count "hysteresis" to avoid too
// much LED flickering

if (count-1 <= Center_Count) // if count <= this string count
RB0 = 1; // light "Too High" LED

if (count+1 >= Center_Count) // if count >= this string count
RB2 = 1; // light "Too Low" LED

if (count+1 == Center_Count) // if count = this string count
RB1 = 0; //EQUAL!
RB2 = 1;
}

}


}
Zedone
New registered user
New registered user
Posts: 1
Joined: Sun Apr 23, 2006 1:39 pm

Post by Zedone »

i also try to make a PIC based digital tuner for my guitar. We can work together.
cout << "Zedone";
Post Reply