scpi-parser
scpi-parser copied to clipboard
Binary encoding of larger data types in <ARBITRARY BLOCK PROGRAM DATA>
It would be nice to support arrays of larger types in arbitrary block.
Currently, there is only one function for parameter SCPI_ParamArbitraryBlock() and one for result SCPI_ResultArbitraryBlock()
It is sometimes needed to transfer larger data types e.g. array of 32bit integers, but endiannes is up to the user of the library.
This problem was partially discussed in #51
Possible solutions
- introduce helper function to translate array of native values to "normal" or "swapped" e.g. on x86, swap bytes while transfering array of int16_t in SCPI's "normal" byte order or do nothing special on AVR32.
- introduce new
SCPI_ParamArbitraryBlockXYZfunctions to do this on the fly but this will probably need additional data buffer
Specification
In the SCPI specification, there are two main chapters about binary encoding of these types
SCPI-99:Volume 1 - 9.1 [:DATA] <type>[,<length>]
SCPI-99:Volume 3 - 6.4.2 FORMat
Among others, there are two types of encoding "normal" and "swapped". It seems that "normal" is big-endian representation and "swapped" is little-endian.
| type name | description |
|---|---|
| ASCii | Comma-separated <Numeric> data |
| IFP32 | IEEE floating point, 32 bits. |
| IFP64 | IEEE floating point, 64 bits. |
| INT8 | IEEE 8-bit signed integer (default). |
| INT16 | IEEE 16-bit signed integer. |
| INT32 | IEEE 32-bit signed integer. |
| INT64 | IEEE 64-bit signed integer. |
| SFP32 | IEEE swapped floating point, 32 bits. |
| SFP64 | IEEE swapped floating point, 64 bits. |
| SINT16 | Swapped IEEE 16-bit signed integer. |
| SINT32 | Swapped IEEE 32-bit signed integer. |
| SINT64 | Swapped IEEE 64-bit signed integer. |
| SUINT16 | Swapped IEEE 16-bit unsigned integer. |
| SUINT32 | Swapped IEEE 32-bit unsigned integer. |
| SUINT64 | Swapped IEEE 64-bit unsigned integer. |
| UINT8 | IEEE 8-bit unsigned integer. |
| UINT16 | IEEE 16-bit unsigned integerUINT16. |
| UINT32 | IEEE 32-bit unsigned integerUINT32. |
| UINT64 | IEEE 64-bit unsigned integerUINT64 |
Just some thoughts, instead of appending the type to the function name, the type could be provided as an argument. If the type endianness is the same as the platform, then only the length is checked to be type size aligned, otherwise swapping is also provided. There are libraries available for swapping, but it is actually trivial the only advantage from a library would be it SIMD instructions could be used.
It is also possible to have one function and parameter as type as you propose.
It can look like your implementation of processing of array/buffer of numbers. But this will be better to have separate functions.
This is straightforward
SCPI_ResultBufferUInt8(..., values, countof(values), NORMAL)
SCPI_ResultBufferInt32(..., values, countof(values), SWAPPED)
SCPI_ResultBufferFloat(..., values, countof(values), ASCII)
SCPI_ResultBufferDouble(..., values, countof(values), NORMAL)
This will consume all following parameters or only one arbitrary block with swapped UInt16 values.
SCPI_ParamBufferUInt16(..., values, countof(values), ASCII_OR_SWAPPED, &result_count, ...)
This will consume only one arbitrary block of NORMAL (big-endian) 64bit integers, no ASCII encoding allowed.
SCPI_ParamBufferInt64(..., values, countof(values), NORMAL, &result_count, ...)
For me, it sounds better SCPI_ResultArrayFloat then SCPI_ResultBufferFloat, for that purpose.
We can also officially divide SCPI_ResultArbitraryBlock into two functions - SCPI_ResultArbitraryBlockHeader and SCPI_ResultArbitraryBlockData. You can later call SCPI_ResultArbitraryBlockData more then once.
I have introduced first support in 3b99af699baba3ddbec2fbe74af6392678fbe31d for returning arrays. It is still not well tested, it is not optimal but it is first step.
I would like to introduce also reading array parameters and also unit tests for all new functions.
Result functions are now ready. They are also covered by tests. Missing part is Parameter functions.
Array parameters are prepared but currently support only text.