aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorrobot-piglet <robot-piglet@yandex-team.com>2024-07-18 09:29:05 +0300
committerrobot-piglet <robot-piglet@yandex-team.com>2024-07-18 09:37:09 +0300
commit785d98a7912f39e17f8f523f1417a9a255e1f866 (patch)
tree3cd501966e45307e1a624199b41cd92aaf0cf79d
parent9a82c7b66f562796be8bb78d80c224b511876ea8 (diff)
downloadydb-785d98a7912f39e17f8f523f1417a9a255e1f866.tar.gz
Intermediate changes
-rw-r--r--contrib/libs/croaring/include/roaring/portability.h10
-rw-r--r--contrib/libs/croaring/include/roaring/roaring64.h11
-rw-r--r--contrib/libs/croaring/include/roaring/roaring_types.h4
-rw-r--r--contrib/libs/croaring/src/art/art.c13
-rw-r--r--contrib/libs/croaring/src/roaring.c6
-rw-r--r--contrib/libs/croaring/src/roaring64.c25
-rw-r--r--contrib/libs/croaring/ya.make4
-rw-r--r--contrib/python/simplejson/py2/.dist-info/METADATA3
-rw-r--r--contrib/python/simplejson/py2/simplejson/__init__.py106
-rw-r--r--contrib/python/simplejson/py2/simplejson/_speedups.c30
-rw-r--r--contrib/python/simplejson/py2/simplejson/decoder.py82
-rw-r--r--contrib/python/simplejson/py2/simplejson/encoder.py30
-rw-r--r--contrib/python/simplejson/py2/simplejson/scanner.py6
-rw-r--r--contrib/python/simplejson/py2/simplejson/tests/test_decode.py8
-rw-r--r--contrib/python/simplejson/py2/simplejson/tests/test_fail.py4
-rw-r--r--contrib/python/simplejson/py2/simplejson/tests/test_float.py7
-rw-r--r--contrib/python/simplejson/py2/simplejson/tests/test_scanstring.py4
-rw-r--r--contrib/python/simplejson/py2/ya.make2
18 files changed, 207 insertions, 148 deletions
diff --git a/contrib/libs/croaring/include/roaring/portability.h b/contrib/libs/croaring/include/roaring/portability.h
index 78081ec88e..5aebe193c9 100644
--- a/contrib/libs/croaring/include/roaring/portability.h
+++ b/contrib/libs/croaring/include/roaring/portability.h
@@ -589,6 +589,16 @@ static inline uint32_t croaring_refcount_get(const croaring_refcount_t *val) {
#define CROARING_DEPRECATED
#endif // defined(__GNUC__) || defined(__clang__)
+// We want to initialize structs to zero portably (C and C++), without
+// warnings. We can do mystruct s = CROARING_ZERO_INITIALIZER;
+#if __cplusplus
+#define CROARING_ZERO_INITIALIZER \
+ {}
+#else
+#define CROARING_ZERO_INITIALIZER \
+ { 0 }
+#endif
+
// We need portability.h to be included first,
// but we also always want isadetection.h to be
// included (right after).
diff --git a/contrib/libs/croaring/include/roaring/roaring64.h b/contrib/libs/croaring/include/roaring/roaring64.h
index acf16d65bf..c71bccb917 100644
--- a/contrib/libs/croaring/include/roaring/roaring64.h
+++ b/contrib/libs/croaring/include/roaring/roaring64.h
@@ -203,6 +203,11 @@ void roaring64_bitmap_remove_range_closed(roaring64_bitmap_t *r, uint64_t min,
uint64_t max);
/**
+ * Empties the bitmap.
+ */
+void roaring64_bitmap_clear(roaring64_bitmap_t *r);
+
+/**
* Returns true if the provided value is present.
*/
bool roaring64_bitmap_contains(const roaring64_bitmap_t *r, uint64_t val);
@@ -273,6 +278,12 @@ uint64_t roaring64_bitmap_range_cardinality(const roaring64_bitmap_t *r,
uint64_t min, uint64_t max);
/**
+ * Returns the number of elements in the range [min, max]
+ */
+uint64_t roaring64_bitmap_range_closed_cardinality(const roaring64_bitmap_t *r,
+ uint64_t min, uint64_t max);
+
+/**
* Returns true if the bitmap is empty (cardinality is zero).
*/
bool roaring64_bitmap_is_empty(const roaring64_bitmap_t *r);
diff --git a/contrib/libs/croaring/include/roaring/roaring_types.h b/contrib/libs/croaring/include/roaring/roaring_types.h
index 88f354a6b1..3a8a618945 100644
--- a/contrib/libs/croaring/include/roaring/roaring_types.h
+++ b/contrib/libs/croaring/include/roaring/roaring_types.h
@@ -8,6 +8,8 @@
#include <stdbool.h>
#include <stdint.h>
+#include <roaring/portability.h>
+
#ifdef __cplusplus
extern "C" {
namespace roaring {
@@ -89,6 +91,8 @@ typedef struct roaring_statistics_s {
max_value; /* the maximal value, undefined if cardinality is zero */
uint32_t
min_value; /* the minimal value, undefined if cardinality is zero */
+
+ CROARING_DEPRECATED
uint64_t sum_value; /* deprecated always zero */
uint64_t cardinality; /* total number of values stored in the bitmap */
diff --git a/contrib/libs/croaring/src/art/art.c b/contrib/libs/croaring/src/art/art.c
index 135cee4984..dc2f17a5d9 100644
--- a/contrib/libs/croaring/src/art/art.c
+++ b/contrib/libs/croaring/src/art/art.c
@@ -1670,7 +1670,7 @@ static bool art_node_iterator_lower_bound(const art_node_t *node,
}
art_iterator_t art_init_iterator(const art_t *art, bool first) {
- art_iterator_t iterator = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0};
+ art_iterator_t iterator = CROARING_ZERO_INITIALIZER;
if (art->root == NULL) {
return iterator;
}
@@ -1693,8 +1693,11 @@ bool art_iterator_lower_bound(art_iterator_t *iterator,
// a valid key. Start from the root.
iterator->frame = 0;
iterator->depth = 0;
- return art_node_iterator_lower_bound(art_iterator_node(iterator),
- iterator, key);
+ art_node_t *root = art_iterator_node(iterator);
+ if (root == NULL) {
+ return false;
+ }
+ return art_node_iterator_lower_bound(root, iterator, key);
}
int compare_result =
art_compare_prefix(iterator->key, 0, key, 0, ART_KEY_BYTES);
@@ -1727,7 +1730,7 @@ bool art_iterator_lower_bound(art_iterator_t *iterator,
}
art_iterator_t art_lower_bound(const art_t *art, const art_key_chunk_t *key) {
- art_iterator_t iterator = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0};
+ art_iterator_t iterator = CROARING_ZERO_INITIALIZER;
if (art->root != NULL) {
art_node_iterator_lower_bound(art->root, &iterator, key);
}
@@ -1735,7 +1738,7 @@ art_iterator_t art_lower_bound(const art_t *art, const art_key_chunk_t *key) {
}
art_iterator_t art_upper_bound(const art_t *art, const art_key_chunk_t *key) {
- art_iterator_t iterator = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0};
+ art_iterator_t iterator = CROARING_ZERO_INITIALIZER;
if (art->root != NULL) {
if (art_node_iterator_lower_bound(art->root, &iterator, key) &&
art_compare_keys(iterator.key, key) == 0) {
diff --git a/contrib/libs/croaring/src/roaring.c b/contrib/libs/croaring/src/roaring.c
index 9b7ad8002d..e3847bae92 100644
--- a/contrib/libs/croaring/src/roaring.c
+++ b/contrib/libs/croaring/src/roaring.c
@@ -199,7 +199,7 @@ roaring_bitmap_t *roaring_bitmap_of(size_t n_args, ...) {
// todo: could be greatly optimized but we do not expect this call to ever
// include long lists
roaring_bitmap_t *answer = roaring_bitmap_create();
- roaring_bulk_context_t context = {0, 0, 0, 0};
+ roaring_bulk_context_t context = CROARING_ZERO_INITIALIZER;
va_list ap;
va_start(ap, n_args);
for (size_t i = 0; i < n_args; i++) {
@@ -1541,7 +1541,7 @@ roaring_bitmap_t *roaring_bitmap_deserialize(const void *buf) {
if (bitmap == NULL) {
return NULL;
}
- roaring_bulk_context_t context = {0, 0, 0, 0};
+ roaring_bulk_context_t context = CROARING_ZERO_INITIALIZER;
for (uint32_t i = 0; i < card; i++) {
// elems may not be aligned, read with memcpy
uint32_t elem;
@@ -1584,7 +1584,7 @@ roaring_bitmap_t *roaring_bitmap_deserialize_safe(const void *buf,
if (bitmap == NULL) {
return NULL;
}
- roaring_bulk_context_t context = {0, 0, 0, 0};
+ roaring_bulk_context_t context = CROARING_ZERO_INITIALIZER;
for (uint32_t i = 0; i < card; i++) {
// elems may not be aligned, read with memcpy
uint32_t elem;
diff --git a/contrib/libs/croaring/src/roaring64.c b/contrib/libs/croaring/src/roaring64.c
index 3828abfa0e..d41507b3c4 100644
--- a/contrib/libs/croaring/src/roaring64.c
+++ b/contrib/libs/croaring/src/roaring64.c
@@ -148,6 +148,9 @@ roaring64_bitmap_t *roaring64_bitmap_create(void) {
}
void roaring64_bitmap_free(roaring64_bitmap_t *r) {
+ if (!r) {
+ return;
+ }
art_iterator_t it = art_init_iterator(&r->art, /*first=*/true);
while (it.value != NULL) {
leaf_t *leaf = (leaf_t *)it.value;
@@ -224,7 +227,7 @@ roaring64_bitmap_t *roaring64_bitmap_of_ptr(size_t n_args,
roaring64_bitmap_t *roaring64_bitmap_of(size_t n_args, ...) {
roaring64_bitmap_t *r = roaring64_bitmap_create();
- roaring64_bulk_context_t context = {0, 0, 0, 0, 0, 0, 0};
+ roaring64_bulk_context_t context = CROARING_ZERO_INITIALIZER;
va_list ap;
va_start(ap, n_args);
for (size_t i = 0; i < n_args; i++) {
@@ -317,7 +320,7 @@ void roaring64_bitmap_add_many(roaring64_bitmap_t *r, size_t n_args,
return;
}
const uint64_t *end = vals + n_args;
- roaring64_bulk_context_t context = {0, 0, 0, 0, 0, 0, 0};
+ roaring64_bulk_context_t context = CROARING_ZERO_INITIALIZER;
for (const uint64_t *current_val = vals; current_val != end;
current_val++) {
roaring64_bitmap_add_bulk(r, &context, *current_val);
@@ -641,7 +644,7 @@ void roaring64_bitmap_remove_many(roaring64_bitmap_t *r, size_t n_args,
return;
}
const uint64_t *end = vals + n_args;
- roaring64_bulk_context_t context = {0, 0, 0, 0, 0, 0, 0};
+ roaring64_bulk_context_t context = CROARING_ZERO_INITIALIZER;
for (const uint64_t *current_val = vals; current_val != end;
current_val++) {
roaring64_bitmap_remove_bulk(r, &context, *current_val);
@@ -707,6 +710,10 @@ void roaring64_bitmap_remove_range_closed(roaring64_bitmap_t *r, uint64_t min,
remove_range_closed_at(art, max_high48, 0, max_low16);
}
+void roaring64_bitmap_clear(roaring64_bitmap_t *r) {
+ roaring64_bitmap_remove_range_closed(r, 0, UINT64_MAX);
+}
+
uint64_t roaring64_bitmap_get_cardinality(const roaring64_bitmap_t *r) {
art_iterator_t it = art_init_iterator(&r->art, /*first=*/true);
uint64_t cardinality = 0;
@@ -724,7 +731,17 @@ uint64_t roaring64_bitmap_range_cardinality(const roaring64_bitmap_t *r,
if (min >= max) {
return 0;
}
- max--; // A closed range is easier to work with.
+ // Convert to a closed range
+ // No underflow here: passing the above condition implies min < max, so
+ // there is a number less than max
+ return roaring64_bitmap_range_closed_cardinality(r, min, max - 1);
+}
+
+uint64_t roaring64_bitmap_range_closed_cardinality(const roaring64_bitmap_t *r,
+ uint64_t min, uint64_t max) {
+ if (min > max) {
+ return 0;
+ }
uint64_t cardinality = 0;
uint8_t min_high48[ART_KEY_BYTES];
diff --git a/contrib/libs/croaring/ya.make b/contrib/libs/croaring/ya.make
index ce130ee6da..359cb7d137 100644
--- a/contrib/libs/croaring/ya.make
+++ b/contrib/libs/croaring/ya.make
@@ -10,9 +10,9 @@ LICENSE(
LICENSE_TEXTS(.yandex_meta/licenses.list.txt)
-VERSION(4.0.0)
+VERSION(4.1.0)
-ORIGINAL_SOURCE(https://github.com/RoaringBitmap/CRoaring/archive/v4.0.0.tar.gz)
+ORIGINAL_SOURCE(https://github.com/RoaringBitmap/CRoaring/archive/v4.1.0.tar.gz)
ADDINCL(
GLOBAL contrib/libs/croaring/include
diff --git a/contrib/python/simplejson/py2/.dist-info/METADATA b/contrib/python/simplejson/py2/.dist-info/METADATA
index 498829fb7e..7fe11c11df 100644
--- a/contrib/python/simplejson/py2/.dist-info/METADATA
+++ b/contrib/python/simplejson/py2/.dist-info/METADATA
@@ -1,6 +1,6 @@
Metadata-Version: 2.1
Name: simplejson
-Version: 3.18.4
+Version: 3.19.2
Summary: Simple, fast, extensible JSON encoder/decoder for Python
Home-page: https://github.com/simplejson/simplejson
Author: Bob Ippolito
@@ -26,6 +26,7 @@ Classifier: Programming Language :: Python :: 3.8
Classifier: Programming Language :: Python :: 3.9
Classifier: Programming Language :: Python :: 3.10
Classifier: Programming Language :: Python :: 3.11
+Classifier: Programming Language :: Python :: 3.12
Classifier: Programming Language :: Python :: Implementation :: CPython
Classifier: Programming Language :: Python :: Implementation :: PyPy
Classifier: Topic :: Software Development :: Libraries :: Python Modules
diff --git a/contrib/python/simplejson/py2/simplejson/__init__.py b/contrib/python/simplejson/py2/simplejson/__init__.py
index 47e49a318d..2d1900d8c4 100644
--- a/contrib/python/simplejson/py2/simplejson/__init__.py
+++ b/contrib/python/simplejson/py2/simplejson/__init__.py
@@ -118,7 +118,7 @@ Serializing multiple objects to JSON lines (newline-delimited JSON)::
"""
from __future__ import absolute_import
-__version__ = '3.18.4'
+__version__ = '3.19.2'
__all__ = [
'dump', 'dumps', 'load', 'loads',
'JSONDecoder', 'JSONDecodeError', 'JSONEncoder',
@@ -149,28 +149,10 @@ def _import_c_make_encoder():
except ImportError:
return None
-_default_encoder = JSONEncoder(
- skipkeys=False,
- ensure_ascii=True,
- check_circular=True,
- allow_nan=True,
- indent=None,
- separators=None,
- encoding='utf-8',
- default=None,
- use_decimal=True,
- namedtuple_as_object=True,
- tuple_as_array=True,
- iterable_as_array=False,
- bigint_as_string=False,
- item_sort_key=None,
- for_json=False,
- ignore_nan=False,
- int_as_string_bitcount=None,
-)
+_default_encoder = JSONEncoder()
def dump(obj, fp, skipkeys=False, ensure_ascii=True, check_circular=True,
- allow_nan=True, cls=None, indent=None, separators=None,
+ allow_nan=False, cls=None, indent=None, separators=None,
encoding='utf-8', default=None, use_decimal=True,
namedtuple_as_object=True, tuple_as_array=True,
bigint_as_string=False, sort_keys=False, item_sort_key=None,
@@ -187,10 +169,10 @@ def dump(obj, fp, skipkeys=False, ensure_ascii=True, check_circular=True,
contain non-ASCII characters, so long as they do not need to be escaped
by JSON. When it is true, all non-ASCII characters are escaped.
- If *allow_nan* is false, then it will be a ``ValueError`` to
- serialize out of range ``float`` values (``nan``, ``inf``, ``-inf``)
- in strict compliance of the original JSON specification, instead of using
- the JavaScript equivalents (``NaN``, ``Infinity``, ``-Infinity``). See
+ If *allow_nan* is true (default: ``False``), then out of range ``float``
+ values (``nan``, ``inf``, ``-inf``) will be serialized to
+ their JavaScript equivalents (``NaN``, ``Infinity``, ``-Infinity``)
+ instead of raising a ValueError. See
*ignore_nan* for ECMA-262 compliant behavior.
If *indent* is a string, then JSON array elements and object members
@@ -258,7 +240,7 @@ def dump(obj, fp, skipkeys=False, ensure_ascii=True, check_circular=True,
"""
# cached encoder
if (not skipkeys and ensure_ascii and
- check_circular and allow_nan and
+ check_circular and not allow_nan and
cls is None and indent is None and separators is None and
encoding == 'utf-8' and default is None and use_decimal
and namedtuple_as_object and tuple_as_array and not iterable_as_array
@@ -292,7 +274,7 @@ def dump(obj, fp, skipkeys=False, ensure_ascii=True, check_circular=True,
def dumps(obj, skipkeys=False, ensure_ascii=True, check_circular=True,
- allow_nan=True, cls=None, indent=None, separators=None,
+ allow_nan=False, cls=None, indent=None, separators=None,
encoding='utf-8', default=None, use_decimal=True,
namedtuple_as_object=True, tuple_as_array=True,
bigint_as_string=False, sort_keys=False, item_sort_key=None,
@@ -312,10 +294,11 @@ def dumps(obj, skipkeys=False, ensure_ascii=True, check_circular=True,
for container types will be skipped and a circular reference will
result in an ``OverflowError`` (or worse).
- If ``allow_nan`` is false, then it will be a ``ValueError`` to
- serialize out of range ``float`` values (``nan``, ``inf``, ``-inf``) in
- strict compliance of the JSON specification, instead of using the
- JavaScript equivalents (``NaN``, ``Infinity``, ``-Infinity``).
+ If *allow_nan* is true (default: ``False``), then out of range ``float``
+ values (``nan``, ``inf``, ``-inf``) will be serialized to
+ their JavaScript equivalents (``NaN``, ``Infinity``, ``-Infinity``)
+ instead of raising a ValueError. See
+ *ignore_nan* for ECMA-262 compliant behavior.
If ``indent`` is a string, then JSON array elements and object members
will be pretty-printed with a newline followed by that string repeated
@@ -383,7 +366,7 @@ def dumps(obj, skipkeys=False, ensure_ascii=True, check_circular=True,
"""
# cached encoder
if (not skipkeys and ensure_ascii and
- check_circular and allow_nan and
+ check_circular and not allow_nan and
cls is None and indent is None and separators is None and
encoding == 'utf-8' and default is None and use_decimal
and namedtuple_as_object and tuple_as_array and not iterable_as_array
@@ -412,14 +395,12 @@ def dumps(obj, skipkeys=False, ensure_ascii=True, check_circular=True,
**kw).encode(obj)
-_default_decoder = JSONDecoder(encoding=None, object_hook=None,
- object_pairs_hook=None)
+_default_decoder = JSONDecoder()
def load(fp, encoding=None, cls=None, object_hook=None, parse_float=None,
parse_int=None, parse_constant=None, object_pairs_hook=None,
- use_decimal=False, namedtuple_as_object=True, tuple_as_array=True,
- **kw):
+ use_decimal=False, allow_nan=False, **kw):
"""Deserialize ``fp`` (a ``.read()``-supporting file-like object containing
a JSON document as `str` or `bytes`) to a Python object.
@@ -442,23 +423,27 @@ def load(fp, encoding=None, cls=None, object_hook=None, parse_float=None,
takes priority.
*parse_float*, if specified, will be called with the string of every
- JSON float to be decoded. By default, this is equivalent to
+ JSON float to be decoded. By default, this is equivalent to
``float(num_str)``. This can be used to use another datatype or parser
for JSON floats (e.g. :class:`decimal.Decimal`).
*parse_int*, if specified, will be called with the string of every
- JSON int to be decoded. By default, this is equivalent to
+ JSON int to be decoded. By default, this is equivalent to
``int(num_str)``. This can be used to use another datatype or parser
for JSON integers (e.g. :class:`float`).
- *parse_constant*, if specified, will be called with one of the
- following strings: ``'-Infinity'``, ``'Infinity'``, ``'NaN'``. This
- can be used to raise an exception if invalid JSON numbers are
- encountered.
+ *allow_nan*, if True (default false), will allow the parser to
+ accept the non-standard floats ``NaN``, ``Infinity``, and ``-Infinity``
+ and enable the use of the deprecated *parse_constant*.
If *use_decimal* is true (default: ``False``) then it implies
parse_float=decimal.Decimal for parity with ``dump``.
+ *parse_constant*, if specified, will be
+ called with one of the following strings: ``'-Infinity'``,
+ ``'Infinity'``, ``'NaN'``. It is not recommended to use this feature,
+ as it is rare to parse non-compliant JSON containing these values.
+
To use a custom ``JSONDecoder`` subclass, specify it with the ``cls``
kwarg. NOTE: You should use *object_hook* or *object_pairs_hook* instead
of subclassing whenever possible.
@@ -468,12 +453,12 @@ def load(fp, encoding=None, cls=None, object_hook=None, parse_float=None,
encoding=encoding, cls=cls, object_hook=object_hook,
parse_float=parse_float, parse_int=parse_int,
parse_constant=parse_constant, object_pairs_hook=object_pairs_hook,
- use_decimal=use_decimal, **kw)
+ use_decimal=use_decimal, allow_nan=allow_nan, **kw)
def loads(s, encoding=None, cls=None, object_hook=None, parse_float=None,
parse_int=None, parse_constant=None, object_pairs_hook=None,
- use_decimal=False, **kw):
+ use_decimal=False, allow_nan=False, **kw):
"""Deserialize ``s`` (a ``str`` or ``unicode`` instance containing a JSON
document) to a Python object.
@@ -505,14 +490,18 @@ def loads(s, encoding=None, cls=None, object_hook=None, parse_float=None,
``int(num_str)``. This can be used to use another datatype or parser
for JSON integers (e.g. :class:`float`).
- *parse_constant*, if specified, will be called with one of the
- following strings: ``'-Infinity'``, ``'Infinity'``, ``'NaN'``. This
- can be used to raise an exception if invalid JSON numbers are
- encountered.
+ *allow_nan*, if True (default false), will allow the parser to
+ accept the non-standard floats ``NaN``, ``Infinity``, and ``-Infinity``
+ and enable the use of the deprecated *parse_constant*.
If *use_decimal* is true (default: ``False``) then it implies
parse_float=decimal.Decimal for parity with ``dump``.
+ *parse_constant*, if specified, will be
+ called with one of the following strings: ``'-Infinity'``,
+ ``'Infinity'``, ``'NaN'``. It is not recommended to use this feature,
+ as it is rare to parse non-compliant JSON containing these values.
+
To use a custom ``JSONDecoder`` subclass, specify it with the ``cls``
kwarg. NOTE: You should use *object_hook* or *object_pairs_hook* instead
of subclassing whenever possible.
@@ -521,7 +510,7 @@ def loads(s, encoding=None, cls=None, object_hook=None, parse_float=None,
if (cls is None and encoding is None and object_hook is None and
parse_int is None and parse_float is None and
parse_constant is None and object_pairs_hook is None
- and not use_decimal and not kw):
+ and not use_decimal and not allow_nan and not kw):
return _default_decoder.decode(s)
if cls is None:
cls = JSONDecoder
@@ -539,6 +528,8 @@ def loads(s, encoding=None, cls=None, object_hook=None, parse_float=None,
if parse_float is not None:
raise TypeError("use_decimal=True implies parse_float=Decimal")
kw['parse_float'] = Decimal
+ if allow_nan:
+ kw['allow_nan'] = True
return cls(encoding=encoding, **kw).decode(s)
@@ -560,22 +551,9 @@ def _toggle_speedups(enabled):
scan.make_scanner = scan.py_make_scanner
dec.make_scanner = scan.make_scanner
global _default_decoder
- _default_decoder = JSONDecoder(
- encoding=None,
- object_hook=None,
- object_pairs_hook=None,
- )
+ _default_decoder = JSONDecoder()
global _default_encoder
- _default_encoder = JSONEncoder(
- skipkeys=False,
- ensure_ascii=True,
- check_circular=True,
- allow_nan=True,
- indent=None,
- separators=None,
- encoding='utf-8',
- default=None,
- )
+ _default_encoder = JSONEncoder()
def simple_first(kv):
"""Helper function to pass to item_sort_key to sort simple
diff --git a/contrib/python/simplejson/py2/simplejson/_speedups.c b/contrib/python/simplejson/py2/simplejson/_speedups.c
index ec054c7293..bd56b4dc87 100644
--- a/contrib/python/simplejson/py2/simplejson/_speedups.c
+++ b/contrib/python/simplejson/py2/simplejson/_speedups.c
@@ -1843,7 +1843,7 @@ bail:
}
static PyObject *
-_parse_constant(PyScannerObject *s, PyObject *constant, Py_ssize_t idx, Py_ssize_t *next_idx_ptr)
+_parse_constant(PyScannerObject *s, PyObject *pystr, PyObject *constant, Py_ssize_t idx, Py_ssize_t *next_idx_ptr)
{
/* Read a JSON constant from PyString pystr.
constant is the Python string that was found
@@ -1855,6 +1855,10 @@ _parse_constant(PyScannerObject *s, PyObject *constant, Py_ssize_t idx, Py_ssize
Returns the result of parse_constant
*/
PyObject *rval;
+ if (s->parse_constant == Py_None) {
+ raise_errmsg(ERR_EXPECTING_VALUE, pystr, idx);
+ return NULL;
+ }
/* rval = parse_constant(constant) */
rval = PyObject_CallOneArg(s->parse_constant, constant);
@@ -1886,7 +1890,7 @@ _match_number_str(PyScannerObject *s, PyObject *pystr, Py_ssize_t start, Py_ssiz
/* read a sign if it's there, make sure it's not the end of the string */
if (str[idx] == '-') {
if (idx >= end_idx) {
- raise_errmsg(ERR_EXPECTING_VALUE, pystr, idx);
+ raise_errmsg(ERR_EXPECTING_VALUE, pystr, start);
return NULL;
}
idx++;
@@ -1903,7 +1907,7 @@ _match_number_str(PyScannerObject *s, PyObject *pystr, Py_ssize_t start, Py_ssiz
}
/* no integer digits, error */
else {
- raise_errmsg(ERR_EXPECTING_VALUE, pystr, idx);
+ raise_errmsg(ERR_EXPECTING_VALUE, pystr, start);
return NULL;
}
@@ -1949,8 +1953,10 @@ _match_number_str(PyScannerObject *s, PyObject *pystr, Py_ssize_t start, Py_ssiz
/* rval = PyFloat_FromDouble(PyOS_ascii_atof(PyString_AS_STRING(numstr))); */
double d = PyOS_string_to_double(PyString_AS_STRING(numstr),
NULL, NULL);
- if (d == -1.0 && PyErr_Occurred())
+ if (d == -1.0 && PyErr_Occurred()) {
+ Py_DECREF(numstr);
return NULL;
+ }
rval = PyFloat_FromDouble(d);
}
}
@@ -1993,7 +1999,7 @@ _match_number_unicode(PyScannerObject *s, PyObject *pystr, Py_ssize_t start, Py_
/* read a sign if it's there, make sure it's not the end of the string */
if (PyUnicode_READ(kind, str, idx) == '-') {
if (idx >= end_idx) {
- raise_errmsg(ERR_EXPECTING_VALUE, pystr, idx);
+ raise_errmsg(ERR_EXPECTING_VALUE, pystr, start);
return NULL;
}
idx++;
@@ -2013,7 +2019,7 @@ _match_number_unicode(PyScannerObject *s, PyObject *pystr, Py_ssize_t start, Py_
}
else {
/* no integer digits, error */
- raise_errmsg(ERR_EXPECTING_VALUE, pystr, idx);
+ raise_errmsg(ERR_EXPECTING_VALUE, pystr, start);
return NULL;
}
@@ -2156,7 +2162,7 @@ scan_once_str(PyScannerObject *s, PyObject *pystr, Py_ssize_t idx, Py_ssize_t *n
case 'N':
/* NaN */
if ((idx + 2 < length) && str[idx + 1] == 'a' && str[idx + 2] == 'N') {
- rval = _parse_constant(s, JSON_NaN, idx, next_idx_ptr);
+ rval = _parse_constant(s, pystr, JSON_NaN, idx, next_idx_ptr);
}
else
fallthrough = 1;
@@ -2164,7 +2170,7 @@ scan_once_str(PyScannerObject *s, PyObject *pystr, Py_ssize_t idx, Py_ssize_t *n
case 'I':
/* Infinity */
if ((idx + 7 < length) && str[idx + 1] == 'n' && str[idx + 2] == 'f' && str[idx + 3] == 'i' && str[idx + 4] == 'n' && str[idx + 5] == 'i' && str[idx + 6] == 't' && str[idx + 7] == 'y') {
- rval = _parse_constant(s, JSON_Infinity, idx, next_idx_ptr);
+ rval = _parse_constant(s, pystr, JSON_Infinity, idx, next_idx_ptr);
}
else
fallthrough = 1;
@@ -2172,7 +2178,7 @@ scan_once_str(PyScannerObject *s, PyObject *pystr, Py_ssize_t idx, Py_ssize_t *n
case '-':
/* -Infinity */
if ((idx + 8 < length) && str[idx + 1] == 'I' && str[idx + 2] == 'n' && str[idx + 3] == 'f' && str[idx + 4] == 'i' && str[idx + 5] == 'n' && str[idx + 6] == 'i' && str[idx + 7] == 't' && str[idx + 8] == 'y') {
- rval = _parse_constant(s, JSON_NegInfinity, idx, next_idx_ptr);
+ rval = _parse_constant(s, pystr, JSON_NegInfinity, idx, next_idx_ptr);
}
else
fallthrough = 1;
@@ -2275,7 +2281,7 @@ scan_once_unicode(PyScannerObject *s, PyObject *pystr, Py_ssize_t idx, Py_ssize_
if ((idx + 2 < length) &&
PyUnicode_READ(kind, str, idx + 1) == 'a' &&
PyUnicode_READ(kind, str, idx + 2) == 'N') {
- rval = _parse_constant(s, JSON_NaN, idx, next_idx_ptr);
+ rval = _parse_constant(s, pystr, JSON_NaN, idx, next_idx_ptr);
}
else
fallthrough = 1;
@@ -2290,7 +2296,7 @@ scan_once_unicode(PyScannerObject *s, PyObject *pystr, Py_ssize_t idx, Py_ssize_
PyUnicode_READ(kind, str, idx + 5) == 'i' &&
PyUnicode_READ(kind, str, idx + 6) == 't' &&
PyUnicode_READ(kind, str, idx + 7) == 'y') {
- rval = _parse_constant(s, JSON_Infinity, idx, next_idx_ptr);
+ rval = _parse_constant(s, pystr, JSON_Infinity, idx, next_idx_ptr);
}
else
fallthrough = 1;
@@ -2306,7 +2312,7 @@ scan_once_unicode(PyScannerObject *s, PyObject *pystr, Py_ssize_t idx, Py_ssize_
PyUnicode_READ(kind, str, idx + 6) == 'i' &&
PyUnicode_READ(kind, str, idx + 7) == 't' &&
PyUnicode_READ(kind, str, idx + 8) == 'y') {
- rval = _parse_constant(s, JSON_NegInfinity, idx, next_idx_ptr);
+ rval = _parse_constant(s, pystr, JSON_NegInfinity, idx, next_idx_ptr);
}
else
fallthrough = 1;
diff --git a/contrib/python/simplejson/py2/simplejson/decoder.py b/contrib/python/simplejson/py2/simplejson/decoder.py
index 1a8f772f13..c99a976d84 100644
--- a/contrib/python/simplejson/py2/simplejson/decoder.py
+++ b/contrib/python/simplejson/py2/simplejson/decoder.py
@@ -46,9 +46,35 @@ BACKSLASH = {
DEFAULT_ENCODING = "utf-8"
+if hasattr(sys, 'get_int_max_str_digits'):
+ bounded_int = int
+else:
+ def bounded_int(s, INT_MAX_STR_DIGITS=4300):
+ """Backport of the integer string length conversion limitation
+
+ https://docs.python.org/3/library/stdtypes.html#int-max-str-digits
+ """
+ if len(s) > INT_MAX_STR_DIGITS:
+ raise ValueError("Exceeds the limit (%s) for integer string conversion: value has %s digits" % (INT_MAX_STR_DIGITS, len(s)))
+ return int(s)
+
+
+def scan_four_digit_hex(s, end, _m=re.compile(r'^[0-9a-fA-F]{4}$').match):
+ """Scan a four digit hex number from s[end:end + 4]
+ """
+ msg = "Invalid \\uXXXX escape sequence"
+ esc = s[end:end + 4]
+ if not _m(esc):
+ raise JSONDecodeError(msg, s, end - 2)
+ try:
+ return int(esc, 16), end + 4
+ except ValueError:
+ raise JSONDecodeError(msg, s, end - 2)
+
def py_scanstring(s, end, encoding=None, strict=True,
_b=BACKSLASH, _m=STRINGCHUNK.match, _join=u''.join,
- _PY3=PY3, _maxunicode=sys.maxunicode):
+ _PY3=PY3, _maxunicode=sys.maxunicode,
+ _scan_four_digit_hex=scan_four_digit_hex):
"""Scan the string s for a JSON string. End is the index of the
character in s after the quote that started the JSON string.
Unescapes all valid JSON string escape sequences and raises ValueError
@@ -67,6 +93,7 @@ def py_scanstring(s, end, encoding=None, strict=True,
if chunk is None:
raise JSONDecodeError(
"Unterminated string starting at", s, begin)
+ prev_end = end
end = chunk.end()
content, terminator = chunk.groups()
# Content is contains zero or more unescaped string characters
@@ -81,7 +108,7 @@ def py_scanstring(s, end, encoding=None, strict=True,
elif terminator != '\\':
if strict:
msg = "Invalid control character %r at"
- raise JSONDecodeError(msg, s, end)
+ raise JSONDecodeError(msg, s, prev_end)
else:
_append(terminator)
continue
@@ -100,35 +127,18 @@ def py_scanstring(s, end, encoding=None, strict=True,
end += 1
else:
# Unicode escape sequence
- msg = "Invalid \\uXXXX escape sequence"
- esc = s[end + 1:end + 5]
- escX = esc[1:2]
- if len(esc) != 4 or escX == 'x' or escX == 'X':
- raise JSONDecodeError(msg, s, end - 1)
- try:
- uni = int(esc, 16)
- except ValueError:
- raise JSONDecodeError(msg, s, end - 1)
- if uni < 0 or uni > _maxunicode:
- raise JSONDecodeError(msg, s, end - 1)
- end += 5
+ uni, end = _scan_four_digit_hex(s, end + 1)
# Check for surrogate pair on UCS-4 systems
# Note that this will join high/low surrogate pairs
# but will also pass unpaired surrogates through
if (_maxunicode > 65535 and
uni & 0xfc00 == 0xd800 and
s[end:end + 2] == '\\u'):
- esc2 = s[end + 2:end + 6]
- escX = esc2[1:2]
- if len(esc2) == 4 and not (escX == 'x' or escX == 'X'):
- try:
- uni2 = int(esc2, 16)
- except ValueError:
- raise JSONDecodeError(msg, s, end)
- if uni2 & 0xfc00 == 0xdc00:
- uni = 0x10000 + (((uni - 0xd800) << 10) |
- (uni2 - 0xdc00))
- end += 6
+ uni2, end2 = _scan_four_digit_hex(s, end + 2)
+ if uni2 & 0xfc00 == 0xdc00:
+ uni = 0x10000 + (((uni - 0xd800) << 10) |
+ (uni2 - 0xdc00))
+ end = end2
char = unichr(uni)
# Append the unescaped character
_append(char)
@@ -169,7 +179,7 @@ def JSONObject(state, encoding, strict, scan_once, object_hook,
return pairs, end + 1
elif nextchar != '"':
raise JSONDecodeError(
- "Expecting property name enclosed in double quotes",
+ "Expecting property name enclosed in double quotes or '}'",
s, end)
end += 1
while True:
@@ -296,14 +306,15 @@ class JSONDecoder(object):
| null | None |
+---------------+-------------------+
- It also understands ``NaN``, ``Infinity``, and ``-Infinity`` as
+ When allow_nan=True, it also understands
+ ``NaN``, ``Infinity``, and ``-Infinity`` as
their corresponding ``float`` values, which is outside the JSON spec.
"""
def __init__(self, encoding=None, object_hook=None, parse_float=None,
parse_int=None, parse_constant=None, strict=True,
- object_pairs_hook=None):
+ object_pairs_hook=None, allow_nan=False):
"""
*encoding* determines the encoding used to interpret any
:class:`str` objects decoded by this instance (``'utf-8'`` by
@@ -336,10 +347,13 @@ class JSONDecoder(object):
``int(num_str)``. This can be used to use another datatype or parser
for JSON integers (e.g. :class:`float`).
- *parse_constant*, if specified, will be called with one of the
- following strings: ``'-Infinity'``, ``'Infinity'``, ``'NaN'``. This
- can be used to raise an exception if invalid JSON numbers are
- encountered.
+ *allow_nan*, if True (default false), will allow the parser to
+ accept the non-standard floats ``NaN``, ``Infinity``, and ``-Infinity``.
+
+ *parse_constant*, if specified, will be
+ called with one of the following strings: ``'-Infinity'``,
+ ``'Infinity'``, ``'NaN'``. It is not recommended to use this feature,
+ as it is rare to parse non-compliant JSON containing these values.
*strict* controls the parser's behavior when it encounters an
invalid control character in a string. The default setting of
@@ -353,8 +367,8 @@ class JSONDecoder(object):
self.object_hook = object_hook
self.object_pairs_hook = object_pairs_hook
self.parse_float = parse_float or float
- self.parse_int = parse_int or int
- self.parse_constant = parse_constant or _CONSTANTS.__getitem__
+ self.parse_int = parse_int or bounded_int
+ self.parse_constant = parse_constant or (allow_nan and _CONSTANTS.__getitem__ or None)
self.strict = strict
self.parse_object = JSONObject
self.parse_array = JSONArray
diff --git a/contrib/python/simplejson/py2/simplejson/encoder.py b/contrib/python/simplejson/py2/simplejson/encoder.py
index e93fe43f42..661ff361bf 100644
--- a/contrib/python/simplejson/py2/simplejson/encoder.py
+++ b/contrib/python/simplejson/py2/simplejson/encoder.py
@@ -5,7 +5,7 @@ import re
from operator import itemgetter
# Do not import Decimal directly to avoid reload issues
import decimal
-from .compat import unichr, binary_type, text_type, string_types, integer_types, PY3
+from .compat import binary_type, text_type, string_types, integer_types, PY3
def _import_speedups():
try:
from . import _speedups
@@ -140,7 +140,7 @@ class JSONEncoder(object):
key_separator = ': '
def __init__(self, skipkeys=False, ensure_ascii=True,
- check_circular=True, allow_nan=True, sort_keys=False,
+ check_circular=True, allow_nan=False, sort_keys=False,
indent=None, separators=None, encoding='utf-8', default=None,
use_decimal=True, namedtuple_as_object=True,
tuple_as_array=True, bigint_as_string=False,
@@ -161,10 +161,11 @@ class JSONEncoder(object):
prevent an infinite recursion (which would cause an OverflowError).
Otherwise, no such check takes place.
- If allow_nan is true, then NaN, Infinity, and -Infinity will be
- encoded as such. This behavior is not JSON specification compliant,
- but is consistent with most JavaScript based encoders and decoders.
- Otherwise, it will be a ValueError to encode such floats.
+ If allow_nan is true (default: False), then out of range float
+ values (nan, inf, -inf) will be serialized to
+ their JavaScript equivalents (NaN, Infinity, -Infinity)
+ instead of raising a ValueError. See
+ ignore_nan for ECMA-262 compliant behavior.
If sort_keys is true, then the output of dictionaries will be
sorted by key; this is useful for regression tests to ensure
@@ -294,7 +295,7 @@ class JSONEncoder(object):
# This doesn't pass the iterator directly to ''.join() because the
# exceptions aren't as detailed. The list call should be roughly
# equivalent to the PySequence_Fast that ''.join() would do.
- chunks = self.iterencode(o, _one_shot=True)
+ chunks = self.iterencode(o)
if not isinstance(chunks, (list, tuple)):
chunks = list(chunks)
if self.ensure_ascii:
@@ -302,7 +303,7 @@ class JSONEncoder(object):
else:
return u''.join(chunks)
- def iterencode(self, o, _one_shot=False):
+ def iterencode(self, o):
"""Encode the given object and yield each string
representation as available.
@@ -356,8 +357,7 @@ class JSONEncoder(object):
key_memo = {}
int_as_string_bitcount = (
53 if self.bigint_as_string else self.int_as_string_bitcount)
- if (_one_shot and c_make_encoder is not None
- and self.indent is None):
+ if (c_make_encoder is not None and self.indent is None):
_iterencode = c_make_encoder(
markers, self.default, _encoder, self.indent,
self.key_separator, self.item_separator, self.sort_keys,
@@ -370,7 +370,7 @@ class JSONEncoder(object):
_iterencode = _make_iterencode(
markers, self.default, _encoder, self.indent, floatstr,
self.key_separator, self.item_separator, self.sort_keys,
- self.skipkeys, _one_shot, self.use_decimal,
+ self.skipkeys, self.use_decimal,
self.namedtuple_as_object, self.tuple_as_array,
int_as_string_bitcount,
self.item_sort_key, self.encoding, self.for_json,
@@ -398,14 +398,14 @@ class JSONEncoderForHTML(JSONEncoder):
def encode(self, o):
# Override JSONEncoder.encode because it has hacks for
# performance that make things more complicated.
- chunks = self.iterencode(o, True)
+ chunks = self.iterencode(o)
if self.ensure_ascii:
return ''.join(chunks)
else:
return u''.join(chunks)
- def iterencode(self, o, _one_shot=False):
- chunks = super(JSONEncoderForHTML, self).iterencode(o, _one_shot)
+ def iterencode(self, o):
+ chunks = super(JSONEncoderForHTML, self).iterencode(o)
for chunk in chunks:
chunk = chunk.replace('&', '\\u0026')
chunk = chunk.replace('<', '\\u003c')
@@ -419,7 +419,7 @@ class JSONEncoderForHTML(JSONEncoder):
def _make_iterencode(markers, _default, _encoder, _indent, _floatstr,
- _key_separator, _item_separator, _sort_keys, _skipkeys, _one_shot,
+ _key_separator, _item_separator, _sort_keys, _skipkeys,
_use_decimal, _namedtuple_as_object, _tuple_as_array,
_int_as_string_bitcount, _item_sort_key,
_encoding,_for_json,
diff --git a/contrib/python/simplejson/py2/simplejson/scanner.py b/contrib/python/simplejson/py2/simplejson/scanner.py
index 85e385e147..34710d68c6 100644
--- a/contrib/python/simplejson/py2/simplejson/scanner.py
+++ b/contrib/python/simplejson/py2/simplejson/scanner.py
@@ -60,11 +60,11 @@ def py_make_scanner(context):
else:
res = parse_int(integer)
return res, m.end()
- elif nextchar == 'N' and string[idx:idx + 3] == 'NaN':
+ elif parse_constant and nextchar == 'N' and string[idx:idx + 3] == 'NaN':
return parse_constant('NaN'), idx + 3
- elif nextchar == 'I' and string[idx:idx + 8] == 'Infinity':
+ elif parse_constant and nextchar == 'I' and string[idx:idx + 8] == 'Infinity':
return parse_constant('Infinity'), idx + 8
- elif nextchar == '-' and string[idx:idx + 9] == '-Infinity':
+ elif parse_constant and nextchar == '-' and string[idx:idx + 9] == '-Infinity':
return parse_constant('-Infinity'), idx + 9
else:
raise JSONDecodeError(errmsg, string, idx)
diff --git a/contrib/python/simplejson/py2/simplejson/tests/test_decode.py b/contrib/python/simplejson/py2/simplejson/tests/test_decode.py
index 6960ee58ba..317b4f98d5 100644
--- a/contrib/python/simplejson/py2/simplejson/tests/test_decode.py
+++ b/contrib/python/simplejson/py2/simplejson/tests/test_decode.py
@@ -2,6 +2,7 @@ from __future__ import absolute_import
import decimal
from unittest import TestCase
+import sys
import simplejson as json
from simplejson.compat import StringIO, b, binary_type
from simplejson import OrderedDict
@@ -117,3 +118,10 @@ class TestDecode(TestCase):
diff = id(x) - id(y)
self.assertRaises(ValueError, j.scan_once, y, diff)
self.assertRaises(ValueError, j.raw_decode, y, i)
+
+ def test_bounded_int(self):
+ # SJ-PT-23-03, limit quadratic number parsing per Python 3.11
+ max_str_digits = getattr(sys, 'get_int_max_str_digits', lambda: 4300)()
+ s = '1' + '0' * (max_str_digits - 1)
+ self.assertEqual(json.loads(s), int(s))
+ self.assertRaises(ValueError, json.loads, s + '0')
diff --git a/contrib/python/simplejson/py2/simplejson/tests/test_fail.py b/contrib/python/simplejson/py2/simplejson/tests/test_fail.py
index 788f3a525b..5f9a8f698c 100644
--- a/contrib/python/simplejson/py2/simplejson/tests/test_fail.py
+++ b/contrib/python/simplejson/py2/simplejson/tests/test_fail.py
@@ -145,7 +145,7 @@ class TestFail(TestCase):
('["spam', 'Unterminated string starting at', 1),
('["spam"', "Expecting ',' delimiter", 7),
('["spam",', 'Expecting value', 8),
- ('{', 'Expecting property name enclosed in double quotes', 1),
+ ('{', "Expecting property name enclosed in double quotes or '}'", 1),
('{"', 'Unterminated string starting at', 1),
('{"spam', 'Unterminated string starting at', 1),
('{"spam"', "Expecting ':' delimiter", 7),
@@ -156,6 +156,8 @@ class TestFail(TestCase):
('"', 'Unterminated string starting at', 0),
('"spam', 'Unterminated string starting at', 0),
('[,', "Expecting value", 1),
+ ('--', 'Expecting value', 0),
+ ('"\x18d', "Invalid control character %r", 1),
]
for data, msg, idx in test_cases:
try:
diff --git a/contrib/python/simplejson/py2/simplejson/tests/test_float.py b/contrib/python/simplejson/py2/simplejson/tests/test_float.py
index e382ec21ab..a977969472 100644
--- a/contrib/python/simplejson/py2/simplejson/tests/test_float.py
+++ b/contrib/python/simplejson/py2/simplejson/tests/test_float.py
@@ -7,9 +7,9 @@ from simplejson.decoder import NaN, PosInf, NegInf
class TestFloat(TestCase):
def test_degenerates_allow(self):
for inf in (PosInf, NegInf):
- self.assertEqual(json.loads(json.dumps(inf)), inf)
+ self.assertEqual(json.loads(json.dumps(inf, allow_nan=True), allow_nan=True), inf)
# Python 2.5 doesn't have math.isnan
- nan = json.loads(json.dumps(NaN))
+ nan = json.loads(json.dumps(NaN, allow_nan=True), allow_nan=True)
self.assertTrue((0 + nan) != nan)
def test_degenerates_ignore(self):
@@ -19,6 +19,9 @@ class TestFloat(TestCase):
def test_degenerates_deny(self):
for f in (PosInf, NegInf, NaN):
self.assertRaises(ValueError, json.dumps, f, allow_nan=False)
+ for s in ('Infinity', '-Infinity', 'NaN'):
+ self.assertRaises(ValueError, json.loads, s, allow_nan=False)
+ self.assertRaises(ValueError, json.loads, s)
def test_floats(self):
for num in [1617161771.7650001, math.pi, math.pi**100,
diff --git a/contrib/python/simplejson/py2/simplejson/tests/test_scanstring.py b/contrib/python/simplejson/py2/simplejson/tests/test_scanstring.py
index c6c53b81aa..1f54483420 100644
--- a/contrib/python/simplejson/py2/simplejson/tests/test_scanstring.py
+++ b/contrib/python/simplejson/py2/simplejson/tests/test_scanstring.py
@@ -132,7 +132,9 @@ class TestScanString(TestCase):
self.assertRaises(ValueError,
scanstring, '\\ud834\\x0123"', 0, None, True)
- self.assertRaises(json.JSONDecodeError, scanstring, "\\u-123", 0, None, True)
+ self.assertRaises(json.JSONDecodeError, scanstring, '\\u-123"', 0, None, True)
+ # SJ-PT-23-01: Invalid Handling of Broken Unicode Escape Sequences
+ self.assertRaises(json.JSONDecodeError, scanstring, '\\u EDD"', 0, None, True)
def test_issue3623(self):
self.assertRaises(ValueError, json.decoder.scanstring, "xxx", 1,
diff --git a/contrib/python/simplejson/py2/ya.make b/contrib/python/simplejson/py2/ya.make
index 6683322330..440467d10d 100644
--- a/contrib/python/simplejson/py2/ya.make
+++ b/contrib/python/simplejson/py2/ya.make
@@ -2,7 +2,7 @@
PY2_LIBRARY()
-VERSION(3.18.4)
+VERSION(3.19.2)
LICENSE(MIT)