We don't need to compare the map lengths directly. The memcmp is
sufficient, since the source data is big endian.
Of course, verifying for sorting requires the map has known length.
Signed-off-by: Thiago Macieira <thiago.macieira@intel.com>
The last version of Qt to support MSVC 2015 is no longer maintained, so
I'm skipping that. I'm therefore rededicating MSVC 2017 for 32-bit.
There's also no more no-tests build.
Motivation: half-precision floating point format is used to minimize storage
and traffic mostly. Application level manipulates with single and double
precision usually. So, two routines added to public API to encode/decode given
single precision value in the half precision format
Signed-off-by: S.Phirsov
Signed-off-by: Thiago Macieira <thiago.macieira@intel.com>
MSVC (and I think ICC too) are lacking the simpler, scalar instructions
to convert from single-precision to half-precision and back. Instead, we
need to use the packed data intrinsics.
Fixes#192.
Signed-off-by: Thiago Macieira <thiago.macieira@intel.com>
When a container is closed, the outer container's buffer state is
synchronised with the inner container's state.
This was previously done via:
```
CborError cbor_encoder_close_container(CborEncoder *encoder, const CborEncoder *containerEncoder)
{
if (encoder->end)
encoder->data.ptr = containerEncoder->data.ptr;
else
encoder->data.bytes_needed = containerEncoder->data.bytes_needed;
encoder->end = containerEncoder->end;
...
return CborNoError;
}
```
However, strictly speaking the inner container could have updated `end` to be `NULL` if
the buffer was too small. In that case, the outer container should carry over `bytes_needed`
and not `ptr`. However, the logic was using the outer container's "stale" view of `end`.
However, generally `sizeof(ptr)` and `sizeof(bytes_needed)` are the same, and these values
exist in a union. Therefore, the correct values where still being copied.
This change moves the synchronisation of `end` to ahead of the synchronisation of `data`.
It additionally, actually avoids this potential error by simply synchronising the full `data`
structure, thereby avoiding the conditional logic. Simplifying the code to simply:
```
encoder->end = containerEncoder->end;
encoder->data = containerEncoder->data;
```
I was getting the following error when compiling cborencoder.c as part of
QtBase for FreeBSD MIPS64:
error: explicitly assigning value of variable of type 'uint64_t' (aka 'unsigned long') to itself [-Werror,-Wself-assign]
v = cbor_htonll(v);
Signed-off-by: Alex Richardson <Alexander.Richardson@cl.cam.ac.uk>
The open_memstream.c was using GLIBC macro definition to test if the
library is building on a Linux box. This makes impossible to build
tinycbor against other C libraries, as musl for example.
Signed-off-by: Ricardo Crudo <ricardo.crudo@gmail.com>
bytestring got escaped hex string literal output format to not to confuse e.g. "\x11" bytestring with 11 integer
Signed-off-by: phirsov <41143811+phirsov@users.noreply.github.com>
cbortojson.c: initialization discards 'const' qualifier from pointer target type [-Wdiscarded-qualifiers]
Signed-off-by: Mathieu Stephan <contributors@themooltipass.com>
If a map end (Break byte) occurs before we've read the concrete item for
the value, then the map is invalid.
Fixes#167
Signed-off-by: Thiago Macieira <thiago.macieira@intel.com>
Fixed the error checking example proposed in the comments/documentation at the beginning of the file.
Changed occurrences of `if(!err)` to `if(err)`, and `cbor_assert(err)` to `cbor_assert(!err)`.
Signed-off-by: Elie El Khoury <eliekhoury@hotmail.de>
QCOMPARE macro has a return in case of failure. If a test fails inside
the encodeOne function, we log that error, but were proceeding to
perform more tests (which could fail again and produce more errors).
Signed-off-by: Thiago Macieira <thiago.macieira@intel.com>
Motivation: half-precision floating point format is used to minimize storage
and traffic mostly. Application level manipulates with single and double
precision usually. So, two routines added to public API to encode/decode given
single precision value in the half precision format
Signed-off-by: S.Phirsov
Signed-off-by: Thiago Macieira <thiago.macieira@intel.com>
See previous commit for more details. This just applies the same
technique using malloc/mmap to the the rest of the parser tests.
Signed-off-by: Thiago Macieira <thiago.macieira@intel.com>
We can only validate_number() if we know that we have a number to
validate in the first place. If we've reached the end of our string, the
content that follows is not necessarily a number (it could be a Break
byte). More importantly, we could reach the end of the buffer.
This issue was masked by the way we provided data to the parser. It
always came from read-only memory becausee of QByteArray::fromRawData(),
so valgrind never caught any issues. Using QByteArray directly wouldn't
have helped because it always inserts a terminating null byte, which
always validates as a correct number (unsigned 0) and fails to trigger
valgrind.
So we need to use malloc() directly to make Valgrind complain. And there
was already a test that did:
==26543== Invalid read of size 1
==26543== at 0x483EA10: memmove (in /usr/lib64/valgrind/vgpreload_memcheck-amd64-linux.so)
==26543== by 0x43CEEA: read_bytes_unchecked (cborinternal_p.h:239)
==26543== by 0x43CFEC: extract_number_checked (cborinternal_p.h:286)
==26543== by 0x43D3E9: validate_number (cborvalidation.c:304)
==26543== by 0x43DC7B: validate_value (cborvalidation.c:551)
==26543== by 0x43DE8C: cbor_value_validate (cborvalidation.c:645)
==26543== by 0x4328D2: tst_Parser::strictValidation() (tst_parser.cpp:1637)
==26543== by 0x434632: tst_Parser::qt_static_metacall(QObject*, QMetaObject::Call, int, void**) (tst_parser.moc:291)
==26543== by 0x4C0B36D: QMetaMethod::invoke(QObject*, Qt::ConnectionType, QGenericReturnArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument) const (qmetaobject.cpp:2310)
==26543== by 0x48673E9: QMetaMethod::invoke(QObject*, Qt::ConnectionType, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument) const (qmetaobject.h:122)
==26543== by 0x4860256: QTest::TestMethods::invokeTestOnData(int) const (qtestcase.cpp:922)
==26543== by 0x4860D4B: QTest::TestMethods::invokeTest(int, char const*, QTest::WatchDog*) const (qtestcase.cpp:1121)
==26543== Address 0x61c4db1 is 0 bytes after a block of size 1 alloc'd
==26543== at 0x483777F: malloc (in /usr/lib64/valgrind/vgpreload_memcheck-amd64-linux.so)
==26543== by 0x403891: ParserWrapper::allocateMemory(unsigned long) (tst_parser.cpp:181)
==26543== by 0x436898: ParserWrapper::init(QByteArray const&) (tst_parser.cpp:126)
==26543== by 0x432712: tst_Parser::strictValidation() (tst_parser.cpp:1634)
==26543== by 0x434632: tst_Parser::qt_static_metacall(QObject*, QMetaObject::Call, int, void**) (tst_parser.moc:291)
==26543== by 0x4C0B36D: QMetaMethod::invoke(QObject*, Qt::ConnectionType, QGenericReturnArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument) const (qmetaobject.cpp:2310)
==26543== by 0x48673E9: QMetaMethod::invoke(QObject*, Qt::ConnectionType, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument, QGenericArgument) const (qmetaobject.h:122)
==26543== by 0x4860256: QTest::TestMethods::invokeTestOnData(int) const (qtestcase.cpp:922)
==26543== by 0x4860D4B: QTest::TestMethods::invokeTest(int, char const*, QTest::WatchDog*) const (qtestcase.cpp:1121)
==26543== by 0x4862083: QTest::TestMethods::invokeTests(QObject*) const (qtestcase.cpp:1465)
==26543== by 0x4862C14: QTest::qRun() (qtestcase.cpp:1903)
==26543== by 0x48626C3: QTest::qExec(QObject*, int, char**) (qtestcase.cpp:1792)
==26543==
PASS : tst_Parser::strictValidation(bytearray-0)
This commit goes further and makes it so an out-of-bounds access will
cause a pagefault.
Fixes#156.
Signed-off-by: Thiago Macieira <thiago.macieira@intel.com>
The string chunk getter doesn't set ptr if there was an error
decoding. Instead, we need to deal with the error first.
Signed-off-by: Thiago Macieira <thiago.macieira@intel.com>
This updates to Qt 5.12, since Stephan has a build for that in his
PPA. But we need to turn off RDRNAD support for the Valgrind build, as
it doesn't understand that instruction.
This also downgrades GCC to 5.4, which is what comes by default with
Travis CI.
Signed-off-by: Thiago Macieira <thiago.macieira@intel.com>