guix-commits
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

branch master updated: gnu: json-c: Fix CVE-2020-12762.


From: guix-commits
Subject: branch master updated: gnu: json-c: Fix CVE-2020-12762.
Date: Thu, 06 Aug 2020 02:48:02 -0400

This is an automated email from the git hooks/post-receive script.

efraim pushed a commit to branch master
in repository guix.

The following commit(s) were added to refs/heads/master by this push:
     new 10b4048  gnu: json-c: Fix CVE-2020-12762.
10b4048 is described below

commit 10b40489742bdaa0d193c00dff1446b11c081f6a
Author: Efraim Flashner <efraim@flashner.co.il>
AuthorDate: Thu Aug 6 09:43:40 2020 +0300

    gnu: json-c: Fix CVE-2020-12762.
    
    * gnu/packages/web.scm (json-c)[replacement]: New field.
    (json-c-0.13, json-c-0.12)[source]: Add patch.
    (json-c/fixed): New variable.
    * gnu/packages/patches/json-c-CVE-2020-12762.patch,
    gnu/packages/patches/json-c--0.13-CVE-2020-12762.patch,
    gnu/packages/patches/json-c--0.12-CVE-2020-12762.patch: New files.
    * gnu/local.mk (dist_patch_DATA): Register them.
---
 gnu/local.mk                                       |   3 +
 .../patches/json-c-0.12-CVE-2020-12762.patch       | 175 ++++++++++++++++
 .../patches/json-c-0.13-CVE-2020-12762.patch       | 230 +++++++++++++++++++++
 gnu/packages/patches/json-c-CVE-2020-12762.patch   | 193 +++++++++++++++++
 gnu/packages/web.scm                               |  12 ++
 5 files changed, 613 insertions(+)

diff --git a/gnu/local.mk b/gnu/local.mk
index dee4862..2c42663 100644
--- a/gnu/local.mk
+++ b/gnu/local.mk
@@ -1137,6 +1137,9 @@ dist_patch_DATA =                                         
\
   %D%/packages/patches/iputils-libcap-compat.patch             \
   %D%/packages/patches/irrlicht-use-system-libs.patch          \
   %D%/packages/patches/isl-0.11.1-aarch64-support.patch        \
+  %D%/packages/patches/json-c-CVE-2020-12762.patch             \
+  %D%/packages/patches/json-c-0.13-CVE-2020-12762.patch        \
+  %D%/packages/patches/json-c-0.12-CVE-2020-12762.patch        \
   %D%/packages/patches/jacal-fix-texinfo.patch                 \
   %D%/packages/patches/jamvm-2.0.0-disable-branch-patching.patch       \
   %D%/packages/patches/jamvm-arm.patch                         \
