Go Down

Topic: Vidor 4000 Encoder - faster reading, and reading multiple encoders at same time (Read 532 times) previous topic - next topic


Some of what I'm asking about has been discussed in a couple of topics here, but I haven't seen an answer that relates specifically to this query, so I would greatly appreciate some advice or help.

I'm reading multiple encoders using a Vidor 4000 and the VidorEncoder library, and I want to do two things.

Firstly I want to log 256 encoder positions (32-bit position) at a rate of 25us between samples.   The VidorPheripherals library limits the encoder position output to 16-bits, so instead of trying to hack that to 32-bits I'm using the VidorGraphics library which maintains 32-bit encoder position. 

Discussions on this forum indicate that it takes about 1.5ms or so get the position data into a variable.   There are ideas expressed on this forum about how to reduce this by modifying how the encoder data is transferred from the FPGA, but I don't really understand how to implement any of the ideas described, and I don't know if 25us is achievable.   It doesn't seem impossible given the clock speed but this is outside my area of comfort.

Secondly I want to be able to log position data from up to 8 encoders at the same time.  By this I mean that I want to be able to latch all encoder positions by command, and then sequentially read each of the latched values, all while each encoder continues to count.  This gives me encoder positions from all encoders with an identical time stamp, which is something I need.

I've attached some simplified code that I'm using that measures the time it takes to read 256 encoder samples.  I've also included some pseudo-code for how I'd like to read a set of latched encoders.   I imagine that I'd need some way to simultaneously copy the encoder registers to duplicate registers in the FPGA, which leaves the encoder registers to continue to count as normal.   I don't know how to go about this, but I'm not asking for someone to write any code for me!  If someone could advise on how achievable the 25us sample rate is and how it might be achieved, and whether it is possible to implement somehow the missing code that latches multiple encoders that would be very much appreciated!

many thanks in advance,
Code: [Select]

#include <VidorGraphics.h>
#include <VidorEncoder.h>

VidorEncoder enc0(0);
VidorEncoder enc1(1);
VidorEncoder enc2(2);
VidorEncoder enc3(3);
VidorEncoder enc4(4);
VidorEncoder enc5(5);
VidorEncoder enc6(6);
VidorEncoder enc7(7);
int32_t readHead[8];

void setup() {
  // Let's start the FPGA
  if (!FPGA.begin()) {
    Serial.println("Initialization failed!");
    while (1) {}

void loop() {
  // first part - how fast can I log 256 points?
  // is 25us sample rate possible?
  long x[256];
  Serial.println("start logging data");
  long tstart = micros();
  for (int i = 0; i < 256; i++) { // populate array 'x' with readhead positions
    readHead[0] = enc0.read();
    x[i] = readHead[0];
  long tstop = micros();
  Serial.println("end logging data");
  Serial.print("tstop-tstart = "); Serial.println(tstop-tstart);
  Serial.print((tstop-tstart)/256); Serial.println(" us per sample.");

  // second part - how can I sample 8 encoders at same clock cycle?
  // Need to freeze all encoder values and make them accessible for reading,
  // but still allow all encoders to continue to count while reading the latched values.
  // something like the pseudo-code below would be ideal.
  EncLatch = 1; // latch all encoder inputs
  readHead[0] = enc0.readLatched();
  readHead[1] = enc1.readLatched();
  readHead[2] = enc2.readLatched();
  readHead[3] = enc3.readLatched();
  readHead[4] = enc4.readLatched();
  readHead[5] = enc5.readLatched();
  readHead[6] = enc6.readLatched();
  readHead[7] = enc7.readLatched();
  EncLatch = 0; // unlatch all encoder inputs


I fear that you need to go custom FPGA image and maybe start to read some SAMD documentations (not sure if there some example how to use DMA in arduino)

256 samples of 32 bit values from 8 sensors is 8kB. Without buffering you need over 1.28Mbps link between SAMD21 and FPGA or you miss 25us sample interval.

I recommend that you buffer that 8kB data in FPGA and send it through JTAG, SPI, or serial link when it's done. Other is just to send 32B of data every 25us (need over 1.28Mbps link).

Do you have other tasks for FPGA in this system?

For receiving that data in SAMD I recommend to use DMA for storing that message (from UART or SPI) to certain allocated buffer that you don't have use CPU time for receiving it.

Go Up