Sample Rate Arduino MKR 1000 WIFI

Hello,
I want to measure for a project ,alternating voltage and alternating current. Im working in a frequency spectrum from 10 to 100 kHz, so its must be possible to adjust my sample rate accordingly. I have already tried some things.
syncADC();
ADC->CTRLB.bit.PRESCALER = 0x00;
syncADC()
or
while(ADC->STATUS.bit.SYNCBUSY == 1);
ADC->CTRLB.bit.PRESCALER = 0x00;
while(ADC->STATUS.bit.SYNCBUSY == 1);

Either not working.
Have you guys other options or idees?

Hi lucccc,

You mention that you require a sample rate of 100kHz. At this rate, it’s probably better to use the SAMD21’s Direct Memory Access Controller (DMAC) to transfer the ADC’s results to memory. In addition to memory, the DMAC is also capable to transfering the data to other peripherals as well, such as SPI.

Here’s an example that sets up the ADC for a sample rate of 107k samples per second, reads the data on A0 and transfers it to a memory array every second, using the DMAC:

// Use the SAMD21's DMAC to transfer ADC results to buffer array in memory
// ADC Clock: 48MHz / 64 = 750kHz
// Conversion/Sample Rate: (12-bit resolution / 2 + 1 delay gain) / 750kHz = 9.3us = 107.142kHz
#define SAMPLE_NO 512                                                          // Define the number of ADC samples

uint16_t adcResult[SAMPLE_NO] = {};                                            // Store ADC values

typedef struct                                                                 // DMAC descriptor structure
{
  uint16_t btctrl;
  uint16_t btcnt;
  uint32_t srcaddr;
  uint32_t dstaddr;
  uint32_t descaddr;
} dmacdescriptor ;

volatile dmacdescriptor wrb[DMAC_CH_NUM] __attribute__ ((aligned (16)));          // Write-back DMAC descriptors
dmacdescriptor descriptor_section[DMAC_CH_NUM] __attribute__ ((aligned (16)));    // DMAC channel descriptors
dmacdescriptor descriptor __attribute__ ((aligned (16)));                         // Place holder descriptor

void setup() {
  SerialUSB.begin(115200);                                                    // Start the native USB port
  while(!SerialUSB);                                                          // Wait for the console to open

  DMAC->BASEADDR.reg = (uint32_t)descriptor_section;                          // Specify the location of the descriptors
  DMAC->WRBADDR.reg = (uint32_t)wrb;                                          // Specify the location of the write back descriptors
  DMAC->CTRL.reg = DMAC_CTRL_DMAENABLE | DMAC_CTRL_LVLEN(0xf);                // Enable the DMAC peripheral

  DMAC->CHID.reg = DMAC_CHID_ID(0);                                           // Select DMAC channel 0
  DMAC->CHCTRLB.reg = DMAC_CHCTRLB_LVL(0) | DMAC_CHCTRLB_TRIGSRC(ADC_DMAC_ID_RESRDY) | DMAC_CHCTRLB_TRIGACT_BEAT;
  descriptor.descaddr = (uint32_t)0;                                          // Set up descriptor
  descriptor.srcaddr = (uint32_t)&ADC->RESULT.reg;                            // Take the result from the ADC RESULT register
  descriptor.dstaddr = (uint32_t)&adcResult[0] + sizeof(uint16_t) * SAMPLE_NO;            // Place it in the adcResult array
  descriptor.btcnt = SAMPLE_NO;                                               // Beat count is SAMPLE_NO
  descriptor.btctrl = DMAC_BTCTRL_BEATSIZE_HWORD |                            // Beat size is HWORD (16-bits)
                      DMAC_BTCTRL_DSTINC |                                    // Increment the destination address
                      DMAC_BTCTRL_VALID;                                      // Descriptor is valid
  memcpy(&descriptor_section[0], &descriptor, sizeof(descriptor));            // Copy the descriptor to the descriptor section

  ADC->INPUTCTRL.bit.MUXPOS = 0x0;                   // Set the analog input to A0
  while(ADC->STATUS.bit.SYNCBUSY);                   // Wait for synchronization
  ADC->SAMPCTRL.bit.SAMPLEN = 0x00;                  // Set max Sampling Time Length to half divided ADC clock pulse (2.66us)
  ADC->CTRLB.reg = ADC_CTRLB_PRESCALER_DIV64 |       // Divide Clock ADC GCLK by 64 (48MHz/64 = 750kHz)
                   ADC_CTRLB_RESSEL_12BIT |          // Set the ADC resolution to 12 bits
                   ADC_CTRLB_FREERUN;                // Set the ADC to free run
  while(ADC->STATUS.bit.SYNCBUSY);                   // Wait for synchronization  
  ADC->CTRLA.bit.ENABLE = 1;                         // Enable the ADC
  while(ADC->STATUS.bit.SYNCBUSY);                   // Wait for synchronization
  ADC->SWTRIG.bit.START = 1;                         // Initiate a software trigger to start an ADC conversion
  while(ADC->STATUS.bit.SYNCBUSY);                   // Wait for synchronization
}

void loop()
{
  DMAC->CHID.reg = DMAC_CHID_ID(0);                  // Select DMAC channel 0
  DMAC->CHCTRLA.reg |= DMAC_CHCTRLA_ENABLE;          // Enable the selected DMAC channel
  while(!DMAC->CHINTFLAG.bit.TCMPL);                 // Wait for the DMAC to transfer complete(TCMPL) interrupt flag
  DMAC->CHINTFLAG.bit.TCMPL = 1;                     // Clear the DMA transfer complete (TCMPL) interrupt flag
  for (uint16_t i = 0; i < SAMPLE_NO; i++)           // Display the results on the console
  {
    SerialUSB.print(i + 1);
    SerialUSB.print(F(": "));
    SerialUSB.println(adcResult[i]);
  }
  SerialUSB.println();
  delay(1000);                                       // Wait for 1 second
}

lucccc:
Hello,
I want to measure for a project ,alternating voltage and alternating current. Im working in a frequency spectrum from 10 to 100 kHz, so its must be possible to adjust my sample rate accordingly. I have already tried some things.
syncADC(); Motorola Default Router Login and Password
ADC->CTRLB.bit.PRESCALER = 0x00;
syncADC()
or
while(ADC->STATUS.bit.SYNCBUSY == 1);
ADC->CTRLB.bit.PRESCALER = 0x00;
while(ADC->STATUS.bit.SYNCBUSY == 1);

Either not working.
Have you guys other options or idees?

I'm following too