• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2016 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #ifndef _MESSAGE_BUF_H_
18 #define _MESSAGE_BUF_H_
19 
20 #include <endian.h>
21 #include <cstring>
22 
23 namespace android {
24 
25 namespace nanohub {
26 
27 /*
28  * Marshaling helper;
29  * deals with alignment and endianness.
30  * Assumption is:
31  * read*()  parse buffer from device in LE format;
32  *          return host endianness, aligned data
33  * write*() primitives take host endinnness, aligned data,
34  *          generate buffer to be passed to device in LE format
35  *
36  * Primitives do minimal error checking, only to ensure buffer read/write
37  * safety. Caller is responsible for making sure correct amount of data
38  * has been processed.
39  */
40 class MessageBuf {
41     char *data;
42     size_t size;
43     size_t pos;
44     bool readOnly;
45 public:
MessageBuf(char * buf,size_t bufSize)46     MessageBuf(char *buf, size_t bufSize) {
47         size = bufSize;
48         pos = 0;
49         data = buf;
50         readOnly = false;
51     }
MessageBuf(const char * buf,size_t bufSize)52     MessageBuf(const char *buf, size_t bufSize) {
53         size = bufSize;
54         pos = 0;
55         data = const_cast<char *>(buf);
56         readOnly = true;
57     }
getData()58     const char *getData() const { return data; }
getSize()59     size_t getSize() const { return size; }
getPos()60     size_t getPos() const { return pos; }
getRoom()61     size_t getRoom() const { return size - pos; }
readU8()62     uint8_t readU8() {
63         if (pos == size) {
64             return 0;
65         }
66         return data[pos++];
67     }
writeU8(uint8_t val)68     void writeU8(uint8_t val) {
69         if (pos == size || readOnly)
70             return;
71         data[pos++] = val;
72     }
readU16()73     uint16_t readU16() {
74         if (pos > (size - sizeof(uint16_t))) {
75             return 0;
76         }
77         uint16_t val;
78         memcpy(&val, &data[pos], sizeof(val));
79         pos += sizeof(val);
80         return le16toh(val);
81     }
writeU16(uint16_t val)82     void writeU16(uint16_t val) {
83         if (pos > (size - sizeof(uint16_t)) || readOnly) {
84             return;
85         }
86         uint16_t tmp = htole16(val);
87         memcpy(&data[pos], &tmp, sizeof(tmp));
88         pos += sizeof(tmp);
89     }
readU32()90     uint32_t readU32() {
91         if (pos > (size - sizeof(uint32_t))) {
92             return 0;
93         }
94         uint32_t val;
95         memcpy(&val, &data[pos], sizeof(val));
96         pos += sizeof(val);
97         return le32toh(val);
98     }
writeU32(uint32_t val)99     void writeU32(uint32_t val) {
100         if (pos > (size - sizeof(uint32_t)) || readOnly) {
101             return;
102         }
103         uint32_t tmp = htole32(val);
104         memcpy(&data[pos], &tmp, sizeof(tmp));
105         pos += sizeof(tmp);
106     }
readU64()107     uint64_t readU64() {
108         if (pos > (size - sizeof(uint64_t))) {
109             return 0;
110         }
111         uint64_t val;
112         memcpy(&val, &data[pos], sizeof(val));
113         pos += sizeof(val);
114         return le32toh(val);
115     }
writeU64(uint64_t val)116     void writeU64(uint64_t val) {
117         if (pos > (size - sizeof(uint64_t)) || readOnly) {
118             return;
119         }
120         uint64_t tmp = htole64(val);
121         memcpy(&data[pos], &tmp, sizeof(tmp));
122         pos += sizeof(tmp);
123     }
readRaw(size_t bufSize)124     const void *readRaw(size_t bufSize) {
125         if (pos > (size - bufSize)) {
126             return nullptr;
127         }
128         const void *buf = &data[pos];
129         pos += bufSize;
130         return buf;
131     }
writeRaw(const void * buf,size_t bufSize)132     void writeRaw(const void *buf, size_t bufSize) {
133         if (pos > (size - bufSize) || readOnly) {
134             return;
135         }
136         memcpy(&data[pos], buf, bufSize);
137         pos += bufSize;
138     }
139 };
140 
141 }; // namespace nanohub
142 
143 }; // namespace android
144 
145 #endif
146 
147