Skip to content

Commit

Permalink
Support Python 3.8.
Browse files Browse the repository at this point in the history
  • Loading branch information
serhiy-storchaka committed Oct 16, 2018
1 parent a49c874 commit 674cb26
Show file tree
Hide file tree
Showing 3 changed files with 60 additions and 55 deletions.
70 changes: 35 additions & 35 deletions bytecode/instr.py
Original file line number Diff line number Diff line change
Expand Up @@ -145,31 +145,32 @@ def _check_arg_int(name, arg):
% name)


_stack_effects = {
# NOTE: the entries are all 2-tuples. Entry[0/False] is non-taken jumps.
# Entry[1/True] is for taken jumps.

# opcodes not in dis.stack_effect
_opcode.opmap['EXTENDED_ARG']: (0, 0),
_opcode.opmap['NOP']: (0, 0),

# Jump taken/not-taken are different:
_opcode.opmap['JUMP_IF_TRUE_OR_POP']: (-1, 0),
_opcode.opmap['JUMP_IF_FALSE_OR_POP']: (-1, 0),
_opcode.opmap['FOR_ITER']: (1, -1),
_opcode.opmap['SETUP_WITH']: (1, 6),
_opcode.opmap['SETUP_ASYNC_WITH']: (0, 5),
_opcode.opmap['SETUP_EXCEPT']: (0, 6), # as of 3.7, below for <=3.6
_opcode.opmap['SETUP_FINALLY']: (0, 6), # as of 3.7, below for <=3.6
}

# More stack effect values that are unique to the version of Python.
if sys.version_info < (3, 7):
_stack_effects.update({
_opcode.opmap['SETUP_WITH']: (7, 7),
_opcode.opmap['SETUP_EXCEPT']: (6, 9),
_opcode.opmap['SETUP_FINALLY']: (6, 9),
})
if sys.version_info < (3, 8):
_stack_effects = {
# NOTE: the entries are all 2-tuples. Entry[0/False] is non-taken jumps.
# Entry[1/True] is for taken jumps.

# opcodes not in dis.stack_effect
_opcode.opmap['EXTENDED_ARG']: (0, 0),
_opcode.opmap['NOP']: (0, 0),

# Jump taken/not-taken are different:
_opcode.opmap['JUMP_IF_TRUE_OR_POP']: (-1, 0),
_opcode.opmap['JUMP_IF_FALSE_OR_POP']: (-1, 0),
_opcode.opmap['FOR_ITER']: (1, -1),
_opcode.opmap['SETUP_WITH']: (1, 6),
_opcode.opmap['SETUP_ASYNC_WITH']: (0, 5),
_opcode.opmap['SETUP_EXCEPT']: (0, 6), # as of 3.7, below for <=3.6
_opcode.opmap['SETUP_FINALLY']: (0, 6), # as of 3.7, below for <=3.6
}

# More stack effect values that are unique to the version of Python.
if sys.version_info < (3, 7):
_stack_effects.update({
_opcode.opmap['SETUP_WITH']: (7, 7),
_opcode.opmap['SETUP_EXCEPT']: (6, 9),
_opcode.opmap['SETUP_FINALLY']: (6, 9),
})


class Instr:
Expand Down Expand Up @@ -298,19 +299,18 @@ def lineno(self, lineno):
self._set(self._name, self._arg, lineno)

def stack_effect(self, jump=None):
effect = _stack_effects.get(self._opcode, None)
if effect is not None:
return max(effect) if jump is None else effect[jump]

# TODO: if dis.stack_effect ever expands to take the 'jump' parameter
# then we should pass that through, and perhaps remove some of the
# overrides that are set up in _init_stack_effects()

# All opcodes whose arguments are not represented by integers have
# a stack_effect indepent of their argument.
arg = (self._arg if isinstance(self._arg, int) else
0 if self._opcode >= _opcode.HAVE_ARGUMENT else None)
return dis.stack_effect(self._opcode, arg)
0 if self._opcode >= _opcode.HAVE_ARGUMENT else None)

