Compare commits

..

320 Commits

Author SHA1 Message Date
Benoit Blanchon
589bbbfcca VariantImpl: add toArrayIfNull() and toObjectIfNull() 2025-07-24 18:40:38 +02:00
Benoit Blanchon
03da4aad99 MsgPackSerializer: use iterators to serialize array and objects 2025-07-23 16:31:19 +02:00
Benoit Blanchon
60a767c706 JsonSerializer: use iterators to serialize array and objects 2025-07-23 16:14:03 +02:00
Benoit Blanchon
274fe06b33 VariantImpl: add copy functions 2025-07-20 18:23:03 +02:00
Benoit Blanchon
f680598a2f VariantImpl: remove addValue()
This removes the two-way dependency between `JsonVariant` and `VariantImpl`
2025-07-20 14:56:06 +02:00
Benoit Blanchon
e86c6acf2e Return bool from all built-in toJson converters 2025-07-17 22:11:36 +02:00
Benoit Blanchon
0021ec81d1 StringPool: change dereference to take a StringNode* 2025-07-16 12:32:35 +02:00
Benoit Blanchon
372f2f2767 VariantImpl: extract asOwnedString() 2025-07-16 12:26:28 +02:00
Benoit Blanchon
fc8da90ba7 VariantImpl: extract setOwnedString() 2025-07-16 12:15:58 +02:00
Benoit Blanchon
38f61d322f VariantImpl: change setRawString() to return bool 2025-07-16 12:11:58 +02:00
Benoit Blanchon
3793996d83 VariantImpl: change setRawString() to take an adapted string 2025-07-16 12:08:30 +02:00
Benoit Blanchon
43548db37d ResourceManager: move out-of-class definitions back in the class 2025-07-15 18:32:38 +02:00
Benoit Blanchon
59573ac1f9 ResourceManager: decouple from VariantImpl 2025-07-14 19:51:25 +02:00
Benoit Blanchon
14a48978d9 CollectionIterator: rename next() to move() 2025-07-14 19:51:25 +02:00
Benoit Blanchon
2fa8b9664c VariantImpl: move out-of-class definitions back in the class 2025-07-14 19:51:25 +02:00
Benoit Blanchon
2e20ce0795 CollectionIterator: remove friendship with VariantImpl 2025-07-11 18:36:51 +02:00
Benoit Blanchon
a5164f7fe3 CollectionIterator: remove data() 2025-07-11 18:34:17 +02:00
Benoit Blanchon
a9996d2293 VariantImpl: rename getResourceManager() to resources() 2025-07-11 18:31:38 +02:00
Benoit Blanchon
f9655a90ed VariantImpl: rename getData() to data() 2025-07-11 18:30:10 +02:00
Benoit Blanchon
25942cce2d CollectionIterator: replace value() with operator* and operator-> 2025-07-11 18:24:51 +02:00
Benoit Blanchon
c6fa8c1c1f Add VariantImpl in CollectionIterator 2025-07-11 18:19:35 +02:00
Benoit Blanchon
5589633697 Add ResourceManager* in CollectionIterator +80 2025-07-11 18:06:47 +02:00
Benoit Blanchon
7b7ee6cdeb Add VariantImpl::isUnbound() 2025-07-11 14:32:30 +02:00
Benoit Blanchon
dca5ba481f CollectionIterator: add value() member function 2025-07-10 19:30:51 +02:00
Benoit Blanchon
ec53525452 Rename CollectionData.hpp to CollectionIterator.hpp 2025-07-10 19:30:21 +02:00
Benoit Blanchon
0b9a8b6d2b Replace getData()/getResourceManager() with getImpl() 2025-07-10 19:29:32 +02:00
Benoit Blanchon
f62d6f26e0 Merge ArrayImpl, CollectionImpl, and ObjectImpl into VariantImpl 2025-07-10 19:29:32 +02:00
Benoit Blanchon
1f1227d595 CollectionImpl: attach to VariantData* instead of CollectionData* 2025-07-10 19:29:32 +02:00
Benoit Blanchon
6f28ec0384 CollectionImpl: add allocVariant(), getVariant(), freeVariant() 2025-07-10 19:29:32 +02:00
Benoit Blanchon
6ba4507252 CollectionImpl: add helper getCollectionData() 2025-07-10 19:28:50 +02:00
Benoit Blanchon
a265ef4927 Move CollectionData definition 2025-07-10 19:28:50 +02:00
Benoit Blanchon
8790802ce3 Decouple VariantImpl from ArrayImpl and ObjectImpl 2025-07-10 19:28:50 +02:00
Benoit Blanchon
f1b06b588e Move VariantImpl definition to VariantImpl.hpp 2025-07-10 19:28:50 +02:00
Benoit Blanchon
84fcd90658 Extract VariantImpl 2025-07-10 19:28:50 +02:00
Benoit Blanchon
bd551fa4ce Extract ArrayImpl, CollectionImpl, and ObjectImpl 2025-07-10 19:27:44 +02:00
Benoit Blanchon
d9c6a70595 JsonObject: replace ObjectData* member with VariantData* 2025-07-10 19:17:13 +02:00
Benoit Blanchon
b44aa3a8b5 JsonArray: replace ArrayData* member with VariantData* 2025-07-10 19:17:13 +02:00
Benoit Blanchon
c2290a2386 JsonObjectConst: replace ObjectData* member with VariantData* 2025-07-10 19:17:13 +02:00
Benoit Blanchon
4457cb7cc5 JsonArrayConst: replace ArrayData* member with VariantData* 2025-07-10 19:17:13 +02:00
Benoit Blanchon
1e0bbd518c Add a pool dedicated to 8-byte values (double/int64_t/uint64_t)
This new pool replaced the "extension" slot where a secondary variant slot was used to store 8-byte values.
2025-07-10 19:17:13 +02:00
Benoit Blanchon
cc077c1b63 Store static strings in a dedicated pool
Because a slot id is smaller than a pointer, this change will ultimately allow reducing the slot size.
2025-07-10 19:17:13 +02:00
Benoit Blanchon
509807d3c2 Remove CollectionIterator::nextId_ 2025-07-10 19:16:47 +02:00
Benoit Blanchon
c07744dc0d CI: upgrade Windows runner 2025-06-26 20:47:57 +02:00
Benoit Blanchon
733bc4ee82 Set version to 7.4.2 2025-06-20 09:37:14 +02:00
Benoit Blanchon
9aa77994b4 Remove sponsor Programming Electronics Academy 2025-06-20 08:43:48 +02:00
Benoit Blanchon
f051f8328d Undef true and false macros
Replacing `true` with `1` changes `JsonString("ABC", true)` into `JsonString("ABC", 1)`, so all static strings had a length of 1.

