/src/open62541/tests/fuzz/fuzz_xml_decode_encode.cc
Line | Count | Source (jump to first uncovered line) |
1 | | /* This Source Code Form is subject to the terms of the Mozilla Public |
2 | | * License, v. 2.0. If a copy of the MPL was not distributed with this |
3 | | * file, You can obtain one at http://mozilla.org/MPL/2.0/. |
4 | | * |
5 | | * Copyright 2018 (c) Fraunhofer IOSB (Author: Julius Pfrommer) |
6 | | */ |
7 | | |
8 | | #include <open62541/types.h> |
9 | | |
10 | | /* Decode a message, then encode, decode, encode. |
11 | | * The two encodings must be bit-equal. */ |
12 | | extern "C" int |
13 | 12.1k | LLVMFuzzerTestOneInput(uint8_t *data, size_t size) { |
14 | 12.1k | UA_ByteString buf; |
15 | 12.1k | buf.data = (UA_Byte*)data; |
16 | 12.1k | buf.length = size; |
17 | | |
18 | 12.1k | UA_Variant value; |
19 | 12.1k | UA_Variant_init(&value); |
20 | | |
21 | 12.1k | UA_StatusCode retval = UA_decodeXml(&buf, &value, &UA_TYPES[UA_TYPES_VARIANT], NULL); |
22 | 12.1k | if(retval != UA_STATUSCODE_GOOD) |
23 | 7.80k | return 0; |
24 | | |
25 | | /* This can fail for now. For example length limits are not always computed |
26 | | * 100% identical between encoding and decoding. */ |
27 | 4.30k | size_t xmlSize = UA_calcSizeXml(&value, &UA_TYPES[UA_TYPES_VARIANT], NULL); |
28 | 4.30k | if(xmlSize == 0) { |
29 | 117 | UA_Variant_clear(&value); |
30 | 117 | return 0; |
31 | 117 | } |
32 | | |
33 | 4.19k | UA_ByteString buf2 = UA_BYTESTRING_NULL; |
34 | 4.19k | retval = UA_ByteString_allocBuffer(&buf2, xmlSize); |
35 | 4.19k | if(retval != UA_STATUSCODE_GOOD) { |
36 | 0 | UA_Variant_clear(&value); |
37 | 0 | return 0; |
38 | 0 | } |
39 | | |
40 | 4.19k | retval = UA_encodeXml(&value, &UA_TYPES[UA_TYPES_VARIANT], &buf2, NULL); |
41 | 4.19k | UA_assert(retval == UA_STATUSCODE_GOOD); |
42 | | |
43 | 4.19k | UA_Variant value2; |
44 | 4.19k | UA_Variant_init(&value2); |
45 | 4.19k | retval = UA_decodeXml(&buf2, &value2, &UA_TYPES[UA_TYPES_VARIANT], NULL); |
46 | 4.19k | if(retval == UA_STATUSCODE_BADOUTOFMEMORY) { |
47 | 0 | UA_Variant_clear(&value); |
48 | 0 | UA_ByteString_clear(&buf2); |
49 | 0 | return 0; |
50 | 0 | } |
51 | 4.19k | UA_assert(retval == UA_STATUSCODE_GOOD); |
52 | | |
53 | 4.19k | UA_assert(UA_order(&value, &value2, &UA_TYPES[UA_TYPES_VARIANT]) == UA_ORDER_EQ); |
54 | | |
55 | 4.19k | UA_ByteString buf3 = UA_BYTESTRING_NULL; |
56 | 4.19k | retval = UA_ByteString_allocBuffer(&buf3, xmlSize); |
57 | 4.19k | if(retval != UA_STATUSCODE_GOOD) { |
58 | 0 | UA_Variant_clear(&value); |
59 | 0 | UA_Variant_clear(&value2); |
60 | 0 | UA_ByteString_clear(&buf2); |
61 | 0 | return 0; |
62 | 0 | } |
63 | | |
64 | 4.19k | retval = UA_encodeXml(&value2, &UA_TYPES[UA_TYPES_VARIANT], &buf3, NULL); |
65 | 4.19k | UA_assert(retval == UA_STATUSCODE_GOOD); |
66 | | |
67 | 4.19k | UA_assert(buf2.length == buf3.length); |
68 | 4.19k | UA_assert(memcmp(buf2.data, buf3.data, buf2.length) == 0); |
69 | | |
70 | 4.19k | UA_Variant_clear(&value); |
71 | 4.19k | UA_Variant_clear(&value2); |
72 | 4.19k | UA_ByteString_clear(&buf2); |
73 | 4.19k | UA_ByteString_clear(&buf3); |
74 | 4.19k | return 0; |
75 | 4.19k | } |