added Opcode flags methods
generate `is_branch`, `is_terminator`, `can_trap` methods for `enum Opcode`.
This commit is contained in:
committed by
Jakob Stoklund Olesen
parent
19ac05577c
commit
93aa2b456e
@@ -83,7 +83,7 @@ trap = Instruction(
|
|||||||
'trap', r"""
|
'trap', r"""
|
||||||
Terminate execution unconditionally.
|
Terminate execution unconditionally.
|
||||||
""",
|
""",
|
||||||
is_terminator=True)
|
is_terminator=True, can_trap=True)
|
||||||
|
|
||||||
trapz = Instruction(
|
trapz = Instruction(
|
||||||
'trapz', r"""
|
'trapz', r"""
|
||||||
@@ -91,7 +91,7 @@ trapz = Instruction(
|
|||||||
|
|
||||||
if ``c`` is non-zero, execution continues at the following instruction.
|
if ``c`` is non-zero, execution continues at the following instruction.
|
||||||
""",
|
""",
|
||||||
ins=c)
|
ins=c, can_trap=True)
|
||||||
|
|
||||||
trapnz = Instruction(
|
trapnz = Instruction(
|
||||||
'trapnz', r"""
|
'trapnz', r"""
|
||||||
@@ -99,7 +99,7 @@ trapnz = Instruction(
|
|||||||
|
|
||||||
if ``c`` is zero, execution continues at the following instruction.
|
if ``c`` is zero, execution continues at the following instruction.
|
||||||
""",
|
""",
|
||||||
ins=c)
|
ins=c, can_trap=True)
|
||||||
|
|
||||||
rvals = Operand('rvals', VARIABLE_ARGS, doc='return values')
|
rvals = Operand('rvals', VARIABLE_ARGS, doc='return values')
|
||||||
|
|
||||||
@@ -111,7 +111,7 @@ x_return = Instruction(
|
|||||||
provided return values. The list of return values must match the
|
provided return values. The list of return values must match the
|
||||||
function signature's return types.
|
function signature's return types.
|
||||||
""",
|
""",
|
||||||
ins=rvals)
|
ins=rvals, is_terminator=True)
|
||||||
|
|
||||||
FN = Operand(
|
FN = Operand(
|
||||||
'FN',
|
'FN',
|
||||||
@@ -366,7 +366,7 @@ udiv = Instruction(
|
|||||||
|
|
||||||
This operation traps if the divisor is zero.
|
This operation traps if the divisor is zero.
|
||||||
""",
|
""",
|
||||||
ins=(x, y), outs=a)
|
ins=(x, y), outs=a, can_trap=True)
|
||||||
|
|
||||||
sdiv = Instruction(
|
sdiv = Instruction(
|
||||||
'sdiv', r"""
|
'sdiv', r"""
|
||||||
@@ -377,7 +377,7 @@ sdiv = Instruction(
|
|||||||
representable in :math:`B` bits two's complement. This only happens
|
representable in :math:`B` bits two's complement. This only happens
|
||||||
when :math:`x = -2^{B-1}, y = -1`.
|
when :math:`x = -2^{B-1}, y = -1`.
|
||||||
""",
|
""",
|
||||||
ins=(x, y), outs=a)
|
ins=(x, y), outs=a, can_trap=True)
|
||||||
|
|
||||||
urem = Instruction(
|
urem = Instruction(
|
||||||
'urem', """
|
'urem', """
|
||||||
@@ -385,7 +385,7 @@ urem = Instruction(
|
|||||||
|
|
||||||
This operation traps if the divisor is zero.
|
This operation traps if the divisor is zero.
|
||||||
""",
|
""",
|
||||||
ins=(x, y), outs=a)
|
ins=(x, y), outs=a, can_trap=True)
|
||||||
|
|
||||||
srem = Instruction(
|
srem = Instruction(
|
||||||
'srem', """
|
'srem', """
|
||||||
@@ -399,7 +399,7 @@ srem = Instruction(
|
|||||||
dividend. Should we add a ``smod`` instruction for the case where
|
dividend. Should we add a ``smod`` instruction for the case where
|
||||||
the result has the same sign as the divisor?
|
the result has the same sign as the divisor?
|
||||||
""",
|
""",
|
||||||
ins=(x, y), outs=a)
|
ins=(x, y), outs=a, can_trap=True)
|
||||||
|
|
||||||
a = Operand('a', iB)
|
a = Operand('a', iB)
|
||||||
x = Operand('x', iB)
|
x = Operand('x', iB)
|
||||||
@@ -1136,7 +1136,7 @@ fcvt_to_uint = Instruction(
|
|||||||
|
|
||||||
The result type must have the same number of vector lanes as the input.
|
The result type must have the same number of vector lanes as the input.
|
||||||
""",
|
""",
|
||||||
ins=x, outs=a)
|
ins=x, outs=a, can_trap=True)
|
||||||
|
|
||||||
fcvt_to_sint = Instruction(
|
fcvt_to_sint = Instruction(
|
||||||
'fcvt_to_sint', r"""
|
'fcvt_to_sint', r"""
|
||||||
@@ -1148,7 +1148,7 @@ fcvt_to_sint = Instruction(
|
|||||||
|
|
||||||
The result type must have the same number of vector lanes as the input.
|
The result type must have the same number of vector lanes as the input.
|
||||||
""",
|
""",
|
||||||
ins=x, outs=a)
|
ins=x, outs=a, can_trap=True)
|
||||||
|
|
||||||
x = Operand('x', Int)
|
x = Operand('x', Int)
|
||||||
a = Operand('a', FloatTo)
|
a = Operand('a', FloatTo)
|
||||||
|
|||||||
@@ -80,6 +80,7 @@ class Instruction(object):
|
|||||||
values or `variable_args`.
|
values or `variable_args`.
|
||||||
:param is_terminator: This is a terminator instruction.
|
:param is_terminator: This is a terminator instruction.
|
||||||
:param is_branch: This is a branch instruction.
|
:param is_branch: This is a branch instruction.
|
||||||
|
:param can_trap: This instruction can trap.
|
||||||
"""
|
"""
|
||||||
|
|
||||||
def __init__(self, name, doc, ins=(), outs=(), **kwargs):
|
def __init__(self, name, doc, ins=(), outs=(), **kwargs):
|
||||||
@@ -94,6 +95,9 @@ class Instruction(object):
|
|||||||
self.value_results = tuple(
|
self.value_results = tuple(
|
||||||
i for i, o in enumerate(self.outs) if o.is_value())
|
i for i, o in enumerate(self.outs) if o.is_value())
|
||||||
self._verify_polymorphic()
|
self._verify_polymorphic()
|
||||||
|
self.is_branch = 'is_branch' in kwargs
|
||||||
|
self.is_terminator = 'is_terminator' in kwargs
|
||||||
|
self.can_trap = 'can_trap' in kwargs
|
||||||
InstructionGroup.append(self)
|
InstructionGroup.append(self)
|
||||||
|
|
||||||
def __str__(self):
|
def __str__(self):
|
||||||
|
|||||||
@@ -271,6 +271,22 @@ def gen_opcodes(groups, fmt):
|
|||||||
fmt.line(i.camel_name + ',')
|
fmt.line(i.camel_name + ',')
|
||||||
fmt.line()
|
fmt.line()
|
||||||
|
|
||||||
|
with fmt.indented('impl Opcode {', '}'):
|
||||||
|
attrs = ['is_branch', 'is_terminator', 'can_trap']
|
||||||
|
|
||||||
|
for attr in attrs:
|
||||||
|
if attr != attrs[0]:
|
||||||
|
fmt.line()
|
||||||
|
|
||||||
|
with fmt.indented('fn {}(self) -> bool {{'
|
||||||
|
.format(attr), '}'):
|
||||||
|
with fmt.indented('match self {', '}'):
|
||||||
|
for i in instrs:
|
||||||
|
if getattr(i, attr):
|
||||||
|
fmt.format('Opcode::{} => true,', i.camel_name, i.name)
|
||||||
|
|
||||||
|
fmt.line('_ => false')
|
||||||
|
|
||||||
# Generate a private opcode_format table.
|
# Generate a private opcode_format table.
|
||||||
with fmt.indented(
|
with fmt.indented(
|
||||||
'const OPCODE_FORMAT: [InstructionFormat; {}] = ['
|
'const OPCODE_FORMAT: [InstructionFormat; {}] = ['
|
||||||
|
|||||||
Reference in New Issue
Block a user