Skip to content

Commit 0e43000

Browse files
Try another format.
1 parent c52feb2 commit 0e43000

File tree

6 files changed

+83
-66
lines changed

6 files changed

+83
-66
lines changed

Lib/test/test_bytes.py

Lines changed: 10 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -781,16 +781,16 @@ def __int__(self):
781781
pi = PseudoFloat(3.1415)
782782

783783
exceptions_params = [
784-
('an integer is required for format %x, not float', b'%x', 3.14),
785-
('an integer is required for format %X, not float', b'%X', 2.11),
786-
('an integer is required for format %o, not float', b'%o', 1.79),
787-
(r'an integer is required for format %x, not .*\.PseudoFloat', b'%x', pi),
788-
('an integer is required for format %x, not complex', b'%x', 3j),
789-
('an integer is required for format %X, not complex', b'%X', 2j),
790-
('an integer is required for format %o, not complex', b'%o', 1j),
791-
('a real number is required for format %u, not complex', b'%u', 3j),
792-
('a real number is required for format %i, not complex', b'%i', 2j),
793-
('a real number is required for format %d, not complex', b'%d', 2j),
784+
('%x requires an integer, not float', b'%x', 3.14),
785+
('%X requires an integer, not float', b'%X', 2.11),
786+
('%o requires an integer, not float', b'%o', 1.79),
787+
(r'%x requires an integer, not .*\.PseudoFloat', b'%x', pi),
788+
('%x requires an integer, not complex', b'%x', 3j),
789+
('%X requires an integer, not complex', b'%X', 2j),
790+
('%o requires an integer, not complex', b'%o', 1j),
791+
('%u requires a real number, not complex', b'%u', 3j),
792+
('%i requires a real number, not complex', b'%i', 2j),
793+
('%d requires a real number, not complex', b'%d', 2j),
794794
(
795795
r'%c requires an integer in range\(256\)'
796796
r' or a single byte, not .*\.PseudoFloat',

Lib/test/test_format.py

Lines changed: 23 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -312,12 +312,16 @@ def test_common_format(self):
312312
"not enough arguments for format string (got 0)")
313313
test_exc_common('%(x)r', 1, TypeError,
314314
"format requires a mapping, not int")
315+
test_exc_common('%*r', 1, TypeError,
316+
"not enough arguments for format string (got 1)")
315317
test_exc_common('%*r', 3.14, TypeError,
316-
"* requires int, not float")
318+
"not enough arguments for format string (got 1)")
317319
test_exc_common('%*r', (3.14, 1), TypeError,
318320
"format argument 1: * requires int, not float")
321+
test_exc_common('%.*r', 1, TypeError,
322+
"not enough arguments for format string (got 1)")
319323
test_exc_common('%.*r', 3.14, TypeError,
320-
"* requires int, not float")
324+
"not enough arguments for format string (got 1)")
321325
test_exc_common('%.*r', (3.14, 1), TypeError,
322326
"format argument 1: * requires int, not float")
323327
test_exc_common('%*r', (2**1000, 1), OverflowError,
@@ -329,25 +333,25 @@ def test_common_format(self):
329333
test_exc_common('%.*r', (-2**1000, 1), OverflowError,
330334
"format argument 1: too big for precision")
331335
test_exc_common('%d', '1', TypeError,
332-
"a real number is required for format %d, not str")
336+
"%d requires a real number, not str")
333337
test_exc_common('%d', b'1', TypeError,
334-
"a real number is required for format %d, not bytes")
338+
"%d requires a real number, not bytes")
335339
test_exc_common('%d', ('1',), TypeError,
336-
"format argument 1: a real number is required for format %d, not str")
340+
"format argument 1: %d requires a real number, not str")
337341
test_exc_common('%x', '1', TypeError,
338-
"an integer is required for format %x, not str")
342+
"%x requires an integer, not str")
339343
test_exc_common('%x', 3.14, TypeError,
340-
"an integer is required for format %x, not float")
344+
"%x requires an integer, not float")
341345
test_exc_common('%x', ('1',), TypeError,
342-
"format argument 1: an integer is required for format %x, not str")
346+
"format argument 1: %x requires an integer, not str")
343347
test_exc_common('%i', '1', TypeError,
344-
"a real number is required for format %i, not str")
348+
"%i requires a real number, not str")
345349
test_exc_common('%i', b'1', TypeError,
346-
"a real number is required for format %i, not bytes")
350+
"%i requires a real number, not bytes")
347351
test_exc_common('%g', '1', TypeError,
348-
"a real number is required for format %g, not str")
352+
"%g requires a real number, not str")
349353
test_exc_common('%g', ('1',), TypeError,
350-
"format argument 1: a real number is required for format %g, not str")
354+
"format argument 1: %g requires a real number, not str")
351355

