You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
77 lines
2.2 KiB
77 lines
2.2 KiB
8 years ago
|
From ba52f94929822b1968f05cfbb37985af2e0b83a4 Mon Sep 17 00:00:00 2001
|
||
|
From: Florian Forster <octo@collectd.org>
|
||
|
Date: Tue, 13 Sep 2016 10:44:46 +0200
|
||
|
Subject: [PATCH] curl_json plugin: Skip unexpected non-map values.
|
||
|
|
||
|
Assume, for example, the config `Key "*/foo"`. This config expects JSON
|
||
|
in the form:
|
||
|
|
||
|
{
|
||
|
"bar": {
|
||
|
"foo": 1337
|
||
|
}
|
||
|
}
|
||
|
|
||
|
If the available JSON is instead:
|
||
|
|
||
|
{
|
||
|
"error_code": 0,
|
||
|
"bar": {
|
||
|
"foo": 1337
|
||
|
}
|
||
|
}
|
||
|
|
||
|
the code will take a look at the zero associated with "error_code" and
|
||
|
determine that a map (with key "foo") is expected instead. Previously
|
||
|
the code would continue, eventually calling `cj_get_type()` which
|
||
|
expects that `key->type` is a valid pointer, resulting in a segmentation
|
||
|
fault.
|
||
|
|
||
|
This patch does three things to ensure that this segmentation fault does
|
||
|
not happen again:
|
||
|
|
||
|
1. `cj_get_type()` checks its argument to make sure it is valid before
|
||
|
dereferencing any pointers.
|
||
|
2. In case a non-map is found when a map is expected, the code will
|
||
|
return instead of limping on.
|
||
|
3. After calling `cj_cb_inc_array_index()`, which may update the key,
|
||
|
make sure that it actually did and that key is valid now.
|
||
|
|
||
|
Fixes: #1896
|
||
|
---
|
||
|
src/curl_json.c | 10 ++++++++--
|
||
|
1 file changed, 8 insertions(+), 2 deletions(-)
|
||
|
|
||
|
diff --git a/src/curl_json.c b/src/curl_json.c
|
||
|
index 4188f37..a547ddc 100644
|
||
|
--- a/src/curl_json.c
|
||
|
+++ b/src/curl_json.c
|
||
|
@@ -143,6 +143,9 @@ static int cj_get_type (cj_key_t *key)
|
||
|
{
|
||
|
const data_set_t *ds;
|
||
|
|
||
|
+ if ((key == NULL) || !CJ_IS_KEY (key))
|
||
|
+ return -EINVAL;
|
||
|
+
|
||
|
ds = plugin_get_ds (key->type);
|
||
|
if (ds == NULL)
|
||
|
{
|
||
|
@@ -226,12 +229,15 @@ static int cj_cb_number (void *ctx,
|
||
|
buffer[sizeof (buffer) - 1] = 0;
|
||
|
|
||
|
if ((key == NULL) || !CJ_IS_KEY (key)) {
|
||
|
- if (key != NULL && !db->state[db->depth].in_array/*can be inhomogeneous*/)
|
||
|
+ if (key != NULL && !db->state[db->depth].in_array/*can be inhomogeneous*/) {
|
||
|
NOTICE ("curl_json plugin: Found \"%s\", but the configuration expects"
|
||
|
" a map.", buffer);
|
||
|
+ return (CJ_CB_CONTINUE);
|
||
|
+ }
|
||
|
+
|
||
|
cj_cb_inc_array_index (ctx, /* update_key = */ 1);
|
||
|
key = db->state[db->depth].key;
|
||
|
- if (key == NULL) {
|
||
|
+ if ((key == NULL) || !CJ_IS_KEY (key)) {
|
||
|
return (CJ_CB_CONTINUE);
|
||
|
}
|
||
|
}
|