T
tony.fountaine
I am working on a project to read a Bosch Measurement Data File (MDF).
The file contains a number of blocks that can be read from the file
using a baisc structure.
For example the ID BLOCK is as follows,
(Data Type) (Number of Elements) (Description)
CHAR 8 File identifier,
CHAR 8 Format identifier,
CHAR 8 Program identifier,
UINT16 1 Byte order
UINT16 1 Floating-point
UINT16 1 Version number
UINT16 1 Reserved
CHAR 2 Reserved
CHAR 30 Reserved
The measured data is described with a channel group as follows (Link is
a file offset pointer)
CHAR 2 Block type identifier, always "CG"
UINT16 1 Block size of this block in bytes (entire CGBLOCK)
LINK 1 Pointer to next data Channel group block (CGBLOCK) (NIL
allowed)
LINK 1 Pointer to first channel block (CNBLOCK) (NIL allowed)
LINK 1 Pointer to channel group comment text (TXBLOCK) (NIL allowed)
UINT16 1 Record ID
UINT16 1 Number of channels
UINT16 1 Data record size in bytes (without the record ID), i.e. data
size of the channel group for each sample
UINT32 1 Number of records
This channel group above, defines how big the data record size is and
how many records are contained. The data record can consist of many
channels that are described as follows
CHAR 2 Block type identifier, always "CN"
UINT16 1 Block size of this block in bytes (entire CNBLOCK)
LINK 1 Pointer to next channel block (CNBLOCK) of this channel group
(NIL allowed)
LINK 1 Pointer to the conversion formula (CCBLOCK) of this signal
(NIL allowed).
LINK 1 Reserved
LINK 1 Reserved
LINK 1 Pointer to the channel comment (TXBLOCK) of this signal (NIL
allowed)
UINT16 1 Channel type 0 = data channel, 1 = time channel for all
signals of this group (in each channel group, exactly one
channel must be defined as time channel)
CHAR 32 Signal name, i.e. the first 32 characters of the ASAM-MCD
unique name
CHAR 128 Signal description
UINT16 1 Number of the first bits [0..n] (bit position within a byte:
bit 0 is the least significant bit, bit 7 is the most significant bit)
UINT16 1 Number of bits
UINT16 1 Signal data type
0 = unsigned integer
1 = signed integer (two's complement)
2,3 = IEEE 754 floating-point format
7 = String (NULL terminated)
8 = Byte Array
BOOL 1 Value range - known implementation value
REAL 1 Value range - minimum implementation value
REAL 1 Value range - maximum implementation value
REAL 1 Rate in which the variable was sampled. Unit
LINK 1 Pointer to the ASAM-MCD unique name (TXBLOCK) (NIL allowed)
LINK 1 Pointer to TXBLOCK that contains the signal's display
identifier (default: NIL; NIL allowed)
UINT16 1 Byte offset of the signal in the data record in addition to
bit offset (default value: 0) note: this fields shall only be used if
the CGBLOCK record size and the actual offset
is larger than 8192 Bytes to ensure compatibility; it enables to write
data blocks larger than 8kBytes
Since I cannot determine in advance what the number of channels are and
the data format of each channel what is the best way to create the data
structure in memory. I thought of reading in the raw data to a char
array. Dynamically allocate arrays for each channel. Then casting the
char array to the proper data type for each channel and fill the
arrays. Somehow I believe there must be an easier way to do this. Any
suggestions?
The file contains a number of blocks that can be read from the file
using a baisc structure.
For example the ID BLOCK is as follows,
(Data Type) (Number of Elements) (Description)
CHAR 8 File identifier,
CHAR 8 Format identifier,
CHAR 8 Program identifier,
UINT16 1 Byte order
UINT16 1 Floating-point
UINT16 1 Version number
UINT16 1 Reserved
CHAR 2 Reserved
CHAR 30 Reserved
The measured data is described with a channel group as follows (Link is
a file offset pointer)
CHAR 2 Block type identifier, always "CG"
UINT16 1 Block size of this block in bytes (entire CGBLOCK)
LINK 1 Pointer to next data Channel group block (CGBLOCK) (NIL
allowed)
LINK 1 Pointer to first channel block (CNBLOCK) (NIL allowed)
LINK 1 Pointer to channel group comment text (TXBLOCK) (NIL allowed)
UINT16 1 Record ID
UINT16 1 Number of channels
UINT16 1 Data record size in bytes (without the record ID), i.e. data
size of the channel group for each sample
UINT32 1 Number of records
This channel group above, defines how big the data record size is and
how many records are contained. The data record can consist of many
channels that are described as follows
CHAR 2 Block type identifier, always "CN"
UINT16 1 Block size of this block in bytes (entire CNBLOCK)
LINK 1 Pointer to next channel block (CNBLOCK) of this channel group
(NIL allowed)
LINK 1 Pointer to the conversion formula (CCBLOCK) of this signal
(NIL allowed).
LINK 1 Reserved
LINK 1 Reserved
LINK 1 Pointer to the channel comment (TXBLOCK) of this signal (NIL
allowed)
UINT16 1 Channel type 0 = data channel, 1 = time channel for all
signals of this group (in each channel group, exactly one
channel must be defined as time channel)
CHAR 32 Signal name, i.e. the first 32 characters of the ASAM-MCD
unique name
CHAR 128 Signal description
UINT16 1 Number of the first bits [0..n] (bit position within a byte:
bit 0 is the least significant bit, bit 7 is the most significant bit)
UINT16 1 Number of bits
UINT16 1 Signal data type
0 = unsigned integer
1 = signed integer (two's complement)
2,3 = IEEE 754 floating-point format
7 = String (NULL terminated)
8 = Byte Array
BOOL 1 Value range - known implementation value
REAL 1 Value range - minimum implementation value
REAL 1 Value range - maximum implementation value
REAL 1 Rate in which the variable was sampled. Unit
LINK 1 Pointer to the ASAM-MCD unique name (TXBLOCK) (NIL allowed)
LINK 1 Pointer to TXBLOCK that contains the signal's display
identifier (default: NIL; NIL allowed)
UINT16 1 Byte offset of the signal in the data record in addition to
bit offset (default value: 0) note: this fields shall only be used if
the CGBLOCK record size and the actual offset
is larger than 8192 Bytes to ensure compatibility; it enables to write
data blocks larger than 8kBytes
Since I cannot determine in advance what the number of channels are and
the data format of each channel what is the best way to create the data
structure in memory. I thought of reading in the raw data to a char
array. Dynamically allocate arrays for each channel. Then casting the
char array to the proper data type for each channel and fill the
arrays. Somehow I believe there must be an easier way to do this. Any
suggestions?