Skip to content

Commit c559135

Browse files
gh-143196: Fix crash in non-standard use of internal JSON encoder object (GH-143618)
The internal encoder object returned by undocumented function json.encoder.c_make_encoder() (aka _json.make_encoder()) crashed when it was called with non-zero second argument.
1 parent 3d44f0a commit c559135

File tree

3 files changed

+35
-0
lines changed

3 files changed

+35
-0
lines changed

Lib/test/test_json/test_speedups.py

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -80,3 +80,34 @@ def test(name):
8080
def test_unsortable_keys(self):
8181
with self.assertRaises(TypeError):
8282
self.json.encoder.JSONEncoder(sort_keys=True).encode({'a': 1, 1: 'a'})
83+
84+
def test_current_indent_level(self):
85+
enc = self.json.encoder.c_make_encoder(
86+
markers=None,
87+
default=str,
88+
encoder=self.json.encoder.c_encode_basestring,
89+
indent='\t',
90+
key_separator=': ',
91+
item_separator=', ',
92+
sort_keys=False,
93+
skipkeys=False,
94+
allow_nan=False)
95+
expected = (
96+
'[\n'
97+
'\t"spam", \n'
98+
'\t{\n'
99+
'\t\t"ham": "eggs"\n'
100+
'\t}\n'
101+
']')
102+
self.assertEqual(enc(['spam', {'ham': 'eggs'}], 0)[0], expected)
103+
self.assertEqual(enc(['spam', {'ham': 'eggs'}], -3)[0], expected)
104+
expected2 = (
105+
'[\n'
106+
'\t\t\t\t"spam", \n'
107+
'\t\t\t\t{\n'
108+
'\t\t\t\t\t"ham": "eggs"\n'
109+
'\t\t\t\t}\n'
110+
'\t\t\t]')
111+
self.assertEqual(enc(['spam', {'ham': 'eggs'}], 3)[0], expected2)
112+
self.assertRaises(TypeError, enc, ['spam', {'ham': 'eggs'}], 3.0)
113+
self.assertRaises(TypeError, enc, ['spam', {'ham': 'eggs'}])
Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
Fix crash when the internal encoder object returned by undocumented function
2+
:func:`!json.encoder.c_make_encoder` was called with non-zero second
3+
(*_current_indent_level*) argument.

Modules/_json.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1460,6 +1460,7 @@ encoder_call(PyObject *op, PyObject *args, PyObject *kwds)
14601460
return NULL;
14611461
}
14621462
}
1463+
indent_level = 0;
14631464
if (encoder_listencode_obj(self, writer, obj, indent_level, indent_cache)) {
14641465
PyUnicodeWriter_Discard(writer);
14651466
Py_XDECREF(indent_cache);

0 commit comments

Comments
 (0)