blob: 47b961bd9088492f11d703e5c01b3a08773983a1 [file] [log] [blame]
Paul Greenwood31a54882019-08-01 17:05:09 -05001#pragma once
2
3/**
4@file hei_chip_data_stream.hpp
5@brief Description: The ChipDataStream class
6
Zane Shelley83da2452019-10-25 15:45:34 -05007ChipDataStream makes it possible to read a buffer of binary data using the
8stream operators, ">>".
Paul Greenwood31a54882019-08-01 17:05:09 -05009
10Instantiate ChipDataStream class with a pointer to a data buffer
11and its size in bytes as below:
12
13 ChipDataStream cds(streamData,552);
14
15Use the ">>" stream operator then to read the basic integral types
16(bool, char, uint8_t, int8_t, uint16_t, int16_t, uint32_t,
17int32_t, uint64_t, and int64_t).
18
19Endian issues are taken care of by template specialization.
20**/
21
22#include <endian.h>
Paul Greenwood31a54882019-08-01 17:05:09 -050023#include <string.h>
24
Zane Shelleyca9f6252019-10-25 21:17:30 -050025#include <hei_includes.hpp>
26
Paul Greenwood31a54882019-08-01 17:05:09 -050027namespace libhei
28{
29
30/**
Zane Shelley83da2452019-10-25 15:45:34 -050031 * ChipDataStream
32 * ChipDataStream offers convenient stream operator access to binary data.
33 **/
Paul Greenwood31a54882019-08-01 17:05:09 -050034class ChipDataStream
35{
36
37 private:
Zane Shelley83da2452019-10-25 15:45:34 -050038 /** iv_buffer points to the first address of the Chip Data File
39 buffer. **/
Zane Shelleyfe27b652019-10-28 11:33:07 -050040 const void* const iv_buffer;
Zane Shelley83da2452019-10-25 15:45:34 -050041 /** iv_bufferSize is the size of the data buffer. It is
42 initialized when the ChipDataStream class is instantiated. **/
43 const size_t iv_bufferSize;
44 /** iv_asyncOffset keeps an offset into the buffer. This
45 offset is incremented appropriately as data is read. **/
46 size_t iv_asyncOffset;
Paul Greenwood31a54882019-08-01 17:05:09 -050047
48 public:
Zane Shelley83da2452019-10-25 15:45:34 -050049 /* Constructors */
Paul Greenwood31a54882019-08-01 17:05:09 -050050
Zane Shelley83da2452019-10-25 15:45:34 -050051 /**
52 When instantiating the ChipDataStream object a pointer to a
53 data buffer containing all the data and its size is passed
54 into the class.
55 **/
Zane Shelleyfe27b652019-10-28 11:33:07 -050056 ChipDataStream(void* i_buffer, size_t i_bufferSize) :
Zane Shelley83da2452019-10-25 15:45:34 -050057 iv_asyncOffset(0), iv_buffer(i_buffer), iv_bufferSize(i_bufferSize)
58 {}
Paul Greenwood31a54882019-08-01 17:05:09 -050059
Zane Shelley83da2452019-10-25 15:45:34 -050060 /** Eliminate copy and assignment operator constructors **/
Zane Shelleyfe27b652019-10-28 11:33:07 -050061 ChipDataStream(const ChipDataStream&) = delete;
62 ChipDataStream& operator=(const ChipDataStream&) = delete;
Paul Greenwood31a54882019-08-01 17:05:09 -050063
Zane Shelley83da2452019-10-25 15:45:34 -050064 /** Destructor **/
Paul Greenwood31a54882019-08-01 17:05:09 -050065
Zane Shelley83da2452019-10-25 15:45:34 -050066 ~ChipDataStream() = default;
Paul Greenwood31a54882019-08-01 17:05:09 -050067
Zane Shelley83da2452019-10-25 15:45:34 -050068 /** Functions **/
Paul Greenwood31a54882019-08-01 17:05:09 -050069
Zane Shelley83da2452019-10-25 15:45:34 -050070 /**
71 *@brief Default case for "operator>>" template.
72 *@param D: A type
73 *@param o_right: A pointer to where the data is stored
74 *@return *this: A pointer to "this" object
75 **/
76 template <class D>
Zane Shelleyfe27b652019-10-28 11:33:07 -050077 ChipDataStream& operator>>(D& o_right)
Zane Shelley83da2452019-10-25 15:45:34 -050078 {
79 read(&o_right, sizeof(D));
80 return *this;
81 }
Paul Greenwood31a54882019-08-01 17:05:09 -050082
83 private:
Zane Shelley83da2452019-10-25 15:45:34 -050084 /**
85 *@brief Read does the copy from the buffer
86 *@param o_buf a pointer to the location to copy to
87 *@param i_size the size (in bytes) to copy
88 *@return None\n\n
89 **/
Zane Shelleyfe27b652019-10-28 11:33:07 -050090 void read(void* o_buf, size_t i_size)
Zane Shelley83da2452019-10-25 15:45:34 -050091 {
92 /* Ensure memory is not accessed outside i_buffer */
93 HEI_ASSERT((iv_asyncOffset + i_size) <= iv_bufferSize);
94 /* Copy appropriate bytes from i_buffer to o_buff */
Zane Shelleyfe27b652019-10-28 11:33:07 -050095 memcpy(o_buf, (char*)iv_buffer + iv_asyncOffset, i_size);
Zane Shelley83da2452019-10-25 15:45:34 -050096 /* Increment asynchronous offset to next piece of data */
97 iv_asyncOffset = iv_asyncOffset + i_size;
98 }
Paul Greenwood31a54882019-08-01 17:05:09 -050099};
100
101/*
Zane Shelley83da2452019-10-25 15:45:34 -0500102 * Note: The specializations below ensure the big-endian Chip Data File
103 * format is converted into the host format.
104 */
Paul Greenwood31a54882019-08-01 17:05:09 -0500105
106/**
Zane Shelley83da2452019-10-25 15:45:34 -0500107 * @brief This template extracts a uint16_t data type from the data buffer
108 * @param o_right: A pointer to where the data is stored
109 * @return *this: A pointer to "this" object
110 **/
Zane Shelley7f7a42d2019-10-28 13:28:31 -0500111template <>
112inline ChipDataStream& ChipDataStream::operator>>(uint16_t& o_right)
Zane Shelley83da2452019-10-25 15:45:34 -0500113{
114 read(&o_right, sizeof(o_right));
115 be16toh(o_right);
116 return *this;
117}
Paul Greenwood31a54882019-08-01 17:05:09 -0500118
119/**@brief This template extracts an int16_t type from the data buffer
Zane Shelley83da2452019-10-25 15:45:34 -0500120 * @param o_right: A pointer to where the data is stored
121 * @return *this: A pointer to "this" object
122 **/
Zane Shelley7f7a42d2019-10-28 13:28:31 -0500123template <>
124inline ChipDataStream& ChipDataStream::operator>>(int16_t& o_right)
Zane Shelley83da2452019-10-25 15:45:34 -0500125{
126 read(&o_right, sizeof(o_right));
127 be16toh(o_right);
128 return *this;
129}
Paul Greenwood31a54882019-08-01 17:05:09 -0500130
131/**@brief This template extracts a uint32_t type from the data buffer
Zane Shelley83da2452019-10-25 15:45:34 -0500132 * @param o_right: A pointer to where the data is stored
133 * @return *this: A pointer to "this" object
134 **/
Zane Shelley7f7a42d2019-10-28 13:28:31 -0500135template <>
136inline ChipDataStream& ChipDataStream::operator>>(uint32_t& o_right)
Zane Shelley83da2452019-10-25 15:45:34 -0500137{
138 read(&o_right, sizeof(o_right));
139 be32toh(o_right);
140 return *this;
141}
Paul Greenwood31a54882019-08-01 17:05:09 -0500142
143/**@brief This template extracts an int32_t type from the data buffer
Zane Shelley83da2452019-10-25 15:45:34 -0500144 * @param o_right: A pointer to where the data is stored
145 * @return *this: A pointer to "this" object
146 **/
Zane Shelley7f7a42d2019-10-28 13:28:31 -0500147template <>
148inline ChipDataStream& ChipDataStream::operator>>(int32_t& o_right)
Zane Shelley83da2452019-10-25 15:45:34 -0500149{
150 read(&o_right, sizeof(o_right));
151 be32toh(o_right);
152 return *this;
153}
Paul Greenwood31a54882019-08-01 17:05:09 -0500154
155/**@brief This template extracts a uint64_t type from the data buffer
Zane Shelley83da2452019-10-25 15:45:34 -0500156 * @param o_right: A pointer to where the data is stored
157 * @return *this: A pointer to "this" object
158 **/
Zane Shelley7f7a42d2019-10-28 13:28:31 -0500159template <>
160inline ChipDataStream& ChipDataStream::operator>>(uint64_t& o_right)
Zane Shelley83da2452019-10-25 15:45:34 -0500161{
162 read(&o_right, sizeof(o_right));
163 be64toh(o_right);
164 return *this;
165}
Paul Greenwood31a54882019-08-01 17:05:09 -0500166
167/**@brief This template extracts an int64_t type from the data buffer
Zane Shelley83da2452019-10-25 15:45:34 -0500168 * @param o_right: A pointer to where the data is stored
169 * @return *this: A pointer to "this" object
170 **/
Zane Shelley7f7a42d2019-10-28 13:28:31 -0500171template <>
172inline ChipDataStream& ChipDataStream::operator>>(int64_t& o_right)
Zane Shelley83da2452019-10-25 15:45:34 -0500173{
174 read(&o_right, sizeof(o_right));
175 be64toh(o_right);
176 return *this;
177}
Paul Greenwood31a54882019-08-01 17:05:09 -0500178
Zane Shelley83da2452019-10-25 15:45:34 -0500179} // namespace libhei