|
4 | 4 | import sys |
5 | 5 | import textwrap |
6 | 6 | import unittest |
| 7 | +try: |
| 8 | + import _testinternalcapi |
| 9 | +except ImportError: |
| 10 | + _testinternalcapi = None |
7 | 11 |
|
8 | 12 | from test import support |
9 | | -from test.support.bytecode_helper import BytecodeTestCase, CfgOptimizationTestCase |
| 13 | +from test.support.bytecode_helper import ( |
| 14 | + BytecodeTestCase, CfgOptimizationTestCase, CompilationStepTestCase) |
10 | 15 |
|
11 | 16 |
|
12 | 17 | def compile_pattern_with_fast_locals(pattern): |
@@ -2353,5 +2358,97 @@ def test_list_to_tuple_get_iter_is_safe(self): |
2353 | 2358 | self.assertEqual(items, []) |
2354 | 2359 |
|
2355 | 2360 |
|
| 2361 | +@unittest.skipIf(_testinternalcapi is None, "requires _testinternalcapi") |
| 2362 | +class OptimizeLoadFastTestCase(CompilationStepTestCase): |
| 2363 | + def check(self, insts, expected_insts): |
| 2364 | + self.check_instructions(insts) |
| 2365 | + self.check_instructions(expected_insts) |
| 2366 | + seq = self.seq_from_insts(insts) |
| 2367 | + opt_insts = _testinternalcapi.optimize_load_fast(seq) |
| 2368 | + expected_insts = self.seq_from_insts(expected_insts).get_instructions() |
| 2369 | + self.assertInstructionsMatch(opt_insts, expected_insts) |
| 2370 | + |
| 2371 | + def test_optimized(self): |
| 2372 | + insts = [ |
| 2373 | + ("LOAD_FAST", 0, 1), |
| 2374 | + ("LOAD_FAST", 1, 2), |
| 2375 | + ("BINARY_OP", 2, 3), |
| 2376 | + ] |
| 2377 | + expected = [ |
| 2378 | + ("LOAD_FAST_BORROW", 0, 1), |
| 2379 | + ("LOAD_FAST_BORROW", 1, 2), |
| 2380 | + ("BINARY_OP", 2, 3), |
| 2381 | + ] |
| 2382 | + self.check(insts, expected) |
| 2383 | + |
| 2384 | + insts = [ |
| 2385 | + ("LOAD_FAST", 0, 1), |
| 2386 | + ("LOAD_CONST", 1, 2), |
| 2387 | + ("SWAP", 2, 3), |
| 2388 | + ("POP_TOP", None, 4), |
| 2389 | + ] |
| 2390 | + expected = [ |
| 2391 | + ("LOAD_FAST_BORROW", 0, 1), |
| 2392 | + ("LOAD_CONST", 1, 2), |
| 2393 | + ("SWAP", 2, 3), |
| 2394 | + ("POP_TOP", None, 4), |
| 2395 | + ] |
| 2396 | + self.check(insts, expected) |
| 2397 | + |
| 2398 | + def test_unoptimized_if_unconsumed(self): |
| 2399 | + insts = [ |
| 2400 | + ("LOAD_FAST", 0, 1), |
| 2401 | + ("LOAD_FAST", 1, 2), |
| 2402 | + ("POP_TOP", None, 3), |
| 2403 | + ] |
| 2404 | + expected = [ |
| 2405 | + ("LOAD_FAST", 0, 1), |
| 2406 | + ("LOAD_FAST_BORROW", 1, 2), |
| 2407 | + ("POP_TOP", None, 3), |
| 2408 | + ] |
| 2409 | + self.check(insts, expected) |
| 2410 | + |
| 2411 | + insts = [ |
| 2412 | + ("LOAD_FAST", 0, 1), |
| 2413 | + ("COPY", 1, 2), |
| 2414 | + ("POP_TOP", None, 3), |
| 2415 | + ] |
| 2416 | + self.check(insts, insts) |
| 2417 | + |
| 2418 | + def test_unoptimized_if_support_killed(self): |
| 2419 | + insts = [ |
| 2420 | + ("LOAD_FAST", 0, 1), |
| 2421 | + ("LOAD_CONST", 0, 2), |
| 2422 | + ("STORE_FAST", 0, 3), |
| 2423 | + ("POP_TOP", None, 4), |
| 2424 | + ] |
| 2425 | + self.check(insts, insts) |
| 2426 | + |
| 2427 | + insts = [ |
| 2428 | + ("LOAD_FAST", 0, 1), |
| 2429 | + ("LOAD_CONST", 0, 2), |
| 2430 | + ("LOAD_CONST", 0, 3), |
| 2431 | + ("STORE_FAST_STORE_FAST", 0 << 4 | 1, 4), |
| 2432 | + ("POP_TOP", None, 5), |
| 2433 | + ] |
| 2434 | + self.check(insts, insts) |
| 2435 | + |
| 2436 | + def test_unoptimized_if_aliased(self): |
| 2437 | + insts = [ |
| 2438 | + ("LOAD_FAST", 0, 1), |
| 2439 | + ("STORE_FAST", 1, 2), |
| 2440 | + ] |
| 2441 | + self.check(insts, insts) |
| 2442 | + |
| 2443 | + insts = [ |
| 2444 | + ("LOAD_FAST", 0, 1), |
| 2445 | + ("LOAD_CONST", 0, 3), |
| 2446 | + ("STORE_FAST_STORE_FAST", 0 << 4 | 1, 4), |
| 2447 | + ] |
| 2448 | + self.check(insts, insts) |
| 2449 | + |
| 2450 | + |
| 2451 | + |
| 2452 | + |
2356 | 2453 | if __name__ == "__main__": |
2357 | 2454 | unittest.main() |
0 commit comments