This is a workaround for arduino/ArduinoCore-sam#50
Fixes #2181
2025-06-19 13:59:15 +02:00
Benoit Blanchon
411424b74e CI: upgrade clang-tidy 2025-05-20 20:55:01 +02:00
Benoit Blanchon
5e5c287978 CI: upgrade Clang versions 2025-05-20 18:24:46 +02:00
Benoit Blanchon
377cf63075 CI: upgrade runner to ubuntu-22.04 2025-05-20 14:48:42 +02:00
Benoit Blanchon
3252013509 Set version to 7.4.1 2025-04-11 15:43:42 +02:00
Benoit Blanchon
deab127a2f Fix crash with tiny Flash strings (issue #2170) 2025-04-11 10:23:43 +02:00
Benoit Blanchon
96281de682 Set version to 7.4.0 2025-04-09 14:49:13 +02:00
Benoit Blanchon
f0e84e4933 Fix support for const char[]
Fixes #2166
2025-04-09 08:55:09 +02:00
Benoit Blanchon
91397f9f06 Optimize storage of tiny strings (up to 3 characters) 2025-04-09 08:55:08 +02:00
Benoit Blanchon
7f75985e47 Change StringBuffer::save() to take a VariantData* 2025-02-28 10:05:50 +01:00
Benoit Blanchon
05b68fc7cc Change StringBuilder::save() to take a VariantData* 2025-02-28 09:59:46 +01:00
Benoit Blanchon
b06cee8f4d Remove the overload of setString() for StringNode 2025-02-28 09:23:56 +01:00
Benoit Blanchon
e03d8ae885 Set version to 7.3.1 2025-02-27 19:35:14 +01:00
Benoit Blanchon
cb1dcfa5e4 Reduce code size 2025-02-27 11:13:50 +01:00
Benoit Blanchon
67dd3120e6 Fix conversion from static string to number 2025-02-27 11:01:51 +01:00
Benoit Blanchon
9f3cf04415 Remove useless null check 2025-02-24 16:40:42 +01:00
Benoit Blanchon
01e49b33b7 Update copyright year 2025-02-24 15:18:26 +01:00
Benoit Blanchon
8f7e793f37 Set version to 7.3.0 2024-12-29 17:15:57 +01:00
Benoit Blanchon
254fa5712a Update the release scripts to include the breaking changes section 2024-12-29 16:38:41 +01:00
Benoit Blanchon
de05814294 Move public facing SFINAEs to template declarations 2024-12-23 17:44:52 +01:00
Benoit Blanchon
e33e78d202 Rename undocumented JsonString::isLinked() to isStatic() 2024-11-26 14:32:50 +01:00
Benoit Blanchon
ed5f890d28 Replace JsonString::Ownership with bool 2024-11-26 14:32:36 +01:00
Benoit Blanchon
8931651317 JsonString: change default ownership to Copied 2024-11-26 10:10:52 +01:00
Benoit Blanchon
c078957282 Remove unnecessary universal references 2024-11-25 12:25:59 +01:00
Benoit Blanchon
cf084ae6b4 JsonString: move adapter class in the same file 2024-11-25 12:25:59 +01:00
Benoit Blanchon
f02fcc96a2 JsonArray: remove redundant tests 2024-11-25 12:25:59 +01:00
Benoit Blanchon
594dc707cb Change string copy policy: only string literal are stored by pointer 2024-11-25 12:25:59 +01:00
Benoit Blanchon
5f8e3c0f0f Polyfills: test remove_cv 2024-11-25 12:25:59 +01:00
Benoit Blanchon
afc0a29c2c Polyfills: add decay 2024-11-25 12:25:59 +01:00
Benoit Blanchon
a256ec7fff RamString: use a bitfield to reduce size 2024-11-25 12:25:59 +01:00
Benoit Blanchon
019e8326b7 Implement JsonString from RamString 2024-11-25 11:13:39 +01:00
Benoit Blanchon
bee1095042 Merge all RAM string adapters 2024-11-25 10:46:35 +01:00
Benoit Blanchon
de59dce527 Fix typo in comments 2024-11-25 10:46:34 +01:00
Benoit Blanchon
57a9c50b38 Make ElementProxy and MemberProxy non-copyable 2024-11-25 10:46:21 +01:00
Benoit Blanchon
5e7653b36a Store adapted string in MemberProxy 2024-11-17 15:46:46 +01:00
Benoit Blanchon
8110058729 Fix support for NUL characters in deserializeJson() 2024-11-17 15:40:21 +01:00
Benoit Blanchon
7946ebe1a3 Wandbox: compile with gcc-head 2024-11-15 09:13:00 +01:00
Benoit Blanchon
f9fe8557f1 Set version to 7.2.1 2024-11-15 09:05:29 +01:00
Benoit Blanchon
e007d71b4f Fix operator[](variant) ignoring NUL characters 2024-11-14 14:56:47 +01:00
Benoit Blanchon
67a512a923 Clean up tests of adaptString() 2024-11-14 14:22:51 +01:00
Benoit Blanchon
9cf4f3871d Remove unused overload of stringCompare() and stringEquals() 2024-11-14 14:17:13 +01:00
Benoit Blanchon
31253dbe13 Add more tests with VLAs 2024-11-08 09:37:49 +01:00
Benoit Blanchon
1110d62128 Fix VLA support in JsonDocument::set() 2024-11-08 09:37:23 +01:00
Benoit Blanchon
c6c0649d70 Replace typedef with using 2024-10-23 15:54:08 +02:00
Benoit Blanchon
61ec2c4f95 Reduce boilerplate for failing build tests 2024-10-23 15:47:59 +02:00
Benoit Blanchon
0dd6231b3f Forbid deserializeJson(JsonArray|JsonObject, ...)
Closes #2135
2024-10-23 15:41:34 +02:00
Benoit Blanchon
20219d74f0 Tests: don't link FailingBuilds with catch 2024-10-23 15:04:52 +02:00
Benoit Blanchon
64cbaa6ff7 Remove the workaround for particle-iot/particle-cli#716
This reverts commit 1404b1ef70.
2024-09-28 09:58:48 +02:00
Benoit Blanchon
2512993617 Replace problematic symbol in idf_component.yml
Fixes #2131
2024-09-26 09:18:23 +02:00
Benoit Blanchon
48ee4a178b Use a const reference in is_convertible() 2024-09-21 09:22:12 +02:00
Benoit Blanchon
cd4b2b2463 Set version to 7.2.0 2024-09-18 10:48:50 +02:00
Benoit Blanchon
f806a42cc2 Add support for escape sequence \'
Fixes #2124
2024-09-17 10:33:47 +02:00
Benoit Blanchon
c1a507c158 Set ARDUINOJSON_POOL_CAPACITY from ARDUINOJSON_SLOT_ID_SIZE
This avoids the integer overflow when `ARDUINOJSON_SLOT_ID_SIZE=1` on 64-bit architectures.
2024-09-11 21:08:51 +02:00
Benoit Blanchon
a1809d0f31 Replace sizeof(VariantData) with sizeof(SlotData) 2024-09-10 18:26:58 +02:00
Benoit Blanchon
d92eee8736 Deprecate containsKey() in favor of doc["key"].is<T>()
See #2121
2024-09-06 17:32:09 +02:00
Benoit Blanchon
dd1d96e28f Group calls to getExtension()
This slightly reduces the code size.
2024-09-05 12:15:10 +02:00
Benoit Blanchon
3b64197869 MsgPackDeserializer: check extension allocation result 2024-09-04 14:34:02 +02:00
Benoit Blanchon
1f7a3f3174 JsonDeserializer: use float when the value has few digits 2024-09-04 14:33:14 +02:00
Benoit Blanchon
fd6314e132 Move some numbers tests to use_double_0.cpp 2024-09-04 14:29:19 +02:00
Benoit Blanchon
e4e2557b76 Move test of decomposeFloat() 2024-09-03 13:27:39 +02:00
Benoit Blanchon
3b6bf45b8a Serialize float with less decimal places than double 2024-09-03 11:44:35 +02:00
Benoit Blanchon
65ba36622c Add VariantType 2024-09-02 17:56:19 +02:00
Benoit Blanchon
33452c1f37 Test JsonVariant::as<T>() with extension slots 2024-08-27 16:08:47 +02:00
Benoit Blanchon
ee02c0d573 Test extension slot allocation failure 2024-08-27 16:08:47 +02:00
Benoit Blanchon
0278e94fce Set ARDUINOJSON_USE_DOUBLE to 0 by default on 8-bit architectures 2024-08-27 15:46:12 +02:00
Benoit Blanchon
7643dadaec WIP 2024-08-27 14:40:24 +02:00
Benoit Blanchon
c0bebe35f1 Improve message when user forgets third arg of serializeJson() et al.
See #1449, #1491, #1543, #1665, and #2122
2024-08-27 12:22:53 +02:00
Benoit Blanchon
b5bcb37657 Use enable_if_t instead of enable_if 2024-08-27 10:00:09 +02:00
Benoit Blanchon
b4a5b053ca Merge conf_test for linux and windows
This reverts commit 83516e1740.
2024-08-27 08:03:55 +02:00
Benoit Blanchon
e297932a98 Store 64-bit numbers (double and long long) in an additional slot
This change allows slots to be twices maller on 32-bit architectures.
See #1650 and #2103
2024-08-27 08:02:09 +02:00
Benoit Blanchon
e682337655 Release VariantData resources explicitly before setting value 2024-08-26 15:09:56 +02:00
Benoit Blanchon
4ada3f849c Decouple parseNumber() from VariantData 2024-08-25 16:46:55 +02:00
Benoit Blanchon
5dd203bca4 Rename SlotWithId to Slot 2024-08-25 15:04:39 +02:00
Benoit Blanchon
362201241f Make MemoryPool generic 2024-08-25 14:58:23 +02:00
Benoit Blanchon
2be24eded8 Rename SlotWithId::slot() and VariantWithId::data() to ptr() 2024-08-25 14:54:45 +02:00
Benoit Blanchon
4327f72140 Remove VariantSlot 2024-08-25 14:45:59 +02:00
Benoit Blanchon
f7f1b9745d Hide FreeSlot in MemoryPoolList 2024-08-25 14:39:18 +02:00
Benoit Blanchon
cec18177b0 Move sizeofArray() and sizeofObject() 2024-08-25 14:36:38 +02:00
Benoit Blanchon
f2894552f2 Rename VariantPool to MemoryPool 2024-08-25 14:36:38 +02:00
Benoit Blanchon
d3721cb122 Make VariantSlot a union. Include next slot id in VariantData 2024-08-24 19:20:39 +02:00
Benoit Blanchon
ab72bb8601 Rename flags_ to type_ 2024-08-24 11:18:21 +02:00
Benoit Blanchon
09c89dcacf Store object members with two slots: one for the key and one for the value 2024-08-24 10:45:51 +02:00
Benoit Blanchon
a2b09bfbd2 Remove unused code 2024-08-23 15:28:44 +02:00
Benoit Blanchon
386105be90 Allocate slot before key 2024-08-23 15:27:46 +02:00
Benoit Blanchon
83516e1740 Split conf_test between linux and windows 2024-08-23 15:24:45 +02:00
Benoit Blanchon
bf99aeedb1 Add @LArkema to the list of sponsors 💖 2024-07-02 10:27:36 +02:00
Benoit Blanchon
22dd4da3af Set version to 7.1.0 2024-06-27 18:20:22 +02:00
Benoit Blanchon
55c3b9b3a7 CI: update macOS runner to macos-13 2024-06-18 13:51:40 +02:00
Benoit Blanchon
d83515dcda Add DevContainer files for Clang 13 to 17 2024-06-18 13:51:40 +02:00
Benoit Blanchon
e34c27723a Fix build on modern compilers 2024-06-18 13:51:40 +02:00
Benoit Blanchon
b23ff65b99 Reduce MsgPack deserializer size 2024-06-18 13:51:33 +02:00
Benoit Blanchon
556785dc1e Read MsgPack's 64-bit ints even if ARDUINOJSON_USE_LONG_LONG is 0 2024-06-18 13:50:50 +02:00
Benoit Blanchon
e9c87858d1 Remove files.associations from vscode settings 2024-06-18 09:31:39 +02:00
Benoit Blanchon
208e7a3304 Fix integer overflow in MsgPackDeserializer 2024-06-11 09:47:11 +02:00
Benoit Blanchon
45611924f3 Tests: add user-defined literal ""_s for std::string 2024-06-07 09:35:45 +02:00
Benoit Blanchon
5b88b2c1f6 Update GitHub actions 2024-06-06 18:43:10 +02:00
Benoit Blanchon
e4f3fd8c91 Add support for MsgPack extension 2024-06-06 18:33:48 +02:00
Benoit Blanchon
aec642be20 Rename tests in MixedConfiguration 2024-06-06 18:26:16 +02:00
Benoit Blanchon
5a60c55be7 Don't add partial objects when allocation fails
Fixes #2081
2024-05-23 18:36:24 +02:00
Benoit Blanchon
f99b2d63f9 Make error message more readable in case of an invalid conversion 2024-05-23 14:01:30 +02:00
Benoit Blanchon
1db803bcd3 Add helpers for type traits, such as enable_if_t 2024-05-22 10:22:59 +02:00
Benoit Blanchon
04326d2655 Allow Converter<T>::toJson() to return a boolean as an optimization 2024-05-22 09:27:15 +02:00
Benoit Blanchon
9e0c56acc3 Replace ConverterNeedsWriteableRef with function_traits 2024-05-22 09:27:14 +02:00
Benoit Blanchon
60f9f7eff6 Move CollectionData::releaseSlot() to ResourceManager::freeSlot() 2024-05-17 17:10:45 +02:00
Benoit Blanchon
0fe202af03 CI: don't build fuzzers with Clang 11
Clang 11 fails on GitHub Actions with the following error:
ERROR: UndefinedBehaviorSanitizer failed to allocate 0x0 (0) bytes of SetAlternateSignalStack (error code: 22)
Sanitizer CHECK failed: /build/llvm-toolchain-11-mnvtwk/llvm-toolchain-11-11.1.0/compiler-rt/lib/sanitizer_common/sanitizer_common.cpp:54 ((0 && "unable to mmap")) != (0) (0, 0)
2024-05-16 17:47:07 +02:00
Benoit Blanchon
c41e8cc634 Add dev container for Clang 11 2024-05-16 17:47:07 +02:00
Benoit Blanchon
d486157a9e CMake: fix detection of GCC 4.8 2024-05-16 17:47:07 +02:00
Benoit Blanchon
91aad55412 CI: set cancel-in-progress to true 2024-05-16 17:47:07 +02:00
Benoit Blanchon
98fca74f66 Fix undefined reference to VariantPool::usage() 2024-05-16 17:47:07 +02:00
Benoit Blanchon
60fb268d9a Fix UBSAN error "member call does not point to an object of type"
runtime error: member call on address XXX which does not point to an object of type 'Allocator'
XXX: note: object is of type 'SpyingAllocator'

This is due to the fact that some of the compilation units have different library settings, so a different namespace, and therefore a different `Allocator` class.
2024-05-16 17:47:07 +02:00
Benoit Blanchon
f1899d3049 Fix error resources_ may be used uninitialized
JsonArrayConst.hpp:29:56: error: 'array.ArduinoJson::V704HB22::JsonArrayConst::resources_' may be used uninitialized in this function [-Werror=maybe-uninitialized]
JsonObjectConst.hpp:62:56: error: 'null.ArduinoJson::V704HB22::JsonObjectConst::resources_' may be used uninitialized in this function [-Werror=maybe-uninitialized]
2024-05-16 17:47:07 +02:00
Benoit Blanchon
4b779a7c1d Fix wrong build flags when COVERAGE is not defined 2024-05-16 17:47:07 +02:00
Benoit Blanchon
5d1aa04e21 CI: add Valgrind log to step summary 2024-05-16 17:47:07 +02:00
Benoit Blanchon
2f6db1edb0 CI: remove step summary
CTest errors were ignored in favor or `tee`'s exit code
2024-05-16 17:47:06 +02:00
Benoit Blanchon
aeb30ef307 Support ElementProxy and MemberProxy in JsonDocument's constructor 2024-05-15 13:37:33 +02:00
Benoit Blanchon
1c5e5db071 Test JsonDocument constructor with a JsonVariantConst argument
See #2091
2024-05-15 09:30:22 +02:00
Benoit Blanchon
68a13117dc Allow using a JsonVariant as a key or index
Closes #2080
2024-05-14 21:06:02 +02:00
Benoit Blanchon
071f718473 MsgPack: test failing string allocation 2024-05-06 11:23:20 +02:00
Benoit Blanchon
00949f8276 Remove redundant test 2024-05-06 11:16:55 +02:00
Benoit Blanchon
2c670e0148 Implement MsgPackBinary using raw strings and converters 2024-05-06 11:10:02 +02:00
Benoit Blanchon
002b07f0c5 Reduce the size of deserializeMsgPack() 2024-05-02 20:29:00 +02:00
Benoit Blanchon
5f5f927693 Add tests of as<MsgPackBinary>() 2024-05-01 19:26:19 +02:00
Benoit Blanchon
4d074840da Optimize deserializeMsgPack() 2024-05-01 18:00:59 +02:00
David Gauchard
82de20ee14 Make string support even more generic
Ported from 57354de831
Closes #2084
2024-05-01 14:06:30 +02:00
Benoit Blanchon
ece4d030a8 CI: update runner for the lint job 2024-04-29 19:38:18 +02:00
Benoit Blanchon
4d5c17b5f6 Remove unused #include statements 2024-04-29 18:30:29 +02:00
Aubrey (Sanae)
18a9a5b590 Add MsgPack bin8/bin16/bin32 support
Closes #2078
Closes #922
2024-04-29 16:01:10 +02:00
Benoit Blanchon
cd4bf33132 Fix error "pasting X and Y does not give a valid preprocessing token" 2024-04-18 14:39:05 +02:00
Benoit Blanchon
2cfefe22ac Add ARDUINOJSON_STRING_LENGTH_SIZE to the namespace name 2024-04-18 14:19:43 +02:00
RoboSchmied
0d43e51d48 Fix typo in "endianness"
Closes #2071
2024-03-26 13:43:07 +01:00
Benoit Blanchon
ef28064317 CI: merge the two "amalgamate" jobs 2024-03-18 10:54:36 +01:00
Benoit Blanchon
7c62cdb264 CI: update GitHub Actions 2024-03-17 21:30:42 +01:00
Benoit Blanchon
0ab4bdd691 CI: add a workaround for actions/runner-images#9491 2024-03-17 21:30:42 +01:00
Benoit Blanchon
af8c615266 Rename tests/JsonObject/copy.cpp to set.cpp 2024-03-16 14:02:56 +01:00
Benoit Blanchon
bd13375729 CI: add timeouts in the gcc job 2024-03-14 10:27:09 +01:00
Benoit Blanchon
5f8502ce9d Upgrade to lock-threads version 5+ 2024-03-14 09:51:44 +01:00
Benoit Blanchon
1404b1ef70 Add a workaround for particle-iot/particle-cli#716 2024-03-12 10:02:30 +01:00
Benoit Blanchon
36e1eecc7d Set version to 7.0.4 2024-03-12 09:40:46 +01:00
Benoit Blanchon
ca2f80aeaf Add links to the documentation 2024-02-21 10:48:50 +01:00
Benoit Blanchon
f17fc055d3 Make JSON_STRING_SIZE(N) return N+1 to fix third-party code
ThingsBoard uses this macro to compute size of char arrays ಠ_ಠ
https://github.com/thingsboard/thingsboard-client-sdk/blob/v0.12.2/src/Helper.h#L38

Closes #2054
2024-02-18 20:00:25 +01:00
Benoit Blanchon
04ac53d114 Remove final from JsonArray, JsonObject, and JsonVariant
`final` breaks ThingsBoard ಠ_ಠ
https://github.com/thingsboard/thingsboard-client-sdk/blob/v0.12.2/src/RPC_Response.h#L10

See #2056.
This reverts commit 483a2c9101.
2024-02-18 20:00:24 +01:00
Benoit Blanchon
483a2c9101 Mark JsonArray, JsonObject, and JsonVariant as final
See #2056
2024-02-18 10:52:07 +01:00
Benoit Blanchon
848c0cdc7e Set version to 7.0.3 2024-02-05 13:34:38 +01:00
Benoit Blanchon
46a807bd30 Remove unused NO_INLINE 2024-02-05 11:56:08 +01:00
Benoit Blanchon
cb0dc94db4 Remove most FORCE_INLINEs
I kept only the ones that had a positive impact on code size AND no negative impact on stack memory.

Fixes #2046
2024-02-05 11:48:27 +01:00
Benoit Blanchon
72642e3090 Fix compatibility with GCC 4.8
Closes #2045
2024-02-01 21:37:45 +01:00
Benoit Blanchon
c98b05e207 Dont't inline JsonSerializer::visit(const ArrayData&)
It didn't improve the code size and was inconsistent with this other functions.
2024-02-01 10:24:01 +01:00
Benoit Blanchon
2a87cc5839 Stop using CollectionIterator in MsgPackSerializer
This doesn't reduce code size or stack usage, but as least it's consistent with `JsonSerializer`.
2024-02-01 10:24:01 +01:00
Benoit Blanchon
296fe79bfd Stop using CollectionIterator in JsonSerializer
This reduces stack consumption and code size.
See  #2046
2024-02-01 10:24:00 +01:00
Benoit Blanchon
650d537b5d Improve error messages when using char or char*
See #2043
2024-01-26 10:34:49 +01:00
Benoit Blanchon
0435945a62 Set version to 7.0.2 2024-01-19 14:36:16 +01:00
Benoit Blanchon
844a50296f Fix link to shrinkToFit()'s documentation 2024-01-16 14:29:08 +01:00
Benoit Blanchon
1b143d383b Fix assertion poolIndex < count_ after JsonDocument::clear()
Fixes #2034
2024-01-16 10:10:43 +01:00
Benoit Blanchon
94783fdd2a Set version to 7.0.1 2024-01-10 21:14:07 +01:00
Benoit Blanchon
e41d5d4fa1 Shorten the library description 2024-01-10 18:11:49 +01:00
Benoit Blanchon
5dfa25d3dc Include the number of GitHub stars in the library description. 2024-01-10 18:11:43 +01:00
Benoit Blanchon
a7bfc2212c Fix volatile bool serialized as 1 or 0
Ported from 5d1d2721d1
2024-01-10 14:03:12 +01:00
Benoit Blanchon
315cc722e9 Add more tests for JsonVariantConst 2024-01-08 19:47:40 +01:00
Benoit Blanchon
ca0dda7ac1 Add more tests for JsonArrayConst 2024-01-08 19:47:40 +01:00
Benoit Blanchon
08cac13c43 Add more tests for JsonObjectConst 2024-01-08 19:47:36 +01:00
Benoit Blanchon
44d2d47863 CI: publish package to PlatformIO registry 2024-01-04 18:05:31 +01:00
Benoit Blanchon
3571db6290 Remove unused files in the PlatformIO package 2024-01-04 18:01:52 +01:00
Benoit Blanchon
cc42373367 Fix "no matching function" with JsonObjectConst::operator[]
Fixes #2019
2024-01-03 16:30:44 +01:00
Benoit Blanchon
9dc43d14f3 Set version to 7.0.0 2024-01-03 09:19:34 +01:00
Benoit Blanchon
3fa6b6e04f Fix typo in change log 2024-01-03 09:19:14 +01:00
Benoit Blanchon
2d47b3931d Remove legacy Arduino package from release assets 2024-01-03 09:16:19 +01:00
Benoit Blanchon
0e8a236583 Update copyright year 2024-01-03 08:47:06 +01:00
Benoit Blanchon
955815fbfa Fix function returns incomplete class type on IAR (issue #2001)
Ported from 3e1be980d9
2023-12-07 15:51:29 +01:00
Benoit Blanchon
4cd03fbd26 Fix no instance of overloaded function... on IAR (fixes #2001)
Ported from 6ed87029e2
2023-12-07 15:51:29 +01:00
Benoit Blanchon
f7dcea562f CI: always use libc++ with clang 2023-11-06 13:24:32 +01:00
Benoit Blanchon
4774ca3d29 Force inline ZeroTerminatedRamString::size()
Ported from 7517ecb91b
2023-11-06 09:52:17 +01:00
Benoit Blanchon
26b2ff4c0f Reorder StringNode's members to reduce code size 2023-10-09 15:41:20 +02:00
Benoit Blanchon
7e6b89d21f Use only one byte for the string length on 8-bit platforms 2023-10-09 15:21:18 +02:00
Benoit Blanchon
d20e64187b Use only one byte for the reference counter on 8-bit platforms 2023-10-09 14:47:47 +02:00
Benoit Blanchon
86e06c901f Add ARDUINOJSON_SIZEOF_POINTER 2023-10-09 14:40:18 +02:00
Benoit Blanchon
6fe4b9c01d Detect string length overflows 2023-10-09 14:15:55 +02:00
Benoit Blanchon
9b34069a3b Remove obsolete comments 2023-09-25 15:16:41 +02:00
Benoit Blanchon
30ea01bc31 StringExample: remove obsolete comment 2023-09-24 18:12:01 +02:00
Benoit Blanchon
92c9faf69f Fix 'std::string_view' has not been declared (issue #1967)
Ported from 49e2a8d421
2023-09-13 18:32:38 +02:00
Benoit Blanchon
b20653ee1a Fix 'std::string' has not been declared (issue #1967)
Ported from 259855a87b
2023-09-13 18:31:22 +02:00
Benoit Blanchon
750d53f8c7 Update URLs to point to https://arduinojson.org/v7/ 2023-08-19 16:08:12 +02:00
Benoit Blanchon
7bd2ea1072 Remove mentions of the zero-copy mode 2023-08-19 16:05:42 +02:00
Benoit Blanchon
51c5f1a73a Fix a Clang-Tidy warning 2023-08-10 19:27:03 +02:00
Benoit Blanchon
ac9b74df65 Show a warning when ARDUINOJSON_ENABLE_STRING_DEDUPLICATION is defined 2023-08-10 18:38:05 +02:00
Benoit Blanchon
305e80c09d Show an error if ARDUINOJSON_SLOT_OFFSET_SIZE is defined 2023-08-10 18:28:38 +02:00
Benoit Blanchon
fc1f06822c CI: add GCC 12 2023-08-10 18:25:53 +02:00
Benoit Blanchon
a8c763c40e CI: add clang 11, 12, 13, 14, and 15 2023-08-10 18:25:53 +02:00
Benoit Blanchon
7ab6fc078c CI: remove Clang 3.8 2023-08-10 18:18:30 +02:00
Benoit Blanchon
c98ba999af Add more tests of JsonDocument constructor 2023-08-10 14:30:50 +02:00
Benoit Blanchon
1d583f68da Add stubs for JSON_ARRAY_SIZE, JSON_OBJECT_SIZE, and JSON_STRING_SIZE 2023-08-10 09:54:47 +02:00
Benoit Blanchon
e93fd7657f Add a "Breaking changes" section to the changelog 2023-08-10 09:54:47 +02:00
Benoit Blanchon
78399c2d78 Add a stub for createNestedObject() 2023-08-10 09:54:46 +02:00
Benoit Blanchon
8cc645c40c Add a stub for createNestedArray() 2023-08-10 09:54:45 +02:00
Benoit Blanchon
11373af344 Add a stub for add() 2023-08-10 09:54:44 +02:00
Benoit Blanchon
53d54ba9d7 Add a stub for shallowCopy() 2023-08-10 09:54:44 +02:00
Benoit Blanchon
2f31c932d7 Add a stub for memoryUsage() 2023-08-10 09:54:43 +02:00
Benoit Blanchon
93cb3d2fdc Add a stub for BasicJsonDocument 2023-08-10 09:54:42 +02:00
Benoit Blanchon
be5d5300a2 Add a stub for DynamicJsonDocument 2023-08-10 09:54:40 +02:00
Benoit Blanchon
ea5b019552 Add a stub for StaticJsonDocument 2023-08-10 09:54:28 +02:00
Benoit Blanchon
bc6707b10c Rename tests/JsonObject/invalid.cpp to unbound.cpp 2023-08-09 12:08:21 +02:00
Benoit Blanchon
adea7f4131 Extract VariantRefBaseImpl.hpp 2023-08-09 12:08:21 +02:00
Benoit Blanchon
7f459adc4b Remove createNestedArray() and createNestedObject() 2023-08-09 12:08:21 +02:00
Benoit Blanchon
cdc1262127 Remove unused JsonDocument constructor 2023-08-09 11:07:27 +02:00
Benoit Blanchon
f422b7b37d Replace add() with add<T>() (add(T) is still supported) 2023-08-09 10:57:52 +02:00
Benoit Blanchon
7a587ac2e2 Fix some getVariant() that were accidentally renamed to getSlot() 2023-08-09 10:08:40 +02:00
Benoit Blanchon
38941d5807 Tests: use sections for filters tests 2023-08-01 19:14:11 +02:00
Benoit Blanchon
57454cf97b Don't call shrinkToFit() for deserializeXxx(JsonVariant) 2023-08-01 18:48:10 +02:00
Benoit Blanchon
af6954c224 serializeXxx() sets std::string and String instead of appending 2023-07-31 18:37:35 +02:00
Benoit Blanchon
3003756adb Reformat filters test file 2023-07-31 17:34:53 +02:00
Benoit Blanchon
218a12ca46 Call shrinkToFit() in deserializeJson() and deserializeMsgPack() 2023-07-31 17:34:17 +02:00
Benoit Blanchon
752d01a7f1 Add an enable_if to validate the first argument to deserializeXxx() 2023-07-29 12:05:18 +02:00
Benoit Blanchon
43eed00cd9 Add deserializeXxx(JsonVariant, ...) (resolves #1226) 2023-07-29 12:05:18 +02:00
Benoit Blanchon
bc8ea36781 Tests: gather deserializeMsgPack() errors test cases 2023-07-29 06:33:45 +02:00
Benoit Blanchon
8fb187baed Tests: gather deserializeJson() errors test cases 2023-07-29 06:33:45 +02:00
Benoit Blanchon
db5b5f9ee2 Fix a typo in the changelog 2023-07-29 06:33:44 +02:00
Benoit Blanchon
9122d87f12 Tests: remove duplicate test of incomplete input 2023-07-27 14:31:56 +02:00
Benoit Blanchon
9a11d98117 Tests: make allocator assertions more readable 2023-07-26 09:28:21 +02:00
Benoit Blanchon
30ec507989 Tests: use a consistent naming convention for allocators 2023-07-25 14:53:54 +02:00
Benoit Blanchon
7a76da3bc7 Tests: rename ControllableAllocator to KillswitchAllocator 2023-07-25 14:46:25 +02:00
Benoit Blanchon
a8329564e2 Remove JsonDocument::garbageCollect() 2023-07-25 14:37:25 +02:00
Benoit Blanchon
00c9d8680a Remove memoryUsage() 2023-07-24 17:21:25 +02:00
Benoit Blanchon
2fdacb1ca0 Reduce size of CollectionData::clear() 2023-07-24 10:33:06 +02:00
Benoit Blanchon
228c4cf9fa JsonDocument: use the copy-and-swap idiom 2023-07-24 10:13:17 +02:00
Benoit Blanchon
9d2d257851 Scripts: call wandbox/publish.sh from get-release-page.sh
Ported from 371fa4667e
2023-07-23 18:08:54 +02:00
Benoit Blanchon
5458e916ea Show a link to the doc when user passes an unsupported input type
Ported from 7eec01cdd6
2023-07-23 18:08:21 +02:00
Benoit Blanchon
1a14499612 Preallocate pool list 2023-07-21 17:57:13 +02:00
Benoit Blanchon
f427706e06 VariantPoolList: handle SlotId overflow 2023-07-21 17:57:13 +02:00
Benoit Blanchon
8be0d57d24 VariantPoolList: reduce the size of capacity_ and count_ 2023-07-21 09:47:25 +02:00
Benoit Blanchon
8fcaebb44a Detect null slot id earlier in VariantPoolList::getSlot() 2023-07-20 18:04:06 +02:00
Benoit Blanchon
bd2d232b40 JsonParseExample: use a const char* instead of a char[] 2023-07-20 18:04:06 +02:00
Benoit Blanchon
b69a952e69 Examples: remove outdated comments 2023-07-20 18:04:06 +02:00
Benoit Blanchon
727a1013ca Recycle removed slots 2023-07-20 18:04:06 +02:00
Benoit Blanchon
781e449e78 CollectionData::releaseSlot() takes an iterator 2023-07-20 17:53:52 +02:00
Benoit Blanchon
d4af8cffa7 Store current and next slot id in CollectionIterator 2023-07-20 17:53:52 +02:00
Benoit Blanchon
0f3c73a211 Remove VariantPool::capacity() 2023-07-18 09:08:55 +02:00
Benoit Blanchon
0f319e7ca4 Remove capacity from JsonDocument's constructor 2023-07-18 09:08:55 +02:00
Benoit Blanchon
42b2840009 Create more memory pools as needed (resolves #1074) 2023-07-18 09:08:55 +02:00
Benoit Blanchon
65c67d317a AllocatorLog: support nulls in deallocate() and reallocate() 2023-07-17 17:28:49 +02:00
Benoit Blanchon
c4e5051a7a Store index of slot in the pool instead of a pointer or a distance 2023-07-17 11:20:46 +02:00
Benoit Blanchon
068c40d6ed Add Dev Container configs
Ported from 4ba9c1b0c0
2023-07-17 11:20:46 +02:00
Benoit Blanchon
c203c86a42 CI: add --output-on-failure for coverage and valgrind tasks 2023-07-17 11:20:46 +02:00
Benoit Blanchon
8aec448adf Add missing declaration of offsetof() 2023-07-17 11:20:46 +02:00
Benoit Blanchon
9538bc32af Implement the object copy at the JsonObject level 2023-07-17 11:20:46 +02:00
Benoit Blanchon
b2aa0029b9 Implement array copy at the JsonArray level 2023-07-17 11:20:46 +02:00
Benoit Blanchon
57e9134540 Implement variant copy at the JsonVariant level 2023-07-17 11:20:46 +02:00
Benoit Blanchon
fb4cb96c6c Move JsonArray and JsonObject converters to ConverterImpl.hpp 2023-07-17 11:20:46 +02:00
Benoit Blanchon
5e3f84c718 Merge all visitXxx() into one overloaded visit() function 2023-07-17 11:20:46 +02:00
Benoit Blanchon
64922343e6 visitNull() takes a nullptr_t 2023-07-17 11:20:46 +02:00
Benoit Blanchon
1d07abddcd Add nullptr_t 2023-07-17 11:20:46 +02:00
Benoit Blanchon
21bf4973de visitRawString() takes a RawString 2023-07-17 11:20:46 +02:00
Benoit Blanchon
da845ae01d visitString() takes a JsonString 2023-07-17 11:20:46 +02:00
Benoit Blanchon
5a9d3422f5 Add JsonVariantVisitor and use it for comparisons 2023-07-17 11:20:46 +02:00
Benoit Blanchon
7a9feb4d6e Rename Visitor to VariantDataVisitor 2023-07-17 11:20:46 +02:00
Benoit Blanchon
39e8b63746 Remove shallowCopy() 2023-07-17 11:20:46 +02:00
Benoit Blanchon
c37990d791 CollectionData: addSlot() returns an iterator 2023-07-17 11:20:46 +02:00
Benoit Blanchon
fac5b5a7a7 CollectionData: allocate the slot in addSlot() 2023-07-17 11:20:46 +02:00
Benoit Blanchon
5ceb5d1813 Use CollectionIterator in CollectionData::memoryUsage() 2023-07-17 11:20:46 +02:00
Benoit Blanchon
ec4c73db0b Use CollectionIterator in CollectionData::nesting() 2023-07-17 11:20:45 +02:00
Benoit Blanchon
f86b22cf4f Replace slotRelease() with CollectionData::releaseSlot() 2023-07-17 11:20:45 +02:00
Benoit Blanchon
78a74c4017 Inline slotSize() 2023-07-17 11:20:45 +02:00
Benoit Blanchon
dae0182914 Convert CollectionIterator to GoF style 2023-07-17 11:20:45 +02:00
Benoit Blanchon
0f511b873d VariantPool: store VariantSlots instead of chars 2023-07-12 15:03:56 +02:00
Benoit Blanchon
1d96826371 Add a ResourceManager* member to JsonArrayConst, JsonObjectConst, and JsonVariantConst 2023-07-12 15:03:56 +02:00
Benoit Blanchon
f6b014582f Implement object comparison out of class 2023-07-12 15:03:56 +02:00
Benoit Blanchon
555f3dd5fe Implement array comparison out of class 2023-07-12 15:03:56 +02:00
Benoit Blanchon
04973ca494 Fix ARDUINOJSON_BIN2ALPHA_0110()
Ported from 6c5fde2a55
2023-07-12 15:02:21 +02:00
Benoit Blanchon
01b9b40bd2 Include ARDUINOJSON_SLOT_OFFSET_SIZE in the namespace name
Ported from 433fb4b961
2023-07-12 15:01:28 +02:00
Benoit Blanchon
c8517ee5b6 Fix double call to size() in serializeMsgPack()
Ported from afbcc2106e
2023-07-12 12:00:23 +02:00
Benoit Blanchon
23b01a89b1 Fix double lookup in to<JsonVariant>() 2023-07-05 16:18:35 +02:00
Benoit Blanchon
688e21e75f Add CollectionIterator 2023-06-26 18:23:20 +02:00
Benoit Blanchon
d921cd6d02 Convert "variant functions" to static member functions 2023-06-26 12:33:34 +02:00
Benoit Blanchon
af8bdfbc8f Convert "collection function" to static member functions 2023-06-26 11:58:28 +02:00
Benoit Blanchon
68b1602c35 Extract ObjectData from CollectionData 2023-06-26 11:42:25 +02:00
Benoit Blanchon
7bc73d7849 Extract ArrayData from CollectionData 2023-06-26 11:18:56 +02:00
Benoit Blanchon
67bbb4c90d Manage resources in CollectionData 2023-06-26 10:07:40 +02:00
467 changed files with 14448 additions and 8623 deletions

View File

@@ -0,0 +1,18 @@
{
"name": "Clang 10",
"image": "conanio/clang10",
"runArgs": [
"--name=ArduinoJson-clang10"
],
"customizations": {
"vscode": {
"extensions": [
"ms-vscode.cmake-tools"
],
"settings": {
"cmake.generator": "Unix Makefiles",
"cmake.buildDirectory": "/tmp/build"
}
}
}
}

View File

@@ -0,0 +1,18 @@
{
"name": "Clang 11",
"image": "conanio/clang11",
"runArgs": [
"--name=ArduinoJson-clang11"
],
"customizations": {
"vscode": {
"extensions": [
"ms-vscode.cmake-tools"
],
"settings": {
"cmake.generator": "Unix Makefiles",
"cmake.buildDirectory": "/tmp/build"
}
}
}
}

View File

@@ -0,0 +1,5 @@
FROM ubuntu:22.04
RUN apt-get update
RUN apt-get install -y cmake git clang-13 libc++-13-dev libc++abi-13-dev
ENV CC=clang-13 CXX=clang++-13

View File

@@ -0,0 +1,20 @@
{
"name": "Clang 13",
"build": {
"dockerfile": "Dockerfile"
},
"runArgs": [
"--name=ArduinoJson-clang13"
],
"customizations": {
"vscode": {
"extensions": [
"ms-vscode.cmake-tools"
],
"settings": {
"cmake.generator": "Unix Makefiles",
"cmake.buildDirectory": "/tmp/build"
}
}
}
}

View File

@@ -0,0 +1,5 @@
FROM ubuntu:22.04
RUN apt-get update
RUN apt-get install -y cmake git clang-14 libc++-14-dev libc++abi-14-dev
ENV CC=clang-14 CXX=clang++-14

View File

@@ -0,0 +1,20 @@
{
"name": "Clang 14",
"build": {
"dockerfile": "Dockerfile"
},
"runArgs": [
"--name=ArduinoJson-clang14"
],
"customizations": {
"vscode": {
"extensions": [
"ms-vscode.cmake-tools"
],
"settings": {
"cmake.generator": "Unix Makefiles",
"cmake.buildDirectory": "/tmp/build"
}
}
}
}

View File

@@ -0,0 +1,5 @@
FROM ubuntu:22.04
RUN apt-get update
RUN apt-get install -y cmake git clang-15 libc++-15-dev libc++abi-15-dev
ENV CC=clang-15 CXX=clang++-15

View File

@@ -0,0 +1,20 @@
{
"name": "Clang 15",
"build": {
"dockerfile": "Dockerfile"
},
"runArgs": [
"--name=ArduinoJson-clang15"
],
"customizations": {
"vscode": {
"extensions": [
"ms-vscode.cmake-tools"
],
"settings": {
"cmake.generator": "Unix Makefiles",
"cmake.buildDirectory": "/tmp/build"
}
}
}
}

View File

@@ -0,0 +1,5 @@
FROM ubuntu:22.04
RUN apt-get update
RUN apt-get install -y cmake git clang-16 libc++-16-dev libc++abi-16-dev
ENV CC=clang-16 CXX=clang++-16

View File

@@ -0,0 +1,20 @@
{
"name": "Clang 16",
"build": {
"dockerfile": "Dockerfile"
},
"runArgs": [
"--name=ArduinoJson-clang16"
],
"customizations": {
"vscode": {
"extensions": [
"ms-vscode.cmake-tools"
],
"settings": {
"cmake.generator": "Unix Makefiles",
"cmake.buildDirectory": "/tmp/build"
}
}
}
}

View File

@@ -0,0 +1,5 @@
FROM ubuntu:24.04
RUN apt-get update
RUN apt-get install -y cmake git clang-17 libc++-17-dev libc++abi-17-dev
ENV CC=clang-17 CXX=clang++-17

View File

@@ -0,0 +1,20 @@
{
"name": "Clang 17",
"build": {
"dockerfile": "Dockerfile"
},
"runArgs": [
"--name=ArduinoJson-clang17"
],
"customizations": {
"vscode": {
"extensions": [
"ms-vscode.cmake-tools"
],
"settings": {
"cmake.generator": "Unix Makefiles",
"cmake.buildDirectory": "/tmp/build"
}
}
}
}

View File

@@ -0,0 +1,18 @@
{
"name": "Clang 5",
"image": "conanio/clang50",
"runArgs": [
"--name=ArduinoJson-clang5"
],
"customizations": {
"vscode": {
"extensions": [
"ms-vscode.cmake-tools"
],
"settings": {
"cmake.generator": "Unix Makefiles",
"cmake.buildDirectory": "/tmp/build"
}
}
}
}

View File

@@ -0,0 +1,18 @@
{
"name": "Clang 6",
"image": "conanio/clang60",
"runArgs": [
"--name=ArduinoJson-clang6"
],
"customizations": {
"vscode": {
"extensions": [
"ms-vscode.cmake-tools"
],
"settings": {
"cmake.generator": "Unix Makefiles",
"cmake.buildDirectory": "/tmp/build"
}
}
}
}

View File

@@ -0,0 +1,18 @@
{
"name": "Clang 7",
"image": "conanio/clang7",
"runArgs": [
"--name=ArduinoJson-clang7"
],
"customizations": {
"vscode": {
"extensions": [
"ms-vscode.cmake-tools"
],
"settings": {
"cmake.generator": "Unix Makefiles",
"cmake.buildDirectory": "/tmp/build"
}
}
}
}

View File

@@ -0,0 +1,18 @@
{
"name": "Clang 8",
"image": "conanio/clang8",
"runArgs": [
"--name=ArduinoJson-clang8"
],
"customizations": {
"vscode": {
"extensions": [
"ms-vscode.cmake-tools"
],
"settings": {
"cmake.generator": "Unix Makefiles",
"cmake.buildDirectory": "/tmp/build"
}
}
}
}

View File

@@ -0,0 +1,18 @@
{
"name": "Clang 9",
"image": "conanio/clang9",
"runArgs": [
"--name=ArduinoJson-clang9"
],
"customizations": {
"vscode": {
"extensions": [
"ms-vscode.cmake-tools"
],
"settings": {
"cmake.generator": "Unix Makefiles",
"cmake.buildDirectory": "/tmp/build"
}
}
}
}

View File

@@ -0,0 +1,18 @@
{
"name": "GCC 10",
"image": "conanio/gcc10",
"runArgs": [
"--name=ArduinoJson-gcc10"
],
"customizations": {
"vscode": {
"extensions": [
"ms-vscode.cmake-tools"
],
"settings": {
"cmake.generator": "Unix Makefiles",
"cmake.buildDirectory": "/tmp/build"
}
}
}
}

View File

@@ -0,0 +1,18 @@
{
"name": "GCC 11",
"image": "conanio/gcc11",
"runArgs": [
"--name=ArduinoJson-gcc11"
],
"customizations": {
"vscode": {
"extensions": [
"ms-vscode.cmake-tools"
],
"settings": {
"cmake.generator": "Unix Makefiles",
"cmake.buildDirectory": "/tmp/build"
}
}
}
}

View File

@@ -0,0 +1,4 @@
FROM ubuntu:22.04
RUN apt-get update
RUN apt-get install -y cmake git g++-12

View File

@@ -0,0 +1,20 @@
{
"name": "GCC 12",
"build": {
"dockerfile": "Dockerfile",
},
"runArgs": [
"--name=ArduinoJson-gcc12"
],
"customizations": {
"vscode": {
"extensions": [
"ms-vscode.cmake-tools"
],
"settings": {
"cmake.generator": "Unix Makefiles",
"cmake.buildDirectory": "/tmp/build"
}
}
}
}

View File

@@ -0,0 +1,20 @@
{
"name": "GCC 4.8",
"image": "conanio/gcc48",
"runArgs": [
"--name=ArduinoJson-gcc48"
],
"customizations": {
"vscode": {
"extensions": [
"ms-vscode.cmake-tools",
"josetr.cmake-language-support-vscode",
"ms-vscode.cpptools"
],
"settings": {
"cmake.generator": "Unix Makefiles",
"cmake.buildDirectory": "/tmp/build"
}
}
}
}

View File

@@ -0,0 +1,18 @@
{
"name": "GCC 5",
"image": "conanio/gcc5",
"runArgs": [
"--name=ArduinoJson-gcc5"
],
"customizations": {
"vscode": {
"extensions": [
"ms-vscode.cmake-tools"
],
"settings": {
"cmake.generator": "Unix Makefiles",
"cmake.buildDirectory": "/tmp/build"
}
}
}
}

View File

@@ -0,0 +1,18 @@
{
"name": "GCC 6",
"image": "conanio/gcc6",
"runArgs": [
"--name=ArduinoJson-gcc6"
],
"customizations": {
"vscode": {
"extensions": [
"ms-vscode.cmake-tools"
],
"settings": {
"cmake.generator": "Unix Makefiles",
"cmake.buildDirectory": "/tmp/build"
}
}
}
}

View File

@@ -0,0 +1,18 @@
{
"name": "GCC 7",
"image": "conanio/gcc7",
"runArgs": [
"--name=ArduinoJson-gcc7"
],
"customizations": {
"vscode": {
"extensions": [
"ms-vscode.cmake-tools"
],
"settings": {
"cmake.generator": "Unix Makefiles",
"cmake.buildDirectory": "/tmp/build"
}
}
}
}

View File

@@ -0,0 +1,18 @@
{
"name": "GCC 8",
"image": "conanio/gcc8",
"runArgs": [
"--name=ArduinoJson-gcc8"
],
"customizations": {
"vscode": {
"extensions": [
"ms-vscode.cmake-tools"
],
"settings": {
"cmake.generator": "Unix Makefiles",
"cmake.buildDirectory": "/tmp/build"
}
}
}
}

View File

@@ -0,0 +1,18 @@
{
"name": "GCC 9",
"image": "conanio/gcc9",
"runArgs": [
"--name=ArduinoJson-gcc9"
],
"customizations": {
"vscode": {
"extensions": [
"ms-vscode.cmake-tools"
],
"settings": {
"cmake.generator": "Unix Makefiles",
"cmake.buildDirectory": "/tmp/build"
}
}
}
}

3
.gitattributes vendored
View File

@@ -1 +1,2 @@
*.sh text eol=lf
* text=auto
*.sh text eol=lf

View File

@@ -14,7 +14,7 @@ Before opening a bug report, please use the ArduinoJson Troubleshooter as it may
A clear and concise description of what the bug is.
**Troubleshooter report**
Here is the report generated by the [ArduinoJson Troubleshooter](https://arduinojson.org/v6/troubleshooter/):
Here is the report generated by the [ArduinoJson Troubleshooter](https://arduinojson.org/v7/troubleshooter/):
[Paste the report here]
**Environment**
@@ -27,7 +27,7 @@ Here is the environment that I used:
Here is a small snippet that reproduces the issue.
```c++
JsonDocument doc(1024);
JsonDocument doc;
DeserializationError error = deserializeJson(doc, "{\"hello\":\"world\"}");

View File

@@ -1,8 +1,8 @@
blank_issues_enabled: true
contact_links:
- name: 👨‍🏫 ArduinoJson Assistant
url: https://arduinojson.org/v6/assistant/
url: https://arduinojson.org/v7/assistant/
about: An online tool that computes memory requirements and generates scaffolding code for your project.
- name: 👨‍⚕️ ArduinoJson Troubleshooter
url: https://arduinojson.org/v6/troubleshooter/
url: https://arduinojson.org/v7/troubleshooter/
about: An online tool that helps you diagnose the most common issues with ArduinoJson.

View File

@@ -15,7 +15,7 @@ A clear and concise description of what you're trying to do.
You don't need to explain every aspect of your project: focus on the problem you're having.
**Troubleshooter report**
Here is the report generated by the [ArduinoJson Troubleshooter](https://arduinojson.org/v6/troubleshooter/):
Here is the report generated by the [ArduinoJson Troubleshooter](https://arduinojson.org/v7/troubleshooter/):
[Paste the report here]
**Environment**
@@ -28,7 +28,7 @@ Here is the environment that I'm using':
Here is a small snippet that demonstrate the problem.
```c++
JsonDocument doc(1024);
JsonDocument doc;
DeserializationError error = deserializeJson(doc, "{\"hello\":\"world\"}");

View File

@@ -2,15 +2,19 @@ name: Continuous Integration
on: [push, pull_request]
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: true
jobs:
lint:
name: Lint
runs-on: ubuntu-20.04
runs-on: ubuntu-22.04
steps:
- name: Install
run: sudo apt-get install -y clang-format
- name: Checkout
uses: actions/checkout@v3
uses: actions/checkout@v4
- name: Symlinks
run: find * -type l -printf "::error::%p is a symlink. This is forbidden by the Arduino Library Specification." -exec false {} +
- name: Clang-format
@@ -33,6 +37,7 @@ jobs:
fail-fast: false
matrix:
include:
- gcc: "4.8"
- gcc: "5"
- gcc: "6"
- gcc: "7"
@@ -44,67 +49,97 @@ jobs:
- gcc: "10"
cxxflags: -funsigned-char # Issue #1715
- gcc: "11"
- gcc: "12"
steps:
- name: Workaround for actions/runner-images#9491
run: sudo sysctl vm.mmap_rnd_bits=28
- name: Install
run: |
sudo apt-key adv --keyserver keyserver.ubuntu.com --recv-keys 40976EAF437D05B5 3B4FE6ACC0B21F32
sudo add-apt-repository -yn 'deb http://archive.ubuntu.com/ubuntu/ xenial main universe'
sudo add-apt-repository -yn 'deb http://archive.ubuntu.com/ubuntu/ bionic main universe'
sudo add-apt-repository -yn 'deb http://archive.ubuntu.com/ubuntu/ focal main universe'
sudo apt-get update
sudo apt-get install -y gcc-${{ matrix.gcc }} g++-${{ matrix.gcc }}
timeout-minutes: 5
- name: Checkout
uses: actions/checkout@v3
uses: actions/checkout@v4
timeout-minutes: 1
- name: Configure
run: cmake -DCMAKE_BUILD_TYPE=Debug .
env:
CC: gcc-${{ matrix.gcc }}
CXX: g++-${{ matrix.gcc }}
CXXFLAGS: ${{ matrix.cxxflags }}
timeout-minutes: 1
- name: Build
run: cmake --build .
timeout-minutes: 10
- name: Test
run: |
echo "## CTest output" >> $GITHUB_STEP_SUMMARY
echo '```' >> $GITHUB_STEP_SUMMARY
ctest --output-on-failure -C Debug . | tee -a $GITHUB_STEP_SUMMARY
echo '```' >> $GITHUB_STEP_SUMMARY
run: ctest --output-on-failure -C Debug .
env:
UBSAN_OPTIONS: print_stacktrace=1
timeout-minutes: 2
clang:
name: Clang
needs: lint
runs-on: ubuntu-20.04
strategy:
fail-fast: false
matrix:
include:
- clang: "3.8"
cxxflags: "-stdlib=libc++"
- clang: "3.9"
cxxflags: "-stdlib=libc++"
- clang: "4.0"
cxxflags: "-stdlib=libc++"
- clang: "5.0"
- clang: "6.0"
- clang: "7"
runner: ubuntu-22.04
archive: focal
- clang: "8"
cxxflags: -fsanitize=leak -fno-sanitize-recover=all
runner: ubuntu-22.04
archive: focal
- clang: "9"
cxxflags: -fsanitize=undefined -fno-sanitize-recover=all
runner: ubuntu-22.04
archive: focal
- clang: "10"
cxxflags: -fsanitize=address -fno-sanitize-recover=all
runner: ubuntu-22.04
archive: focal
- clang: "11"
runner: ubuntu-22.04
- clang: "12"
runner: ubuntu-22.04
- clang: "13"
runner: ubuntu-22.04
- clang: 14
- clang: 15
- clang: 16
- clang: 17
- clang: 18
- clang: 19
runs-on: ${{ matrix.runner || 'ubuntu-latest' }}
steps:
- name: Install
- name: Add archive repositories
if: matrix.archive
run: |
sudo gpg --keyserver keyserver.ubuntu.com --recv-keys 3B4FE6ACC0B21F32
sudo gpg --export 3B4FE6ACC0B21F32 | sudo tee /etc/apt/trusted.gpg.d/ubuntu-keyring.gpg > /dev/null
sudo add-apt-repository -yn 'deb http://archive.ubuntu.com/ubuntu/ ${{ matrix.archive }} main'
sudo add-apt-repository -yn 'deb http://archive.ubuntu.com/ubuntu/ ${{ matrix.archive }} universe'
- name: Install Clang ${{ matrix.clang }}
run: |
sudo add-apt-repository -yn 'deb http://archive.ubuntu.com/ubuntu/ xenial main'
sudo add-apt-repository -yn 'deb http://archive.ubuntu.com/ubuntu/ xenial universe'
sudo add-apt-repository -yn 'deb http://archive.ubuntu.com/ubuntu/ bionic main'
sudo add-apt-repository -yn 'deb http://archive.ubuntu.com/ubuntu/ bionic universe'
sudo apt-get update
sudo apt-get install -y clang-${{ matrix.clang }}
- name: Install libc++ ${{ matrix.clang }}
run: sudo apt-get install -y libc++-${{ matrix.clang }}-dev libc++abi-${{ matrix.clang }}-dev
- name: Install libunwind ${{ matrix.clang }}
if: matrix.clang == 12 # dependency is missing in Ubuntu 22.04
run: sudo apt-get install -y libunwind-${{ matrix.clang }}-dev
- name: Checkout
uses: actions/checkout@v3
uses: actions/checkout@v4
- name: Configure
run: cmake -DCMAKE_BUILD_TYPE=Debug .
env:
@@ -112,29 +147,25 @@ jobs:
CXX: clang++-${{ matrix.clang }}
CXXFLAGS: >-
${{ matrix.cxxflags }}
${{ contains(matrix.cxxflags, 'libc++') && '-I/usr/lib/llvm-10/include/c++/v1/' || '' }}
${{ matrix.clang < 11 && '-I/usr/lib/llvm-10/include/c++/v1/' || '' }}
- name: Build
run: cmake --build .
- name: Test
run: |
echo "## CTest output" >> $GITHUB_STEP_SUMMARY
echo '```' >> $GITHUB_STEP_SUMMARY
ctest --output-on-failure -C Debug . | tee -a $GITHUB_STEP_SUMMARY
echo '```' >> $GITHUB_STEP_SUMMARY
run: ctest --output-on-failure -C Debug .
env:
UBSAN_OPTIONS: print_stacktrace=1
conf_test:
name: Test configuration on Linux
needs: [gcc, clang]
runs-on: ubuntu-20.04
runs-on: ubuntu-22.04
steps:
- name: Install
run: |
sudo apt-get update
sudo apt-get install -y g++-multilib gcc-avr avr-libc
- name: Checkout
uses: actions/checkout@v3
uses: actions/checkout@v4
- name: AVR
run: avr-g++ -std=c++11 -Isrc extras/conf_test/avr.cpp
- name: GCC 32-bit
@@ -148,36 +179,39 @@ jobs:
conf_test_windows:
name: Test configuration on Windows
runs-on: windows-2019
runs-on: windows-2022
needs: [gcc, clang]
steps:
- name: Checkout
uses: actions/checkout@v3
uses: actions/checkout@v4
- name: 32-bit
run: |
call "C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\VC\Auxiliary\Build\vcvars32.bat"
call "C:\Program Files\Microsoft Visual Studio\2022\Enterprise\VC\Auxiliary\Build\vcvars32.bat"
cl /Isrc extras/conf_test/x86.cpp
shell: cmd
- name: 64-bit
run: |
call "C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\VC\Auxiliary\Build\vcvars64.bat"
call "C:\Program Files\Microsoft Visual Studio\2022\Enterprise\VC\Auxiliary\Build\vcvars64.bat"
cl /Isrc extras/conf_test/x64.cpp
shell: cmd
xcode:
name: XCode
needs: clang
runs-on: macos-11
runs-on: macos-13
strategy:
fail-fast: false
matrix:
include:
- xcode: "11.7"
- xcode: "12.4"
- xcode: "13.2.1"
- xcode: "14.1"
- xcode: "14.2"
- xcode: "14.3.1"
- xcode: "15.0.1"
- xcode: "15.1"
- xcode: "15.2"
steps:
- name: Checkout
uses: actions/checkout@v3
uses: actions/checkout@v4
- name: Select XCode version
run: sudo xcode-select --switch /Applications/Xcode_${{ matrix.xcode }}.app
- name: Configure
@@ -199,7 +233,7 @@ jobs:
# runs-on: ${{ matrix.os }}
# steps:
# - name: Checkout
# uses: actions/checkout@v3
# uses: actions/checkout@v4
# - name: Configure
# run: cmake -DCMAKE_BUILD_TYPE=Debug .
# - name: Build
@@ -218,10 +252,10 @@ jobs:
board: arduino:avr:uno
- core: arduino:samd
board: arduino:samd:mkr1000
runs-on: ubuntu-20.04
runs-on: ubuntu-22.04
steps:
- name: Checkout
uses: actions/checkout@v3
uses: actions/checkout@v4
- name: Install arduino-cli
run: curl -fsSL https://raw.githubusercontent.com/arduino/arduino-cli/master/install.sh | BINDIR=/usr/local/bin sh
- name: Install core
@@ -294,14 +328,14 @@ jobs:
conf_test: esp8266
steps:
- name: Checkout
uses: actions/checkout@v3
uses: actions/checkout@v4
- name: Set up cache for pip
uses: actions/cache@v3
uses: actions/cache@v4
with:
path: ~/.cache/pip
key: ${{ runner.os }}-pip
- name: Set up Python 3.x
uses: actions/setup-python@v4
uses: actions/setup-python@v5
with:
python-version: "3.x"
- name: Install PlatformIO
@@ -313,7 +347,7 @@ jobs:
if: ${{ matrix.platform == 'nordicnrf52' }}
run: find examples/ -name '*.ino' -exec sed -i 's/\(#include <ArduinoJson.h>\)/\1\n#include <Adafruit_TinyUSB.h>/' {} +
- name: Set up cache for platformio
uses: actions/cache@v3
uses: actions/cache@v4
with:
path: ~/.platformio
key: ${{ runner.os }}-platformio-${{ matrix.platform }}
@@ -362,7 +396,7 @@ jobs:
- board: argon
steps:
- name: Checkout
uses: actions/checkout@v3
uses: actions/checkout@v4
- name: Install Particle CLI
run: sudo npm install -g particle-cli
- name: Login to Particle
@@ -373,14 +407,14 @@ jobs:
arm:
name: GCC for ARM processor
needs: gcc
runs-on: ubuntu-20.04
runs-on: ubuntu-22.04
steps:
- name: Install
run: |
sudo apt-get update
sudo apt-get install -y g++-arm-linux-gnueabihf
- name: Checkout
uses: actions/checkout@v3
uses: actions/checkout@v4
- name: Configure
run: cmake .
env:
@@ -392,18 +426,18 @@ jobs:
coverage:
needs: gcc
name: Coverage
runs-on: ubuntu-20.04
runs-on: ubuntu-22.04
steps:
- name: Install
run: sudo apt-get install -y lcov ninja-build
- name: Checkout
uses: actions/checkout@v3
uses: actions/checkout@v4
- name: Configure
run: cmake -G Ninja -DCOVERAGE=true .
- name: Build
run: ninja
- name: Test
run: ctest -LE 'WillFail|Fuzzing' -T test
run: ctest --output-on-failure -LE 'WillFail|Fuzzing' -T test
- name: lcov --capture
run: lcov --capture --no-external --directory . --output-file coverage.info
- name: lcov --remove
@@ -411,12 +445,12 @@ jobs:
- name: genhtml
run: mkdir coverage && genhtml coverage_filtered.info -o coverage -t ArduinoJson
- name: Upload HTML report
uses: actions/upload-artifact@v3
uses: actions/upload-artifact@v4
with:
name: Coverage report
path: coverage
- name: Upload to Coveralls
uses: coverallsapp/github-action@master
uses: coverallsapp/github-action@v2
with:
github-token: ${{ secrets.GITHUB_TOKEN }}
path-to-lcov: coverage_filtered.info
@@ -424,109 +458,87 @@ jobs:
valgrind:
needs: gcc
name: Valgrind
runs-on: ubuntu-20.04
runs-on: ubuntu-22.04
steps:
- name: Install
run: |
sudo apt-get update
sudo apt-get install -y valgrind ninja-build
- name: Checkout
uses: actions/checkout@v3
uses: actions/checkout@v4
- name: Configure
run: cmake -G Ninja -D MEMORYCHECK_COMMAND_OPTIONS="--error-exitcode=1 --leak-check=full" .
- name: Build
run: ninja
- name: Memcheck
run: ctest -LE WillFail -T memcheck
run: ctest --output-on-failure -LE WillFail -T memcheck
id: memcheck
- name: MemoryChecker.*.log
run: cat Testing/Temporary/MemoryChecker.*.log
run: cat Testing/Temporary/MemoryChecker.*.log > $GITHUB_STEP_SUMMARY
if: failure()
clang-tidy:
needs: clang
name: Clang-Tidy
runs-on: ubuntu-20.04
runs-on: ubuntu-latest
steps:
- name: Install
run: sudo apt-get install -y clang-tidy cmake ninja-build
run: sudo apt-get install -y clang-tidy libc++-dev libc++abi-dev
- name: Checkout
uses: actions/checkout@v3
uses: actions/checkout@v4
- name: Configure
run: cmake -G Ninja -DCMAKE_CXX_CLANG_TIDY="clang-tidy-10;--warnings-as-errors=*" -DCMAKE_BUILD_TYPE=Debug .
run: cmake -G Ninja -DCMAKE_CXX_CLANG_TIDY="clang-tidy;--warnings-as-errors=*" -DCMAKE_BUILD_TYPE=Debug .
env:
CC: clang-10
CXX: clang++-10
CC: clang
CXX: clang++
- name: Check
run: cmake --build . -- -k 0
amalgamate-h:
amalgamate:
needs: gcc
name: Amalgamate ArduinoJson.h
runs-on: ubuntu-20.04
runs-on: ubuntu-22.04
steps:
- name: Checkout
uses: actions/checkout@v3
- name: Amalgamate
id: amalgamate
uses: actions/checkout@v4
- name: Setup
run: |
if [[ $GITHUB_REF == refs/tags/* ]]; then
VERSION=${GITHUB_REF#refs/tags/}
else
VERSION=${GITHUB_SHA::7}
fi
INPUT=src/ArduinoJson.h
OUTPUT=ArduinoJson-$VERSION.h
extras/scripts/build-single-header.sh "$INPUT" "$OUTPUT"
echo "filename=${OUTPUT}" >> $GITHUB_OUTPUT
- name: Smoke test
echo "ARDUINOJSON_H=ArduinoJson-$VERSION.h" >> $GITHUB_ENV
echo "ARDUINOJSON_HPP=ArduinoJson-$VERSION.hpp" >> $GITHUB_ENV
- name: Amalgamate ArduinoJson.h
run: extras/scripts/build-single-header.sh "src/ArduinoJson.h" "$ARDUINOJSON_H"
- name: Amalgamate ArduinoJson.hpp
run: extras/scripts/build-single-header.sh "src/ArduinoJson.hpp" "$ARDUINOJSON_HPP"
- name: Upload artifact
uses: actions/upload-artifact@v4
with:
name: Single headers
path: |
${{ env.ARDUINOJSON_H }}
${{ env.ARDUINOJSON_HPP }}
- name: Smoke test ArduinoJson.h
run: |
g++ -x c++ - <<END
#include "${{ steps.amalgamate.outputs.filename }}"
#include "$ARDUINOJSON_H"
int main() {
JsonDocument doc(300);
JsonDocument doc;
deserializeJson(doc, "{}");
}
END
- name: Upload artifact
uses: actions/upload-artifact@v3
with:
name: Single headers
path: ${{ steps.amalgamate.outputs.filename }}
amalgamate-hpp:
needs: gcc
name: Amalgamate ArduinoJson.hpp
runs-on: ubuntu-20.04
steps:
- name: Checkout
uses: actions/checkout@v3
- name: Amalgamate
id: amalgamate
run: |
if [[ $GITHUB_REF == refs/tags/* ]]; then
VERSION=${GITHUB_REF#refs/tags/}
else
VERSION=${GITHUB_SHA::7}
fi
INPUT=src/ArduinoJson.hpp
OUTPUT=ArduinoJson-$VERSION.hpp
extras/scripts/build-single-header.sh "$INPUT" "$OUTPUT"
echo "filename=${OUTPUT}" >> $GITHUB_OUTPUT
- name: Smoke test
- name: Smoke test ArduinoJson.hpp
run: |
g++ -x c++ - <<END
#include "${{ steps.amalgamate.outputs.filename }}"
#include "$ARDUINOJSON_HPP"
int main() {
ArduinoJson::JsonDocument doc(300);
ArduinoJson::JsonDocument doc;
deserializeJson(doc, "{}");
}
END
- name: Upload artifact
uses: actions/upload-artifact@v3
with:
name: Single headers
path: ${{ steps.amalgamate.outputs.filename }}
esp-idf:
needs: gcc
@@ -534,14 +546,14 @@ jobs:
runs-on: ubuntu-latest
steps:
- name: Setup cache
uses: actions/cache@v3
uses: actions/cache@v4
with:
path: ~/.espressif
key: ${{ runner.os }}-esp-idf
- name: Checkout ArduinoJson
uses: actions/checkout@v3
uses: actions/checkout@v4
- name: Checkout ESP-IDF
uses: actions/checkout@v3
uses: actions/checkout@v4
with:
repository: espressif/esp-idf
path: esp-idf
@@ -561,7 +573,7 @@ jobs:
codeql:
name: CodeQL
runs-on: ubuntu-20.04
runs-on: ubuntu-22.04
needs: gcc
permissions:
@@ -570,20 +582,20 @@ jobs:
security-events: write
steps:
- name: Checkout repository
uses: actions/checkout@v3
- name: Checkout repository
uses: actions/checkout@v4
- name: Initialize CodeQL
uses: github/codeql-action/init@v2
with:
languages: cpp
- name: Initialize CodeQL
uses: github/codeql-action/init@v3
with:
languages: cpp
- name: Build
run: |
cmake -DCMAKE_BUILD_TYPE=Debug .
cmake --build .
- name: Build
run: |
cmake -DCMAKE_BUILD_TYPE=Debug .
cmake --build .
- name: Perform CodeQL Analysis
uses: github/codeql-action/analyze@v2
with:
category: "/language:cpp"
- name: Perform CodeQL Analysis
uses: github/codeql-action/analyze@v3
with:
category: "/language:cpp"

View File

@@ -8,7 +8,7 @@ jobs:
lock:
runs-on: ubuntu-latest
steps:
- uses: dessant/lock-threads@v4
- uses: dessant/lock-threads@v5
with:
github-token: ${{ github.token }}
issue-inactive-days: 30

View File

@@ -8,7 +8,7 @@ on:
jobs:
release:
name: Create release
runs-on: ubuntu-20.04
runs-on: ubuntu-22.04
steps:
- name: Set variables
id: init
@@ -16,12 +16,18 @@ jobs:
echo "tag=${GITHUB_REF#refs/tags/}" >> $GITHUB_OUTPUT
echo "version=${GITHUB_REF#refs/tags/v}" >> $GITHUB_OUTPUT
- name: Checkout
uses: actions/checkout@v3
uses: actions/checkout@v4
- name: Write release body
id: body
run: |
FILENAME=RELEASE.md
extras/scripts/get-release-body.sh ${{ steps.init.outputs.tag }} CHANGELOG.md | tee $FILENAME
tee $FILENAME <<END
## Changes
$(extras/scripts/extract_changes.awk CHANGELOG.md)
[View version history](https://github.com/bblanchon/ArduinoJson/blob/${{ steps.init.outputs.tag }}/CHANGELOG.md)
END
echo "filename=$FILENAME" >> $GITHUB_OUTPUT
- name: Amalgamate ArduinoJson.h
id: amalgamate_h
@@ -35,18 +41,12 @@ jobs:
FILENAME=ArduinoJson-${{ steps.init.outputs.tag }}.hpp
extras/scripts/build-single-header.sh src/ArduinoJson.hpp "$FILENAME"
echo "filename=$FILENAME" >> $GITHUB_OUTPUT
- name: Create Arduino package
id: arduino
run: |
FILENAME=ArduinoJson-${{ steps.init.outputs.tag }}.zip
extras/scripts/build-arduino-package.sh . "$FILENAME"
echo "filename=$FILENAME" >> $GITHUB_OUTPUT
- name: Create release
uses: ncipollo/release-action@v1
with:
bodyFile: ${{ steps.body.outputs.filename }}
name: ArduinoJson ${{ steps.init.outputs.version }}
artifacts: ${{ steps.amalgamate_h.outputs.filename }},${{ steps.amalgamate_hpp.outputs.filename }},${{ steps.arduino.outputs.filename }}
artifacts: ${{ steps.amalgamate_h.outputs.filename }},${{ steps.amalgamate_hpp.outputs.filename }}
token: ${{ secrets.GITHUB_TOKEN }}
idf:
@@ -54,7 +54,7 @@ jobs:
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v3
uses: actions/checkout@v4
- name: Upload component to the component registry
uses: espressif/upload-components-ci-action@v1
with:
@@ -69,8 +69,25 @@ jobs:
- name: Install
run: npm install -g particle-cli
- name: Checkout
uses: actions/checkout@v3
uses: actions/checkout@v4
- name: Login
run: particle login --token ${{ secrets.PARTICLE_TOKEN }}
- name: Publish
run: bash -eux extras/scripts/publish-particle-library.sh
platformio:
name: PlatformIO
runs-on: ubuntu-latest
steps:
- name: Set up Python 3.x
uses: actions/setup-python@v5
with:
python-version: "3.x"
- name: Install PlatformIO
run: pip install platformio
- name: Checkout
uses: actions/checkout@v4
- name: Publish
run: pio pkg publish --no-interactive --no-notify
env:
PLATFORMIO_AUTH_TOKEN: ${{ secrets.PLATFORMIO_AUTH_TOKEN }}

View File

@@ -1,3 +1,4 @@
.devcontainer/
.github/
examples/
extras/
extras/

View File

@@ -1,6 +1,5 @@
{
"C_Cpp.default.configurationProvider": "ms-vscode.cmake-tools",
"cmake.generator": "Ninja",
"git.inputValidationLength": 80,
"git.inputValidationSubjectLength": 72,
"files.insertFinalNewline": true,

View File

@@ -1,5 +1,5 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#include "src/ArduinoJson.h"

View File

@@ -4,14 +4,289 @@ ArduinoJson: change log
HEAD
----
* Optimize storage of static strings
> ### BREAKING CHANGES
>
> Static string cannot contain NUL characters anymore (they could since 7.3.0).
> This is an extremely rare case, so you probably won't be affected.
>
> For example, the following code produces different output in 7.3 and 7.4:
>
> ```cpp
> JsonDocument doc;
> doc["a\0b"] = "c\0d";
> serializeJson(doc, Serial);
> // With Arduino 7.3 -> {"a\u0000b":"c\u0000d"}
> // With Arduino 7.4 -> {"a":"c"}
> ```
>
> `JsonString` contructor now only accepts two arguments, not three.
> If your code uses `JsonString` to store a string as a pointer, you must remove the size argument.
>
> For example, if you have something like this:
>
> ```cpp
> doc["key"] = JsonString(str.c_str(), str.size(), true);
> ```
>
> You must replace with either:
>
> ```cpp
> doc["key"] = JsonString(str.c_str(), true); // store as pointer, cannot contain NUL characters
> doc["key"] = JsonString(str.c_str(), str.size()); // store by copy, NUL characters allowed
> doc["key"] = str; // same as previous line for supported string classes (`String`, `std::string`, etc.)
> ```
v7.4.2 (2025-06-20)
------
* Fix truncated strings on Arduino Due (issue #2181)
v7.4.1 (2025-04-11)
------
* Fix crash with tiny Flash strings (issue #2170)
v7.4.0 (2025-04-09)
------
* Optimize storage of tiny strings (up to 3 characters)
* Fix support for `const char[]` (issue #2166)
v7.3.1 (2025-02-27)
------
* Fix conversion from static string to number
* Slightly reduce code size
v7.3.0 (2024-12-29)
------
* Fix support for NUL characters in `deserializeJson()`
* Make `ElementProxy` and `MemberProxy` non-copyable
* Change string copy policy: only string literal are stored by pointer
* `JsonString` is now stored by copy, unless specified otherwise
* Replace undocumented `JsonString::Ownership` with `bool`
* Rename undocumented `JsonString::isLinked()` to `isStatic()`
* Move public facing SFINAEs to template declarations
> ### BREAKING CHANGES
>
> In previous versions, `MemberProxy` (the class returned by `operator[]`) could lead to dangling pointers when used with a temporary string.
> To prevent this issue, `MemberProxy` and `ElementProxy` are now non-copyable.
>
> Your code is likely to be affected if you use `auto` to store the result of `operator[]`. For example, the following line won't compile anymore:
>
> ```cpp
> auto value = doc["key"];
> ```
>
> To fix the issue, you must append either `.as<T>()` or `.to<T>()`, depending on the situation.
>
> For example, if you are extracting values from a JSON document, you should update like this:
>
> ```diff
> - auto config = doc["config"];
> + auto config = doc["config"].as<JsonObject>();
> const char* name = config["name"];
> ```
>
> However, if you are building a JSON document, you should update like this:
>
> ```diff
> - auto config = doc["config"];
> + auto config = doc["config"].to<JsonObject>();
> config["name"] = "ArduinoJson";
> ```
v7.2.1 (2024-11-15)
------
* Forbid `deserializeJson(JsonArray|JsonObject, ...)` (issue #2135)
* Fix VLA support in `JsonDocument::set()`
* Fix `operator[](variant)` ignoring NUL characters
v7.2.0 (2024-09-18)
------
* Store object members with two slots: one for the key and one for the value
* Store 64-bit numbers (`double` and `long long`) in an additional slot
* Reduce the slot size (see table below)
* Improve message when user forgets third arg of `serializeJson()` et al.
* Set `ARDUINOJSON_USE_DOUBLE` to `0` by default on 8-bit architectures
* Deprecate `containsKey()` in favor of `doc["key"].is<T>()`
* Add support for escape sequence `\'` (issue #2124)
| Architecture | before | after |
|--------------|----------|----------|
| 8-bit | 8 bytes | 6 bytes |
| 32-bit | 16 bytes | 8 bytes |
| 64-bit | 24 bytes | 16 bytes |
> ### BREAKING CHANGES
>
> After being on the death row for years, the `containsKey()` method has finally been deprecated.
> You should replace `doc.containsKey("key")` with `doc["key"].is<T>()`, which not only checks that the key exists but also that the value is of the expected type.
>
> ```cpp
> // Before
> if (doc.containsKey("value")) {
> int value = doc["value"];
> // ...
> }
>
> // After
> if (doc["value"].is<int>()) {
> int value = doc["value"];
> // ...
> }
> ```
v7.1.0 (2024-06-27)
------
* Add `ARDUINOJSON_STRING_LENGTH_SIZE` to the namespace name
* Add support for MsgPack binary (PR #2078 by @Sanae6)
* Add support for MsgPack extension
* Make string support even more generic (PR #2084 by @d-a-v)
* Optimize `deserializeMsgPack()`
* Allow using a `JsonVariant` as a key or index (issue #2080)
Note: works only for reading, not for writing
* Support `ElementProxy` and `MemberProxy` in `JsonDocument`'s constructor
* Don't add partial objects when allocation fails (issue #2081)
* Read MsgPack's 64-bit integers even if `ARDUINOJSON_USE_LONG_LONG` is `0`
(they are set to `null` if they don't fit in a `long`)
v7.0.4 (2024-03-12)
------
* Make `JSON_STRING_SIZE(N)` return `N+1` to fix third-party code (issue #2054)
v7.0.3 (2024-02-05)
------
* Improve error messages when using `char` or `char*` (issue #2043)
* Reduce stack consumption (issue #2046)
* Fix compatibility with GCC 4.8 (issue #2045)
v7.0.2 (2024-01-19)
------
* Fix assertion `poolIndex < count_` after `JsonDocument::clear()` (issue #2034)
v7.0.1 (2024-01-10)
------
* Fix "no matching function" with `JsonObjectConst::operator[]` (issue #2019)
* Remove unused files in the PlatformIO package
* Fix `volatile bool` serialized as `1` or `0` instead of `true` or `false` (issue #2029)
v7.0.0 (2024-01-03)
------
* Remove `BasicJsonDocument`
* Remove `StaticJsonDocument`
* Add abstract `Allocator` class
* Merge `DynamicJsonDocument` with `JsonDocument`
* Remove `JSON_ARRAY_SIZE()`, `JSON_OBJECT_SIZE()`, and `JSON_STRING_SIZE()`
* Remove `ARDUINOJSON_ENABLE_STRING_DEDUPLICATION` (string deduplication cannot be enabled anymore)
* Remove `ARDUINOJSON_ENABLE_STRING_DEDUPLICATION` (string deduplication cannot be disabled anymore)
* Remove `JsonDocument::capacity()`
* Store the strings in the heap
* Reference-count shared strings
* Always store `serialized("string")` by copy (#1915)
* Remove the zero-copy mode of `deserializeJson()` and `deserializeMsgPack()`
* Fix double lookup in `to<JsonVariant>()`
* Fix double call to `size()` in `serializeMsgPack()`
* Include `ARDUINOJSON_SLOT_OFFSET_SIZE` in the namespace name
* Remove `JsonVariant::shallowCopy()`
* `JsonDocument`'s capacity grows as needed, no need to pass it to the constructor anymore
* `JsonDocument`'s allocator is not monotonic anymore, removed values get recycled
* Show a link to the documentation when user passes an unsupported input type
* Remove `JsonDocument::memoryUsage()`
* Remove `JsonDocument::garbageCollect()`
* Add `deserializeJson(JsonVariant, ...)` and `deserializeMsgPack(JsonVariant, ...)` (#1226)
* Call `shrinkToFit()` in `deserializeJson()` and `deserializeMsgPack()`
* `serializeJson()` and `serializeMsgPack()` replace the content of `std::string` and `String` instead of appending to it
* Replace `add()` with `add<T>()` (`add(T)` is still supported)
* Remove `createNestedArray()` and `createNestedObject()` (use `to<JsonArray>()` and `to<JsonObject>()` instead)
> ### BREAKING CHANGES
>
> As every major release, ArduinoJson 7 introduces several breaking changes.
> I added some stubs so that most existing programs should compile, but I highty recommend you upgrade your code.
>
> #### `JsonDocument`
>
> In ArduinoJson 6, you could allocate the memory pool on the stack (with `StaticJsonDocument`) or in the heap (with `DynamicJsonDocument`).
> In ArduinoJson 7, the memory pool is always allocated in the heap, so `StaticJsonDocument` and `DynamicJsonDocument` have been merged into `JsonDocument`.
>
> In ArduinoJson 6, `JsonDocument` had a fixed capacity; in ArduinoJson 7, it has an elastic capacity that grows as needed.
> Therefore, you don't need to specify the capacity anymore, so the macros `JSON_ARRAY_SIZE()`, `JSON_OBJECT_SIZE()`, and `JSON_STRING_SIZE()` have been removed.
>
> ```c++
> // ArduinoJson 6
> StaticJsonDocument<256> doc;
> // or
> DynamicJsonDocument doc(256);
>
> // ArduinoJson 7
> JsonDocument doc;
> ```
>
> In ArduinoJson 7, `JsonDocument` reuses released memory, so `garbageCollect()` has been removed.
> `shrinkToFit()` is still available and releases the over-allocated memory.
>
> Due to a change in the implementation, it's not possible to store a pointer to a variant from another `JsonDocument`, so `shallowCopy()` has been removed.
>
> In ArduinoJson 6, the meaning of `memoryUsage()` was clear: it returned the number of bytes used in the memory pool.
> In ArduinoJson 7, the meaning of `memoryUsage()` would be ambiguous, so it has been removed.
>
> #### Custom allocators
>
> In ArduinoJson 6, you could specify a custom allocator class as a template parameter of `BasicJsonDocument`.
> In ArduinoJson 7, you must inherit from `ArduinoJson::Allocator` and pass a pointer to an instance of your class to the constructor of `JsonDocument`.
>
> ```c++
> // ArduinoJson 6
> class MyAllocator {
> // ...
> };
> BasicJsonDocument<MyAllocator> doc(256);
>
> // ArduinoJson 7
> class MyAllocator : public ArduinoJson::Allocator {
> // ...
> };
> MyAllocator myAllocator;
> JsonDocument doc(&myAllocator);
> ```
>
> #### `createNestedArray()` and `createNestedObject()`
>
> In ArduinoJson 6, you could create a nested array or object with `createNestedArray()` and `createNestedObject()`.
> In ArduinoJson 7, you must use `add<T>()` or `to<T>()` instead.
>
> For example, to create `[[],{}]`, you would write:
>
> ```c++
> // ArduinoJson 6
> arr.createNestedArray();
> arr.createNestedObject();
>
> // ArduinoJson 7
> arr.add<JsonArray>();
> arr.add<JsonObject>();
> ```
>
> And to create `{"array":[],"object":{}}`, you would write:
>
> ```c++
> // ArduinoJson 6
> obj.createNestedArray("array");
> obj.createNestedObject("object");
>
> // ArduinoJson 7
> obj["array"].to<JsonArray>();
> obj["object"].to<JsonObject>();
> ```

View File

@@ -1,5 +1,5 @@
# ArduinoJson - https://arduinojson.org
# Copyright © 2014-2023, Benoit BLANCHON
# Copyright © 2014-2025, Benoit BLANCHON
# MIT License
cmake_minimum_required(VERSION 3.15)
@@ -10,7 +10,7 @@ if(ESP_PLATFORM)
return()
endif()
project(ArduinoJson VERSION 7.0.0)
project(ArduinoJson VERSION 7.4.2)
if(CMAKE_PROJECT_NAME STREQUAL PROJECT_NAME)
include(CTest)

View File

@@ -1,7 +1,7 @@
The MIT License (MIT)
---------------------
Copyright © 2014-2023, Benoit BLANCHON
Copyright © 2014-2025, Benoit BLANCHON
Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the “Software”), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:

View File

@@ -15,29 +15,28 @@ ArduinoJson is a C++ JSON library for Arduino and IoT (Internet Of Things).
## Features
* [JSON deserialization](https://arduinojson.org/v6/api/json/deserializejson/)
* [Optionally decodes UTF-16 escape sequences to UTF-8](https://arduinojson.org/v6/api/config/decode_unicode/)
* [Optionally stores links to the input buffer (zero-copy)](https://arduinojson.org/v6/api/json/deserializejson/)
* [Optionally supports comments in the input](https://arduinojson.org/v6/api/config/enable_comments/)
* [Optionally filters the input to keep only desired values](https://arduinojson.org/v6/api/json/deserializejson/#filtering)
* [JSON deserialization](https://arduinojson.org/v7/api/json/deserializejson/)
* [Optionally decodes UTF-16 escape sequences to UTF-8](https://arduinojson.org/v7/api/config/decode_unicode/)
* [Optionally supports comments in the input](https://arduinojson.org/v7/api/config/enable_comments/)
* [Optionally filters the input to keep only desired values](https://arduinojson.org/v7/api/json/deserializejson/#filtering)
* Supports single quotes as a string delimiter
* Compatible with [NDJSON](http://ndjson.org/) and [JSON Lines](https://jsonlines.org/)
* [JSON serialization](https://arduinojson.org/v6/api/json/serializejson/)
* [Can write to a buffer or a stream](https://arduinojson.org/v6/api/json/serializejson/)
* [Optionally indents the document (prettified JSON)](https://arduinojson.org/v6/api/json/serializejsonpretty/)
* [MessagePack serialization](https://arduinojson.org/v6/api/msgpack/serializemsgpack/)
* [MessagePack deserialization](https://arduinojson.org/v6/api/msgpack/deserializemsgpack/)
* [JSON serialization](https://arduinojson.org/v7/api/json/serializejson/)
* [Can write to a buffer or a stream](https://arduinojson.org/v7/api/json/serializejson/)
* [Optionally indents the document (prettified JSON)](https://arduinojson.org/v7/api/json/serializejsonpretty/)
* [MessagePack serialization](https://arduinojson.org/v7/api/msgpack/serializemsgpack/)
* [MessagePack deserialization](https://arduinojson.org/v7/api/msgpack/deserializemsgpack/)
* Efficient
* [Twice smaller than the "official" Arduino_JSON library](https://arduinojson.org/2019/11/19/arduinojson-vs-arduino_json/)
* [Almost 10% faster than the "official" Arduino_JSON library](https://arduinojson.org/2019/11/19/arduinojson-vs-arduino_json/)
* [Consumes roughly 10% less RAM than the "official" Arduino_JSON library](https://arduinojson.org/2019/11/19/arduinojson-vs-arduino_json/)
* [Deduplicates strings](https://arduinojson.org/news/2020/08/01/version-6-16-0/)
* Versatile
* Supports [custom allocators (to use external RAM chip, for example)](https://arduinojson.org/v6/how-to/use-external-ram-on-esp32/)
* Supports [`String`](https://arduinojson.org/v6/api/config/enable_arduino_string/), [`std::string`](https://arduinojson.org/v6/api/config/enable_std_string/), and [`std::string_view`](https://arduinojson.org/v6/api/config/enable_string_view/)
* Supports [`Stream`](https://arduinojson.org/v6/api/config/enable_arduino_stream/) and [`std::istream`/`std::ostream`](https://arduinojson.org/v6/api/config/enable_std_stream/)
* Supports [Flash strings](https://arduinojson.org/v6/api/config/enable_progmem/)
* Supports [custom readers](https://arduinojson.org/v6/api/json/deserializejson/#custom-reader) and [custom writers](https://arduinojson.org/v6/api/json/serializejson/#custom-writer)
* Supports [custom allocators (to use external RAM chip, for example)](https://arduinojson.org/v7/how-to/use-external-ram-on-esp32/)
* Supports [`String`](https://arduinojson.org/v7/api/config/enable_arduino_string/), [`std::string`](https://arduinojson.org/v7/api/config/enable_std_string/), and [`std::string_view`](https://arduinojson.org/v7/api/config/enable_string_view/)
* Supports [`Stream`](https://arduinojson.org/v7/api/config/enable_arduino_stream/) and [`std::istream`/`std::ostream`](https://arduinojson.org/v7/api/config/enable_std_stream/)
* Supports [Flash strings](https://arduinojson.org/v7/api/config/enable_progmem/)
* Supports [custom readers](https://arduinojson.org/v7/api/json/deserializejson/#custom-reader) and [custom writers](https://arduinojson.org/v7/api/json/serializejson/#custom-writer)
* Supports [custom converters](https://arduinojson.org/news/2021/05/04/version-6-18-0/)
* Portable
* Usable on any C++ project (not limited to Arduino)
@@ -67,29 +66,29 @@ ArduinoJson is a C++ JSON library for Arduino and IoT (Internet Of Things).
* [Visual Micro](http://www.visualmicro.com/)
* [Visual Studio](https://www.visualstudio.com/)
* [Even works with online compilers like wandbox.org](https://wandbox.org/permlink/RlZSKy17DjJ6HcdN)
* [CMake friendly](https://arduinojson.org/v6/how-to/use-arduinojson-with-cmake/)
* [CMake friendly](https://arduinojson.org/v7/how-to/use-arduinojson-with-cmake/)
* Well designed
* [Elegant API](http://arduinojson.org/v6/example/)
* [Elegant API](http://arduinojson.org/v7/example/)
* [Thread-safe](https://en.wikipedia.org/wiki/Thread_safety)
* Self-contained (no external dependency)
* `const` friendly
* [`for` friendly](https://arduinojson.org/v6/api/jsonobject/begin_end/)
* [`for` friendly](https://arduinojson.org/v7/api/jsonobject/begin_end/)
* [TMP friendly](https://en.wikipedia.org/wiki/Template_metaprogramming)
* Handles [integer overflows](https://arduinojson.org/v6/api/jsonvariant/as/#integer-overflows)
* Handles [integer overflows](https://arduinojson.org/v7/api/jsonvariant/as/#integer-overflows)
* Well tested
* [Unit test coverage close to 100%](https://coveralls.io/github/bblanchon/ArduinoJson?branch=7.x)
* Continuously tested on
* [Visual Studio 2017, 2019, 2022](https://ci.appveyor.com/project/bblanchon/arduinojson/branch/7.x)
* [GCC 5, 6, 7, 8, 9, 10, 11](https://github.com/bblanchon/ArduinoJson/actions?query=workflow%3A%22Continuous+Integration%22)
* [Clang 3.8, 3.9, 4.0, 5.0, 6.0, 7, 8, 9, 10](https://github.com/bblanchon/ArduinoJson/actions?query=workflow%3A%22Continuous+Integration%22)
* [GCC 4.8, 5, 6, 7, 8, 9, 10, 11, 12](https://github.com/bblanchon/ArduinoJson/actions?query=workflow%3A%22Continuous+Integration%22)
* [Clang 7 to 19](https://github.com/bblanchon/ArduinoJson/actions?query=workflow%3A%22Continuous+Integration%22)
* [Continuously fuzzed with Google OSS Fuzz](https://bugs.chromium.org/p/oss-fuzz/issues/list?sort=-opened&can=1&q=proj:arduinojson)
* Passes all default checks of [clang-tidy](https://releases.llvm.org/10.0.0/tools/clang/tools/extra/docs/clang-tidy/)
* Well documented
* [Tutorials](https://arduinojson.org/v6/doc/deserialization/)
* [Examples](https://arduinojson.org/v6/example/)
* [How-tos](https://arduinojson.org/v6/example/)
* [FAQ](https://arduinojson.org/v6/faq/)
* [Troubleshooter](https://arduinojson.org/v6/troubleshooter/)
* [Tutorials](https://arduinojson.org/v7/doc/deserialization/)
* [Examples](https://arduinojson.org/v7/example/)
* [How-tos](https://arduinojson.org/v7/example/)
* [FAQ](https://arduinojson.org/v7/faq/)
* [Troubleshooter](https://arduinojson.org/v7/troubleshooter/)
* [Book](https://arduinojson.org/book/)
* [Changelog](CHANGELOG.md)
* Vibrant user community
@@ -104,9 +103,9 @@ ArduinoJson is a C++ JSON library for Arduino and IoT (Internet Of Things).
Here is a program that parses a JSON document with ArduinoJson.
```c++
char json[] = "{\"sensor\":\"gps\",\"time\":1351824120,\"data\":[48.756080,2.302038]}";
const char* json = "{\"sensor\":\"gps\",\"time\":1351824120,\"data\":[48.756080,2.302038]}";
JsonDocument doc(1024);
JsonDocument doc;
deserializeJson(doc, json);
const char* sensor = doc["sensor"];
@@ -115,14 +114,14 @@ double latitude = doc["data"][0];
double longitude = doc["data"][1];
```
See the [tutorial on arduinojson.org](https://arduinojson.org/v6/doc/deserialization/)
See the [tutorial on arduinojson.org](https://arduinojson.org/v7/doc/deserialization/)
### Serialization
Here is a program that generates a JSON document with ArduinoJson:
```c++
JsonDocument doc(1024);
JsonDocument doc;
doc["sensor"] = "gps";
doc["time"] = 1351824120;
@@ -134,21 +133,19 @@ serializeJson(doc, Serial);
// {"sensor":"gps","time":1351824120,"data":[48.756080,2.302038]}
```
See the [tutorial on arduinojson.org](https://arduinojson.org/v6/doc/serialization/)
See the [tutorial on arduinojson.org](https://arduinojson.org/v7/doc/serialization/)
## Sponsors
ArduinoJson is thankful to its sponsors. Please give them a visit; they deserve it!
<p>
<a href="https://www.programmingelectronics.com/" rel="sponsored">
<img src="https://arduinojson.org/images/2021/10/programmingeleactronicsacademy.png" alt="Programming Electronics Academy" width="200">
</a>
</p>
<p>
<a href="https://github.com/1technophile" rel="sponsored">
<img alt="1technophile" src="https://avatars.githubusercontent.com/u/12672732?s=40&v=4">
</a>
<a href="https://github.com/LArkema" rel="sponsored">
<img alt="LArkema" src="https://avatars.githubusercontent.com/u/38381313?s=40&v=4">
</a>
</p>
If you run a commercial project that embeds ArduinoJson, think about [sponsoring the library's development](https://github.com/sponsors/bblanchon): it ensures the code that your products rely on stays actively maintained. It can also give your project some exposure to the makers' community.

View File

@@ -1,4 +1,4 @@
version: 7.0.0.{build}
version: 7.4.2.{build}
environment:
matrix:
- APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2022

View File

@@ -1,5 +1,5 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
//
// This example shows how to store your project configuration in a file.
@@ -17,18 +17,13 @@
// * CLK <-> pin 13
// * CS <-> pin 4
//
// https://arduinojson.org/v6/example/config/
// https://arduinojson.org/v7/example/config/
#include <ArduinoJson.h>
#include <SD.h>
#include <SPI.h>
// Our configuration structure.
//
// Never use a JsonDocument to store the configuration!
// A JsonDocument is *not* a permanent storage; it's only a temporary storage
// used during the serialization phase. See:
// https://arduinojson.org/v6/faq/why-must-i-create-a-separate-config-object/
struct Config {
char hostname[64];
int port;
@@ -43,9 +38,7 @@ void loadConfiguration(const char* filename, Config& config) {
File file = SD.open(filename);
// Allocate a temporary JsonDocument
// Don't forget to change the capacity to match your requirements.
// Use https://arduinojson.org/v6/assistant to compute the capacity.
JsonDocument doc(512);
JsonDocument doc;
// Deserialize the JSON document
DeserializationError error = deserializeJson(doc, file);
@@ -75,9 +68,7 @@ void saveConfiguration(const char* filename, const Config& config) {
}
// Allocate a temporary JsonDocument
// Don't forget to change the capacity to match your requirements.
// Use https://arduinojson.org/assistant to compute the capacity.
JsonDocument doc(256);
JsonDocument doc;
// Set the values in the document
doc["hostname"] = config.hostname;
@@ -145,7 +136,7 @@ void loop() {
// ------------------
//
// File is an unbuffered stream, which is not optimal for ArduinoJson.
// See: https://arduinojson.org/v6/how-to/improve-speed/
// See: https://arduinojson.org/v7/how-to/improve-speed/
// See also
// --------

View File

@@ -1,10 +1,10 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
//
// This example shows how to use DeserializationOption::Filter
//
// https://arduinojson.org/v6/example/filter/
// https://arduinojson.org/v7/example/filter/
#include <ArduinoJson.h>
@@ -34,12 +34,12 @@ void setup() {
"1000000,\"timezone\":0,\"sunrise\":1581492085,\"sunset\":1581527294}}");
// The filter: it contains "true" for each value we want to keep
JsonDocument filter(200);
JsonDocument filter;
filter["list"][0]["dt"] = true;
filter["list"][0]["main"]["temp"] = true;
// Deserialize the document
JsonDocument doc(400);
JsonDocument doc;
deserializeJson(doc, input_json, DeserializationOption::Filter(filter));
// Print the result

View File

@@ -1,10 +1,10 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
//
// This example shows how to generate a JSON document with ArduinoJson.
//
// https://arduinojson.org/v6/example/generator/
// https://arduinojson.org/v7/example/generator/
#include <ArduinoJson.h>
@@ -15,25 +15,18 @@ void setup() {
continue;
// Allocate the JSON document
//
// Inside the parentheses, 200 is the RAM allocated to this document.
// Don't forget to change this value to match your requirement.
// Use https://arduinojson.org/v6/assistant to compute the capacity.
JsonDocument doc(200);
JsonDocument doc;
// Add values in the document
//
doc["sensor"] = "gps";
doc["time"] = 1351824120;
// Add an array.
//
JsonArray data = doc.createNestedArray("data");
// Add an array
JsonArray data = doc["data"].to<JsonArray>();
data.add(48.756080);
data.add(2.302038);
// Generate the minified JSON and send it to the Serial port.
//
// Generate the minified JSON and send it to the Serial port
serializeJson(doc, Serial);
// The above line prints:
// {"sensor":"gps","time":1351824120,"data":[48.756080,2.302038]}
@@ -41,8 +34,7 @@ void setup() {
// Start a new line
Serial.println();
// Generate the prettified JSON and send it to the Serial port.
//
// Generate the prettified JSON and send it to the Serial port
serializeJsonPretty(doc, Serial);
// The above line prints:
// {

View File

@@ -1,5 +1,5 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
//
// This example shows how to parse a JSON document in an HTTP response.
@@ -16,7 +16,7 @@
// ]
// }
//
// https://arduinojson.org/v6/example/http-client/
// https://arduinojson.org/v7/example/http-client/
#include <ArduinoJson.h>
#include <Ethernet.h>
@@ -25,7 +25,8 @@
void setup() {
// Initialize Serial port
Serial.begin(9600);
while (!Serial) continue;
while (!Serial)
continue;
// Initialize Ethernet library
byte mac[] = {0xDE, 0xAD, 0xBE, 0xEF, 0xFE, 0xED};
@@ -77,8 +78,7 @@ void setup() {
}
// Allocate the JSON document
// Use https://arduinojson.org/v6/assistant to compute the capacity.
JsonDocument doc(256);
JsonDocument doc;
// Parse JSON object
DeserializationError error = deserializeJson(doc, client);
@@ -108,7 +108,7 @@ void loop() {
// ------------------
//
// EthernetClient is an unbuffered stream, which is not optimal for ArduinoJson.
// See: https://arduinojson.org/v6/how-to/improve-speed/
// See: https://arduinojson.org/v7/how-to/improve-speed/
// See also
// --------

View File

@@ -1,10 +1,10 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
//
// This example shows how to deserialize a JSON document with ArduinoJson.
//
// https://arduinojson.org/v6/example/parser/
// https://arduinojson.org/v7/example/parser/
#include <ArduinoJson.h>
@@ -15,34 +15,23 @@ void setup() {
continue;
// Allocate the JSON document
//
// Inside the parentheses, 200 is the capacity of the memory pool in bytes.
// Don't forget to change this value to match your JSON document.
// Use https://arduinojson.org/v6/assistant to compute the capacity.
JsonDocument doc(200);
JsonDocument doc;
// JSON input string.
//
// Using a char[], as shown here, enables the "zero-copy" mode. This mode uses
// the minimal amount of memory because the JsonDocument stores pointers to
// the input buffer.
// If you use another type of input, ArduinoJson must copy the strings from
// the input to the JsonDocument, so you need to increase the capacity of the
// JsonDocument.
char json[] =
const char* json =
"{\"sensor\":\"gps\",\"time\":1351824120,\"data\":[48.756080,2.302038]}";
// Deserialize the JSON document
DeserializationError error = deserializeJson(doc, json);
// Test if parsing succeeds.
// Test if parsing succeeds
if (error) {
Serial.print(F("deserializeJson() failed: "));
Serial.println(error.f_str());
return;
}
// Fetch values.
// Fetch the values
//
// Most of the time, you can rely on the implicit casts.
// In other case, you can do doc["time"].as<long>();
@@ -51,7 +40,7 @@ void setup() {
double latitude = doc["data"][0];
double longitude = doc["data"][1];
// Print values.
// Print the values
Serial.println(sensor);
Serial.println(time);
Serial.println(latitude, 6);

View File

@@ -1,5 +1,5 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
//
// This example shows how to implement an HTTP server that sends a JSON document
@@ -13,7 +13,7 @@
// "digital": [1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0]
// }
//
// https://arduinojson.org/v6/example/http-server/
// https://arduinojson.org/v7/example/http-server/
#include <ArduinoJson.h>
#include <Ethernet.h>
@@ -57,11 +57,10 @@ void loop() {
client.read();
// Allocate a temporary JsonDocument
// Use https://arduinojson.org/v6/assistant to compute the capacity.
JsonDocument doc(500);
JsonDocument doc;
// Create the "analog" array
JsonArray analogValues = doc.createNestedArray("analog");
JsonArray analogValues = doc["analog"].to<JsonArray>();
for (int pin = 0; pin < 6; pin++) {
// Read the analog input
int value = analogRead(pin);
@@ -71,7 +70,7 @@ void loop() {
}
// Create the "digital" array
JsonArray digitalValues = doc.createNestedArray("digital");
JsonArray digitalValues = doc["digital"].to<JsonArray>();
for (int pin = 0; pin < 14; pin++) {
// Read the digital input
int value = digitalRead(pin);
@@ -103,7 +102,7 @@ void loop() {
// ------------------
//
// EthernetClient is an unbuffered stream, which is not optimal for ArduinoJson.
// See: https://arduinojson.org/v6/how-to/improve-speed/
// See: https://arduinojson.org/v7/how-to/improve-speed/
// See also
// --------

View File

@@ -1,5 +1,5 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
//
// This example shows how to send a JSON document to a UDP socket.
@@ -17,7 +17,7 @@
// $ ncat -ulp 8888
// See https://nmap.org/ncat/
//
// https://arduinojson.org/v6/example/udp-beacon/
// https://arduinojson.org/v7/example/udp-beacon/
#include <ArduinoJson.h>
#include <Ethernet.h>
@@ -47,11 +47,10 @@ void setup() {
void loop() {
// Allocate a temporary JsonDocument
// Use https://arduinojson.org/v6/assistant to compute the capacity.
JsonDocument doc(500);
JsonDocument doc;
// Create the "analog" array
JsonArray analogValues = doc.createNestedArray("analog");
JsonArray analogValues = doc["analog"].to<JsonArray>();
for (int pin = 0; pin < 6; pin++) {
// Read the analog input
int value = analogRead(pin);
@@ -61,7 +60,7 @@ void loop() {
}
// Create the "digital" array
JsonArray digitalValues = doc.createNestedArray("digital");
JsonArray digitalValues = doc["digital"].to<JsonArray>();
for (int pin = 0; pin < 14; pin++) {
// Read the digital input
int value = digitalRead(pin);
@@ -91,7 +90,7 @@ void loop() {
// ------------------
//
// EthernetUDP is an unbuffered stream, which is not optimal for ArduinoJson.
// See: https://arduinojson.org/v6/how-to/improve-speed/
// See: https://arduinojson.org/v7/how-to/improve-speed/
// See also
// --------

View File

@@ -1,11 +1,11 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
//
// This example shows how to deserialize a MessagePack document with
// ArduinoJson.
//
// https://arduinojson.org/v6/example/msgpack-parser/
// https://arduinojson.org/v7/example/msgpack-parser/
#include <ArduinoJson.h>
@@ -16,20 +16,9 @@ void setup() {
continue;
// Allocate the JSON document
//
// Inside the parentheses, 200 is the capacity of the memory pool in bytes.
// Don't forget to change this value to match your JSON document.
// Use https://arduinojson.org/v6/assistant to compute the capacity.
JsonDocument doc(200);
JsonDocument doc;
// MessagePack input string.
//
// Using a char[], as shown here, enables the "zero-copy" mode. This mode uses
// the minimal amount of memory because the JsonDocument stores pointers to
// the input buffer.
// If you use another type of input, ArduinoJson must copy the strings from
// the input to the JsonDocument, so you need to increase the capacity of the
// JsonDocument.
// The MessagePack input string
uint8_t input[] = {131, 166, 115, 101, 110, 115, 111, 114, 163, 103, 112, 115,
164, 116, 105, 109, 101, 206, 80, 147, 50, 248, 164, 100,
97, 116, 97, 146, 203, 64, 72, 96, 199, 58, 188, 148,
@@ -41,16 +30,17 @@ void setup() {
// "data": [48.75608, 2.302038]
// }
// Parse the input
DeserializationError error = deserializeMsgPack(doc, input);
// Test if parsing succeeded.
// Test if parsing succeeded
if (error) {
Serial.print("deserializeMsgPack() failed: ");
Serial.println(error.f_str());
return;
}
// Fetch values.
// Fetch the values
//
// Most of the time, you can rely on the implicit casts.
// In other case, you can do doc["time"].as<long>();
@@ -59,7 +49,7 @@ void setup() {
double latitude = doc["data"][0];
double longitude = doc["data"][1];
// Print values.
// Print the values
Serial.println(sensor);
Serial.println(time);
Serial.println(latitude, 6);

View File

@@ -1,5 +1,5 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
//
// This example shows the different ways you can use Flash strings with
@@ -9,12 +9,12 @@
// JsonDocument. Prefer plain old char*, as they are more efficient in term of
// code size, speed, and memory usage.
//
// https://arduinojson.org/v6/example/progmem/
// https://arduinojson.org/v7/example/progmem/
#include <ArduinoJson.h>
void setup() {
JsonDocument doc(1024);
JsonDocument doc;
// You can use a Flash String as your JSON input.
// WARNING: the strings in the input will be duplicated in the JsonDocument.

View File

@@ -1,5 +1,5 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
//
// This example shows the different ways you can use String with ArduinoJson.
@@ -8,12 +8,12 @@
// JsonDocument. Prefer plain old char[], as they are more efficient in term of
// code size, speed, and memory usage.
//
// https://arduinojson.org/v6/example/string/
// https://arduinojson.org/v7/example/string/
#include <ArduinoJson.h>
void setup() {
JsonDocument doc(1024);
JsonDocument doc;
// You can use a String as your JSON input.
// WARNING: the string in the input will be duplicated in the JsonDocument.
@@ -55,7 +55,6 @@ void setup() {
}
// Lastly, you can print the resulting JSON to a String
// WARNING: it doesn't replace the content but appends to it
String output;
serializeJson(doc, output);
}

View File

@@ -1,3 +1,7 @@
if(NOT DEFINED COVERAGE)
set(COVERAGE OFF)
endif()
if(CMAKE_CXX_COMPILER_ID MATCHES "(GNU|Clang)")
add_compile_options(
-pedantic
@@ -30,10 +34,20 @@ if(CMAKE_CXX_COMPILER_ID MATCHES "(GNU|Clang)")
endif()
if(CMAKE_CXX_COMPILER_ID STREQUAL "GNU")
if((CMAKE_CXX_COMPILER_VERSION VERSION_GREATER 4.8) AND(NOT ${COVERAGE}))
if((CMAKE_CXX_COMPILER_VERSION VERSION_GREATER 4.9) AND(NOT ${COVERAGE}))
add_compile_options(-g -Og)
else()
add_compile_options(-g -O0)
else() # GCC 4.8
add_compile_options(
-g
-O0 # GCC 4.8 doesn't support -Og
-Wno-shadow # allow the same name for a function parameter and a member functions
-Wp,-w # Disable preprocessing warnings (see below)
)
# GCC 4.8 doesn't support __has_include, so we need to help him
add_definitions(
-DARDUINOJSON_ENABLE_STD_STRING=1
-DARDUINOJSON_ENABLE_STD_STREAM=1
)
endif()
add_compile_options(
@@ -64,6 +78,9 @@ if(CMAKE_CXX_COMPILER_ID MATCHES "Clang")
endif()
if(CMAKE_CXX_COMPILER_ID STREQUAL "Clang")
add_compile_options(-stdlib=libc++)
link_libraries(c++ m)
if((CMAKE_CXX_COMPILER_VERSION VERSION_GREATER 4.0) AND(NOT ${COVERAGE}))
add_compile_options(-g -Og)
else()

View File

@@ -1,5 +1,5 @@
# ArduinoJson - https://arduinojson.org
# Copyright © 2014-2023, Benoit BLANCHON
# Copyright © 2014-2025, Benoit BLANCHON
# MIT License
cmake_minimum_required(VERSION 3.5)

View File

@@ -1,5 +1,5 @@
# ArduinoJson - https://arduinojson.org
# Copyright © 2014-2023, Benoit BLANCHON
# Copyright © 2014-2025, Benoit BLANCHON
# MIT License
idf_component_register(

View File

@@ -1,12 +1,12 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#include <ArduinoJson.h>
extern "C" void app_main() {
char buffer[256];
JsonDocument doc(200);
JsonDocument doc;
doc["hello"] = "world";
serializeJson(doc, buffer);

View File

@@ -4,15 +4,15 @@ static_assert(ARDUINOJSON_ENABLE_PROGMEM == 1, "ARDUINOJSON_ENABLE_PROGMEM");
static_assert(ARDUINOJSON_USE_LONG_LONG == 0, "ARDUINOJSON_USE_LONG_LONG");
static_assert(ARDUINOJSON_SLOT_OFFSET_SIZE == 1,
"ARDUINOJSON_SLOT_OFFSET_SIZE");
static_assert(ARDUINOJSON_SLOT_ID_SIZE == 1, "ARDUINOJSON_SLOT_ID_SIZE");
static_assert(ARDUINOJSON_POOL_CAPACITY == 16, "ARDUINOJSON_POOL_CAPACITY");
static_assert(ARDUINOJSON_LITTLE_ENDIAN == 1, "ARDUINOJSON_LITTLE_ENDIAN");
static_assert(ARDUINOJSON_USE_DOUBLE == 1, "ARDUINOJSON_USE_DOUBLE");
static_assert(ARDUINOJSON_USE_DOUBLE == 0, "ARDUINOJSON_USE_DOUBLE");
static_assert(sizeof(ArduinoJson::detail::VariantSlot) == 8,
"sizeof(VariantSlot)");
static_assert(sizeof(ArduinoJson::detail::VariantData) == 6, "slot size");
void setup() {}
void loop() {}

View File

@@ -2,15 +2,15 @@
static_assert(ARDUINOJSON_USE_LONG_LONG == 1, "ARDUINOJSON_USE_LONG_LONG");
static_assert(ARDUINOJSON_SLOT_OFFSET_SIZE == 2,
"ARDUINOJSON_SLOT_OFFSET_SIZE");
static_assert(ARDUINOJSON_SLOT_ID_SIZE == 2, "ARDUINOJSON_SLOT_ID_SIZE");
static_assert(ARDUINOJSON_POOL_CAPACITY == 128, "ARDUINOJSON_POOL_CAPACITY");
static_assert(ARDUINOJSON_LITTLE_ENDIAN == 1, "ARDUINOJSON_LITTLE_ENDIAN");
static_assert(ARDUINOJSON_USE_DOUBLE == 1, "ARDUINOJSON_USE_DOUBLE");
static_assert(sizeof(ArduinoJson::detail::VariantSlot) == 16,
"sizeof(VariantSlot)");
static_assert(sizeof(ArduinoJson::detail::VariantData) == 8, "slot size");
void setup() {}
void loop() {}

View File

@@ -2,14 +2,14 @@
static_assert(ARDUINOJSON_USE_LONG_LONG == 1, "ARDUINOJSON_USE_LONG_LONG");
static_assert(ARDUINOJSON_SLOT_OFFSET_SIZE == 4,
"ARDUINOJSON_SLOT_OFFSET_SIZE");
static_assert(ARDUINOJSON_SLOT_ID_SIZE == 4, "ARDUINOJSON_SLOT_ID_SIZE");
static_assert(ARDUINOJSON_POOL_CAPACITY == 256, "ARDUINOJSON_POOL_CAPACITY");
static_assert(ARDUINOJSON_LITTLE_ENDIAN == 1, "ARDUINOJSON_LITTLE_ENDIAN");
static_assert(ARDUINOJSON_USE_DOUBLE == 1, "ARDUINOJSON_USE_DOUBLE");
static_assert(sizeof(ArduinoJson::detail::VariantSlot) == 32,
"sizeof(VariantSlot)");
static_assert(sizeof(ArduinoJson::detail::VariantData) == 16, "slot size");
int main() {}

View File

@@ -2,14 +2,14 @@
static_assert(ARDUINOJSON_USE_LONG_LONG == 1, "ARDUINOJSON_USE_LONG_LONG");
static_assert(ARDUINOJSON_SLOT_OFFSET_SIZE == 2,
"ARDUINOJSON_SLOT_OFFSET_SIZE");
static_assert(ARDUINOJSON_SLOT_ID_SIZE == 2, "ARDUINOJSON_SLOT_ID_SIZE");
static_assert(ARDUINOJSON_POOL_CAPACITY == 128, "ARDUINOJSON_POOL_CAPACITY");
static_assert(ARDUINOJSON_LITTLE_ENDIAN == 1, "ARDUINOJSON_LITTLE_ENDIAN");
static_assert(ARDUINOJSON_USE_DOUBLE == 1, "ARDUINOJSON_USE_DOUBLE");
static_assert(sizeof(ArduinoJson::detail::VariantSlot) == 16,
"sizeof(VariantSlot)");
static_assert(sizeof(ArduinoJson::detail::VariantData) == 8, "slot size");
int main() {}

View File

@@ -1,5 +1,5 @@
# ArduinoJson - https://arduinojson.org
# Copyright © 2014-2023, Benoit BLANCHON
# Copyright © 2014-2025, Benoit BLANCHON
# MIT License
set(CMAKE_CXX_STANDARD 11)
@@ -52,7 +52,16 @@ macro(add_fuzzer name)
)
endmacro()
if(CMAKE_CXX_COMPILER_ID STREQUAL "Clang" AND CMAKE_CXX_COMPILER_VERSION VERSION_GREATER 6)
# Needs Clang 6+ to compile
if(CMAKE_CXX_COMPILER_ID STREQUAL "Clang" AND CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 6)
if(DEFINED ENV{GITHUB_ACTIONS} AND CMAKE_CXX_COMPILER_VERSION MATCHES "^11\\.")
# Clang 11 fails on GitHub Actions with the following error:
# > ERROR: UndefinedBehaviorSanitizer failed to allocate 0x0 (0) bytes of SetAlternateSignalStack (error code: 22)
# > Sanitizer CHECK failed: /build/llvm-toolchain-11-mnvtwk/llvm-toolchain-11-11.1.0/compiler-rt/lib/sanitizer_common/sanitizer_common.cpp:54 ((0 && "unable to mmap")) != (0) (0, 0)
message(WARNING "Fuzzing is disabled on GitHub Actions to workaround a bug in Clang 11")
return()
endif()
add_fuzzer(json)
add_fuzzer(msgpack)
endif()

View File

@@ -1,7 +1,7 @@
#include <ArduinoJson.h>
extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size) {
JsonDocument doc(4096);
JsonDocument doc;
DeserializationError error = deserializeJson(doc, data, size);
if (!error) {
std::string json;

View File

@@ -1,7 +1,7 @@
#include <ArduinoJson.h>
extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size) {
JsonDocument doc(4096);
JsonDocument doc;
DeserializationError error = deserializeMsgPack(doc, data, size);
if (!error) {
std::string json;

View File

@@ -1,5 +1,5 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
// This file is NOT use by Google's OSS fuzz

View File

@@ -1,23 +0,0 @@
#!/bin/bash
set -eu
INPUT=$1
OUTPUT=$2
cd "$INPUT"
# remove existing file
rm -f "$OUTPUT"
# create zip
7z a "$OUTPUT" \
-xr!.vs \
CHANGELOG.md \
examples \
src \
keywords.txt \
library.properties \
LICENSE.txt \
README.md \
ArduinoJson.h

View File

@@ -0,0 +1,29 @@
#!/usr/bin/awk -f
# Start echoing after the first list item
/\* / {
STARTED=1
EMPTY_LINE=0
}
# Remember if we have seen an empty line
/^[[:space:]]*$/ {
EMPTY_LINE=1
}
# Exit when seeing a new version number
/^v[[:digit:]]/ {
if (STARTED) exit
}
# Print if the line is not empty
# and restore the empty line we have skipped
!/^[[:space:]]*$/ {
if (STARTED) {
if (EMPTY_LINE) {
print ""
EMPTY_LINE=0
}
print
}
}

View File

@@ -1,14 +0,0 @@
#!/bin/bash
set -eu
TAG="$1"
CHANGELOG="$2"
cat << END
## Changes
$(awk '/\* /{ FOUND=1 } /^[[:space:]]*$/ { if(FOUND) exit } { if(FOUND) print }' "$CHANGELOG")
[View version history](https://github.com/bblanchon/ArduinoJson/blob/$TAG/CHANGELOG.md)
END

View File

@@ -4,15 +4,15 @@ set -eu
VERSION="$1"
CHANGELOG="$2"
FRONTMATTER="$3"
ARDUINOJSON_H="$3"
cat << END
---
branch: v6
branch: v7
version: $VERSION
date: '$(date +'%Y-%m-%d')'
$(cat "$FRONTMATTER")
$(extras/scripts/wandbox/publish.sh "$ARDUINOJSON_H")
---
$(awk '/\* /{ FOUND=1; print; next } { if (FOUND) exit}' "$CHANGELOG")
$(extras/scripts/extract_changes.awk "$CHANGELOG")
END

View File

@@ -2,7 +2,7 @@
set -eu
which awk sed jq 7z curl perl >/dev/null
which awk sed jq curl perl >/dev/null
cd "$(dirname "$0")/../.."
@@ -15,6 +15,7 @@ VERSION="$1"
DATE=$(date +%F)
TAG="v$VERSION"
VERSION_REGEX='[0-9]+\.[0-9]+\.[0-9]+(-[a-z0-9]+)?'
STARS=$(curl -s https://api.github.com/repos/bblanchon/ArduinoJson | jq '.stargazers_count')
update_version_in_source () {
IFS=".-" read MAJOR MINOR REVISION EXTRA < <(echo "$VERSION")
@@ -29,16 +30,25 @@ update_version_in_source () {
sed -i~ -bE "s/(project\\s*\\(ArduinoJson\\s+VERSION\\s+).*?\\)/\\1$MAJOR.$MINOR.$REVISION)/" CMakeLists.txt
rm CMakeLists.txt~
sed -i~ -bE "s/\"version\":.*$/\"version\": \"$VERSION\",/" library.json
sed -i~ -bE \
-e "s/\"version\":.*$/\"version\": \"$VERSION\",/" \
-e "s/[0-9]+ stars/$STARS stars/" \
library.json
rm library.json~
sed -i~ -bE "s/version=.*$/version=$VERSION/" library.properties
sed -i~ -bE \
-e "s/version=.*$/version=$VERSION/" \
-e "s/[0-9]+ stars/$STARS stars/" \
library.properties
rm library.properties~
sed -i~ -bE "s/version: .*$/version: $VERSION.{build}/" appveyor.yml
rm appveyor.yml~
sed -i~ -bE "s/^version: .*$/version: \"$VERSION\"/" idf_component.yml
sed -i~ -bE \
-e "s/^version: .*$/version: \"$VERSION\"/" \
-e "s/[0-9]+ stars/$STARS stars/" \
idf_component.yml
rm idf_component.yml~
sed -i~ -bE \
@@ -70,10 +80,8 @@ commit_new_version
add_tag
push
extras/scripts/build-arduino-package.sh . "../ArduinoJson-$TAG.zip"
extras/scripts/build-single-header.sh "src/ArduinoJson.h" "../ArduinoJson-$TAG.h"
extras/scripts/build-single-header.sh "src/ArduinoJson.hpp" "../ArduinoJson-$TAG.hpp"
extras/scripts/wandbox/publish.sh "../ArduinoJson-$TAG.h" > "../ArduinoJson-$TAG-wandbox.txt" || echo "Wandbox failed!"
extras/scripts/get-release-page.sh "$VERSION" "CHANGELOG.md" "../ArduinoJson-$TAG-wandbox.txt" > "../ArduinoJson-$TAG.md"
extras/scripts/get-release-page.sh "$VERSION" "CHANGELOG.md" "../ArduinoJson-$TAG.h" > "../ArduinoJson-$TAG.md"
echo "You can now copy ../ArduinoJson-$TAG.md into arduinojson.org/collections/_versions/$VERSION.md"

View File

@@ -1,5 +1,5 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
//
// This example shows how to generate a JSON document with ArduinoJson.
@@ -9,25 +9,18 @@
int main() {
// Allocate the JSON document
//
// Inside the parentheses, 200 is the RAM allocated to this document.
// Don't forget to change this value to match your requirement.
// Use https://arduinojson.org/v6/assistant to compute the capacity.
JsonDocument doc(200);
JsonDocument doc;
// Add values in the document
//
// Add values in the document.
doc["sensor"] = "gps";
doc["time"] = 1351824120;
// Add an array.
//
JsonArray data = doc.createNestedArray("data");
// Add an array
JsonArray data = doc["data"].to<JsonArray>();
data.add(48.756080);
data.add(2.302038);
// Generate the minified JSON and send it to STDOUT
//
serializeJson(doc, std::cout);
// The above line prints:
// {"sensor":"gps","time":1351824120,"data":[48.756080,2.302038]}
@@ -36,7 +29,6 @@ int main() {
std::cout << std::endl;
// Generate the prettified JSON and send it to STDOUT
//
serializeJsonPretty(doc, std::cout);
// The above line prints:
// {

View File

@@ -1,5 +1,5 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
//
// This example shows how to deserialize a JSON document with ArduinoJson.
@@ -9,33 +9,22 @@
int main() {
// Allocate the JSON document
//
// Inside the parentheses, 200 is the capacity of the memory pool in bytes.
// Don't forget to change this value to match your JSON document.
// Use https://arduinojson.org/v6/assistant to compute the capacity.
JsonDocument doc(300);
JsonDocument doc;
// JSON input string.
//
// Using a char[], as shown here, enables the "zero-copy" mode. This mode uses
// the minimal amount of memory because the JsonDocument stores pointers to
// the input buffer.
// If you use another type of input, ArduinoJson must copy the strings from
// the input to the JsonDocument, so you need to increase the capacity of the
// JsonDocument.
char json[] =
// JSON input string
const char* json =
"{\"sensor\":\"gps\",\"time\":1351824120,\"data\":[48.756080,2.302038]}";
// Deserialize the JSON document
DeserializationError error = deserializeJson(doc, json);
// Test if parsing succeeds.
// Test if parsing succeeds
if (error) {
std::cerr << "deserializeJson() failed: " << error.c_str() << std::endl;
return 1;
}
// Fetch values.
// Fetch the values
//
// Most of the time, you can rely on the implicit casts.
// In other case, you can do doc["time"].as<long>();
@@ -44,7 +33,7 @@ int main() {
double latitude = doc["data"][0];
double longitude = doc["data"][1];
// Print values.
// Print the values
std::cout << sensor << std::endl;
std::cout << time << std::endl;
std::cout << latitude << std::endl;

View File

@@ -1,5 +1,5 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
//
// This example shows how to generate a JSON document with ArduinoJson.
@@ -9,17 +9,9 @@
int main() {
// Allocate the JSON document
//
// Inside the parentheses, 300 is the size of the memory pool in bytes.
// Don't forget to change this value to match your JSON document.
// Use https://arduinojson.org/assistant to compute the capacity.
JsonDocument doc(300);
JsonDocument doc;
// MessagePack input string.
//
// It's better to use a char[] as shown here.
// If you use a const char* or a String, ArduinoJson will
// have to make a copy of the input in the JsonBuffer.
// The MessagePack input string
uint8_t input[] = {131, 166, 115, 101, 110, 115, 111, 114, 163, 103, 112, 115,
164, 116, 105, 109, 101, 206, 80, 147, 50, 248, 164, 100,
97, 116, 97, 146, 203, 64, 72, 96, 199, 58, 188, 148,
@@ -31,20 +23,16 @@ int main() {
// "data": [48.75608, 2.302038]
// }
// doc of the object tree.
//
// It's a reference to the JsonObject, the actual bytes are inside the
// JsonBuffer with all the other nodes of the object tree.
// Memory is freed when jsonBuffer goes out of scope.
// Parse the input
DeserializationError error = deserializeMsgPack(doc, input);
// Test if parsing succeeds.
// Test if parsing succeeds
if (error) {
std::cerr << "deserializeMsgPack() failed: " << error.c_str() << std::endl;
return 1;
}
// Fetch values.
// Fetch the values
//
// Most of the time, you can rely on the implicit casts.
// In other case, you can do doc["time"].as<long>();
@@ -53,7 +41,7 @@ int main() {
double latitude = doc["data"][0];
double longitude = doc["data"][1];
// Print values.
// Print the values
std::cout << sensor << std::endl;
std::cout << time << std::endl;
std::cout << latitude << std::endl;

View File

@@ -15,7 +15,7 @@ compile() {
"code":$(read_string "$FILE_PATH"),
"codes": [{"file":"ArduinoJson.h","code":$(read_string "$ARDUINOJSON_H")}],
"options": "warning,c++11",
"compiler": "gcc-5.5.0",
"compiler": "gcc-head",
"save": true
}
END

View File

@@ -1,25 +1,32 @@
# ArduinoJson - https://arduinojson.org
# Copyright © 2014-2023, Benoit BLANCHON
# Copyright © 2014-2025, Benoit BLANCHON
# MIT License
set(CMAKE_CXX_STANDARD 11)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
add_subdirectory(catch)
link_libraries(ArduinoJson)
link_libraries(ArduinoJson catch)
# Failing builds should only link with ArduinoJson, not catch
add_subdirectory(FailingBuilds)
add_subdirectory(catch)
link_libraries(catch)
include_directories(Helpers)
add_subdirectory(Cpp17)
add_subdirectory(Cpp20)
add_subdirectory(FailingBuilds)
add_subdirectory(Deprecated)
add_subdirectory(IntegrationTests)
add_subdirectory(JsonArray)
add_subdirectory(JsonArrayConst)
add_subdirectory(JsonDeserializer)
add_subdirectory(JsonDocument)
add_subdirectory(JsonObject)
add_subdirectory(JsonObjectConst)
add_subdirectory(JsonSerializer)
add_subdirectory(JsonVariant)
add_subdirectory(JsonVariantConst)
add_subdirectory(ResourceManager)
add_subdirectory(Misc)
add_subdirectory(MixedConfiguration)

View File

@@ -1,5 +1,5 @@
# ArduinoJson - https://arduinojson.org
# Copyright © 2014-2023, Benoit BLANCHON
# Copyright © 2014-2025, Benoit BLANCHON
# MIT License
if(MSVC_VERSION LESS 1910)

View File

@@ -1,17 +1,28 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
// we expect ArduinoJson.h to include <string_view>
// but we don't want it to included accidentally
#undef ARDUINO
#define ARDUINOJSON_ENABLE_STD_STREAM 0
#define ARDUINOJSON_ENABLE_STD_STRING 0
#include <ArduinoJson.h>
#include <catch.hpp>
#include <string_view>
#include "Allocators.hpp"
#include "Literals.hpp"
#if !ARDUINOJSON_ENABLE_STRING_VIEW
# error ARDUINOJSON_ENABLE_STRING_VIEW must be set to 1
#endif
using ArduinoJson::detail::sizeofArray;
using ArduinoJson::detail::sizeofString;
TEST_CASE("string_view") {
JsonDocument doc(256);
SpyingAllocator spy;
JsonDocument doc(&spy);
JsonVariant variant = doc.to<JsonVariant>();
SECTION("deserializeJson()") {
@@ -22,7 +33,7 @@ TEST_CASE("string_view") {
SECTION("JsonDocument::set()") {
doc.set(std::string_view("123", 2));
REQUIRE(doc.as<std::string>() == "12");
REQUIRE(doc.as<std::string_view>() == "12");
}
SECTION("JsonDocument::operator[]() const") {
@@ -56,18 +67,15 @@ TEST_CASE("string_view") {
SECTION("String deduplication") {
doc.add(std::string_view("example one", 7));
REQUIRE(doc.memoryUsage() == sizeofArray(1) + sizeofString(7));
doc.add(std::string_view("example two", 7));
REQUIRE(doc.memoryUsage() == sizeofArray(2) + sizeofString(7));
doc.add(std::string_view("example\0tree", 12));
REQUIRE(doc.memoryUsage() ==
sizeofArray(3) + sizeofString(7) + sizeofString(12));
doc.add(std::string_view("example\0tree and a half", 12));
REQUIRE(doc.memoryUsage() ==
sizeofArray(4) + sizeofString(7) + sizeofString(12));
REQUIRE(spy.log() == AllocatorLog{
Allocate(sizeofPool()),
Allocate(sizeofString("example")),
Allocate(sizeofString("example tree")),
});
}
SECTION("as<std::string_view>()") {
@@ -85,7 +93,7 @@ TEST_CASE("string_view") {
}
SECTION("String containing NUL") {
doc.set(std::string("hello\0world", 11));
doc.set("hello\0world"_s);
REQUIRE(doc.as<std::string_view>().size() == 11);
REQUIRE(doc.as<std::string_view>() == std::string_view("hello\0world", 11));
}

View File

@@ -1,5 +1,5 @@
# ArduinoJson - https://arduinojson.org
# Copyright © 2014-2023, Benoit BLANCHON
# Copyright © 2014-2025, Benoit BLANCHON
# MIT License
if(MSVC_VERSION LESS 1910)

View File

@@ -4,7 +4,7 @@
#include <string>
TEST_CASE("C++20 smoke test") {
JsonDocument doc(128);
JsonDocument doc;
deserializeJson(doc, "{\"hello\":\"world\"}");
REQUIRE(doc["hello"] == "world");

View File

@@ -0,0 +1,69 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#include <ArduinoJson.h>
#include <catch.hpp>
#include <string>
using ArduinoJson::detail::is_base_of;
static std::string allocatorLog;
struct CustomAllocator {
CustomAllocator() {
allocatorLog = "";
}
void* allocate(size_t n) {
allocatorLog += "A";
return malloc(n);
}
void deallocate(void* p) {
free(p);
allocatorLog += "D";
}
void* reallocate(void* p, size_t n) {
allocatorLog += "R";
return realloc(p, n);
}
};
TEST_CASE("BasicJsonDocument") {
allocatorLog.clear();
SECTION("is a JsonDocument") {
REQUIRE(
is_base_of<JsonDocument, BasicJsonDocument<CustomAllocator>>::value ==
true);
}
SECTION("deserialize / serialize") {
BasicJsonDocument<CustomAllocator> doc(256);
deserializeJson(doc, "{\"hello\":\"world\"}");
REQUIRE(doc.as<std::string>() == "{\"hello\":\"world\"}");
doc.clear();
REQUIRE(allocatorLog == "AARARDDD");
}
SECTION("copy") {
BasicJsonDocument<CustomAllocator> doc(256);
doc["hello"] = "world";
auto copy = doc;
REQUIRE(copy.as<std::string>() == "{\"hello\":\"world\"}");
REQUIRE(allocatorLog == "AAAA");
}
SECTION("capacity") {
BasicJsonDocument<CustomAllocator> doc(256);
REQUIRE(doc.capacity() == 256);
}
SECTION("garbageCollect()") {
BasicJsonDocument<CustomAllocator> doc(256);
doc.garbageCollect();
}
}

View File

@@ -0,0 +1,35 @@
# ArduinoJson - https://arduinojson.org
# Copyright © 2014-2025, Benoit BLANCHON
# MIT License
if(CMAKE_CXX_COMPILER_ID MATCHES "(GNU|Clang)")
add_compile_options(
-w
)
endif()
if(MSVC)
add_compile_options(
/wd4996
)
endif()
add_executable(DeprecatedTests
add.cpp
BasicJsonDocument.cpp
containsKey.cpp
createNestedArray.cpp
createNestedObject.cpp
DynamicJsonDocument.cpp
macros.cpp
memoryUsage.cpp
shallowCopy.cpp
StaticJsonDocument.cpp
)
add_test(Deprecated DeprecatedTests)
set_tests_properties(Deprecated
PROPERTIES
LABELS "Catch"
)

View File

@@ -0,0 +1,37 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#include <ArduinoJson.h>
#include <catch.hpp>
using ArduinoJson::detail::is_base_of;
TEST_CASE("DynamicJsonDocument") {
SECTION("is a JsonDocument") {
REQUIRE(is_base_of<JsonDocument, DynamicJsonDocument>::value == true);
}
SECTION("deserialize / serialize") {
DynamicJsonDocument doc(256);
deserializeJson(doc, "{\"hello\":\"world\"}");
REQUIRE(doc.as<std::string>() == "{\"hello\":\"world\"}");
}
SECTION("copy") {
DynamicJsonDocument doc(256);
doc["hello"] = "world";
auto copy = doc;
REQUIRE(copy.as<std::string>() == "{\"hello\":\"world\"}");
}
SECTION("capacity") {
DynamicJsonDocument doc(256);
REQUIRE(doc.capacity() == 256);
}
SECTION("garbageCollect()") {
DynamicJsonDocument doc(256);
doc.garbageCollect();
}
}

View File

@@ -0,0 +1,32 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#include <ArduinoJson.h>
#include <catch.hpp>
using ArduinoJson::detail::is_base_of;
TEST_CASE("StaticJsonDocument") {
SECTION("is a JsonDocument") {
REQUIRE(is_base_of<JsonDocument, StaticJsonDocument<256>>::value == true);
}
SECTION("deserialize / serialize") {
StaticJsonDocument<256> doc;
deserializeJson(doc, "{\"hello\":\"world\"}");
REQUIRE(doc.as<std::string>() == "{\"hello\":\"world\"}");
}
SECTION("copy") {
StaticJsonDocument<256> doc;
doc["hello"] = "world";
auto copy = doc;
REQUIRE(copy.as<std::string>() == "{\"hello\":\"world\"}");
}
SECTION("capacity") {
StaticJsonDocument<256> doc;
REQUIRE(doc.capacity() == 256);
}
}

View File

@@ -0,0 +1,38 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#include <ArduinoJson.h>
#include <catch.hpp>
TEST_CASE("JsonArray::add()") {
JsonDocument doc;
JsonArray array = doc.to<JsonArray>();
array.add().set(42);
REQUIRE(doc.as<std::string>() == "[42]");
}
TEST_CASE("JsonDocument::add()") {
JsonDocument doc;
doc.add().set(42);
REQUIRE(doc.as<std::string>() == "[42]");
}
TEST_CASE("ElementProxy::add()") {
JsonDocument doc;
doc[0].add().set(42);
REQUIRE(doc.as<std::string>() == "[[42]]");
}
TEST_CASE("MemberProxy::add()") {
JsonDocument doc;
doc["x"].add().set(42);
REQUIRE(doc.as<std::string>() == "{\"x\":[42]}");
}
TEST_CASE("JsonVariant::add()") {
JsonDocument doc;
JsonVariant v = doc.add();
v.add().set(42);
REQUIRE(doc.as<std::string>() == "[[42]]");
}

View File

@@ -0,0 +1,246 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#include <ArduinoJson.h>
#include <catch.hpp>
#include "Literals.hpp"
TEST_CASE("JsonDocument::containsKey()") {
JsonDocument doc;
SECTION("returns true on object") {
doc["hello"] = "world";
REQUIRE(doc.containsKey("hello") == true);
}
SECTION("returns true when value is null") {
doc["hello"] = static_cast<const char*>(0);
REQUIRE(doc.containsKey("hello") == true);
}
SECTION("returns true when key is a std::string") {
doc["hello"] = "world";
REQUIRE(doc.containsKey("hello"_s) == true);
}
SECTION("returns false on object") {
doc["world"] = "hello";
REQUIRE(doc.containsKey("hello") == false);
}
SECTION("returns false on array") {
doc.add("hello");
REQUIRE(doc.containsKey("hello") == false);
}
SECTION("returns false on null") {
REQUIRE(doc.containsKey("hello") == false);
}
SECTION("supports JsonVariant") {
doc["hello"] = "world";
doc["key"] = "hello";
REQUIRE(doc.containsKey(doc["key"]) == true);
REQUIRE(doc.containsKey(doc["foo"]) == false);
}
#ifdef HAS_VARIABLE_LENGTH_ARRAY
SECTION("supports VLAs") {
size_t i = 16;
char vla[i];
strcpy(vla, "hello");
doc["hello"] = "world";
REQUIRE(doc.containsKey(vla) == true);
}
#endif
}
TEST_CASE("MemberProxy::containsKey()") {
JsonDocument doc;
const auto& mp = doc["hello"];
SECTION("containsKey(const char*)") {
mp["key"] = "value";
REQUIRE(mp.containsKey("key") == true);
REQUIRE(mp.containsKey("key") == true);
}
SECTION("containsKey(std::string)") {
mp["key"] = "value";
REQUIRE(mp.containsKey("key"_s) == true);
REQUIRE(mp.containsKey("key"_s) == true);
}
#ifdef HAS_VARIABLE_LENGTH_ARRAY
SECTION("supports VLAs") {
size_t i = 16;
char vla[i];
strcpy(vla, "hello");
mp["hello"] = "world";
REQUIRE(mp.containsKey(vla) == true);
}
#endif
}
TEST_CASE("JsonObject::containsKey()") {
JsonDocument doc;
JsonObject obj = doc.to<JsonObject>();
obj["hello"] = 42;
SECTION("returns true only if key is present") {
REQUIRE(false == obj.containsKey("world"));
REQUIRE(true == obj.containsKey("hello"));
}
SECTION("returns false after remove()") {
obj.remove("hello");
REQUIRE(false == obj.containsKey("hello"));
}
#ifdef HAS_VARIABLE_LENGTH_ARRAY
SECTION("key is a VLA") {
size_t i = 16;
char vla[i];
strcpy(vla, "hello");
REQUIRE(true == obj.containsKey(vla));
}
#endif
SECTION("key is a JsonVariant") {
doc["key"] = "hello";
REQUIRE(true == obj.containsKey(obj["key"]));
REQUIRE(false == obj.containsKey(obj["hello"]));
}
SECTION("std::string") {
REQUIRE(true == obj.containsKey("hello"_s));
}
SECTION("unsigned char[]") {
unsigned char key[] = "hello";
REQUIRE(true == obj.containsKey(key));
}
}
TEST_CASE("JsonObjectConst::containsKey()") {
JsonDocument doc;
doc["hello"] = 42;
auto obj = doc.as<JsonObjectConst>();
SECTION("supports const char*") {
REQUIRE(false == obj.containsKey("world"));
REQUIRE(true == obj.containsKey("hello"));
}
SECTION("supports std::string") {
REQUIRE(false == obj.containsKey("world"_s));
REQUIRE(true == obj.containsKey("hello"_s));
}
#ifdef HAS_VARIABLE_LENGTH_ARRAY
SECTION("supports VLA") {
size_t i = 16;
char vla[i];
strcpy(vla, "hello");
REQUIRE(true == obj.containsKey(vla));
}
#endif
SECTION("supports JsonVariant") {
doc["key"] = "hello";
REQUIRE(true == obj.containsKey(obj["key"]));
REQUIRE(false == obj.containsKey(obj["hello"]));
}
}
TEST_CASE("JsonVariant::containsKey()") {
JsonDocument doc;
JsonVariant var = doc.to<JsonVariant>();
SECTION("returns false is unbound") {
CHECK_FALSE(JsonVariant().containsKey("hello"));
}
SECTION("containsKey(const char*)") {
var["hello"] = "world";
REQUIRE(var.containsKey("hello") == true);
REQUIRE(var.containsKey("world") == false);
}
SECTION("containsKey(std::string)") {
var["hello"] = "world";
REQUIRE(var.containsKey("hello"_s) == true);
REQUIRE(var.containsKey("world"_s) == false);
}
SECTION("containsKey(JsonVariant)") {
var["hello"] = "world";
var["key"] = "hello";
REQUIRE(var.containsKey(doc["key"]) == true);
REQUIRE(var.containsKey(doc["foo"]) == false);
}
#ifdef HAS_VARIABLE_LENGTH_ARRAY
SECTION("supports VLAs") {
size_t i = 16;
char vla[i];
strcpy(vla, "hello");
var["hello"] = "world";
REQUIRE(var.containsKey(vla) == true);
}
#endif
}
TEST_CASE("JsonVariantConst::containsKey()") {
JsonDocument doc;
doc["hello"] = "world";
JsonVariantConst var = doc.as<JsonVariant>();
SECTION("support const char*") {
REQUIRE(var.containsKey("hello") == true);
REQUIRE(var.containsKey("world") == false);
}
SECTION("support std::string") {
REQUIRE(var.containsKey("hello"_s) == true);
REQUIRE(var.containsKey("world"_s) == false);
}
#ifdef HAS_VARIABLE_LENGTH_ARRAY
SECTION("supports VLA") {
size_t i = 16;
char vla[i];
strcpy(vla, "hello");
REQUIRE(true == var.containsKey(vla));
}
#endif
SECTION("support JsonVariant") {
doc["key"] = "hello";
REQUIRE(var.containsKey(var["key"]) == true);
REQUIRE(var.containsKey(var["foo"]) == false);
}
}

View File

@@ -0,0 +1,113 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#include <ArduinoJson.h>
#include <catch.hpp>
#include <string>
#include "Literals.hpp"
TEST_CASE("JsonDocument::createNestedArray()") {
JsonDocument doc;
SECTION("createNestedArray()") {
JsonArray array = doc.createNestedArray();
array.add(42);
REQUIRE(doc.as<std::string>() == "[[42]]");
}
SECTION("createNestedArray(const char*)") {
JsonArray array = doc.createNestedArray("key");
array.add(42);
REQUIRE(doc.as<std::string>() == "{\"key\":[42]}");
}
SECTION("createNestedArray(std::string)") {
JsonArray array = doc.createNestedArray("key"_s);
array.add(42);
REQUIRE(doc.as<std::string>() == "{\"key\":[42]}");
}
#ifdef HAS_VARIABLE_LENGTH_ARRAY
SECTION("createNestedArray(VLA)") {
size_t i = 16;
char vla[i];
strcpy(vla, "key");
JsonArray array = doc.createNestedArray(vla);
array.add(42);
REQUIRE(doc.as<std::string>() == "{\"key\":[42]}");
}
#endif
}
TEST_CASE("JsonArray::createNestedArray()") {
JsonDocument doc;
JsonArray array = doc.to<JsonArray>();
JsonArray nestedArray = array.createNestedArray();
nestedArray.add(42);
REQUIRE(doc.as<std::string>() == "[[42]]");
}
TEST_CASE("JsonObject::createNestedArray()") {
JsonDocument doc;
JsonObject object = doc.to<JsonObject>();
SECTION("createNestedArray(const char*)") {
JsonArray array = object.createNestedArray("key");
array.add(42);
REQUIRE(doc.as<std::string>() == "{\"key\":[42]}");
}
SECTION("createNestedArray(std::string)") {
JsonArray array = object.createNestedArray("key"_s);
array.add(42);
REQUIRE(doc.as<std::string>() == "{\"key\":[42]}");
}
#ifdef HAS_VARIABLE_LENGTH_ARRAY
SECTION("createNestedArray(VLA)") {
size_t i = 16;
char vla[i];
strcpy(vla, "key");
JsonArray array = object.createNestedArray(vla);
array.add(42);
REQUIRE(doc.as<std::string>() == "{\"key\":[42]}");
}
#endif
}
TEST_CASE("JsonVariant::createNestedArray()") {
JsonDocument doc;
JsonVariant variant = doc.to<JsonVariant>();
SECTION("createNestedArray()") {
JsonArray array = variant.createNestedArray();
array.add(42);
REQUIRE(doc.as<std::string>() == "[[42]]");
}
SECTION("createNestedArray(const char*)") {
JsonArray array = variant.createNestedArray("key");
array.add(42);
REQUIRE(doc.as<std::string>() == "{\"key\":[42]}");
}
SECTION("createNestedArray(std::string)") {
JsonArray array = variant.createNestedArray("key"_s);
array.add(42);
REQUIRE(doc.as<std::string>() == "{\"key\":[42]}");
}
#ifdef HAS_VARIABLE_LENGTH_ARRAY
SECTION("createNestedArray(VLA)") {
size_t i = 16;
char vla[i];
strcpy(vla, "key");
JsonArray array = variant.createNestedArray(vla);
array.add(42);
REQUIRE(doc.as<std::string>() == "{\"key\":[42]}");
}
#endif
}

View File

@@ -0,0 +1,113 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#include <ArduinoJson.h>
#include <catch.hpp>
#include <string>
#include "Literals.hpp"
TEST_CASE("JsonDocument::createNestedObject()") {
JsonDocument doc;
SECTION("createNestedObject()") {
JsonObject object = doc.createNestedObject();
object["hello"] = "world";
REQUIRE(doc.as<std::string>() == "[{\"hello\":\"world\"}]");
}
SECTION("createNestedObject(const char*)") {
JsonObject object = doc.createNestedObject("key");
object["hello"] = "world";
REQUIRE(doc.as<std::string>() == "{\"key\":{\"hello\":\"world\"}}");
}
SECTION("createNestedObject(std::string)") {
JsonObject object = doc.createNestedObject("key"_s);
object["hello"] = "world";
REQUIRE(doc.as<std::string>() == "{\"key\":{\"hello\":\"world\"}}");
}
#ifdef HAS_VARIABLE_LENGTH_ARRAY
SECTION("createNestedObject(VLA)") {
size_t i = 16;
char vla[i];
strcpy(vla, "key");
JsonObject object = doc.createNestedObject(vla);
object["hello"] = "world";
REQUIRE(doc.as<std::string>() == "{\"key\":{\"hello\":\"world\"}}");
}
#endif
}
TEST_CASE("JsonArray::createNestedObject()") {
JsonDocument doc;
JsonArray array = doc.to<JsonArray>();
JsonObject object = array.createNestedObject();
object["hello"] = "world";
REQUIRE(doc.as<std::string>() == "[{\"hello\":\"world\"}]");
}
TEST_CASE("JsonObject::createNestedObject()") {
JsonDocument doc;
JsonObject object = doc.to<JsonObject>();
SECTION("createNestedObject(const char*)") {
JsonObject nestedObject = object.createNestedObject("key");
nestedObject["hello"] = "world";
REQUIRE(doc.as<std::string>() == "{\"key\":{\"hello\":\"world\"}}");
}
SECTION("createNestedObject(std::string)") {
JsonObject nestedObject = object.createNestedObject("key"_s);
nestedObject["hello"] = "world";
REQUIRE(doc.as<std::string>() == "{\"key\":{\"hello\":\"world\"}}");
}
#ifdef HAS_VARIABLE_LENGTH_ARRAY
SECTION("createNestedObject(VLA)") {
size_t i = 16;
char vla[i];
strcpy(vla, "key");
JsonObject nestedObject = object.createNestedObject(vla);
nestedObject["hello"] = "world";
REQUIRE(doc.as<std::string>() == "{\"key\":{\"hello\":\"world\"}}");
}
#endif
}
TEST_CASE("JsonVariant::createNestedObject()") {
JsonDocument doc;
JsonVariant variant = doc.to<JsonVariant>();
SECTION("createNestedObject()") {
JsonObject object = variant.createNestedObject();
object["hello"] = "world";
REQUIRE(doc.as<std::string>() == "[{\"hello\":\"world\"}]");
}
SECTION("createNestedObject(const char*)") {
JsonObject object = variant.createNestedObject("key");
object["hello"] = "world";
REQUIRE(doc.as<std::string>() == "{\"key\":{\"hello\":\"world\"}}");
}
SECTION("createNestedObject(std::string)") {
JsonObject object = variant.createNestedObject("key"_s);
object["hello"] = "world";
REQUIRE(doc.as<std::string>() == "{\"key\":{\"hello\":\"world\"}}");
}
#ifdef HAS_VARIABLE_LENGTH_ARRAY
SECTION("createNestedObject(VLA)") {
size_t i = 16;
char vla[i];
strcpy(vla, "key");
JsonObject object = variant.createNestedObject(vla);
object["hello"] = "world";
REQUIRE(doc.as<std::string>() == "{\"key\":{\"hello\":\"world\"}}");
}
#endif
}

View File

@@ -0,0 +1,18 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#include <ArduinoJson.h>
#include <catch.hpp>
TEST_CASE("JSON_ARRAY_SIZE") {
REQUIRE(JSON_ARRAY_SIZE(10) == ArduinoJson::detail::sizeofArray(10));
}
TEST_CASE("JSON_OBJECT_SIZE") {
REQUIRE(JSON_OBJECT_SIZE(10) == ArduinoJson::detail::sizeofObject(10));
}
TEST_CASE("JSON_STRING_SIZE") {
REQUIRE(JSON_STRING_SIZE(10) == 11); // issue #2054
}

View File

@@ -0,0 +1,51 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#include <ArduinoJson.h>
#include <catch.hpp>
TEST_CASE("JsonArray::memoryUsage()") {
JsonArray array;
REQUIRE(array.memoryUsage() == 0);
}
TEST_CASE("JsonArrayConst::memoryUsage()") {
JsonArrayConst array;
REQUIRE(array.memoryUsage() == 0);
}
TEST_CASE("JsonDocument::memoryUsage()") {
JsonDocument doc;
REQUIRE(doc.memoryUsage() == 0);
}
TEST_CASE("JsonObject::memoryUsage()") {
JsonObject array;
REQUIRE(array.memoryUsage() == 0);
}
TEST_CASE("JsonObjectConst::memoryUsage()") {
JsonObjectConst array;
REQUIRE(array.memoryUsage() == 0);
}
TEST_CASE("JsonVariant::memoryUsage()") {
JsonVariant doc;
REQUIRE(doc.memoryUsage() == 0);
}
TEST_CASE("JsonVariantConst::memoryUsage()") {
JsonVariantConst doc;
REQUIRE(doc.memoryUsage() == 0);
}
TEST_CASE("ElementProxy::memoryUsage()") {
JsonDocument doc;
REQUIRE(doc[0].memoryUsage() == 0);
}
TEST_CASE("MemberProxy::memoryUsage()") {
JsonDocument doc;
REQUIRE(doc["hello"].memoryUsage() == 0);
}

View File

@@ -0,0 +1,14 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#include <ArduinoJson.h>
#include <catch.hpp>
TEST_CASE("shallowCopy()") {
JsonDocument doc1, doc2;
doc1["b"] = "c";
doc2["a"].shallowCopy(doc1);
REQUIRE(doc2.as<std::string>() == "{\"a\":{\"b\":\"c\"}}");
}

View File

@@ -1,8 +1,12 @@
# ArduinoJson - https://arduinojson.org
# Copyright © 2014-2023, Benoit BLANCHON
# Copyright © 2014-2025, Benoit BLANCHON
# MIT License
macro(build_should_fail target)
macro(add_failing_build source_file)
get_filename_component(target ${source_file} NAME_WE)
add_executable(${target} ${source_file})
set_target_properties(${target}
PROPERTIES
EXCLUDE_FROM_ALL TRUE
@@ -16,21 +20,13 @@ macro(build_should_fail target)
set_tests_properties(${target}
PROPERTIES
WILL_FAIL TRUE
LABELS "WillFail;Catch"
LABELS "WillFail"
)
endmacro()
add_executable(Issue978 Issue978.cpp)
build_should_fail(Issue978)
add_executable(read_long_long read_long_long.cpp)
build_should_fail(read_long_long)
add_executable(write_long_long write_long_long.cpp)
build_should_fail(write_long_long)
add_executable(variant_as_char variant_as_char.cpp)
build_should_fail(variant_as_char)
add_executable(assign_char assign_char.cpp)
build_should_fail(assign_char)
add_failing_build(Issue978.cpp)
add_failing_build(read_long_long.cpp)
add_failing_build(write_long_long.cpp)
add_failing_build(variant_as_char.cpp)
add_failing_build(assign_char.cpp)
add_failing_build(deserialize_object.cpp)

View File

@@ -1,5 +1,5 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#include <ArduinoJson.h>
@@ -8,6 +8,6 @@ struct Stream {};
int main() {
Stream* stream = 0;
JsonDocument doc(1024);
JsonDocument doc;
deserializeJson(doc, stream);
}

View File

@@ -1,5 +1,5 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#include <ArduinoJson.h>
@@ -7,6 +7,6 @@
// See issue #1498
int main() {
JsonDocument doc(1024);
JsonDocument doc;
doc["dummy"] = 'A';
}

View File

@@ -0,0 +1,12 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#include <ArduinoJson.h>
// See issue #2135
int main() {
JsonObject obj;
deserializeJson(obj, "");
}

View File

@@ -1,5 +1,5 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#define ARDUINOJSON_USE_LONG_LONG 0
@@ -11,6 +11,6 @@
ARDUINOJSON_ASSERT_INTEGER_TYPE_IS_SUPPORTED(long long)
int main() {
JsonDocument doc(1024);
JsonDocument doc;
doc["dummy"].as<long long>();
}

View File

@@ -1,5 +1,5 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#include <ArduinoJson.h>
@@ -7,6 +7,6 @@
// See issue #1498
int main() {
JsonDocument doc(1024);
JsonDocument doc;
doc["dummy"].as<char>();
}

View File

@@ -1,5 +1,5 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#define ARDUINOJSON_USE_LONG_LONG 0
@@ -10,6 +10,6 @@
#endif
int main() {
JsonDocument doc(1024);
JsonDocument doc;
doc["dummy"] = static_cast<long long>(42);
}

View File

@@ -1,13 +1,17 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#pragma once
#include <ArduinoJson/Memory/Allocator.hpp>
#include <ArduinoJson/Memory/MemoryPool.hpp>
#include <ArduinoJson/Memory/StringBuilder.hpp>
#include <sstream>
namespace {
struct FailingAllocator : ArduinoJson::Allocator {
static FailingAllocator* instance() {
static FailingAllocator allocator;
@@ -29,41 +33,72 @@ struct FailingAllocator : ArduinoJson::Allocator {
}
};
class AllocatorLogEntry {
public:
AllocatorLogEntry(std::string s, size_t n = 1) : str_(s), count_(n) {}
const std::string& str() const {
return str_;
}
size_t count() const {
return count_;
}
AllocatorLogEntry operator*(size_t n) const {
return AllocatorLogEntry(str_, n);
}
private:
std::string str_;
size_t count_;
};
inline AllocatorLogEntry Allocate(size_t s) {
char buffer[32];
snprintf(buffer, sizeof(buffer), "allocate(%zu)", s);
return AllocatorLogEntry(buffer);
}
inline AllocatorLogEntry AllocateFail(size_t s) {
char buffer[32];
snprintf(buffer, sizeof(buffer), "allocate(%zu) -> nullptr", s);
return AllocatorLogEntry(buffer);
}
inline AllocatorLogEntry Reallocate(size_t s1, size_t s2) {
char buffer[32];
snprintf(buffer, sizeof(buffer), "reallocate(%zu, %zu)", s1, s2);
return AllocatorLogEntry(buffer);
}
inline AllocatorLogEntry ReallocateFail(size_t s1, size_t s2) {
char buffer[32];
snprintf(buffer, sizeof(buffer), "reallocate(%zu, %zu) -> nullptr", s1, s2);
return AllocatorLogEntry(buffer);
}
inline AllocatorLogEntry Deallocate(size_t s) {
char buffer[32];
snprintf(buffer, sizeof(buffer), "deallocate(%zu)", s);
return AllocatorLogEntry(buffer);
}
class AllocatorLog {
public:
static std::string Allocate(size_t s) {
char buffer[32];
sprintf(buffer, "allocate(%zu)", s);
return buffer;
AllocatorLog() = default;
AllocatorLog(std::initializer_list<AllocatorLogEntry> list) {
for (auto& entry : list)
append(entry);
}
static std::string AllocateFail(size_t s) {
char buffer[32];
sprintf(buffer, "allocate(%zu) -> nullptr", s);
return buffer;
void clear() {
log_.str("");
}
static std::string Reallocate(size_t s1, size_t s2) {
char buffer[32];
sprintf(buffer, "reallocate(%zu, %zu)", s1, s2);
return buffer;
};
static std::string ReallocateFail(size_t s1, size_t s2) {
char buffer[32];
sprintf(buffer, "reallocate(%zu, %zu) -> nullptr", s1, s2);
return buffer;
};
static std::string Deallocate(size_t s) {
char buffer[32];
sprintf(buffer, "deallocate(%zu)", s);
return buffer;
};
AllocatorLog& operator<<(const std::string& s) {
log_ << s << "\n";
return *this;
void append(const AllocatorLogEntry& entry) {
for (size_t i = 0; i < entry.count(); i++)
log_ << entry.str() << "\n";
}
std::string str() const {
@@ -94,43 +129,49 @@ class SpyingAllocator : public ArduinoJson::Allocator {
: upstream_(upstream) {}
virtual ~SpyingAllocator() {}
size_t allocatedBytes() const {
return allocatedBytes_;
}
void* allocate(size_t n) override {
auto block = reinterpret_cast<AllocatedBlock*>(
upstream_->allocate(sizeof(AllocatedBlock) + n - 1));
if (block) {
log_ << AllocatorLog::Allocate(n);
log_.append(Allocate(n));
allocatedBytes_ += n;
block->size = n;
return block->payload;
} else {
log_ << AllocatorLog::AllocateFail(n);
log_.append(AllocateFail(n));
return nullptr;
}
}
void deallocate(void* p) override {
auto block = AllocatedBlock::fromPayload(p);
log_ << AllocatorLog::Deallocate(block->size);
allocatedBytes_ -= block->size;
log_.append(Deallocate(block ? block->size : 0));
upstream_->deallocate(block);
}
void* reallocate(void* p, size_t n) override {
auto block = AllocatedBlock::fromPayload(p);
auto oldSize = block->size;
auto oldSize = block ? block->size : 0;
block = reinterpret_cast<AllocatedBlock*>(
upstream_->reallocate(block, sizeof(AllocatedBlock) + n - 1));
if (block) {
log_ << AllocatorLog::Reallocate(oldSize, n);
ARDUINOJSON_ASSERT(block->size == oldSize);
log_.append(Reallocate(oldSize, n));
block->size = n;
allocatedBytes_ += n - oldSize;
return block->payload;
} else {
log_ << AllocatorLog::ReallocateFail(oldSize, n);
log_.append(ReallocateFail(oldSize, n));
return nullptr;
}
}
void clearLog() {
log_ = AllocatorLog();
log_.clear();
}
const AllocatorLog& log() const {
@@ -143,6 +184,8 @@ class SpyingAllocator : public ArduinoJson::Allocator {
char payload[1];
static AllocatedBlock* fromPayload(void* p) {
if (!p)
return nullptr;
return reinterpret_cast<AllocatedBlock*>(
// Cast to void* to silence "cast increases required alignment of
// target type [-Werror=cast-align]"
@@ -153,17 +196,18 @@ class SpyingAllocator : public ArduinoJson::Allocator {
AllocatorLog log_;
Allocator* upstream_;
size_t allocatedBytes_ = 0;
};
class ControllableAllocator : public ArduinoJson::Allocator {
class KillswitchAllocator : public ArduinoJson::Allocator {
public:
ControllableAllocator(
KillswitchAllocator(
Allocator* upstream = ArduinoJson::detail::DefaultAllocator::instance())
: enabled_(true), upstream_(upstream) {}
virtual ~ControllableAllocator() {}
: working_(true), upstream_(upstream) {}
virtual ~KillswitchAllocator() {}
void* allocate(size_t n) override {
return enabled_ ? upstream_->allocate(n) : 0;
return working_ ? upstream_->allocate(n) : 0;
}
void deallocate(void* p) override {
@@ -171,15 +215,16 @@ class ControllableAllocator : public ArduinoJson::Allocator {
}
void* reallocate(void* ptr, size_t n) override {
return enabled_ ? upstream_->reallocate(ptr, n) : 0;
return working_ ? upstream_->reallocate(ptr, n) : 0;
}
void disable() {
enabled_ = false;
// Turn the killswitch on, so all allocation fail
void on() {
working_ = false;
}
private:
bool enabled_;
bool working_;
Allocator* upstream_;
};
@@ -217,3 +262,33 @@ class TimebombAllocator : public ArduinoJson::Allocator {
size_t countdown_ = 0;
Allocator* upstream_;
};
} // namespace
inline size_t sizeofPoolList(size_t n = ARDUINOJSON_INITIAL_POOL_COUNT) {
using namespace ArduinoJson::detail;
return sizeof(MemoryPool<VariantData>) * n;
}
template <typename T = ArduinoJson::detail::VariantData>
inline size_t sizeofPool(
ArduinoJson::detail::SlotCount n = ARDUINOJSON_POOL_CAPACITY) {
return ArduinoJson::detail::MemoryPool<T>::slotsToBytes(n);
}
inline size_t sizeofStaticStringPool(
ArduinoJson::detail::SlotCount n = ARDUINOJSON_POOL_CAPACITY) {
using namespace ArduinoJson::detail;
return MemoryPool<const char*>::slotsToBytes(n);
}
inline size_t sizeofStringBuffer(size_t iteration = 1) {
// returns 31, 63, 127, 255, etc.
auto capacity = ArduinoJson::detail::StringBuilder::initialCapacity;
for (size_t i = 1; i < iteration; i++)
capacity = capacity * 2 + 1;
return ArduinoJson::detail::sizeofString(capacity);
}
inline size_t sizeofString(const char* s) {
return ArduinoJson::detail::sizeofString(strlen(s));
}

View File

@@ -1,5 +1,5 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#pragma once

View File

@@ -1,5 +1,5 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2023, Benoit BLANCHON
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#pragma once

View File

@@ -0,0 +1,12 @@
// ArduinoJson - https://arduinojson.org
// Copyright © 2014-2025, Benoit BLANCHON
// MIT License
#pragma once
#include <string>
// the space before _s is required by GCC 4.8
inline std::string operator"" _s(const char* str, size_t len) {
return std::string(str, len);
}

Some files were not shown because too many files have changed in this diff Show More