User | Revision | Line number | New contents of line |
samux |
0:0cf0e27feaad
|
1
|
#include "MbedJSONValue.h"
|
samux |
0:0cf0e27feaad
|
2
|
|
samux |
0:0cf0e27feaad
|
3
|
# include <stdlib.h>
|
samux |
0:0cf0e27feaad
|
4
|
# include <stdio.h>
|
samux |
0:0cf0e27feaad
|
5
|
|
samux |
0:0cf0e27feaad
|
6
|
// Clean up
|
samux |
0:0cf0e27feaad
|
7
|
void MbedJSONValue::clean() {
|
samux |
0:0cf0e27feaad
|
8
|
switch (_type) {
|
samux |
0:0cf0e27feaad
|
9
|
case TypeString:
|
samux |
0:0cf0e27feaad
|
10
|
delete _value.asString;
|
samux |
0:0cf0e27feaad
|
11
|
break;
|
samux |
0:0cf0e27feaad
|
12
|
case TypeArray:
|
samux |
0:0cf0e27feaad
|
13
|
for (int i = 0; i < index_array; i++)
|
samux |
0:0cf0e27feaad
|
14
|
delete array[i];
|
samux |
0:0cf0e27feaad
|
15
|
index_array = 0;
|
samux |
0:0cf0e27feaad
|
16
|
break;
|
samux |
0:0cf0e27feaad
|
17
|
case TypeObject:
|
samux |
0:0cf0e27feaad
|
18
|
for (int i = 0; i < index_token; i++) {
|
samux |
0:0cf0e27feaad
|
19
|
delete token[i];
|
samux |
0:0cf0e27feaad
|
20
|
delete token_name[i];
|
samux |
0:0cf0e27feaad
|
21
|
}
|
samux |
0:0cf0e27feaad
|
22
|
index_token = 0;
|
samux |
0:0cf0e27feaad
|
23
|
break;
|
samux |
0:0cf0e27feaad
|
24
|
default:
|
samux |
0:0cf0e27feaad
|
25
|
break;
|
samux |
0:0cf0e27feaad
|
26
|
}
|
samux |
0:0cf0e27feaad
|
27
|
_type = TypeNull;
|
samux |
0:0cf0e27feaad
|
28
|
_type = TypeNull;
|
samux |
0:0cf0e27feaad
|
29
|
}
|
samux |
0:0cf0e27feaad
|
30
|
|
samux |
0:0cf0e27feaad
|
31
|
bool MbedJSONValue::hasMember(char * name)
|
samux |
0:0cf0e27feaad
|
32
|
{
|
samux |
0:0cf0e27feaad
|
33
|
for(int i = 0; i < index_token; i++)
|
samux |
0:0cf0e27feaad
|
34
|
if( !strcmp(name, (*(token_name[i])).c_str() ))
|
samux |
0:0cf0e27feaad
|
35
|
return true;
|
samux |
0:0cf0e27feaad
|
36
|
return false;
|
samux |
0:0cf0e27feaad
|
37
|
}
|
samux |
0:0cf0e27feaad
|
38
|
|
samux |
0:0cf0e27feaad
|
39
|
|
samux |
0:0cf0e27feaad
|
40
|
void copy(const std::string& s, std::back_insert_iterator<std::string> oi) {
|
samux |
0:0cf0e27feaad
|
41
|
std::copy(s.begin(), s.end(), oi);
|
samux |
0:0cf0e27feaad
|
42
|
}
|
samux |
0:0cf0e27feaad
|
43
|
|
samux |
0:0cf0e27feaad
|
44
|
void serialize_str(const std::string& s, std::back_insert_iterator<std::string> oi) {
|
samux |
0:0cf0e27feaad
|
45
|
*oi++ = '"';
|
samux |
0:0cf0e27feaad
|
46
|
for (std::string::const_iterator i = s.begin(); i != s.end(); ++i) {
|
samux |
0:0cf0e27feaad
|
47
|
switch (*i) {
|
samux |
0:0cf0e27feaad
|
48
|
#define MAP(val, sym) case val: copy(sym, oi); break
|
samux |
0:0cf0e27feaad
|
49
|
MAP('"', "\\\"");
|
samux |
0:0cf0e27feaad
|
50
|
MAP('\\', "\\\\");
|
samux |
0:0cf0e27feaad
|
51
|
MAP('/', "\\/");
|
samux |
0:0cf0e27feaad
|
52
|
MAP('\b', "\\b");
|
samux |
0:0cf0e27feaad
|
53
|
MAP('\f', "\\f");
|
samux |
0:0cf0e27feaad
|
54
|
MAP('\n', "\\n");
|
samux |
0:0cf0e27feaad
|
55
|
MAP('\r', "\\r");
|
samux |
0:0cf0e27feaad
|
56
|
MAP('\t', "\\t");
|
samux |
0:0cf0e27feaad
|
57
|
#undef MAP
|
samux |
0:0cf0e27feaad
|
58
|
default:
|
samux |
0:0cf0e27feaad
|
59
|
if ((unsigned char)*i < 0x20 || *i == 0x7f) {
|
samux |
0:0cf0e27feaad
|
60
|
char buf[7];
|
samux |
0:0cf0e27feaad
|
61
|
sprintf(buf, "\\u%04x", *i & 0xff);
|
samux |
0:0cf0e27feaad
|
62
|
copy(buf, buf + 6, oi);
|
samux |
0:0cf0e27feaad
|
63
|
} else {
|
samux |
0:0cf0e27feaad
|
64
|
*oi++ = *i;
|
samux |
0:0cf0e27feaad
|
65
|
}
|
samux |
0:0cf0e27feaad
|
66
|
break;
|
samux |
0:0cf0e27feaad
|
67
|
}
|
samux |
0:0cf0e27feaad
|
68
|
}
|
samux |
0:0cf0e27feaad
|
69
|
*oi++ = '"';
|
samux |
0:0cf0e27feaad
|
70
|
}
|
samux |
0:0cf0e27feaad
|
71
|
|
samux |
0:0cf0e27feaad
|
72
|
std::string MbedJSONValue::serialize(){
|
samux |
0:0cf0e27feaad
|
73
|
std::string s;
|
samux |
0:0cf0e27feaad
|
74
|
serialize(std::back_inserter(s));
|
samux |
0:0cf0e27feaad
|
75
|
return s;
|
samux |
0:0cf0e27feaad
|
76
|
}
|
samux |
0:0cf0e27feaad
|
77
|
|
samux |
0:0cf0e27feaad
|
78
|
std::string MbedJSONValue::to_str(){
|
samux |
0:0cf0e27feaad
|
79
|
switch (_type) {
|
samux |
0:0cf0e27feaad
|
80
|
case TypeNull:
|
samux |
0:0cf0e27feaad
|
81
|
return "null";
|
samux |
0:0cf0e27feaad
|
82
|
case TypeBoolean:
|
samux |
0:0cf0e27feaad
|
83
|
return _value.asBool ? "true" : "false";
|
samux |
0:0cf0e27feaad
|
84
|
case TypeInt: {
|
samux |
0:0cf0e27feaad
|
85
|
char buf[10];
|
samux |
0:0cf0e27feaad
|
86
|
sprintf(buf, "%d", _value.asInt);
|
samux |
0:0cf0e27feaad
|
87
|
return buf;
|
samux |
0:0cf0e27feaad
|
88
|
}
|
samux |
0:0cf0e27feaad
|
89
|
case TypeDouble: {
|
samux |
0:0cf0e27feaad
|
90
|
char buf[10];
|
samux |
0:0cf0e27feaad
|
91
|
sprintf(buf, "%f", _value.asDouble);
|
samux |
0:0cf0e27feaad
|
92
|
return buf;
|
samux |
0:0cf0e27feaad
|
93
|
}
|
samux |
0:0cf0e27feaad
|
94
|
default:
|
samux |
0:0cf0e27feaad
|
95
|
break;
|
samux |
0:0cf0e27feaad
|
96
|
}
|
samux |
0:0cf0e27feaad
|
97
|
return NULL;
|
samux |
0:0cf0e27feaad
|
98
|
}
|
samux |
0:0cf0e27feaad
|
99
|
|
samux |
0:0cf0e27feaad
|
100
|
|
samux |
0:0cf0e27feaad
|
101
|
|
samux |
0:0cf0e27feaad
|
102
|
void MbedJSONValue::serialize(std::back_insert_iterator<std::string> oi) {
|
samux |
0:0cf0e27feaad
|
103
|
switch (_type) {
|
samux |
0:0cf0e27feaad
|
104
|
case TypeString:
|
samux |
0:0cf0e27feaad
|
105
|
serialize_str(*_value.asString, oi);
|
samux |
0:0cf0e27feaad
|
106
|
break;
|
samux |
0:0cf0e27feaad
|
107
|
case TypeArray: {
|
samux |
0:0cf0e27feaad
|
108
|
*oi++ = '[';
|
samux |
0:0cf0e27feaad
|
109
|
for (int i = 0; i < index_array; i++) {
|
samux |
0:0cf0e27feaad
|
110
|
if (i)
|
samux |
0:0cf0e27feaad
|
111
|
*oi++ = ',';
|
samux |
0:0cf0e27feaad
|
112
|
(*this)[i].serialize(oi);
|
samux |
0:0cf0e27feaad
|
113
|
}
|
samux |
0:0cf0e27feaad
|
114
|
*oi++ = ']';
|
samux |
0:0cf0e27feaad
|
115
|
break;
|
samux |
0:0cf0e27feaad
|
116
|
}
|
samux |
0:0cf0e27feaad
|
117
|
case TypeObject: {
|
samux |
0:0cf0e27feaad
|
118
|
*oi++ = '{';
|
samux |
0:0cf0e27feaad
|
119
|
for (int i = 0; i < index_token; i++) {
|
samux |
0:0cf0e27feaad
|
120
|
if (i)
|
samux |
0:0cf0e27feaad
|
121
|
*oi++ = ',';
|
samux |
0:0cf0e27feaad
|
122
|
serialize_str(*(token_name[i]), oi);
|
samux |
0:0cf0e27feaad
|
123
|
*oi++ = ':';
|
samux |
0:0cf0e27feaad
|
124
|
(*(token[i])).serialize(oi);
|
samux |
0:0cf0e27feaad
|
125
|
}
|
samux |
0:0cf0e27feaad
|
126
|
*oi++ = '}';
|
samux |
0:0cf0e27feaad
|
127
|
break;
|
samux |
0:0cf0e27feaad
|
128
|
}
|
samux |
0:0cf0e27feaad
|
129
|
default:
|
samux |
0:0cf0e27feaad
|
130
|
copy(to_str(), oi);
|
samux |
0:0cf0e27feaad
|
131
|
break;
|
samux |
0:0cf0e27feaad
|
132
|
}
|
samux |
0:0cf0e27feaad
|
133
|
}
|
samux |
0:0cf0e27feaad
|
134
|
|
samux |
0:0cf0e27feaad
|
135
|
|
samux |
0:0cf0e27feaad
|
136
|
|
samux |
0:0cf0e27feaad
|
137
|
MbedJSONValue& MbedJSONValue::operator[](int i) {
|
samux |
0:0cf0e27feaad
|
138
|
_type = TypeArray;
|
samux |
0:0cf0e27feaad
|
139
|
if (i < NB_TOKEN && index_array == i ) {
|
samux |
0:0cf0e27feaad
|
140
|
#ifdef DEBUG
|
samux |
0:0cf0e27feaad
|
141
|
printf("will add an element to the array\r\n");
|
samux |
0:0cf0e27feaad
|
142
|
#endif
|
samux |
0:0cf0e27feaad
|
143
|
array[i] = new MbedJSONValue();
|
samux |
0:0cf0e27feaad
|
144
|
index_array++;
|
samux |
0:0cf0e27feaad
|
145
|
return *(array[i]);
|
samux |
0:0cf0e27feaad
|
146
|
}
|
samux |
0:0cf0e27feaad
|
147
|
if (i < NB_TOKEN && index_array > i)
|
samux |
0:0cf0e27feaad
|
148
|
return *(array[i]);
|
samux |
0:0cf0e27feaad
|
149
|
|
samux |
0:0cf0e27feaad
|
150
|
//if the user is not doing something wrong, this code is never executed!!
|
samux |
0:0cf0e27feaad
|
151
|
return *(new MbedJSONValue());
|
samux |
0:0cf0e27feaad
|
152
|
}
|
samux |
0:0cf0e27feaad
|
153
|
|
samux |
0:0cf0e27feaad
|
154
|
MbedJSONValue& MbedJSONValue::operator[](std::string k) {
|
samux |
0:0cf0e27feaad
|
155
|
_type = TypeObject;
|
samux |
0:0cf0e27feaad
|
156
|
for (int i = 0; i < index_token; i++) {
|
samux |
0:0cf0e27feaad
|
157
|
#ifdef DEBUG
|
samux |
0:0cf0e27feaad
|
158
|
printf("k: %s\r\n", k.c_str());
|
samux |
0:0cf0e27feaad
|
159
|
printf("str: %s\r\n", token_name[i]->c_str());
|
samux |
0:0cf0e27feaad
|
160
|
#endif
|
samux |
0:0cf0e27feaad
|
161
|
//existing token
|
samux |
0:0cf0e27feaad
|
162
|
if (!strcmp(k.c_str(), token_name[i]->c_str())) {
|
samux |
0:0cf0e27feaad
|
163
|
#ifdef DEBUG
|
samux |
0:0cf0e27feaad
|
164
|
printf("token found: %d\r\n", i);
|
samux |
0:0cf0e27feaad
|
165
|
#endif
|
samux |
0:0cf0e27feaad
|
166
|
return *(token[i]);
|
samux |
0:0cf0e27feaad
|
167
|
}
|
samux |
0:0cf0e27feaad
|
168
|
}
|
samux |
0:0cf0e27feaad
|
169
|
|
samux |
0:0cf0e27feaad
|
170
|
if(index_token >= NB_TOKEN)
|
samux |
0:0cf0e27feaad
|
171
|
index_token = NB_TOKEN - 1;
|
samux |
0:0cf0e27feaad
|
172
|
//non existing token
|
samux |
0:0cf0e27feaad
|
173
|
token_name[index_token] = new std::string(k);
|
samux |
0:0cf0e27feaad
|
174
|
token[index_token] = new MbedJSONValue();
|
samux |
0:0cf0e27feaad
|
175
|
index_token++;
|
samux |
0:0cf0e27feaad
|
176
|
return *(token[index_token - 1]);
|
samux |
0:0cf0e27feaad
|
177
|
}
|
samux |
0:0cf0e27feaad
|
178
|
|
samux |
0:0cf0e27feaad
|
179
|
MbedJSONValue& MbedJSONValue::operator[](std::string k) const
|
samux |
0:0cf0e27feaad
|
180
|
{
|
samux |
0:0cf0e27feaad
|
181
|
for (int i = 0; i < index_token; i++) {
|
samux |
0:0cf0e27feaad
|
182
|
#ifdef DEBUG
|
samux |
0:0cf0e27feaad
|
183
|
printf("k: %s\r\n", k.c_str());
|
samux |
0:0cf0e27feaad
|
184
|
printf("str: %s\r\n", token_name[i]->c_str());
|
samux |
0:0cf0e27feaad
|
185
|
#endif
|
samux |
0:0cf0e27feaad
|
186
|
if (!strcmp(k.c_str(), token_name[i]->c_str())) {
|
samux |
0:0cf0e27feaad
|
187
|
#ifdef DEBUG
|
samux |
0:0cf0e27feaad
|
188
|
printf("token found: %d\r\n", i);
|
samux |
0:0cf0e27feaad
|
189
|
#endif
|
samux |
0:0cf0e27feaad
|
190
|
return *(token[i]);
|
samux |
0:0cf0e27feaad
|
191
|
}
|
samux |
0:0cf0e27feaad
|
192
|
}
|
samux |
0:0cf0e27feaad
|
193
|
|
samux |
0:0cf0e27feaad
|
194
|
//if the user is not doing something wrong, this code is never executed!!
|
samux |
0:0cf0e27feaad
|
195
|
return *(new MbedJSONValue());
|
samux |
0:0cf0e27feaad
|
196
|
}
|
samux |
0:0cf0e27feaad
|
197
|
|
samux |
0:0cf0e27feaad
|
198
|
|
samux |
0:0cf0e27feaad
|
199
|
// Operators
|
samux |
0:0cf0e27feaad
|
200
|
MbedJSONValue& MbedJSONValue::operator=(MbedJSONValue const& rhs) {
|
samux |
0:0cf0e27feaad
|
201
|
if (this != &rhs) {
|
samux |
0:0cf0e27feaad
|
202
|
clean();
|
samux |
0:0cf0e27feaad
|
203
|
_type = rhs._type;
|
samux |
0:0cf0e27feaad
|
204
|
switch (_type) {
|
samux |
0:0cf0e27feaad
|
205
|
case TypeBoolean:
|
samux |
0:0cf0e27feaad
|
206
|
_value.asBool = rhs._value.asBool;
|
samux |
0:0cf0e27feaad
|
207
|
break;
|
samux |
0:0cf0e27feaad
|
208
|
case TypeInt:
|
samux |
0:0cf0e27feaad
|
209
|
_value.asInt = rhs._value.asInt;
|
samux |
0:0cf0e27feaad
|
210
|
break;
|
samux |
0:0cf0e27feaad
|
211
|
case TypeDouble:
|
samux |
0:0cf0e27feaad
|
212
|
_value.asDouble = rhs._value.asDouble;
|
samux |
0:0cf0e27feaad
|
213
|
break;
|
samux |
0:0cf0e27feaad
|
214
|
case TypeString:
|
samux |
0:0cf0e27feaad
|
215
|
_value.asString = new std::string(*rhs._value.asString);
|
samux |
0:0cf0e27feaad
|
216
|
break;
|
samux |
0:0cf0e27feaad
|
217
|
case TypeArray:
|
samux |
0:0cf0e27feaad
|
218
|
for (int i = 0; i < rhs.index_array; i++)
|
samux |
0:0cf0e27feaad
|
219
|
(*this)[i] = rhs[i];
|
samux |
0:0cf0e27feaad
|
220
|
case TypeObject:
|
samux |
0:0cf0e27feaad
|
221
|
for (int i = 0; i < rhs.index_token; i++)
|
samux |
0:0cf0e27feaad
|
222
|
(*this)[*(rhs.token_name[i])] = rhs[*(rhs.token_name[i])];
|
samux |
0:0cf0e27feaad
|
223
|
default:
|
samux |
0:0cf0e27feaad
|
224
|
break;
|
samux |
0:0cf0e27feaad
|
225
|
}
|
samux |
0:0cf0e27feaad
|
226
|
}
|
samux |
0:0cf0e27feaad
|
227
|
return *this;
|
samux |
0:0cf0e27feaad
|
228
|
}
|
samux |
0:0cf0e27feaad
|
229
|
|
samux |
0:0cf0e27feaad
|
230
|
|
samux |
0:0cf0e27feaad
|
231
|
// Works for strings, arrays, and structs.
|
samux |
0:0cf0e27feaad
|
232
|
int MbedJSONValue::size() const {
|
samux |
0:0cf0e27feaad
|
233
|
switch (_type) {
|
samux |
0:0cf0e27feaad
|
234
|
case TypeString:
|
samux |
0:0cf0e27feaad
|
235
|
return int(_value.asString->size());
|
samux |
0:0cf0e27feaad
|
236
|
case TypeArray:
|
samux |
0:0cf0e27feaad
|
237
|
return index_array;
|
samux |
0:0cf0e27feaad
|
238
|
case TypeObject:
|
samux |
0:0cf0e27feaad
|
239
|
return index_token;
|
samux |
0:0cf0e27feaad
|
240
|
default:
|
samux |
0:0cf0e27feaad
|
241
|
break;
|
samux |
0:0cf0e27feaad
|
242
|
}
|
samux |
0:0cf0e27feaad
|
243
|
return -1;
|
samux |
0:0cf0e27feaad
|
244
|
}
|
samux |
0:0cf0e27feaad
|
245
|
|