-1

So, I am using the LTC 2366, 3 MSPS ADC and using the code given below, was able to achieve a sampling rate of about 380 KSPS.

#include <stdio.h>
#include <time.h>
#include <bcm2835.h>

int main(int argc, char**argv) {
    FILE *f_0 = fopen("adc_test.dat", "w");
    clock_t start, end;
    double time_taken;

    if (!bcm2835_init()) {
        return 1;
    }

    bcm2835_spi_begin();
    bcm2835_spi_setBitOrder(BCM2835_SPI_BIT_ORDER_MSBFIRST);
    bcm2835_spi_setDataMode(BCM2835_SPI_MODE0);
    bcm2835_spi_setClockDivider(32);
    bcm2835_spi_chipSelect(BCM2835_SPI_CS0);
    bcm2835_spi_setChipSelectPolarity(BCM2835_SPI_CS0, LOW);
    int i;
    char buf_[0] = {0x01, (0x08|0)<<4, 0x00}; // really doesn't matter what this is
    char readBuf_0[2];
    start = clock();
    for (i=0; i<380000; i++) {
        bcm2835_spi_transfernb(buf_0, readBuf_0, 2);
        fprintf(f_0, "%d\n", (readBuf_0[0]<<6) + (readBuf_0[1]>>2));
    }
    end = clock();
    time_taken = ((double)(end-start)/CLOCKS_PER_SEC);
    printf("%f", (double)(time_taken));
    printf(" seconds \n");
    bcm2835_spi_end();
    bcm2835_close();
    return 0;
}

This returns about 1 second every time.

When I used the exact same code with LTC 2315, I still get a sampling rate of about 380 KSPS. How come? First of all, why is the 3 MSPS ADC giving me only 380 KSPS and not something like 2 MSPS? Second, when I change the ADC to something that's about 70% faster, I get the same sampling rate, why is that? Is that the limit of the Pi? Any way of improving this to get at least 1 MSPS?

Thank you

2
  • Related: raspberrypi.stackexchange.com/questions/111996/… Commented May 16, 2020 at 16:44
  • Reduce the clock divider maybe? Converting the number format to human readable after the main loop might also help. You could perhaps also transfer multiple commands at once.. Since the bcm2835_spi_transfernb() call seems to support transferring a whole buffer. Commented Aug 16, 2023 at 11:05

2 Answers 2

0

Frankly you are doing very well to get 380 KSPS out of the Pi.

If you were using the Linux SPI driver you would top out at about 70 KSPS.

The reason you get as much as you do is because the bcm2835 library implements its own SPI driver which does not have the overheads of the Linux driver.

I showed my results at http://abyz.me.uk/rpi/pigpio/faq.html#How_fast_is_SPI which probably confirm what you are seeing.

The Linux SPI driver does allow you to chain multiple transactions into a single call. I have not benchmarked that approach. I would certainly explore that possibility in your situation.

6
  • 1) How do I use the Linux SPI driver? 2) Why then are the ADCs marked with a sampling rate of 3-5 MSPS? There must be a way of achieving that speed. Commented Mar 25, 2018 at 21:48
  • 1) standard Linux open/close/read/write calls of SPI device. Google should show examples. 2) you need a computer also capable of running at that rate. I'm not sure what rate an operating system less device like an Atmel (Arduino) might achieve.
    – joan
    Commented Mar 25, 2018 at 21:58
  • With an Arduino Due, I got about 920 KSPS with the 5 MSPS ADC. But that still isn't fast enough. Which device would be faster than the Pi? Commented Mar 25, 2018 at 23:51
  • An Arduino would seem to be the way to go then. I'm not sure if you can do what you want in bare metal on the Pi. Even if you could it seems like there should be far cheaper microprocessor solutions.
    – joan
    Commented Mar 26, 2018 at 7:32
  • Far cheaper? Which one? Arduino gives only 20% of the speed of the ADC and a for loop runs for like 1 million times in a second, that seems to me the limit of Arduino using the way that I'm using Commented Mar 26, 2018 at 16:18
0

Long story short, SPI on the Arduino may have lots of overheads. To counter that, you can use parallel ADCs. You can easily find a well-written tutorial there.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.