• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

bblanchon / ArduinoJson / 4766013433

pending completion
4766013433

push

github

Benoit Blanchon
Increase coverage

8 of 8 new or added lines in 3 files covered. (100.0%)

3321 of 3342 relevant lines covered (99.37%)

6648.12 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

98.73
/src/ArduinoJson/Variant/VariantFunctions.hpp
1
// ArduinoJson - https://arduinojson.org
2
// Copyright © 2014-2023, Benoit BLANCHON
3
// MIT License
4

5
#pragma once
6

7
#include <ArduinoJson/Polyfills/assert.hpp>
8
#include <ArduinoJson/Polyfills/attributes.hpp>
9
#include <ArduinoJson/Strings/StoragePolicy.hpp>
10
#include <ArduinoJson/Variant/VariantData.hpp>
11
#include <ArduinoJson/Variant/Visitor.hpp>
12

13
ARDUINOJSON_BEGIN_PRIVATE_NAMESPACE
14

15
void slotRelease(const VariantSlot* slot, MemoryPool* pool);
16
bool collectionCopy(CollectionData* dst, const CollectionData* src,
17
                    MemoryPool* pool);
18
VariantData* collectionAddElement(CollectionData* array, MemoryPool* pool);
19
void collectionRemoveElement(CollectionData* data, size_t index,
20
                             MemoryPool* pool);
21
template <typename TAdaptedString>
22
void collectionRemoveMember(CollectionData* data, TAdaptedString key,
23
                            MemoryPool* pool);
24

25
template <typename TVisitor>
26
inline typename TVisitor::result_type variantAccept(const VariantData* var,
5,535✔
27
                                                    TVisitor& visitor) {
28
  if (var != 0)
5,535✔
29
    return var->accept(visitor);
5,378✔
30
  else
31
    return visitor.visitNull();
157✔
32
}
33

34
inline void variantRelease(const VariantData* var, MemoryPool* pool) {
67,832✔
35
  ARDUINOJSON_ASSERT(var != nullptr);
36
  auto s = var->getOwnedString();
67,832✔
37
  if (s)
67,832✔
38
    pool->dereferenceString(s);
11✔
39

40
  auto c = var->asCollection();
67,832✔
41
  if (c) {
67,832✔
42
    for (auto slot = c->head(); slot; slot = slot->next())
21✔
43
      slotRelease(slot, pool);
10✔
44
  }
45
}
67,832✔
46

47
inline bool variantCopyFrom(VariantData* dst, const VariantData* src,
75✔
48
                            MemoryPool* pool) {
49
  if (!dst)
75✔
50
    return false;
4✔
51
  if (!src) {
71✔
52
    dst->setNull();
4✔
53
    return true;
4✔
54
  }
55
  switch (src->type()) {
67✔
56
    case VALUE_IS_ARRAY:
12✔
57
      return collectionCopy(&dst->toArray(), src->asArray(), pool);
12✔
58
    case VALUE_IS_OBJECT:
17✔
59
      return collectionCopy(&dst->toObject(), src->asObject(), pool);
17✔
60
    case VALUE_IS_OWNED_STRING: {
11✔
61
      auto str = adaptString(src->asString());
11✔
62
      auto dup = storeString(pool, str, StringStoragePolicy::Copy());
11✔
63
      if (!dup)
11✔
64
        return false;
1✔
65
      dst->setString(dup);
10✔
66
      return true;
10✔
67
    }
68
    case VALUE_IS_OWNED_RAW: {
3✔
69
      auto str = adaptString(src->asRaw());
3✔
70
      auto dup = storeString(pool, str, StringStoragePolicy::Copy());
3✔
71
      if (!dup)
3✔
72
        return false;
1✔
73
      dst->setOwnedRaw(dup.c_str(), str.size());
2✔
74
      return true;
2✔
75
    }
76
    default:
24✔
77
      *dst = *src;
24✔
78
      return true;
24✔
79
  }
80
}
81

82
inline void variantSetNull(VariantData* var, MemoryPool* pool) {
420✔
83
  if (!var)
420✔
84
    return;
1✔
85
  variantRelease(var, pool);
419✔
86
  var->setNull();
419✔
87
}
88

89
inline void variantSetBoolean(VariantData* var, bool value, MemoryPool* pool) {
253✔
90
  if (!var)
253✔
91
    return;
4✔
92
  variantRelease(var, pool);
249✔
93
  var->setBoolean(value);
249✔
94
}
95

96
inline void variantSetFloat(VariantData* var, JsonFloat value,
63✔
97
                            MemoryPool* pool) {
98
  if (!var)
63✔
99
    return;
2✔
100
  variantRelease(var, pool);
61✔
101
  var->setFloat(value);
61✔
102
}
103

104
template <typename T>
105
inline void variantSetInteger(VariantData* var, T value, MemoryPool* pool) {
591✔
106
  if (!var)
591✔
107
    return;
19✔
108
  variantRelease(var, pool);
572✔
109
  var->setInteger(value);
572✔
110
}
111

112
template <typename TAdaptedString>
113
inline void variantSetString(VariantData* var, TAdaptedString value,
65,960✔
114
                             MemoryPool* pool) {
115
  if (!var)
65,960✔
116
    return;
6✔
117
  variantRelease(var, pool);
65,954✔
118
  JsonString str = storeString(pool, value);
65,954✔
119
  if (str)
65,954✔
120
    var->setString(str);
398✔
121
  else
122
    var->setNull();
65,556✔
123
}
124