diff --git a/gnu/packages/patches/json-c-0.12-CVE-2020-12762.patch 
b/gnu/packages/patches/json-c-0.12-CVE-2020-12762.patch
new file mode 100644
index 0000000..4c06d12
--- /dev/null
+++ b/gnu/packages/patches/json-c-0.12-CVE-2020-12762.patch
@@ -0,0 +1,175 @@
+https://github.com/json-c/json-c/pull/611
+https://github.com/json-c/json-c/commit/74accb17cde1b88794b2b764cabaaf1f0858656c.patch
+
+From 74accb17cde1b88794b2b764cabaaf1f0858656c Mon Sep 17 00:00:00 2001
+From: =?UTF-8?q?Bj=C3=B6rn=20Esser?= <besser82@fedoraproject.org>
+Date: Fri, 15 May 2020 20:38:40 +0200
+Subject: [PATCH] Fix CVE-2020-12762.
+
+This commit is a squashed and slightly modified backport
+of the following commits on the master branch:
+
+  * 77d935b
+  * d07b910
+  * 519dfe1
+  * a59d5ac
+---
+ linkhash.c           | 12 +++++++++++-
+ printbuf.c           | 18 +++++++++++++++++-
+ tests/test4.c        | 31 ++++++++++++++++++++++++++++++-
+ tests/test4.expected |  1 +
+ 4 files changed, 59 insertions(+), 3 deletions(-)
+
+diff --git a/linkhash.c b/linkhash.c
+index 8791a421e7..6543e171f9 100644
+--- a/linkhash.c
++++ b/linkhash.c
+@@ -10,6 +10,7 @@
+  *
+  */
+ 
++#include <assert.h>
+ #include <stdio.h>
+ #include <string.h>
+ #include <stdlib.h>
+@@ -431,6 +432,8 @@ struct lh_table* lh_table_new(int size, const char *name,
+       int i;
+       struct lh_table *t;
+ 
++      /* Allocate space for elements to avoid divisions by zero. */
++      assert(size > 0);
+       t = (struct lh_table*)calloc(1, sizeof(struct lh_table));
+       if(!t) lh_abort("lh_table_new: calloc failed\n");
+       t->count = 0;
+@@ -495,7 +498,14 @@ int lh_table_insert(struct lh_table *t, void *k, const 
void *v)
+       unsigned long h, n;
+ 
+       t->inserts++;
+-      if(t->count >= t->size * LH_LOAD_FACTOR) lh_table_resize(t, t->size * 
2);
++      if (t->count >= t->size * LH_LOAD_FACTOR) {
++              /* Avoid signed integer overflow with large tables. */
++              int new_size = (t->size > INT_MAX / 2) ? INT_MAX : (t->size * 
2);
++              if (t->size == INT_MAX)
++                      return -1;
++
++              lh_table_resize(t, new_size);
++      }
+ 
+       h = t->hash_fn(k);
+       n = h % t->size;
+diff --git a/printbuf.c b/printbuf.c
+index 9d56522000..31dd86f87d 100644
+--- a/printbuf.c
++++ b/printbuf.c
+@@ -15,6 +15,7 @@
+ 
+ #include "config.h"
+ 
++#include <limits.h>
+ #include <stdio.h>
+ #include <stdlib.h>
+ #include <string.h>
+@@ -63,7 +64,16 @@ static int printbuf_extend(struct printbuf *p, int min_size)
+       if (p->size >= min_size)
+               return 0;
+ 
+-      new_size = json_max(p->size * 2, min_size + 8);
++      /* Prevent signed integer overflows with large buffers. */
++      if (min_size > INT_MAX - 8)
++              return -1;
++      if (p->size > INT_MAX / 2)
++              new_size =  min_size + 8;
++      else {
++              new_size = p->size * 2;
++              if (new_size < min_size + 8)
++                      new_size = min_size + 8;
++      }
+ #ifdef PRINTBUF_DEBUG
+       MC_DEBUG("printbuf_memappend: realloc "
+         "bpos=%d min_size=%d old_size=%d new_size=%d\n",
+@@ -78,6 +88,9 @@ static int printbuf_extend(struct printbuf *p, int min_size)
+ 
+ int printbuf_memappend(struct printbuf *p, const char *buf, int size)
+ {
++  /* Prevent signed integer overflows with large buffers. */
++  if (size > INT_MAX - p->bpos - 1)
++    return -1;
+   if (p->size <= p->bpos + size + 1) {
+     if (printbuf_extend(p, p->bpos + size + 1) < 0)
+       return -1;
+@@ -94,6 +107,9 @@ int printbuf_memset(struct printbuf *pb, int offset, int 
charvalue, int len)
+ 
+       if (offset == -1)
+               offset = pb->bpos;
++      /* Prevent signed integer overflows with large buffers. */
++      if (len > INT_MAX - offset)
++              return -1;
+       size_needed = offset + len;
+       if (pb->size < size_needed)
+       {
+diff --git a/tests/test4.c b/tests/test4.c
+index 23e97dac1b..8b05848a13 100644
+--- a/tests/test4.c
++++ b/tests/test4.c
+@@ -2,9 +2,11 @@
+  * gcc -o utf8 utf8.c -I/home/y/include -L./.libs -ljson
+  */
+ 
++#include "config.h"
++#include <assert.h>
+ #include <stdio.h>
++#include <stdlib.h>
+ #include <string.h>
+-#include "config.h"
+ 
+ #include "json_inttypes.h"
+ #include "json_object.h"
+@@ -24,6 +26,30 @@ void print_hex( const char* s)
+       printf("\n");
+ }
+ 
++static void test_lot_of_adds(void);
++static void test_lot_of_adds()
++{
++      int ii;
++      char key[50];
++      json_object *jobj = json_object_new_object();
++      assert(jobj != NULL);
++      for (ii = 0; ii < 500; ii++)
++      {
++              snprintf(key, sizeof(key), "k%d", ii);
++              json_object *iobj = json_object_new_int(ii);
++              assert(iobj != NULL);
++              json_object_object_add(jobj, key, iobj);
++              if (json_object_object_get_ex(jobj, key, &iobj) == FALSE)
++              {
++                      fprintf(stderr, "FAILED to add object #%d\n", ii);
++                      abort();
++              }
++      }
++      printf("%s\n", json_object_to_json_string(jobj));
++      assert(json_object_object_length(jobj) == 500);
++      json_object_put(jobj);
++}
++
+ int main()
+ {
+       const char *input = 
"\"\\ud840\\udd26,\\ud840\\udd27,\\ud800\\udd26,\\ud800\\udd27\"";
+@@ -49,5 +75,8 @@ int main()
+               retval = 1;
+       }
+       json_object_put(parse_result);
++
++      test_lot_of_adds();
++
+       return retval;
+ }
+diff --git a/tests/test4.expected b/tests/test4.expected
+index 68d4336d90..cb2744012b 100644
+--- a/tests/test4.expected
++++ b/tests/test4.expected
+@@ -1,3 +1,4 @@
+ input: "\ud840\udd26,\ud840\udd27,\ud800\udd26,\ud800\udd27"
+ JSON parse result is correct: 𠄦,𠄧,𐄦,𐄧
+ PASS
++{ "k0": 0, "k1": 1, "k2": 2, "k3": 3, "k4": 4, "k5": 5, "k6": 6, "k7": 7, 
"k8": 8, "k9": 9, "k10": 10, "k11": 11, "k12": 12, "k13": 13, "k14": 14, "k15": 
15, "k16": 16, "k17": 17, "k18": 18, "k19": 19, "k20": 20, "k21": 21, "k22": 
22, "k23": 23, "k24": 24, "k25": 25, "k26": 26, "k27": 27, "k28": 28, "k29": 
29, "k30": 30, "k31": 31, "k32": 32, "k33": 33, "k34": 34, "k35": 35, "k36": 
36, "k37": 37, "k38": 38, "k39": 39, "k40": 40, "k41": 41, "k42": 42, "k43": 
43, "k44": 44, "k45": 45, "k4 [...]
diff --git a/gnu/packages/patches/json-c-0.13-CVE-2020-12762.patch 
b/gnu/packages/patches/json-c-0.13-CVE-2020-12762.patch
new file mode 100644
index 0000000..7a6743b
--- /dev/null
+++ b/gnu/packages/patches/json-c-0.13-CVE-2020-12762.patch
@@ -0,0 +1,230 @@
+https://github.com/json-c/json-c/pull/607
+https://github.com/json-c/json-c/commit/865b5a65199973bb63dff8e47a2f57e04fec9736.patch
+
+From 865b5a65199973bb63dff8e47a2f57e04fec9736 Mon Sep 17 00:00:00 2001
+From: =?UTF-8?q?Bj=C3=B6rn=20Esser?= <besser82@fedoraproject.org>
+Date: Thu, 14 May 2020 12:32:30 +0200
+Subject: [PATCH] Fix CVE-2020-12762.
+
+This commit is a squashed backport of the following commits
+on the master branch:
+
+  * 099016b7e8d70a6d5dd814e788bba08d33d48426
+  * 77d935b7ae7871a1940cd827e850e6063044ec45
+  * d07b91014986900a3a75f306d302e13e005e9d67
+  * 519dfe1591d85432986f9762d41d1a883198c157
+  * a59d5acfab4485d5133114df61785b1fc633e0c6
+---
+ arraylist.c          |  3 +++
+ linkhash.c           | 21 ++++++++++++++-------
+ printbuf.c           | 38 ++++++++++++++++++++++++++------------
+ tests/test4.c        | 30 +++++++++++++++++++++++++++++-
+ tests/test4.expected |  1 +
+ 5 files changed, 73 insertions(+), 20 deletions(-)
+
+diff --git a/arraylist.c b/arraylist.c
+index ddeb8d4eb4..e737052e32 100644
+--- a/arraylist.c
++++ b/arraylist.c
+@@ -135,6 +135,9 @@ array_list_del_idx( struct array_list *arr, size_t idx, 
size_t count )
+ {
+       size_t i, stop;
+ 
++      /* Avoid overflow in calculation with large indices. */
++      if (idx > SIZE_T_MAX - count)
++              return -1;
+       stop = idx + count;
+       if ( idx >= arr->length || stop > arr->length ) return -1;
+       for ( i = idx; i < stop; ++i ) {
+diff --git a/linkhash.c b/linkhash.c
+index 5497061a8a..6435a154ac 100644
+--- a/linkhash.c
++++ b/linkhash.c
+@@ -12,12 +12,13 @@
+ 
+ #include "config.h"
+ 
+-#include <stdio.h>
+-#include <string.h>
+-#include <stdlib.h>
++#include <assert.h>
++#include <limits.h>
+ #include <stdarg.h>
+ #include <stddef.h>
+-#include <limits.h>
++#include <stdio.h>
++#include <stdlib.h>
++#include <string.h>
+ 
+ #ifdef HAVE_ENDIAN_H
+ # include <endian.h>    /* attempt to define endianness */
+@@ -28,8 +29,8 @@
+ # include <windows.h>   /* Get InterlockedCompareExchange */
+ #endif
+ 
+-#include "random_seed.h"
+ #include "linkhash.h"
++#include "random_seed.h"
+ 
+ /* hash functions */
+ static unsigned long lh_char_hash(const void *k);
+@@ -498,7 +499,9 @@ struct lh_table* lh_table_new(int size,
+       int i;
+       struct lh_table *t;
+ 
+-      t = (struct lh_table*)calloc(1, sizeof(struct lh_table));
++      /* Allocate space for elements to avoid divisions by zero. */
++      assert(size > 0);
++      t = (struct lh_table *)calloc(1, sizeof(struct lh_table));
+       if (!t)
+               return NULL;
+ 
+@@ -577,8 +580,12 @@ int lh_table_insert_w_hash(struct lh_table *t, const void 
*k, const void *v, con
+       unsigned long n;
+ 
+       if (t->count >= t->size * LH_LOAD_FACTOR)
+-              if (lh_table_resize(t, t->size * 2) != 0)
++      {
++              /* Avoid signed integer overflow with large tables. */
++              int new_size = (t->size > INT_MAX / 2) ? INT_MAX : (t->size * 
2);
++              if (t->size == INT_MAX || lh_table_resize(t, new_size) != 0)
+                       return -1;
++      }
+ 
+       n = h % t->size;
+ 
+diff --git a/printbuf.c b/printbuf.c
+index 6c77b5defd..6fc56de455 100644
+--- a/printbuf.c
++++ b/printbuf.c
+@@ -15,6 +15,7 @@
+ 
+ #include "config.h"
+ 
++#include <limits.h>
+ #include <stdio.h>
+ #include <stdlib.h>
+ #include <string.h>
+@@ -64,10 +65,16 @@ static int printbuf_extend(struct printbuf *p, int 
min_size)
+ 
+       if (p->size >= min_size)
+               return 0;
+-
+-      new_size = p->size * 2;
+-      if (new_size < min_size + 8)
+-              new_size =  min_size + 8;
++      /* Prevent signed integer overflows with large buffers. */
++      if (min_size > INT_MAX - 8)
++              return -1;
++      if (p->size > INT_MAX / 2)
++              new_size = min_size + 8;
++      else {
++              new_size = p->size * 2;
++              if (new_size < min_size + 8)
++                      new_size = min_size + 8;
++      }
+ #ifdef PRINTBUF_DEBUG
+       MC_DEBUG("printbuf_memappend: realloc "
+         "bpos=%d min_size=%d old_size=%d new_size=%d\n",
+@@ -82,14 +89,18 @@ static int printbuf_extend(struct printbuf *p, int 
min_size)
+ 
+ int printbuf_memappend(struct printbuf *p, const char *buf, int size)
+ {
+-  if (p->size <= p->bpos + size + 1) {
+-    if (printbuf_extend(p, p->bpos + size + 1) < 0)
+-      return -1;
+-  }
+-  memcpy(p->buf + p->bpos, buf, size);
+-  p->bpos += size;
+-  p->buf[p->bpos]= '\0';
+-  return size;
++      /* Prevent signed integer overflows with large buffers. */
++      if (size > INT_MAX - p->bpos - 1)
++              return -1;
++      if (p->size <= p->bpos + size + 1)
++      {
++              if (printbuf_extend(p, p->bpos + size + 1) < 0)
++                      return -1;
++      }
++      memcpy(p->buf + p->bpos, buf, size);
++      p->bpos += size;
++      p->buf[p->bpos] = '\0';
++      return size;
+ }
+ 
+ int printbuf_memset(struct printbuf *pb, int offset, int charvalue, int len)
+@@ -98,6 +109,9 @@ int printbuf_memset(struct printbuf *pb, int offset, int 
charvalue, int len)
+ 
+       if (offset == -1)
+               offset = pb->bpos;
++      /* Prevent signed integer overflows with large buffers. */
++      if (len > INT_MAX - offset)
++              return -1;
+       size_needed = offset + len;
+       if (pb->size < size_needed)
+       {
+diff --git a/tests/test4.c b/tests/test4.c
+index fc8b79dbf4..82d3f494de 100644
+--- a/tests/test4.c
++++ b/tests/test4.c
+@@ -2,9 +2,11 @@
+  * gcc -o utf8 utf8.c -I/home/y/include -L./.libs -ljson
+  */
+ 
++#include "config.h"
++#include <assert.h>
+ #include <stdio.h>
++#include <stdlib.h>
+ #include <string.h>
+-#include "config.h"
+ 
+ #include "json_inttypes.h"
+ #include "json_object.h"
+@@ -24,6 +26,29 @@ void print_hex(const char* s)
+       putchar('\n');
+ }
+ 
++static void test_lot_of_adds(void);
++static void test_lot_of_adds()
++{
++      int ii;
++      char key[50];
++      json_object *jobj = json_object_new_object();
++      assert(jobj != NULL);
++      for (ii = 0; ii < 500; ii++)
++      {
++              snprintf(key, sizeof(key), "k%d", ii);
++              json_object *iobj = json_object_new_int(ii);
++              assert(iobj != NULL);
++              if (json_object_object_add(jobj, key, iobj))
++              {
++                      fprintf(stderr, "FAILED to add object #%d\n", ii);
++                      abort();
++              }
++      }
++      printf("%s\n", json_object_to_json_string(jobj));
++      assert(json_object_object_length(jobj) == 500);
++      json_object_put(jobj);
++}
++
+ int main(void)
+ {
+       const char *input = 
"\"\\ud840\\udd26,\\ud840\\udd27,\\ud800\\udd26,\\ud800\\udd27\"";
+@@ -49,5 +74,8 @@ int main(void)
+               retval = 1;
+       }
+       json_object_put(parse_result);
++
++      test_lot_of_adds();
++
+       return retval;
+ }
+diff --git a/tests/test4.expected b/tests/test4.expected
+index 68d4336d90..cb2744012b 100644
+--- a/tests/test4.expected
++++ b/tests/test4.expected
+@@ -1,3 +1,4 @@
+ input: "\ud840\udd26,\ud840\udd27,\ud800\udd26,\ud800\udd27"
+ JSON parse result is correct: 𠄦,𠄧,𐄦,𐄧
+ PASS
++{ "k0": 0, "k1": 1, "k2": 2, "k3": 3, "k4": 4, "k5": 5, "k6": 6, "k7": 7, 
"k8": 8, "k9": 9, "k10": 10, "k11": 11, "k12": 12, "k13": 13, "k14": 14, "k15": 
15, "k16": 16, "k17": 17, "k18": 18, "k19": 19, "k20": 20, "k21": 21, "k22": 
22, "k23": 23, "k24": 24, "k25": 25, "k26": 26, "k27": 27, "k28": 28, "k29": 
29, "k30": 30, "k31": 31, "k32": 32, "k33": 33, "k34": 34, "k35": 35, "k36": 
36, "k37": 37, "k38": 38, "k39": 39, "k40": 40, "k41": 41, "k42": 42, "k43": 
43, "k44": 44, "k45": 45, "k4 [...]
diff --git a/gnu/packages/patches/json-c-CVE-2020-12762.patch 
b/gnu/packages/patches/json-c-CVE-2020-12762.patch
new file mode 100644
index 0000000..80daa47
--- /dev/null
+++ b/gnu/packages/patches/json-c-CVE-2020-12762.patch
@@ -0,0 +1,193 @@
+https://github.com/json-c/json-c/pull/608
+https://github.com/json-c/json-c/commit/5d6fa331418d49f1bd488553fd1cfa9ab023fabb.patch
+
+From 5d6fa331418d49f1bd488553fd1cfa9ab023fabb Mon Sep 17 00:00:00 2001
+From: =?UTF-8?q?Bj=C3=B6rn=20Esser?= <besser82@fedoraproject.org>
+Date: Thu, 14 May 2020 12:32:30 +0200
+Subject: [PATCH] Fix CVE-2020-12762.
+
+This commit is a squashed backport of the following commits
+on the master branch:
+
+  * 099016b7e8d70a6d5dd814e788bba08d33d48426
+  * 77d935b7ae7871a1940cd827e850e6063044ec45
+  * d07b91014986900a3a75f306d302e13e005e9d67
+  * 519dfe1591d85432986f9762d41d1a883198c157
+  * a59d5acfab4485d5133114df61785b1fc633e0c6
+  * 26f080997d41cfdb17beab65e90c82217d0ac43b
+---
+ arraylist.c          |  3 +++
+ linkhash.c           |  9 ++++++++-
+ printbuf.c           | 18 ++++++++++++++++--
+ tests/test4.c        | 29 +++++++++++++++++++++++++++++
+ tests/test4.expected |  1 +
+ 5 files changed, 57 insertions(+), 3 deletions(-)
+
+diff --git a/arraylist.c b/arraylist.c
+index 12ad8af6d3..e5524aca75 100644
+--- a/arraylist.c
++++ b/arraylist.c
+@@ -136,6 +136,9 @@ int array_list_del_idx(struct array_list *arr, size_t idx, 
size_t count)
+ {
+       size_t i, stop;
+ 
++      /* Avoid overflow in calculation with large indices. */
++      if (idx > SIZE_T_MAX - count)
++              return -1;
+       stop = idx + count;
+       if (idx >= arr->length || stop > arr->length)
+               return -1;
+diff --git a/linkhash.c b/linkhash.c
+index 7ea58c0abf..b021ef10b0 100644
+--- a/linkhash.c
++++ b/linkhash.c
+@@ -12,6 +12,7 @@
+ 
+ #include "config.h"
+ 
++#include <assert.h>
+ #include <limits.h>
+ #include <stdarg.h>
+ #include <stddef.h>
+@@ -499,6 +500,8 @@ struct lh_table *lh_table_new(int size, lh_entry_free_fn 
*free_fn, lh_hash_fn *h
+       int i;
+       struct lh_table *t;
+ 
++      /* Allocate space for elements to avoid divisions by zero. */
++      assert(size > 0);
+       t = (struct lh_table *)calloc(1, sizeof(struct lh_table));
+       if (!t)
+               return NULL;
+@@ -578,8 +581,12 @@ int lh_table_insert_w_hash(struct lh_table *t, const void 
*k, const void *v, con
+       unsigned long n;
+ 
+       if (t->count >= t->size * LH_LOAD_FACTOR)
+-              if (lh_table_resize(t, t->size * 2) != 0)
++      {
++              /* Avoid signed integer overflow with large tables. */
++              int new_size = (t->size > INT_MAX / 2) ? INT_MAX : (t->size * 
2);
++              if (t->size == INT_MAX || lh_table_resize(t, new_size) != 0)
+                       return -1;
++      }
+ 
+       n = h % t->size;
+ 
+diff --git a/printbuf.c b/printbuf.c
+index 976c12dde5..f9b15b1191 100644
+--- a/printbuf.c
++++ b/printbuf.c
+@@ -15,6 +15,7 @@
+ 
+ #include "config.h"
+ 
++#include <limits.h>
+ #include <stdio.h>
+ #include <stdlib.h>
+ #include <string.h>
+@@ -66,9 +67,16 @@ static int printbuf_extend(struct printbuf *p, int min_size)
+       if (p->size >= min_size)
+               return 0;
+ 
+-      new_size = p->size * 2;
+-      if (new_size < min_size + 8)
++      /* Prevent signed integer overflows with large buffers. */
++      if (min_size > INT_MAX - 8)
++              return -1;
++      if (p->size > INT_MAX / 2)
+               new_size = min_size + 8;
++      else {
++              new_size = p->size * 2;
++              if (new_size < min_size + 8)
++                      new_size = min_size + 8;
++      }
+ #ifdef PRINTBUF_DEBUG
+       MC_DEBUG("printbuf_memappend: realloc "
+                "bpos=%d min_size=%d old_size=%d new_size=%d\n",
+@@ -83,6 +91,9 @@ static int printbuf_extend(struct printbuf *p, int min_size)
+ 
+ int printbuf_memappend(struct printbuf *p, const char *buf, int size)
+ {
++      /* Prevent signed integer overflows with large buffers. */
++      if (size > INT_MAX - p->bpos - 1)
++              return -1;
+       if (p->size <= p->bpos + size + 1)
+       {
+               if (printbuf_extend(p, p->bpos + size + 1) < 0)
+@@ -100,6 +111,9 @@ int printbuf_memset(struct printbuf *pb, int offset, int 
charvalue, int len)
+ 
+       if (offset == -1)
+               offset = pb->bpos;
++      /* Prevent signed integer overflows with large buffers. */
++      if (len > INT_MAX - offset)
++              return -1;
+       size_needed = offset + len;
+       if (pb->size < size_needed)
+       {
+diff --git a/tests/test4.c b/tests/test4.c
+index bd964ec789..288cec1792 100644
+--- a/tests/test4.c
++++ b/tests/test4.c
+@@ -3,12 +3,15 @@
+  */
+ 
+ #include "config.h"
++#include <assert.h>
+ #include <stdio.h>
++#include <stdlib.h>
+ #include <string.h>
+ 
+ #include "json_inttypes.h"
+ #include "json_object.h"
+ #include "json_tokener.h"
++#include "snprintf_compat.h"
+ 
+ void print_hex(const char *s)
+ {
+@@ -24,6 +27,29 @@ void print_hex(const char *s)
+       putchar('\n');
+ }
+ 
++static void test_lot_of_adds(void);
++static void test_lot_of_adds()
++{
++      int ii;
++      char key[50];
++      json_object *jobj = json_object_new_object();
++      assert(jobj != NULL);
++      for (ii = 0; ii < 500; ii++)
++      {
++              snprintf(key, sizeof(key), "k%d", ii);
++              json_object *iobj = json_object_new_int(ii);
++              assert(iobj != NULL);
++              if (json_object_object_add(jobj, key, iobj))
++              {
++                      fprintf(stderr, "FAILED to add object #%d\n", ii);
++                      abort();
++              }
++      }
++      printf("%s\n", json_object_to_json_string(jobj));
++      assert(json_object_object_length(jobj) == 500);
++      json_object_put(jobj);
++}
++
+ int main(void)
+ {
+       const char *input = 
"\"\\ud840\\udd26,\\ud840\\udd27,\\ud800\\udd26,\\ud800\\udd27\"";
+@@ -52,5 +78,8 @@ int main(void)
+               retval = 1;
+       }
+       json_object_put(parse_result);
++
++      test_lot_of_adds();
++
+       return retval;
+ }
+diff --git a/tests/test4.expected b/tests/test4.expected
+index 68d4336d90..cb2744012b 100644
+--- a/tests/test4.expected
++++ b/tests/test4.expected
+@@ -1,3 +1,4 @@
+ input: "\ud840\udd26,\ud840\udd27,\ud800\udd26,\ud800\udd27"
+ JSON parse result is correct: 𠄦,𠄧,𐄦,𐄧
+ PASS
++{ "k0": 0, "k1": 1, "k2": 2, "k3": 3, "k4": 4, "k5": 5, "k6": 6, "k7": 7, 
"k8": 8, "k9": 9, "k10": 10, "k11": 11, "k12": 12, "k13": 13, "k14": 14, "k15": 
15, "k16": 16, "k17": 17, "k18": 18, "k19": 19, "k20": 20, "k21": 21, "k22": 
22, "k23": 23, "k24": 24, "k25": 25, "k26": 26, "k27": 27, "k28": 28, "k29": 
29, "k30": 30, "k31": 31, "k32": 32, "k33": 33, "k34": 34, "k35": 35, "k36": 
36, "k37": 37, "k38": 38, "k39": 39, "k40": 40, "k41": 41, "k42": 42, "k43": 
43, "k44": 44, "k45": 45, "k4 [...]
diff --git a/gnu/packages/web.scm b/gnu/packages/web.scm
index b9c3b7f..c846bef 100644
--- a/gnu/packages/web.scm
+++ b/gnu/packages/web.scm
@@ -770,6 +770,7 @@ data.")
 
 (define-public json-c
   (package
+    (replacement json-c/fixed)
     (name "json-c")
     (version "0.14")
     (source (origin
@@ -790,6 +791,15 @@ parse JSON-formatted strings back into the C 
representation of JSON objects.
 It aims to conform to RFC 7159.")
     (license license:x11)))
 
+(define json-c/fixed
+  (package
+    (inherit json-c)
+    (name "json-c")
+    (version "0.14")
+    (source (origin
+              (inherit (package-source json-c))
+              (patches (search-patches "json-c-CVE-2020-12762.patch"))))))
+
 ;; TODO: Remove these old versions when all dependents have been updated.
 (define-public json-c-0.13
   (package
@@ -802,6 +812,7 @@ It aims to conform to RFC 7159.")
                    version ".tar.gz"))
              (sha256
               (base32 "0ws8dz9nk8q2c0gbf66kg2r6mrkl7kamd3gpdv9zsyrz9n6n0zmq"))
+              (patches (search-patches "json-c-0.13-CVE-2020-12762.patch"))
              (modules '((guix build utils)))
              (snippet
               '(begin
@@ -824,6 +835,7 @@ It aims to conform to RFC 7159.")
                    version ".tar.gz"))
              (sha256
               (base32 "08qibrq29a5v7g23wi5icy6l4fbfw90h9ccps6vq0bcklx8n84ra"))
+              (patches (search-patches "json-c-0.12-CVE-2020-12762.patch"))
              (modules '((guix build utils)))
              (snippet
               '(begin



reply via email to

[Prev in Thread] Current Thread [Next in Thread]