352356
def test_str_format(self):
353357
testformat("%r", "\u0378", "'\\u0378'") # non printable
@@ -386,11 +390,11 @@ def test_str_format(self):
386390
test_exc('%(x).*r', {'x': 1}, ValueError,
387391
"* cannot be used with a parenthesised mapping key at position 0")
388392
test_exc('%(x)d', {'x': '1'}, TypeError,
389-
"format argument 'x': a real number is required for format %d, not str")
393+
"format argument 'x': %d requires a real number, not str")
390394
test_exc('%(x)x', {'x': '1'}, TypeError,
391-
"format argument 'x': an integer is required for format %x, not str")
395+
"format argument 'x': %x requires an integer, not str")
392396
test_exc('%(x)g', {'x': '1'}, TypeError,
393-
"format argument 'x': a real number is required for format %g, not str")
397+
"format argument 'x': %g requires a real number, not str")
394398
test_exc('%c', -1, OverflowError, "%c argument not in range(0x110000)")
395399
test_exc('%c', (-1,), OverflowError,
396400
"format argument 1: %c argument not in range(0x110000)")
@@ -466,7 +470,7 @@ def __bytes__(self):
466470
test_exc(b"abc %\nd", 1, ValueError,
467471
"stray % at position 4 or unexpected format character with code 0x0a at position 5")
468472
test_exc(b"abc %'d", 1, ValueError,
469-
"stray % at position 4 or unexpected format character with code 0x27 at position 5")
473+
"stray % at position 4 or unexpected format character \"'\" at position 5")
470474
test_exc(b"abc %\x1fd", 1, ValueError,
471475
"stray % at position 4 or unexpected format character with code 0x1f at position 5")
472476
test_exc(b"abc %\x7fd", 1, ValueError,
@@ -488,11 +492,11 @@ def __bytes__(self):
488492
test_exc(b'%(x).*r', {b'x': 1}, ValueError,
489493
"* cannot be used with a parenthesised mapping key at position 0")
490494
test_exc(b'%(x)d', {b'x': '1'}, TypeError,
491-
"format argument b'x': a real number is required for format %d, not str")
495+
"format argument b'x': %d requires a real number, not str")
492496
test_exc(b'%(x)x', {b'x': '1'}, TypeError,
493-
"format argument b'x': an integer is required for format %x, not str")
497+
"format argument b'x': %x requires an integer, not str")
494498
test_exc(b'%(x)g', {b'x': '1'}, TypeError,
495-
"format argument b'x': a real number is required for format %g, not str")
499+
"format argument b'x': %g requires a real number, not str")
496500
test_exc(b"%c", -1, OverflowError,
497501
"%c argument not in range(256)")
498502
test_exc(b"%c", (-1,), OverflowError,

Lib/test/test_peepholer.py

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -744,16 +744,16 @@ def test_format_errors(self):
744744
'unsupported format %z at position 2'):
745745
eval("'%s%z' % (x, 5)", {'x': 1234})
746746
with self.assertRaisesRegex(TypeError,
747-
'format argument 1: a real number is required for format %d, not str'):
747+
'format argument 1: %d requires a real number, not str'):
748748
eval("'%d' % (x,)", {'x': '1234'})
749749
with self.assertRaisesRegex(TypeError,
750-
'format argument 1: an integer is required for format %x, not float'):
750+
'format argument 1: %x requires an integer, not float'):
751751
eval("'%x' % (x,)", {'x': 1234.56})
752752
with self.assertRaisesRegex(TypeError,
753-
'format argument 1: an integer is required for format %x, not str'):
753+
'format argument 1: %x requires an integer, not str'):
754754
eval("'%x' % (x,)", {'x': '1234'})
755755
with self.assertRaisesRegex(TypeError,
756-
'format argument 1: a real number is required for format %f, not str'):
756+
'format argument 1: %f requires a real number, not str'):
757757
eval("'%f' % (x,)", {'x': '1234'})
758758
with self.assertRaisesRegex(TypeError,
759759
'not enough arguments for format string'):