125
template <typename T>
126
inline void variantSetOwnedRaw(VariantData* var, SerializedValue<T> value,
13✔
127
                               MemoryPool* pool) {
128
  if (!var)
13✔
129
    return;
×
130
  variantRelease(var, pool);
13✔
131
  const char* dup = pool->saveString(adaptString(value.data(), value.size()));
13✔
132
  if (dup)
13✔
133
    var->setOwnedRaw(dup, value.size());
11✔
134
  else
135
    var->setNull();
2✔
136
}
137

138
inline void variantSetLinkedRaw(VariantData* var,
20✔
139
                                SerializedValue<const char*> value,
140
                                MemoryPool* pool) {
141
  if (!var)
20✔
142
    return;
2✔
143
  variantRelease(var, pool);
18✔
144
  if (value.data())
18✔
145
    var->setLinkedRaw(value.data(), value.size());
17✔
146
  else
147
    var->setNull();
1✔
148
}
149

150
inline size_t variantSize(const VariantData* var) {
30✔
151
  return var != 0 ? var->size() : 0;
30✔
152
}
153

154
inline CollectionData* variantToArray(VariantData* var, MemoryPool* pool) {
222✔
155
  if (!var)
222✔
156
    return 0;
2✔
157
  variantRelease(var, pool);
220✔
158
  return &var->toArray();
220✔
159
}
160

161
inline CollectionData* variantToObject(VariantData* var, MemoryPool* pool) {
274✔
162
  if (!var)
274✔
163
    return 0;
2✔
164
  variantRelease(var, pool);
272✔
165
  return &var->toObject();
272✔
166
}
167

168
inline VariantData* variantGetElement(const VariantData* var, size_t index) {
429✔
169
  return var != 0 ? var->getElement(index) : 0;
429✔
170
}
171

172
inline VariantData* variantAddElement(VariantData* var, MemoryPool* pool) {
248✔
173
  if (!var)
248✔
174
    return nullptr;
6✔
175
  auto array = var->isNull() ? &var->toArray() : var->asArray();
242✔
176
  return collectionAddElement(array, pool);
242✔
177
}
178

179
inline NO_INLINE VariantData* variantGetOrAddElement(VariantData* var,
137✔
180
                                                     size_t index,
181
                                                     MemoryPool* pool) {
182
  if (!var)
137✔
183
    return nullptr;
1✔
184
  auto array = var->isNull() ? &var->toArray() : var->asArray();
136✔
185
  if (!array)
136✔
186
    return nullptr;
1✔
187
  VariantSlot* slot = array->head();
135✔
188
  while (slot && index > 0) {
145✔
189
    slot = slot->next();
10✔
190
    index--;
10✔
191
  }
192
  if (!slot)
135✔
193
    index++;
101✔
194
  while (index > 0) {
249✔
195
    slot = pool->allocVariant();
114✔
196
    if (!slot)
114✔
197
      return nullptr;
×
198
    array->add(slot);
114✔
199
    index--;
114✔
200
  }
201
  return slot->data();
135✔
202
}
203

204
inline void variantRemoveElement(VariantData* var, size_t index,
8✔
205
                                 MemoryPool* pool) {
206
  if (!var)
8✔
207
    return;
1✔
208
  collectionRemoveElement(var->asArray(), index, pool);
7✔
209
}
210

211
template <typename TAdaptedString>
212
VariantData* variantGetMember(const VariantData* var, TAdaptedString key) {
2,139✔
213
  if (!var)
2,139✔
214
    return 0;
12✔
215
  return var->getMember(key);
2,127✔
216
}
217

218
template <typename TAdaptedString>
219
VariantData* variantGetOrAddMember(VariantData* var, TAdaptedString key,
805✔
220
                                   MemoryPool* pool) {
221
  if (!var || key.isNull())
805✔
222
    return nullptr;
6✔
223
  auto obj = var->isNull() ? &var->toObject() : var->asObject();
799✔
224
  if (!obj)
799✔
225
    return nullptr;
1✔
226
  auto slot = obj->get(key);
798✔
227
  if (slot)
798✔
228
    return slot->data();
33✔
229
  return collectionAddMember(obj, key, pool);
765✔
230
}
231

232
template <typename TAdaptedString>
233
void variantRemoveMember(VariantData* var, TAdaptedString key,
14✔
234
                         MemoryPool* pool) {
235
  if (!var)
14✔
236
    return;
1✔
237
  collectionRemoveMember(var->asObject(), key, pool);
13✔
238
}
239

240
inline bool variantIsNull(const VariantData* var) {
1,237✔
241
  return var == 0 || var->isNull();
1,237✔
242
}
243

244
inline size_t variantNesting(const VariantData* var) {
24✔
245
  if (!var)
24✔
246
    return 0;
3✔
247

248
  const CollectionData* collection = var->asCollection();
21✔
249
  if (!collection)
21✔
250
    return 0;
5✔
251

252
  size_t maxChildNesting = 0;
16✔
253
  for (const VariantSlot* s = collection->head(); s; s = s->next()) {
22✔
254
    size_t childNesting = variantNesting(s->data());
6✔
255
    if (childNesting > maxChildNesting)
6✔
256
      maxChildNesting = childNesting;
4✔
257
  }
258
  return maxChildNesting + 1;
16✔
259
}
260

261
ARDUINOJSON_END_PRIVATE_NAMESPACE
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2025 Coveralls, Inc