blob: 9f0a75b84a03c3a59170b26fbca72b84f753c26d [file] [log] [blame]
Victor Stinner3b5cf852017-06-09 16:48:45 +02001import datetime
Jeremy Hyltonbea39472001-05-29 16:26:20 +00002import unittest
Serhiy Storchaka5eb788b2017-06-06 18:45:22 +03003from test.support import cpython_only
Victor Stinner3b5cf852017-06-09 16:48:45 +02004try:
5 import _testcapi
6except ImportError:
7 _testcapi = None
Sylvain96c7c062017-06-15 17:05:23 +02008import struct
9import collections
Oren Milmanbf9075a2017-08-23 21:16:48 +030010import itertools
Jeroen Demeyer77aa3962019-05-22 13:09:35 +020011import gc
Jeremy Hyltonbea39472001-05-29 16:26:20 +000012
INADA Naoki2aaf98c2018-09-26 12:59:00 +090013
14class FunctionCalls(unittest.TestCase):
15
16 def test_kwargs_order(self):
17 # bpo-34320: **kwargs should preserve order of passed OrderedDict
18 od = collections.OrderedDict([('a', 1), ('b', 2)])
19 od.move_to_end('a')
20 expected = list(od.items())
21
22 def fn(**kw):
23 return kw
24
25 res = fn(**od)
26 self.assertIsInstance(res, dict)
27 self.assertEqual(list(res.items()), expected)
28
29
Jeremy Hyltonbea39472001-05-29 16:26:20 +000030# The test cases here cover several paths through the function calling
31# code. They depend on the METH_XXX flag that is used to define a C
32# function, which can't be verified from Python. If the METH_XXX decl
33# for a C function changes, these tests may not cover the right paths.
34
35class CFunctionCalls(unittest.TestCase):
36
37 def test_varargs0(self):
Guido van Rossume2b70bc2006-08-18 22:13:04 +000038 self.assertRaises(TypeError, {}.__contains__)
Jeremy Hyltonbea39472001-05-29 16:26:20 +000039
40 def test_varargs1(self):
Guido van Rossume2b70bc2006-08-18 22:13:04 +000041 {}.__contains__(0)
Jeremy Hyltonbea39472001-05-29 16:26:20 +000042
43 def test_varargs2(self):
Guido van Rossume2b70bc2006-08-18 22:13:04 +000044 self.assertRaises(TypeError, {}.__contains__, 0, 1)
Jeremy Hyltonbea39472001-05-29 16:26:20 +000045
46 def test_varargs0_ext(self):
47 try:
Guido van Rossume2b70bc2006-08-18 22:13:04 +000048 {}.__contains__(*())
Jeremy Hyltonbea39472001-05-29 16:26:20 +000049 except TypeError:
50 pass
51
52 def test_varargs1_ext(self):
Guido van Rossume2b70bc2006-08-18 22:13:04 +000053 {}.__contains__(*(0,))
Jeremy Hyltonbea39472001-05-29 16:26:20 +000054
55 def test_varargs2_ext(self):
56 try:
Guido van Rossume2b70bc2006-08-18 22:13:04 +000057 {}.__contains__(*(1, 2))
Jeremy Hyltonbea39472001-05-29 16:26:20 +000058 except TypeError:
59 pass
60 else:
61 raise RuntimeError
62
Jeremy Hyltonbea39472001-05-29 16:26:20 +000063 def test_varargs1_kw(self):
Guido van Rossume2b70bc2006-08-18 22:13:04 +000064 self.assertRaises(TypeError, {}.__contains__, x=2)
Jeremy Hyltonbea39472001-05-29 16:26:20 +000065
66 def test_varargs2_kw(self):
Guido van Rossume2b70bc2006-08-18 22:13:04 +000067 self.assertRaises(TypeError, {}.__contains__, x=2, y=2)
Jeremy Hyltonbea39472001-05-29 16:26:20 +000068
69 def test_oldargs0_0(self):
70 {}.keys()
71
72 def test_oldargs0_1(self):
73 self.assertRaises(TypeError, {}.keys, 0)
74
75 def test_oldargs0_2(self):
76 self.assertRaises(TypeError, {}.keys, 0, 1)
77
78 def test_oldargs0_0_ext(self):
79 {}.keys(*())
80
81 def test_oldargs0_1_ext(self):
82 try:
83 {}.keys(*(0,))
84 except TypeError:
85 pass
86 else:
87 raise RuntimeError
88
89 def test_oldargs0_2_ext(self):
90 try:
91 {}.keys(*(1, 2))
92 except TypeError:
93 pass
94 else:
95 raise RuntimeError
96
97 def test_oldargs0_0_kw(self):
98 try:
99 {}.keys(x=2)
100 except TypeError:
101 pass
102 else:
103 raise RuntimeError
104
105 def test_oldargs0_1_kw(self):
106 self.assertRaises(TypeError, {}.keys, x=2)
107
108 def test_oldargs0_2_kw(self):
109 self.assertRaises(TypeError, {}.keys, x=2, y=2)
110
111 def test_oldargs1_0(self):
Raymond Hettinger31017ae2004-03-04 08:25:44 +0000112 self.assertRaises(TypeError, [].count)
Jeremy Hyltonbea39472001-05-29 16:26:20 +0000113
114 def test_oldargs1_1(self):
Raymond Hettinger31017ae2004-03-04 08:25:44 +0000115 [].count(1)
Jeremy Hyltonbea39472001-05-29 16:26:20 +0000116
117 def test_oldargs1_2(self):
Raymond Hettinger31017ae2004-03-04 08:25:44 +0000118 self.assertRaises(TypeError, [].count, 1, 2)
Jeremy Hyltonbea39472001-05-29 16:26:20 +0000119
120 def test_oldargs1_0_ext(self):
121 try:
Raymond Hettinger31017ae2004-03-04 08:25:44 +0000122 [].count(*())
Jeremy Hyltonbea39472001-05-29 16:26:20 +0000123 except TypeError:
124 pass
125 else:
126 raise RuntimeError
127
128 def test_oldargs1_1_ext(self):
Raymond Hettinger31017ae2004-03-04 08:25:44 +0000129 [].count(*(1,))
Jeremy Hyltonbea39472001-05-29 16:26:20 +0000130
131 def test_oldargs1_2_ext(self):
132 try:
Raymond Hettinger31017ae2004-03-04 08:25:44 +0000133 [].count(*(1, 2))
Jeremy Hyltonbea39472001-05-29 16:26:20 +0000134 except TypeError:
135 pass
136 else:
137 raise RuntimeError
138
139 def test_oldargs1_0_kw(self):
Raymond Hettinger31017ae2004-03-04 08:25:44 +0000140 self.assertRaises(TypeError, [].count, x=2)
Jeremy Hyltonbea39472001-05-29 16:26:20 +0000141
142 def test_oldargs1_1_kw(self):
Raymond Hettinger31017ae2004-03-04 08:25:44 +0000143 self.assertRaises(TypeError, [].count, {}, x=2)
Jeremy Hyltonbea39472001-05-29 16:26:20 +0000144
145 def test_oldargs1_2_kw(self):
Raymond Hettinger31017ae2004-03-04 08:25:44 +0000146 self.assertRaises(TypeError, [].count, x=2, y=2)
Jeremy Hyltonbea39472001-05-29 16:26:20 +0000147
Fred Drake2e2be372001-09-20 21:33:42 +0000148
Serhiy Storchaka5eb788b2017-06-06 18:45:22 +0300149@cpython_only
150class CFunctionCallsErrorMessages(unittest.TestCase):
151
152 def test_varargs0(self):
153 msg = r"__contains__\(\) takes exactly one argument \(0 given\)"
154 self.assertRaisesRegex(TypeError, msg, {}.__contains__)
155
156 def test_varargs2(self):
157 msg = r"__contains__\(\) takes exactly one argument \(2 given\)"
158 self.assertRaisesRegex(TypeError, msg, {}.__contains__, 0, 1)
159
Serhiy Storchakaf9f1cca2017-06-09 19:27:06 +0300160 def test_varargs3(self):
Serhiy Storchakaf2f55e72019-03-13 23:03:22 +0200161 msg = r"^from_bytes\(\) takes exactly 2 positional arguments \(3 given\)"
Serhiy Storchakaf9f1cca2017-06-09 19:27:06 +0300162 self.assertRaisesRegex(TypeError, msg, int.from_bytes, b'a', 'little', False)
163
Xtreak63262782018-12-21 20:15:13 +0530164 def test_varargs1min(self):
Xtreak1426daa2018-07-23 01:43:26 +0530165 msg = r"get expected at least 1 argument, got 0"
166 self.assertRaisesRegex(TypeError, msg, {}.get)
167
Xtreak63262782018-12-21 20:15:13 +0530168 msg = r"expected 1 argument, got 0"
169 self.assertRaisesRegex(TypeError, msg, {}.__delattr__)
170
171 def test_varargs2min(self):
Xtreak1426daa2018-07-23 01:43:26 +0530172 msg = r"getattr expected at least 2 arguments, got 0"
173 self.assertRaisesRegex(TypeError, msg, getattr)
174
Xtreak63262782018-12-21 20:15:13 +0530175 def test_varargs1max(self):
Xtreak1426daa2018-07-23 01:43:26 +0530176 msg = r"input expected at most 1 argument, got 2"
177 self.assertRaisesRegex(TypeError, msg, input, 1, 2)
178
Xtreak63262782018-12-21 20:15:13 +0530179 def test_varargs2max(self):
Xtreak1426daa2018-07-23 01:43:26 +0530180 msg = r"get expected at most 2 arguments, got 3"
181 self.assertRaisesRegex(TypeError, msg, {}.get, 1, 2, 3)
182
Serhiy Storchaka5eb788b2017-06-06 18:45:22 +0300183 def test_varargs1_kw(self):
184 msg = r"__contains__\(\) takes no keyword arguments"
185 self.assertRaisesRegex(TypeError, msg, {}.__contains__, x=2)
186
187 def test_varargs2_kw(self):
188 msg = r"__contains__\(\) takes no keyword arguments"
189 self.assertRaisesRegex(TypeError, msg, {}.__contains__, x=2, y=2)
190
Sylvain74453812017-06-10 06:51:48 +0200191 def test_varargs3_kw(self):
192 msg = r"bool\(\) takes no keyword arguments"
193 self.assertRaisesRegex(TypeError, msg, bool, x=2)
194
195 def test_varargs4_kw(self):
196 msg = r"^index\(\) takes no keyword arguments$"
197 self.assertRaisesRegex(TypeError, msg, [].index, x=2)
198
199 def test_varargs5_kw(self):
200 msg = r"^hasattr\(\) takes no keyword arguments$"
201 self.assertRaisesRegex(TypeError, msg, hasattr, x=2)
202
Sylvain96c7c062017-06-15 17:05:23 +0200203 def test_varargs6_kw(self):
204 msg = r"^getattr\(\) takes no keyword arguments$"
205 self.assertRaisesRegex(TypeError, msg, getattr, x=2)
206
207 def test_varargs7_kw(self):
208 msg = r"^next\(\) takes no keyword arguments$"
209 self.assertRaisesRegex(TypeError, msg, next, x=2)
210
211 def test_varargs8_kw(self):
212 msg = r"^pack\(\) takes no keyword arguments$"
213 self.assertRaisesRegex(TypeError, msg, struct.pack, x=2)
214
215 def test_varargs9_kw(self):
216 msg = r"^pack_into\(\) takes no keyword arguments$"
217 self.assertRaisesRegex(TypeError, msg, struct.pack_into, x=2)
218
219 def test_varargs10_kw(self):
220 msg = r"^index\(\) takes no keyword arguments$"
221 self.assertRaisesRegex(TypeError, msg, collections.deque().index, x=2)
222
223 def test_varargs11_kw(self):
224 msg = r"^pack\(\) takes no keyword arguments$"
225 self.assertRaisesRegex(TypeError, msg, struct.Struct.pack, struct.Struct(""), x=2)
226
Sylvain96480882017-07-09 05:45:06 +0200227 def test_varargs12_kw(self):
228 msg = r"^staticmethod\(\) takes no keyword arguments$"
229 self.assertRaisesRegex(TypeError, msg, staticmethod, func=id)
230
231 def test_varargs13_kw(self):
232 msg = r"^classmethod\(\) takes no keyword arguments$"
233 self.assertRaisesRegex(TypeError, msg, classmethod, func=id)
234
Oren Milmanbf9075a2017-08-23 21:16:48 +0300235 def test_varargs14_kw(self):
236 msg = r"^product\(\) takes at most 1 keyword argument \(2 given\)$"
237 self.assertRaisesRegex(TypeError, msg,
238 itertools.product, 0, repeat=1, foo=2)
239
240 def test_varargs15_kw(self):
241 msg = r"^ImportError\(\) takes at most 2 keyword arguments \(3 given\)$"
242 self.assertRaisesRegex(TypeError, msg,
243 ImportError, 0, name=1, path=2, foo=3)
244
245 def test_varargs16_kw(self):
246 msg = r"^min\(\) takes at most 2 keyword arguments \(3 given\)$"
247 self.assertRaisesRegex(TypeError, msg,
248 min, 0, default=1, key=2, foo=3)
249
250 def test_varargs17_kw(self):
251 msg = r"^print\(\) takes at most 4 keyword arguments \(5 given\)$"
252 self.assertRaisesRegex(TypeError, msg,
253 print, 0, sep=1, end=2, file=3, flush=4, foo=5)
254
Serhiy Storchaka5eb788b2017-06-06 18:45:22 +0300255 def test_oldargs0_1(self):
256 msg = r"keys\(\) takes no arguments \(1 given\)"
257 self.assertRaisesRegex(TypeError, msg, {}.keys, 0)
258
259 def test_oldargs0_2(self):
260 msg = r"keys\(\) takes no arguments \(2 given\)"
261 self.assertRaisesRegex(TypeError, msg, {}.keys, 0, 1)
262
263 def test_oldargs0_1_kw(self):
264 msg = r"keys\(\) takes no keyword arguments"
265 self.assertRaisesRegex(TypeError, msg, {}.keys, x=2)
266
267 def test_oldargs0_2_kw(self):
268 msg = r"keys\(\) takes no keyword arguments"
269 self.assertRaisesRegex(TypeError, msg, {}.keys, x=2, y=2)
270
271 def test_oldargs1_0(self):
272 msg = r"count\(\) takes exactly one argument \(0 given\)"
273 self.assertRaisesRegex(TypeError, msg, [].count)
274
275 def test_oldargs1_2(self):
276 msg = r"count\(\) takes exactly one argument \(2 given\)"
277 self.assertRaisesRegex(TypeError, msg, [].count, 1, 2)
278
279 def test_oldargs1_0_kw(self):
280 msg = r"count\(\) takes no keyword arguments"
281 self.assertRaisesRegex(TypeError, msg, [].count, x=2)
282
283 def test_oldargs1_1_kw(self):
284 msg = r"count\(\) takes no keyword arguments"
285 self.assertRaisesRegex(TypeError, msg, [].count, {}, x=2)
286
287 def test_oldargs1_2_kw(self):
288 msg = r"count\(\) takes no keyword arguments"
289 self.assertRaisesRegex(TypeError, msg, [].count, x=2, y=2)
290
291
Victor Stinner3b5cf852017-06-09 16:48:45 +0200292def pyfunc(arg1, arg2):
293 return [arg1, arg2]
294
295
296def pyfunc_noarg():
297 return "noarg"
298
299
300class PythonClass:
301 def method(self, arg1, arg2):
302 return [arg1, arg2]
303
304 def method_noarg(self):
305 return "noarg"
306
307 @classmethod
308 def class_method(cls):
309 return "classmethod"
310
311 @staticmethod
312 def static_method():
313 return "staticmethod"
314
315
316PYTHON_INSTANCE = PythonClass()
317
318
319IGNORE_RESULT = object()
320
321
322@cpython_only
323class FastCallTests(unittest.TestCase):
324 # Test calls with positional arguments
325 CALLS_POSARGS = (
326 # (func, args: tuple, result)
327
328 # Python function with 2 arguments
329 (pyfunc, (1, 2), [1, 2]),
330
331 # Python function without argument
332 (pyfunc_noarg, (), "noarg"),
333
334 # Python class methods
335 (PythonClass.class_method, (), "classmethod"),
336 (PythonClass.static_method, (), "staticmethod"),
337
338 # Python instance methods
339 (PYTHON_INSTANCE.method, (1, 2), [1, 2]),
340 (PYTHON_INSTANCE.method_noarg, (), "noarg"),
341 (PYTHON_INSTANCE.class_method, (), "classmethod"),
342 (PYTHON_INSTANCE.static_method, (), "staticmethod"),
343
344 # C function: METH_NOARGS
345 (globals, (), IGNORE_RESULT),
346
347 # C function: METH_O
348 (id, ("hello",), IGNORE_RESULT),
349
350 # C function: METH_VARARGS
351 (dir, (1,), IGNORE_RESULT),
352
353 # C function: METH_VARARGS | METH_KEYWORDS
354 (min, (5, 9), 5),
355
356 # C function: METH_FASTCALL
357 (divmod, (1000, 33), (30, 10)),
358
359 # C type static method: METH_FASTCALL | METH_CLASS
360 (int.from_bytes, (b'\x01\x00', 'little'), 1),
361
362 # bpo-30524: Test that calling a C type static method with no argument
363 # doesn't crash (ignore the result): METH_FASTCALL | METH_CLASS
364 (datetime.datetime.now, (), IGNORE_RESULT),
365 )
366
367 # Test calls with positional and keyword arguments
368 CALLS_KWARGS = (
369 # (func, args: tuple, kwargs: dict, result)
370
371 # Python function with 2 arguments
372 (pyfunc, (1,), {'arg2': 2}, [1, 2]),
373 (pyfunc, (), {'arg1': 1, 'arg2': 2}, [1, 2]),
374
375 # Python instance methods
376 (PYTHON_INSTANCE.method, (1,), {'arg2': 2}, [1, 2]),
377 (PYTHON_INSTANCE.method, (), {'arg1': 1, 'arg2': 2}, [1, 2]),
378
379 # C function: METH_VARARGS | METH_KEYWORDS
380 (max, ([],), {'default': 9}, 9),
381
382 # C type static method: METH_FASTCALL | METH_CLASS
383 (int.from_bytes, (b'\x01\x00',), {'byteorder': 'little'}, 1),
384 (int.from_bytes, (), {'bytes': b'\x01\x00', 'byteorder': 'little'}, 1),
385 )
386
387 def check_result(self, result, expected):
388 if expected is IGNORE_RESULT:
389 return
390 self.assertEqual(result, expected)
391
392 def test_fastcall(self):
393 # Test _PyObject_FastCall()
394
395 for func, args, expected in self.CALLS_POSARGS:
396 with self.subTest(func=func, args=args):
397 result = _testcapi.pyobject_fastcall(func, args)
398 self.check_result(result, expected)
399
400 if not args:
401 # args=NULL, nargs=0
402 result = _testcapi.pyobject_fastcall(func, None)
403 self.check_result(result, expected)
404
Jeroen Demeyeraacc77f2019-05-29 20:31:52 +0200405 def test_vectorcall_dict(self):
Victor Stinner3b5cf852017-06-09 16:48:45 +0200406 # Test _PyObject_FastCallDict()
407
408 for func, args, expected in self.CALLS_POSARGS:
409 with self.subTest(func=func, args=args):
410 # kwargs=NULL
411 result = _testcapi.pyobject_fastcalldict(func, args, None)
412 self.check_result(result, expected)
413
414 # kwargs={}
415 result = _testcapi.pyobject_fastcalldict(func, args, {})
416 self.check_result(result, expected)
417
418 if not args:
419 # args=NULL, nargs=0, kwargs=NULL
420 result = _testcapi.pyobject_fastcalldict(func, None, None)
421 self.check_result(result, expected)
422
423 # args=NULL, nargs=0, kwargs={}
424 result = _testcapi.pyobject_fastcalldict(func, None, {})
425 self.check_result(result, expected)
426
427 for func, args, kwargs, expected in self.CALLS_KWARGS:
428 with self.subTest(func=func, args=args, kwargs=kwargs):
429 result = _testcapi.pyobject_fastcalldict(func, args, kwargs)
430 self.check_result(result, expected)
431
Jeroen Demeyeraacc77f2019-05-29 20:31:52 +0200432 def test_vectorcall(self):
433 # Test _PyObject_Vectorcall()
Victor Stinner3b5cf852017-06-09 16:48:45 +0200434
435 for func, args, expected in self.CALLS_POSARGS:
436 with self.subTest(func=func, args=args):
437 # kwnames=NULL
Jeroen Demeyeraacc77f2019-05-29 20:31:52 +0200438 result = _testcapi.pyobject_vectorcall(func, args, None)
Victor Stinner3b5cf852017-06-09 16:48:45 +0200439 self.check_result(result, expected)
440
441 # kwnames=()
Jeroen Demeyeraacc77f2019-05-29 20:31:52 +0200442 result = _testcapi.pyobject_vectorcall(func, args, ())
Victor Stinner3b5cf852017-06-09 16:48:45 +0200443 self.check_result(result, expected)
444
445 if not args:
446 # kwnames=NULL
Jeroen Demeyeraacc77f2019-05-29 20:31:52 +0200447 result = _testcapi.pyobject_vectorcall(func, None, None)
Victor Stinner3b5cf852017-06-09 16:48:45 +0200448 self.check_result(result, expected)
449
450 # kwnames=()
Jeroen Demeyeraacc77f2019-05-29 20:31:52 +0200451 result = _testcapi.pyobject_vectorcall(func, None, ())
Victor Stinner3b5cf852017-06-09 16:48:45 +0200452 self.check_result(result, expected)
453
454 for func, args, kwargs, expected in self.CALLS_KWARGS:
455 with self.subTest(func=func, args=args, kwargs=kwargs):
456 kwnames = tuple(kwargs.keys())
457 args = args + tuple(kwargs.values())
Jeroen Demeyeraacc77f2019-05-29 20:31:52 +0200458 result = _testcapi.pyobject_vectorcall(func, args, kwnames)
Victor Stinner3b5cf852017-06-09 16:48:45 +0200459 self.check_result(result, expected)
460
Jeroen Demeyer77aa3962019-05-22 13:09:35 +0200461 def test_fastcall_clearing_dict(self):
462 # Test bpo-36907: the point of the test is just checking that this
463 # does not crash.
464 class IntWithDict:
465 __slots__ = ["kwargs"]
466 def __init__(self, **kwargs):
467 self.kwargs = kwargs
468 def __index__(self):
469 self.kwargs.clear()
470 gc.collect()
471 return 0
472 x = IntWithDict(dont_inherit=IntWithDict())
473 # We test the argument handling of "compile" here, the compilation
474 # itself is not relevant. When we pass flags=x below, x.__index__() is
475 # called, which changes the keywords dict.
476 compile("pass", "", "exec", x, **x.kwargs)
Victor Stinner3b5cf852017-06-09 16:48:45 +0200477
Fred Drake2e2be372001-09-20 21:33:42 +0000478if __name__ == "__main__":
Zachary Ware38c707e2015-04-13 15:00:43 -0500479 unittest.main()