Lib/test/test_str.py

Lines changed: 10 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1578,16 +1578,16 @@ def __int__(self):
15781578
self.assertEqual('%X' % letter_m, '6D')
15791579
self.assertEqual('%o' % letter_m, '155')
15801580
self.assertEqual('%c' % letter_m, 'm')
1581-
self.assertRaisesRegex(TypeError, 'an integer is required for format %x, not float', operator.mod, '%x', 3.14)
1582-
self.assertRaisesRegex(TypeError, 'an integer is required for format %X, not float', operator.mod, '%X', 2.11)
1583-
self.assertRaisesRegex(TypeError, 'an integer is required for format %o, not float', operator.mod, '%o', 1.79)
1584-
self.assertRaisesRegex(TypeError, r'an integer is required for format %x, not .*\.PseudoFloat', operator.mod, '%x', pi)
1585-
self.assertRaisesRegex(TypeError, 'an integer is required for format %x, not complex', operator.mod, '%x', 3j)
1586-
self.assertRaisesRegex(TypeError, 'an integer is required for format %X, not complex', operator.mod, '%X', 2j)
1587-
self.assertRaisesRegex(TypeError, 'an integer is required for format %o, not complex', operator.mod, '%o', 1j)
1588-
self.assertRaisesRegex(TypeError, 'a real number is required for format %u, not complex', operator.mod, '%u', 3j)
1589-
self.assertRaisesRegex(TypeError, 'a real number is required for format %i, not complex', operator.mod, '%i', 2j)
1590-
self.assertRaisesRegex(TypeError, 'a real number is required for format %d, not complex', operator.mod, '%d', 1j)
1581+
self.assertRaisesRegex(TypeError, '%x requires an integer, not float', operator.mod, '%x', 3.14)
1582+
self.assertRaisesRegex(TypeError, '%X requires an integer, not float', operator.mod, '%X', 2.11)
1583+
self.assertRaisesRegex(TypeError, '%o requires an integer, not float', operator.mod, '%o', 1.79)
1584+
self.assertRaisesRegex(TypeError, r'%x requires an integer, not .*\.PseudoFloat', operator.mod, '%x', pi)
1585+
self.assertRaisesRegex(TypeError, '%x requires an integer, not complex', operator.mod, '%x', 3j)
1586+
self.assertRaisesRegex(TypeError, '%X requires an integer, not complex', operator.mod, '%X', 2j)
1587+
self.assertRaisesRegex(TypeError, '%o requires an integer, not complex', operator.mod, '%o', 1j)
1588+
self.assertRaisesRegex(TypeError, '%u requires a real number, not complex', operator.mod, '%u', 3j)
1589+
self.assertRaisesRegex(TypeError, '%i requires a real number, not complex', operator.mod, '%i', 2j)
1590+
self.assertRaisesRegex(TypeError, '%d requires a real number, not complex', operator.mod, '%d', 1j)
15911591
self.assertRaisesRegex(TypeError, r'%c requires an integer or a unicode character, not .*\.PseudoFloat', operator.mod, '%c', pi)
15921592

