Well... I cannot figure out then. I am so badly lost in this... I have been studying registers of SAM for few days and it doesn't look promising. Perhaps somebody could assist me?
What I have now is this (briefly):
#define SMP_RATE 96000UL
#define CLK_MAIN 84000000UL
#define TMR_CNTR CLK_MAIN / (2 * SMP_RATE)
const int sampleQty = 2048;
double samples[sampleQty];
int currSample;
volatile uint8_t flag;
void pio_TIOA0 () // Configure Ard pin 2 as output from TC0 channel A (copy of trigger event)
{
PIOB->PIO_PDR = PIO_PB25B_TIOA0 ; // disable PIO control
PIOB->PIO_IDR = PIO_PB25B_TIOA0 ; // disable PIO interrupts
PIOB->PIO_ABSR |= PIO_PB25B_TIOA0 ; // switch to B peripheral
}
void tmr_setup ()
{
pmc_enable_periph_clk(TC_INTERFACE_ID + 0 *3 + 0); // clock the TC0 channel 0
TcChannel * t = &(TC0->TC_CHANNEL)[0] ; // pointer to TC0 registers for its channel 0
t->TC_CCR = TC_CCR_CLKDIS ; // disable internal clocking while setup regs
t->TC_IDR = 0xFFFFFFFF ; // disable interrupts
t->TC_SR ; // read int status reg to clear pending
t->TC_CMR = TC_CMR_TCCLKS_TIMER_CLOCK1 | // use TCLK1 (prescale by 2, = 42MHz)
TC_CMR_WAVE | // waveform mode
TC_CMR_WAVSEL_UP_RC | // count-up PWM using RC as threshold
TC_CMR_EEVT_XC0 | // Set external events from XC0 (this setup TIOB as output)
TC_CMR_ACPA_CLEAR | TC_CMR_ACPC_CLEAR |
TC_CMR_BCPB_CLEAR | TC_CMR_BCPC_CLEAR ;
t->TC_RC = TMR_CNTR; // counter resets on RC, so sets period in terms of 42MHz clock
t->TC_RA = TMR_CNTR / 2; // roughly square wave
t->TC_CMR = (t->TC_CMR & 0xFFF0FFFF) | TC_CMR_ACPA_CLEAR | TC_CMR_ACPC_SET ; // set clear and set from RA and RC compares
t->TC_CCR = TC_CCR_CLKEN | TC_CCR_SWTRG ; // re-enable local clocking and switch to hardware trigger source.
}
void adc_setup ()
{
pmc_enable_periph_clk(ID_ADC);
adc_init(ADC, SystemCoreClock, ADC_FREQ_MAX, ADC_STARTUP_FAST);
adc_disable_all_channel(ADC);
adc_enable_interrupt(ADC, ADC_IER_EOC7); // I use only AN0, so as I understand this will trigger handler after conversion. However, I need to read 5-6 analog channels right away... :(
NVIC_EnableIRQ(ADC_IRQn); // enable ADC interrupt vector
adc_enable_channel(ADC, ADC_CHANNEL_7); // AN0
adc_configure_trigger(ADC, ADC_TRIG_TIO_CH_0, 0);
adc_start(ADC);
}
void ADC_Handler(void) {
if (((adc_get_status(ADC) & ADC_ISR_EOC7) == ADC_ISR_EOC7)) {
samples[currSample] = adc_get_latest_value(ADC);
currSample += 1;
};
}
void setup() {
Serial.begin(115200);
adc_setup ();
tmr_setup ();
pio_TIOA0 (); // drive Arduino pin 2 at SMPL_RATE to bring clock out
}
void loop() {
}
I do setup in Setup() event and then Due just stucks, when I upload it... nothing happens. I tried several more modifications to this, but no use.. Then I did a second approach like this (from Atmel site):
void adc_setup(void) {
adc_init(ADC, SystemCoreClock, ADC_FREQ_MAX, 8);
adc_configure_timing(ADC, 0, ADC_SETTLING_TIME_3, 1);
adc_enable_channel(ADC, ADC_CHANNEL_7);
adc_enable_interrupt(ADC, ADC_IER_DRDY);
adc_configure_trigger(ADC, ADC_TRIG_SW, 0);
adc_start(ADC);
}
void ADC_IrqHandler(void) {
// Check the ADC conversion status
if ((adc_get_status(ADC) & ADC_ISR_DRDY) == ADC_ISR_DRDY) {
// Get latest digital data value from ADC and can be used by application
uint32_t result = adc_get_latest_value(ADC);
}
}
void setup() {
Serial.begin(115200);
adc_setup ();
}
void loop() {
}
And this one does stuck as well... Have no idea, what is wrong with the setup... Basically, my goal is to read 5 analog channels right away. I need at least 100Khz of sampling rate for each channel (to read 40Khz sound saves), so at least 500-600Khz of sampling freq. Moreover, I do not know how to measure actual frequency, because, when you set it up, sometimes (because of various reasons) it is not as fast as defined by parameters, so what I do is I write down start time in micros() and then write down end time. Dividing this time by sample number (quite big) I get approximate duration of one sample. However, when I tried this here, I got soma magic results as well.. any ideas?
Anyway, thanks a lot for any help, because I am really stuck with this for DAYS... if you manage to help me, that would be fabulous.
Thanks a lot.