1

I would like to timestamp the data collected from AnalogBinLogger.ino on an Arduino Uno. The sketch uses 512-byte buffers, and I have read that writing data in 512-byte chunks is 'better' in terms of write latencies.

The sketch uses this structure for the buffers:

// Data block for 10-bit ADC mode.
const size_t DATA_DIM16 = 254;
struct block16_t {
 unsigned short count; // count of data values
 unsigned short overrun; // count of overruns since last block
 unsigned short data[DATA_DIM16];
};

Since I want to add the timestamps which are of unsigned long type, I would have to modify the structure as follows:

// Data block for 10-bit ADC mode.
const size_t DATA_DIM16 = 254;
struct block16_t {
 unsigned short count; // count of data values
 unsigned short overrun; // count of overruns since last block
 unsigned short data[DATA_DIM16];
 unsigned long milli[DATA_DIM16]; // time in milliseconds
};

Now, this structure exceeds 512 bytes and is 1528 bytes. Due to unavailability of enough free stack, my program doesn't run (sketch reports FreeStack to be 1135 bytes). How can I go about this?

PS: My root problem is to achieve time-synchronisation among multiple data-collecting Arduinos which sample at high rates like 8kHz. Due to clock drifts, even if I sync the start times, the timestamps collected afterwards would not be relative to each other. Hence I plan to have a master Arduino send its time to the others in regular intervals.

asked Jun 27, 2019 at 4:52
0

2 Answers 2

1

The straightforward solution:

const size_t DATA_DIM16 = 84;
struct block16_t {
 unsigned short count; // count of data values
 unsigned short overrun; // count of overruns since last block
 unsigned short data[DATA_DIM16];
 unsigned long milli[DATA_DIM16]; // time in milliseconds
 unsigned long padding; // pad to 512 bytes
};

Now, I suggest to think again about your requirements. Do you really need a 32-bit timestamp for every data point? If they are closely spaced in time, a 16-bit, or even 8-bit timestamp should be enough. You could put a full 32-bit timestamp at the beginning of each block, then only 8-bit timestamps for every data point. This would allow you to store 168 samples per block. You could even pack a 6-bit timestamp with the data sample into an uint16_t, and have 252 samples per block.

answered Jun 27, 2019 at 7:46
1

Writing in 512 byte chunks is done by SD libraries, so you could rely on that layer and simply write and store single events

struct block_t {
 uint32_t milli; // time in milliseconds
 uint16_t data;
 uint8_t overrun; // overrun status since last block
};

I do not know your AnalogBinLogger.ino. In other circumstances there's no such 512 byte limit, but a general and strict RAM limit. (You could decrease your DATA_DIM to make it fit safely)

answered Jun 27, 2019 at 7:56
2
  • My understanding is that a 512-byte buffer was chosen for its efficiency, which is an important consideration when you try to log data at a high rate. Commented Jun 27, 2019 at 8:06
  • github.com/greiman/SdFat/blob/master/examples/AnalogBinLogger/… is an interesting example. Thanks @Edgar and Harini Commented Jun 28, 2019 at 9:18

Your Answer

Draft saved
Draft discarded

Sign up or log in

Sign up using Google
Sign up using Email and Password

Post as a guest

Required, but never shown

Post as a guest

Required, but never shown

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

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.