15931593
class RaisingNumber:

Objects/bytesobject.c

Lines changed: 23 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -419,15 +419,17 @@ PyBytes_FromFormat(const char *format, ...)
419419
} while (0)
420420

421421
Py_LOCAL_INLINE(PyObject *)
422-
getnextarg(PyObject *args, Py_ssize_t arglen, Py_ssize_t *p_argidx)
422+
getnextarg(PyObject *args, Py_ssize_t arglen, Py_ssize_t *p_argidx, int allowone)
423423
{
424424
Py_ssize_t argidx = *p_argidx;
425425
if (argidx < arglen) {
426426
(*p_argidx)++;
427-
if (arglen < 0)
428-
return args;
429-
else
427+
if (arglen >= 0) {
430428
return PyTuple_GetItem(args, argidx);
429+
}
430+
else if (allowone) {
431+
return args;
432+
}
431433
}
432434
PyErr_Format(PyExc_TypeError,
433435
"not enough arguments for format string (got %zd)",
@@ -452,7 +454,7 @@ formatfloat(PyObject *v, Py_ssize_t argidx, PyObject *key,
452454
if (x == -1.0 && PyErr_Occurred()) {
453455
if (PyErr_ExceptionMatches(PyExc_TypeError)) {
454456
FORMAT_ERROR(PyExc_TypeError,
455-
"a real number is required for format %%%c, not %T",
457+
"%%%c requires a real number, not %T",
456458
type, v);
457459
}
458460
return NULL;
@@ -511,10 +513,11 @@ formatlong(PyObject *v, Py_ssize_t argidx, PyObject *key,
511513
return NULL;
512514
}
513515
FORMAT_ERROR(PyExc_TypeError,
514-
"%s is required for format %%%c, not %T",
516+
"%%%c requires %s, not %T",
517+
type,
515518
(type == 'o' || type == 'x' || type == 'X') ? "an integer"
516519
: "a real number",
517-
type, v);
520+
v);
518521
return NULL;
519522
}
520523

@@ -782,7 +785,7 @@ _PyBytes_FormatEx(const char *format, Py_ssize_t format_len,
782785
(Py_ssize_t)(fmtstart - format - 1));
783786
goto error;
784787
}
785-
v = getnextarg(args, arglen, &argidx);
788+
v = getnextarg(args, arglen, &argidx, 0);
786789
if (v == NULL)
787790
goto error;
788791
if (!PyLong_Check(v)) {
@@ -833,7 +836,7 @@ _PyBytes_FormatEx(const char *format, Py_ssize_t format_len,
833836
(Py_ssize_t)(fmtstart - format - 1));
834837
goto error;
835838
}
836-
v = getnextarg(args, arglen, &argidx);
839+
v = getnextarg(args, arglen, &argidx, 0);
837840
if (v == NULL)
838841
goto error;
839842
if (!PyLong_Check(v)) {
@@ -862,8 +865,8 @@ _PyBytes_FormatEx(const char *format, Py_ssize_t format_len,
862865
break;
863866
if (prec > (INT_MAX - ((int)c - '0')) / 10) {
864867
PyErr_Format(PyExc_ValueError,
865-
"precision too big at position %zd",
866-
(Py_ssize_t)(fmtstart - format - 1));
868+
"precision too big at position %zd",
869+
(Py_ssize_t)(fmtstart - format - 1));
867870
goto error;
868871
}
869872
prec = prec*10 + (c - '0');
@@ -882,7 +885,7 @@ _PyBytes_FormatEx(const char *format, Py_ssize_t format_len,
882885
(Py_ssize_t)(fmtstart - format - 1));
883886
goto error;
884887
}
885-
v = getnextarg(args, arglen, &argidx);
888+
v = getnextarg(args, arglen, &argidx, 1);
886889
if (v == NULL)
887890
goto error;
888891

@@ -1012,6 +1015,14 @@ _PyBytes_FormatEx(const char *format, Py_ssize_t format_len,
10121015
"unsupported format %%%c at position %zd",
10131016
c, (Py_ssize_t)(fmtstart - format - 1));
10141017
}
1018+
else if (c == '\'') {
1019+
PyErr_Format(PyExc_ValueError,
1020+
"stray %% at position %zd or unexpected "
1021+
"format character \"'\" "
1022+
"at position %zd",
1023+
(Py_ssize_t)(fmtstart - format - 1),
1024+
(Py_ssize_t)(fmt - format - 1));
1025+
}
10151026
else if (c >= 32 && c < 127 && c != '\'') {
10161027
PyErr_Format(PyExc_ValueError,
10171028
"stray %% at position %zd or unexpected "

Objects/unicode_format.c

Lines changed: 13 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -93,16 +93,18 @@ struct unicode_format_arg_t {
9393

9494

9595
static PyObject *
96-
unicode_format_getnextarg(struct unicode_formatter_t *ctx)
96+
unicode_format_getnextarg(struct unicode_formatter_t *ctx, int allowone)
9797
{
9898
Py_ssize_t argidx = ctx->argidx;
9999

100-
if (argidx < ctx->arglen) {
100+
if (argidx < ctx->arglen && (allowone || ctx->arglen >= 0)) {
101101
ctx->argidx++;
102-
if (ctx->arglen < 0)
103-
return ctx->args;
104-
else
102+
if (ctx->arglen >= 0) {
105103
return PyTuple_GetItem(ctx->args, argidx);
104+
}
105+
else if (allowone) {
106+
return ctx->args;
107+
}
106108
}
107109
PyErr_Format(PyExc_TypeError,
108110
"not enough arguments for format string (got %zd)",
@@ -134,7 +136,7 @@ formatfloat(PyObject *v,
134136
if (x == -1.0 && PyErr_Occurred()) {
135137
if (PyErr_ExceptionMatches(PyExc_TypeError)) {
136138
FORMAT_ERROR(PyExc_TypeError,
137-
"a real number is required for format %%%c, not %T",
139+
"%%%c requires a real number, not %T",
138140
arg->ch, v);
139141
}
140142
return -1;
@@ -392,12 +394,12 @@ mainformatlong(PyObject *v,
392394
case 'x':
393395
case 'X':
394396
FORMAT_ERROR(PyExc_TypeError,
395-
"an integer is required for format %%%c, not %T",
397+
"%%%c requires an integer, not %T",
396398
arg->ch, v);
397399
break;
398400
default:
399401
FORMAT_ERROR(PyExc_TypeError,
400-
"a real number is required for format %%%c, not %T",
402+
"%%%c requires a real number, not %T",
401403
arg->ch, v);
402404
break;
403405
}
@@ -540,7 +542,7 @@ unicode_format_arg_parse(struct unicode_formatter_t *ctx,
540542
arg->fmtstart);
541543
return -1;
542544
}
543-
v = unicode_format_getnextarg(ctx);
545+
v = unicode_format_getnextarg(ctx, 0);
544546
if (v == NULL)
545547
return -1;
546548
if (!PyLong_Check(v)) {
@@ -599,7 +601,7 @@ unicode_format_arg_parse(struct unicode_formatter_t *ctx,
599601
arg->fmtstart);
600602
return -1;
601603
}
602-
v = unicode_format_getnextarg(ctx);
604+
v = unicode_format_getnextarg(ctx, 0);
603605
if (v == NULL)
604606
return -1;
605607
if (!PyLong_Check(v)) {
@@ -684,7 +686,7 @@ unicode_format_arg_format(struct unicode_formatter_t *ctx,
684686
if (ctx->fmtcnt == 0)
685687
ctx->writer.overallocate = 0;
686688

687-
v = unicode_format_getnextarg(ctx);
689+
v = unicode_format_getnextarg(ctx, 1);
688690
if (v == NULL)
689691
return -1;
690692

0 commit comments

Comments
 (0)