if sys.version_info < (3, 8):
effect = _stack_effects.get(self._opcode, None)
if effect is not None:
return max(effect) if jump is None else effect[jump]
return dis.stack_effect(self._opcode, arg)
else:
return dis.stack_effect(self._opcode, arg, jump=jump)

def copy(self):
return self.__class__(self._name, self._arg, lineno=self._lineno)
Expand Down
2 changes: 2 additions & 0 deletions bytecode/tests/test_cfg.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
#!/usr/bin/env python3
import io
import sys
import unittest
import contextlib
from bytecode import (Label, Compare, SetLineno, Instr,
Expand Down Expand Up @@ -215,6 +216,7 @@ def test_from_bytecode(self):
Instr('RETURN_VALUE', lineno=4)])
# FIXME: test other attributes

@unittest.skipIf(sys.version_info >= (3, 8), "requires Python < 3.8")
def test_from_bytecode_loop(self):
# for x in (1, 2, 3):
# if x == 2:
Expand Down
43 changes: 23 additions & 20 deletions bytecode/tests/test_peephole_opt.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import sys
import unittest
from bytecode import Label, Instr, Compare, Bytecode, ControlFlowGraph
from bytecode import peephole_opt
Expand Down Expand Up @@ -432,27 +433,28 @@ def test_return_value(self):
# return + JUMP_ABSOLUTE: remove JUMP_ABSOLUTE
# while 1:
# return 7
setup_loop = Label()
return_label = Label()
code = Bytecode([setup_loop,
Instr('SETUP_LOOP', return_label, lineno=2),
Instr('LOAD_CONST', 7, lineno=3),
Instr('RETURN_VALUE', lineno=3),
Instr('JUMP_ABSOLUTE', setup_loop, lineno=3),
Instr('POP_BLOCK', lineno=3),
return_label,
Instr('LOAD_CONST', None, lineno=3),
Instr('RETURN_VALUE', lineno=3)])
code = ControlFlowGraph.from_bytecode(code)
if sys.version_info < (3, 8):
setup_loop = Label()
return_label = Label()
code = Bytecode([setup_loop,
Instr('SETUP_LOOP', return_label, lineno=2),
Instr('LOAD_CONST', 7, lineno=3),
Instr('RETURN_VALUE', lineno=3),
Instr('JUMP_ABSOLUTE', setup_loop, lineno=3),
Instr('POP_BLOCK', lineno=3),
return_label,
Instr('LOAD_CONST', None, lineno=3),
Instr('RETURN_VALUE', lineno=3)])
code = ControlFlowGraph.from_bytecode(code)

end_loop = Label()
self.check(code,
Instr('SETUP_LOOP', end_loop, lineno=2),
Instr('LOAD_CONST', 7, lineno=3),
Instr('RETURN_VALUE', lineno=3),
end_loop,
Instr('LOAD_CONST', None, lineno=3),
Instr('RETURN_VALUE', lineno=3))
end_loop = Label()
self.check(code,
Instr('SETUP_LOOP', end_loop, lineno=2),
Instr('LOAD_CONST', 7, lineno=3),
Instr('RETURN_VALUE', lineno=3),
end_loop,
Instr('LOAD_CONST', None, lineno=3),
Instr('RETURN_VALUE', lineno=3))

def test_not_jump_if_false(self):
# Replace UNARY_NOT+POP_JUMP_IF_FALSE with POP_JUMP_IF_TRUE
Expand Down Expand Up @@ -630,6 +632,7 @@ def test_jump_if_true_to_jump_if_false(self):
Instr('LOAD_CONST', None),
Instr('RETURN_VALUE'))

@unittest.skipIf(sys.version_info >= (3, 8), "requires Python < 3.8")
def test_jump_if_false_to_jump_if_false(self):
# Replace JUMP_IF_FALSE_OR_POP jumping to POP_JUMP_IF_FALSE <label>
# with POP_JUMP_IF_FALSE <label>
Expand Down

0 comments on commit 674cb26

Please sign in to comment.