delorie.com/archives/browse.cgi   search  
Mail Archives: geda-user/2014/01/02/16:11:03

X-Authentication-Warning: delorie.com: mail set sender to geda-user-bounces using -f
X-Recipient: geda-user AT delorie DOT com
Message-ID: <52C5D542.6040001@buffalo.edu>
Date: Thu, 02 Jan 2014 16:08:18 -0500
From: "Stephen R. Besch" <sbesch AT buffalo DOT edu>
User-Agent: Mozilla/5.0 (X11; Linux i686; rv:24.0) Gecko/20100101 Thunderbird/24.2.0
MIME-Version: 1.0
To: geda-user AT delorie DOT com
Subject: Re: [geda-user] Help sending a sine wave to a speaker
References: <CALSZ9go-H-4HnAfvdQyLsVEcbNG0pT33wEM=G-CfZmDXVcMQrw AT mail DOT gmail DOT com>
In-Reply-To: <CALSZ9go-H-4HnAfvdQyLsVEcbNG0pT33wEM=G-CfZmDXVcMQrw@mail.gmail.com>
X-PM-EL-Spam-Prob: X: 10%
Reply-To: geda-user AT delorie DOT com

Rob,

I know that this a few days late, but I do have some ideas - not so much 
as to where the error was, since someone already answered this, but in 
terms of sine wave generation in general. Basically, I would probably 
never use the SIN(x) function directly at all but I would generate the 
sine function from a pre-calculated table. This is not as costly as you 
might think. In your case, 1KHz at 8KHz sample rate, the table only 
requires (worst case) 8 samples, most of which are redundant. These are 
Sin(0)=0, Sin(45)=(sqrt2/2), Sin(90)=1, Sin(135)=Sin(45), Sin(180)=0, 
Sin(225)=-Sin(45), Sin(270)=-1, Sin(315)=-Sin(45).
In point of fact, there are only 3 unique values(0.0, 1.0, and ~0.707). 
The rest are obtained from these by logic and sign inversion. The truth 
is that the same is true for higher sampling rates too. Your table only 
needs to contain a quarter wave of a 1Hz sine wave. Higher or lower 
frequencies can be obtained by changing the rate at which samples are 
played back (i.e., play at 8kHz and you get 1KHz, Play at 4kHz and you 
get 500Hz, Play at 16KHz and you get 2KHz.

Now, a sine wave sampled at 8f (such as in your case) may look a bit 
choppy. But played back through an analog output with a 3db roll off 
pole set to some suitable frequency will pull almost the high frequency 
edges out of the output and give you an almost perfect sine wave.

Stephen R. Besch

On 12/31/2013 02:26 PM, Rob Butts wrote:
> It has been a while since I've written major C code so I'm having a hard
> time coming up with the code.
> I have a simple design where I use a microchip pic16f1825 to read a byte
> from an eeprom via spi and send it to a dac and ultimately to a speaker.
> As a dac and speaker test I want to send a simple 1000Hz sine wave to the
> dac at an 8KHz rate.
>
> Can anyone check my thoughts below?  Here's my thinking...
> If I set my timer to interrupt at an 8KHz rate and if I want to play the
> tone for 10 seconds the for loop might look something like this:
>
> for(j=0; j < 80000; j++){
>       // j is the sample index
>      // straight sine function means one cycle per 2*pi samples
>      // sample(j) = sin(j)
>      // multiply by 2*pi now it is one cycle per sample
>      // sample(j) = sin((2 * pi) * j)
>      // multiply by 1,000 samples per second now it is cycles per second
>      // sample(j) = sin(1000 * 2 * pi * j
>      // divide by 8000 samples per second now it is cycles per 8000 samples
>      // sample(j) = sin(1000 * 2 * pi * j / 8000)
>      // the 1000 cycles is the frequency so in those terms
>      //  sample(j) = sin(freq * 2 * pi * j / 8000)
>      // now if I want to normalize the amplitude to 0xff  the final value is
>      // sample(j) = 0xff * sin(freq * 2 * pi * j / 8000)
>      // so...    declaring sample as a float
>      sample = 0xff * sin(freq * 2 * pi * j / 8000);
>      while(!update_dac){    // where update_dac is set to 1 in the timer
> interrupt handler
>      }
>      update_ dac = 0;
>      send_dac((UINT8) sample);
> }
>
> When I execute the code and step through it the value for sample when j = 1
> is 180.238where I expect 3.146
>
> Can someone see my error or what is going on?
>
> Thanks
>


-- 
fictio cedit veritati

- Raw text -


  webmaster     delorie software   privacy  
  Copyright © 2019   by DJ Delorie     Updated Jul 2019