# Producing a sine wave with the DAC?

Its being a few days i am trying to achieve something that I dont really know if possible. Using the `Samd21` chip(`Arduino Zero`), I am using a timer and a `DAC` to produce a sine wave.

The required frequencies are 100Khz to 3Mhz. I know its sounds too much, but according to my calculations its possible- I would like to know if I am wrong with my software approach.

Pseudo is this :

1.I create a look-up table of a sine wave = array of a sine samples that holds N samples 2.I use a timer with a pre scale of 1, where the clock speed is 48Mhz 3.Each timer tick I produce from the DAC 1 sample from the sine wave 4.To change frequencies I am changing the timer top counter value.

If we try to speak about the max frequency, according to Nyquist , a 3MHz sine must be sampled with at least 6MHz sample rate, and my sine array has 15 samples, means 45Mhz sampling rate.(=good)

Then the sine frequency is :

``````sineF= TimerF*sineSamples = TimerF*15
``````

Than means I need a timer frequency of :

``````TimerF=15*sineF = 15*3Mhz=45MHz
``````

So, both are good, the timer max f can be 45Mhz, and the sampling rate is good according to Nyquist.

The only concern here, is if the DAC can do that(speed), and if changing the timer frequency fast enough (even every period) is acceptable.

Is this whole software approach true ? If its not, producing a square wave probably possible,since it requires much less speed, but then, can you turn it into a nice clean sin wave with filters?

Thanks.

First, I have to say I am not familiar with the Zero hardware, so I am answering in quite general terms. Hopefully you will also get some answers with hardware-specific information. That being said, here are my first thoughts:

1. Your approach seems reasonable to me, but you are too optimistic regarding the achievable sampling rate.

2. DACs are usually fast. It's unlikely that the DAC will limit the frequency you can achieve.

3. You cannot achieve a sampling frequency of 45 MHz in software with a CPU running at 48 MHz: your code to output a sample would have to run in less than 1.07 CPU cycles.

4. You may achieve a higher sampling rate with an array of 16 samples rather than 15, as wrapping the array index modulo 16 can be optimized by the compiler into a bitwise AND, which is likely to be faster than computing `index%15`.

5. Fastest would probably be to use a busy loop with constant execution time and interrupts turned off (I know how to do that on AVR, but not on ARM). Problem is: the program cannot do anything else than outputting samples.

• Thanks a lot, I think that DAC's are really slowly, I could see that other DAC's of ARM's such as the Due, are capable of max 1MHz rate. And regarding to your assumption on the sampling frequency of 48MHz, you can definitely do that, a pre scale 1 for a timer provide it with a processor clock speed, and if you count to 1( timer counter 1 cycle) you do get a 48MHz, this is how it works with any frequency , so I am not sure you assumptions are correct. – Curnelious Apr 27 '16 at 8:15
• The problem is not triggering the timer fast enough, it's having any time between triggerings of the timer to actually retrieve the sample from the LUT and send it to the DAC. There just isn't any time. – Majenko Apr 27 '16 at 8:19
• Ok, I have checked it out, DAC is too slow! its 350ksps, that means 350Khz, so it IS a limit. Regarding the timer you are right. So I can just put it on 16Mhz, or something similar(?) – Curnelious Apr 27 '16 at 8:22
• You have to allow enough time for the instructions you are executing to run. That means, effectively, one clock cycle for each and every assembly (NOT C) instruction. That could be hundreds of clock cycles - maybe thousands - depending on just what you are doing in your interrupt routine. I am not familiar with that chip, but if it has DMA that would be a more efficient way of doing it. – Majenko Apr 27 '16 at 9:22