summaryrefslogtreecommitdiff
path: root/core
diff options
context:
space:
mode:
authorRĂ©mi Verschelde <remi@verschelde.fr>2021-07-30 17:15:13 +0200
committerGitHub <noreply@github.com>2021-07-30 17:15:13 +0200
commitc27ef1565ff44eaacc081081b6b21b23665fbe10 (patch)
tree81feb76f016d7fd280d6d2485a273e7dd3eb0f08 /core
parent23bf04ae9acfa5ec74e960564fe91ffe683ec934 (diff)
parent324636473aa65165caeee29e9b70e2d8c21fcb96 (diff)
Merge pull request #51068 from Faless/net/4.x_marshalls_recurse
[Net] Fix Marshalls infinite recursion crash.
Diffstat (limited to 'core')
-rw-r--r--core/io/marshalls.cpp18
-rw-r--r--core/io/marshalls.h2
-rw-r--r--core/variant/variant.h5
3 files changed, 16 insertions, 9 deletions
diff --git a/core/io/marshalls.cpp b/core/io/marshalls.cpp
index 4a1d3e5212..4f85eced93 100644
--- a/core/io/marshalls.cpp
+++ b/core/io/marshalls.cpp
@@ -1031,7 +1031,8 @@ static void _encode_string(const String &p_string, uint8_t *&buf, int &r_len) {
}
}
-Error encode_variant(const Variant &p_variant, uint8_t *r_buffer, int &r_len, bool p_full_objects) {
+Error encode_variant(const Variant &p_variant, uint8_t *r_buffer, int &r_len, bool p_full_objects, int p_depth) {
+ ERR_FAIL_COND_V_MSG(p_depth > Variant::MAX_RECURSION_DEPTH, ERR_OUT_OF_MEMORY, "Potential inifite recursion detected. Bailing.");
uint8_t *buf = r_buffer;
r_len = 0;
@@ -1380,10 +1381,8 @@ Error encode_variant(const Variant &p_variant, uint8_t *r_buffer, int &r_len, bo
_encode_string(E.name, buf, r_len);
int len;
- Error err = encode_variant(obj->get(E.name), buf, len, p_full_objects);
- if (err) {
- return err;
- }
+ Error err = encode_variant(obj->get(E.name), buf, len, p_full_objects, p_depth + 1);
+ ERR_FAIL_COND_V(err, err);
ERR_FAIL_COND_V(len % 4, ERR_BUG);
r_len += len;
if (buf) {
@@ -1433,7 +1432,8 @@ Error encode_variant(const Variant &p_variant, uint8_t *r_buffer, int &r_len, bo
r_len++; //pad
*/
int len;
- encode_variant(E, buf, len, p_full_objects);
+ Error err = encode_variant(E, buf, len, p_full_objects, p_depth + 1);
+ ERR_FAIL_COND_V(err, err);
ERR_FAIL_COND_V(len % 4, ERR_BUG);
r_len += len;
if (buf) {
@@ -1441,7 +1441,8 @@ Error encode_variant(const Variant &p_variant, uint8_t *r_buffer, int &r_len, bo
}
Variant *v = d.getptr(E);
ERR_FAIL_COND_V(!v, ERR_BUG);
- encode_variant(*v, buf, len, p_full_objects);
+ err = encode_variant(*v, buf, len, p_full_objects, p_depth + 1);
+ ERR_FAIL_COND_V(err, err);
ERR_FAIL_COND_V(len % 4, ERR_BUG);
r_len += len;
if (buf) {
@@ -1462,7 +1463,8 @@ Error encode_variant(const Variant &p_variant, uint8_t *r_buffer, int &r_len, bo
for (int i = 0; i < v.size(); i++) {
int len;
- encode_variant(v.get(i), buf, len, p_full_objects);
+ Error err = encode_variant(v.get(i), buf, len, p_full_objects, p_depth + 1);
+ ERR_FAIL_COND_V(err, err);
ERR_FAIL_COND_V(len % 4, ERR_BUG);
r_len += len;
if (buf) {
diff --git a/core/io/marshalls.h b/core/io/marshalls.h
index 3ebed914a3..05804d5a46 100644
--- a/core/io/marshalls.h
+++ b/core/io/marshalls.h
@@ -213,6 +213,6 @@ public:
};
Error decode_variant(Variant &r_variant, const uint8_t *p_buffer, int p_len, int *r_len = nullptr, bool p_allow_objects = false);
-Error encode_variant(const Variant &p_variant, uint8_t *r_buffer, int &r_len, bool p_full_objects = false);
+Error encode_variant(const Variant &p_variant, uint8_t *r_buffer, int &r_len, bool p_full_objects = false, int p_depth = 0);
#endif // MARSHALLS_H
diff --git a/core/variant/variant.h b/core/variant/variant.h
index 4dc706e853..780f9b4e70 100644
--- a/core/variant/variant.h
+++ b/core/variant/variant.h
@@ -118,6 +118,11 @@ public:
VARIANT_MAX
};
+ enum {
+ // Maximum recursion depth allowed when serializing variants.
+ MAX_RECURSION_DEPTH = 1024,
+ };
+
private:
friend struct _VariantCall;
friend class VariantInternal;