1
0
mirror of https://github.com/myhdl/myhdl.git synced 2025-01-24 21:52:56 +08:00

Initial module decorator support

This commit is contained in:
Jan Decaluwe 2016-01-26 16:39:32 +01:00
parent 755d2b8c13
commit becb7a4cff
16 changed files with 338 additions and 97 deletions

View File

@ -32,12 +32,11 @@ from myhdl import Cosimulation, StopSimulation, _SuspendSimulation
from myhdl import _simulator, SimulationError
from myhdl._simulator import _signals, _siglist, _futureEvents
from myhdl._Waiter import _Waiter, _inferWaiter, _SignalWaiter,_SignalTupleWaiter
from myhdl._util import _flatten, _printExcInfo
from myhdl._util import _printExcInfo
from myhdl._instance import _Instantiator
from myhdl._module import _ModuleInstance
from myhdl._ShadowSignal import _ShadowSignal
schedule = _futureEvents.append
class _error:
@ -46,6 +45,21 @@ _error.ArgType = "Inappriopriate argument type"
_error.MultipleCosim = "Only a single cosimulator argument allowed"
_error.DuplicatedArg = "Duplicated argument"
# flatten Module objects out
def _flatten(*args):
arglist = []
for arg in args:
if isinstance(arg, _ModuleInstance):
arg = arg.subs
if isinstance(arg, (list, tuple, set)):
for item in arg:
arglist.extend(_flatten(item))
else:
arglist.append(arg)
return arglist
class Simulation(object):
""" Simulation class.
@ -231,4 +245,3 @@ def _makeWaiters(arglist):
if hasattr(sig, '_waiter'):
waiters.append(sig._waiter)
return waiters, cosim

View File

@ -82,6 +82,8 @@ class AlwaysCombError(Error):
pass
class InstanceError(Error):
pass
class ModuleError(Error):
pass
class CosimulationError(Error):
pass
class ExtractHierarchyError(Error):
@ -130,6 +132,7 @@ from ._always_comb import always_comb
from ._always_seq import always_seq, ResetSignal
from ._always import always
from ._instance import instance
from ._module import module
from ._enum import enum, EnumType, EnumItemType
from ._traceSignals import traceSignals
@ -159,6 +162,7 @@ __all__ = ["bin",
"Simulation",
"instances",
"instance",
"module",
"always_comb",
"always_seq",
"ResetSignal",

View File

@ -29,7 +29,7 @@ from myhdl._delay import delay
from myhdl._Signal import _Signal, _WaiterList, posedge, negedge
from myhdl._Waiter import _Waiter, _SignalWaiter, _SignalTupleWaiter, \
_DelayWaiter, _EdgeWaiter, _EdgeTupleWaiter
from myhdl._instance import _Instantiator
from myhdl._instance import _Instantiator, _getCallInfo
class _error:
pass
@ -40,6 +40,7 @@ _error.DecNrOfArgs = "decorator should have arguments"
def always(*args):
modname, modctxt = _getCallInfo()
for arg in args:
if isinstance(arg, _Signal):
arg._read = True
@ -56,16 +57,16 @@ def always(*args):
raise AlwaysError(_error.ArgType)
if func.__code__.co_argcount > 0:
raise AlwaysError(_error.NrOfArgs)
return _Always(func, args)
return _Always(func, args, modname=modname, modctxt=modctxt)
return _always_decorator
class _Always(_Instantiator):
def __init__(self, func, senslist):
def __init__(self, func, senslist, modname, modctxt):
self.func = func
self.senslist = tuple(senslist)
super(_Always, self).__init__(self.genfunc)
super(_Always, self).__init__(self.genfunc, modname=modname, modctxt=modctxt)
@property
def funcobj(self):

View File

@ -30,7 +30,7 @@ from myhdl import AlwaysCombError
from myhdl._Signal import _Signal, _isListOfSigs
from myhdl._util import _isGenFunc, _dedent
from myhdl._Waiter import _Waiter, _SignalWaiter, _SignalTupleWaiter
from myhdl._instance import _Instantiator
from myhdl._instance import _getCallInfo
from myhdl._always import _Always
class _error:
@ -43,51 +43,22 @@ _error.EmbeddedFunction = "embedded functions in always_comb function argument n
_error.EmptySensitivityList= "sensitivity list is empty"
def always_comb(func):
modname, modctxt = _getCallInfo()
if not isinstance( func, FunctionType):
raise AlwaysCombError(_error.ArgType)
if _isGenFunc(func):
raise AlwaysCombError(_error.ArgType)
if func.__code__.co_argcount > 0:
raise AlwaysCombError(_error.NrOfArgs)
c = _AlwaysComb(func)
c = _AlwaysComb(func, modname=modname, modctxt=modctxt)
return c
# class _AlwaysComb(_Instantiator):
class _AlwaysComb(_Always):
# def __init__(self, func, symdict):
# self.func = func
# self.symdict = symdict
# s = inspect.getsource(func)
# # remove decorators
# s = re.sub(r"@.*", "", s)
# s = s.lstrip()
# tree = compiler.parse(s)
# v = _SigNameVisitor(symdict)
# compiler.walk(tree, v)
# self.inputs = v.inputs
# self.outputs = v.outputs
# senslist = []
# for n in self.inputs:
# s = self.symdict[n]
# if isinstance(s, Signal):
# senslist.append(s)
# else: # list of sigs
# senslist.extend(s)
# self.senslist = tuple(senslist)
# self.gen = self.genfunc()
# if len(self.senslist) == 0:
# raise AlwaysCombError(_error.EmptySensitivityList)
# if len(self.senslist) == 1:
# W = _SignalWaiter
# else:
# W = _SignalTupleWaiter
# self.waiter = W(self.gen)
def __init__(self, func):
def __init__(self, func, modname, modctxt):
senslist = []
super(_AlwaysComb, self).__init__(func, senslist)
super(_AlwaysComb, self).__init__(func, senslist, modname=modname, modctxt=modctxt)
inouts = self.inouts | self.inputs.intersection(self.outputs)
if inouts:

View File

@ -32,6 +32,7 @@ from myhdl._delay import delay
from myhdl._Signal import _Signal, _WaiterList,_isListOfSigs
from myhdl._Waiter import _Waiter, _EdgeWaiter, _EdgeTupleWaiter
from myhdl._always import _Always
from myhdl._instance import _getCallInfo
# evacuate this later
AlwaysSeqError = AlwaysError
@ -59,6 +60,7 @@ class ResetSignal(_Signal):
def always_seq(edge, reset):
modname, modctxt = _getCallInfo()
if not isinstance(edge, _WaiterList):
raise AlwaysSeqError(_error.EdgeType)
edge.sig._read = True
@ -76,13 +78,13 @@ def always_seq(edge, reset):
raise AlwaysSeqError(_error.ArgType)
if func.__code__.co_argcount > 0:
raise AlwaysSeqError(_error.NrOfArgs)
return _AlwaysSeq(func, edge, reset)
return _AlwaysSeq(func, edge, reset, modname=modname, modctxt=modctxt)
return _always_seq_decorator
class _AlwaysSeq(_Always):
def __init__(self, func, edge, reset):
def __init__(self, func, edge, reset, modname, modctxt):
senslist = [edge]
self.reset = reset
if reset is not None:
@ -97,7 +99,7 @@ class _AlwaysSeq(_Always):
else:
self.genfunc = self.genfunc_no_reset
super(_AlwaysSeq, self).__init__(func, senslist)
super(_AlwaysSeq, self).__init__(func, senslist, modname=modname, modctxt=modctxt)
if self.inouts:
raise AlwaysSeqError(_error.SigAugAssign, v.inouts)

63
myhdl/_getHierarchy.py Normal file
View File

@ -0,0 +1,63 @@
# This file is part of the myhdl library, a Python package for using
# Python as a Hardware Description Language.
#
# Copyright (C) 2003-2016 Jan Decaluwe
#
# The myhdl library is free software; you can redistribute it and/or
# modify it under the terms of the GNU Lesser General Public License as
# published by the Free Software Foundation; either version 2.1 of the
# License, or (at your option) any later version.
#
# This library is distributed in the hope that it will be useful, but
# WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
# Lesser General Public License for more details.
#
# You should have received a copy of the GNU Lesser General Public
# License along with this library; if not, write to the Free Software
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
""" myhdl _getHierarchy module.
"""
from __future__ import absolute_import
from myhdl._extractHierarchy import _Instance
from myhdl._instance import _Instantiator
from myhdl._module import _ModuleInstance
class _Hierarchy(object):
def __init__(self, name, modinst):
self.top = modinst
self.hierarchy = hierarchy = []
self.absnames = absnames = {}
_getHierarchyHelper(1, modinst, hierarchy)
# compatibility with _extractHierarchy
# walk the hierarchy to define relative and absolute names
names = {}
top_inst = hierarchy[0]
obj, subs = top_inst.obj, top_inst.subs
names[id(obj)] = name
absnames[id(obj)] = name
for inst in hierarchy:
obj, subs = inst.obj, inst.subs
inst.name = names[id(obj)]
tn = absnames[id(obj)]
for sn, so in subs:
names[id(so)] = sn
absnames[id(so)] = "%s_%s" % (tn, sn)
# print (names)
# print(absnames)
def _getHierarchy(name, modinst):
h = _Hierarchy(name, modinst)
return h
def _getHierarchyHelper(level, modinst, hierarchy):
subs = [(s.name, s) for s in modinst.subs]
inst = _Instance(level, modinst, subs, modinst.sigdict, modinst.memdict)
hierarchy.append(inst)
for inst in modinst.subs:
if isinstance(inst, _ModuleInstance):
_getHierarchyHelper(level+1, inst, hierarchy)

View File

@ -21,6 +21,7 @@
from __future__ import absolute_import
import inspect
from types import FunctionType
from myhdl import InstanceError
@ -34,19 +35,42 @@ class _error:
_error.NrOfArgs = "decorated generator function should not have arguments"
_error.ArgType = "decorated object should be a generator function"
def _getCallInfo():
"""Get info of the callers of e.g. an instantiator decorator.
For hierarchy extraction, instantator decorators should only be used
within a module context. This function is hack to get info to check
that. It uses theframe stack:
0: this function
1: the instantiator decorator
2: the module function that defines instances
3: the caller of the module function, e.g. the ModuleInstance class.
"""
from myhdl import _module
modname = inspect.stack()[2][3]
modctxt = False
f_locals = inspect.stack()[3][0].f_locals
if 'self' in f_locals:
print f_locals['self'].__class__
modctxt = isinstance(f_locals['self'], _module._ModuleInstance)
return modname, modctxt
def instance(genfunc):
modname, modctxt = _getCallInfo()
if not isinstance(genfunc, FunctionType):
raise InstanceError(_error.ArgType)
if not _isGenFunc(genfunc):
raise InstanceError(_error.ArgType)
if genfunc.__code__.co_argcount > 0:
raise InstanceError(_error.NrOfArgs)
return _Instantiator(genfunc)
return _Instantiator(genfunc, modname=modname, modctxt=modctxt)
class _Instantiator(object):
def __init__(self, genfunc):
def __init__(self, genfunc, modname, modctxt):
self.modname = modname
self.modctxt = modctxt
self.genfunc = genfunc
self.gen = genfunc()
# infer symdict
@ -73,6 +97,12 @@ class _Instantiator(object):
self.outputs = v.outputs
self.inouts = v.inouts
self.embedded_func = v.embedded_func
self.sigdict = v.sigdict
self.losdict = v.losdict
@property
def name(self):
return self.funcobj.__name__
@property
def funcobj(self):

95
myhdl/_module.py Normal file
View File

@ -0,0 +1,95 @@
# This file is part of the myhdl library, a Python package for using
# Python as a Hardware Description Language.
#
# Copyright (C) 2003-2016 Jan Decaluwe
#
# The myhdl library is free software; you can redistribute it and/or
# modify it under the terms of the GNU Lesser General Public License as
# published by the Free Software Foundation; either version 2.1 of the
# License, or (at your option) any later version.
#
# This library is distributed in the hope that it will be useful, but
# WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
# Lesser General Public License for more details.
# You should have received a copy of the GNU Lesser General Public
# License along with this library; if not, write to the Free Software
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
""" Module with the @module decorator function. """
from __future__ import absolute_import
import functools
import inspect
from myhdl import ModuleError
from myhdl._instance import _Instantiator
from myhdl._util import _flatten
from myhdl._extractHierarchy import _MemInfo, _makeMemInfo
class _error:
pass
_error.ArgType = "A module should return module or instantiator objects"
_error.InstanceError = "%s: submodule %s should be encapsulated in a module decorator"
def module(modfunc):
return _Module(modfunc)
class _Module(object):
def __init__(self, modfunc):
self.modfunc = modfunc
self.__name__ = self.name = modfunc.__name__
self.count = 0
def __call__(self, *args, **kwargs):
modinst = _ModuleInstance(self, *args, **kwargs)
self.count += 1
return modinst
class _ModuleInstance(object):
def __init__(self, mod, *args, **kwargs):
self.mod = mod
self.sigdict = {}
self.memdict = {}
# flatten, but keep ModuleInstance objects
self.subs = _flatten(mod.modfunc(*args, **kwargs))
self.verifyMod()
self.updateMod()
self.inferInterface(*args, **kwargs)
self.name = self.__name__ = mod.__name__ + '_' + str(mod.count)
def verifyMod(self):
for inst in self.subs:
# print (inst.name, type(inst))
if not isinstance(inst, (_ModuleInstance, _Instantiator)):
raise ModuleError(_error.ArgType)
if isinstance(inst, _Instantiator):
if not inst.modctxt:
raise ModuleError(_error.InstanceError % (self.mod.name, inst.modname))
def updateMod(self):
losdict = {}
for inst in self.subs:
if isinstance(inst, _Instantiator):
self.sigdict.update(inst.sigdict)
losdict.update(inst.losdict)
else:
# reset instantiation counter
self.mod.count = 0
# compatibility patches from _extractHierarchy
for s in self.sigdict.values():
s._markUsed()
for n, l in losdict.items():
m = _makeMemInfo(l)
self.memdict[n] = m
m._used = True
def inferInterface(self, *args, **kwargs):
from myhdl.conversion._analyze import _analyzeTopFunc
intf = _analyzeTopFunc(self.mod.modfunc, *args, **kwargs)
self.argnames = intf.argnames
self.argdict = intf.argdict

View File

@ -25,6 +25,8 @@ now -- function that returns the current simulation time
"""
_signals = []
_siglist = []
_futureEvents = []

View File

@ -13,6 +13,8 @@ class _SigNameVisitor(ast.NodeVisitor):
self.inouts = set()
self.embedded_func = None
self.context = 'input'
self.sigdict = {}
self.losdict = {}
def visit_Module(self, node):
for n in node.body:
@ -34,20 +36,24 @@ class _SigNameVisitor(ast.NodeVisitor):
self.generic_visit(node)
def visit_Name(self, node):
id = node.id
if id not in self.symdict:
n = node.id
if n not in self.symdict:
return
s = self.symdict[id]
s = self.symdict[n]
if isinstance(s, (_Signal, intbv)) or _isListOfSigs(s):
if self.context == 'input':
self.inputs.add(id)
self.inputs.add(n)
elif self.context == 'output':
self.outputs.add(id)
self.outputs.add(n)
elif self.context == 'inout':
self.inouts.add(id)
self.inouts.add(n)
else:
print(self.context)
raise AssertionError("bug in _SigNameVisitor")
if isinstance(s, _Signal):
self.sigdict[n] = s
elif _isListOfSigs(s):
self.losdict[n] = s
def visit_Assign(self, node):
self.context = 'output'

View File

@ -55,6 +55,8 @@ from myhdl._util import _flatten
from myhdl._compat import integer_types, class_types, StringIO
from myhdl._ShadowSignal import _TristateSignal, _TristateDriver
from myhdl._module import _ModuleInstance
from myhdl._getHierarchy import _getHierarchy
_version = myhdl.__version__.replace('.','')
_shortversion = _version.replace('dev','')
@ -70,6 +72,8 @@ def _checkArgs(arglist):
def _flatten(*args):
arglist = []
for arg in args:
if isinstance(arg, _ModuleInstance):
arg = arg.subs
if id(arg) in _userCodeMap['vhdl']:
arglist.append(_userCodeMap['vhdl'][id(arg)])
elif isinstance(arg, (list, tuple, set)):
@ -125,18 +129,28 @@ class _ToVHDLConvertor(object):
from myhdl import _traceSignals
if _traceSignals._tracing:
raise ToVHDLError("Cannot use toVHDL while tracing signals")
if not callable(func):
raise ToVHDLError(_error.FirstArgType, "got %s" % type(func))
if not isinstance(func, _ModuleInstance):
if not callable(func):
raise ToVHDLError(_error.FirstArgType, "got %s" % type(func))
_converting = 1
if self.name is None:
name = func.__name__
if isinstance(func, _ModuleInstance):
name = func.mod.__name__
else:
name = str(self.name)
try:
h = _HierExtr(name, func, *args, **kwargs)
finally:
_converting = 0
if isinstance(func, _ModuleInstance):
try:
h = _getHierarchy(name, func)
finally:
_converting = 0
else:
try:
h = _HierExtr(name, func, *args, **kwargs)
finally:
_converting = 0
if self.directory is None:
directory = ''
@ -170,7 +184,10 @@ class _ToVHDLConvertor(object):
_annotateTypes(genlist)
### infer interface
intf = _analyzeTopFunc(func, *args, **kwargs)
if isinstance(func, _ModuleInstance):
intf = func # already inferred
else:
intf = _analyzeTopFunc(func, *args, **kwargs)
intf.name = name
# sanity checks on interface
for portname in intf.argnames:

View File

@ -52,6 +52,9 @@ from myhdl.conversion._analyze import (_analyzeSigs, _analyzeGens, _analyzeTopFu
from myhdl._Signal import _Signal
from myhdl._ShadowSignal import _TristateSignal, _TristateDriver
from myhdl._module import _ModuleInstance
from myhdl._getHierarchy import _getHierarchy
_converting = 0
_profileFunc = None
@ -63,6 +66,8 @@ def _checkArgs(arglist):
def _flatten(*args):
arglist = []
for arg in args:
if isinstance(arg, _ModuleInstance):
arg = arg.subs
if id(arg) in _userCodeMap['verilog']:
arglist.append(_userCodeMap['verilog'][id(arg)])
elif isinstance(arg, (list, tuple, set)):
@ -120,18 +125,28 @@ class _ToVerilogConvertor(object):
from myhdl import _traceSignals
if _traceSignals._tracing:
raise ToVerilogError("Cannot use toVerilog while tracing signals")
if not callable(func):
raise ToVerilogError(_error.FirstArgType, "got %s" % type(func))
if not isinstance(func, _ModuleInstance):
if not callable(func):
raise ToVerilogError(_error.FirstArgType, "got %s" % type(func))
_converting = 1
if self.name is None:
name = func.__name__
if isinstance(func, _ModuleInstance):
name = func.mod.__name__
else:
name = str(self.name)
try:
h = _HierExtr(name, func, *args, **kwargs)
finally:
_converting = 0
if isinstance(func, _ModuleInstance):
try:
h = _getHierarchy(name, func)
finally:
_converting = 0
else:
try:
h = _HierExtr(name, func, *args, **kwargs)
finally:
_converting = 0
if self.directory is None:
directory = ''
@ -152,8 +167,13 @@ class _ToVerilogConvertor(object):
siglist, memlist = _analyzeSigs(h.hierarchy)
_annotateTypes(genlist)
intf = _analyzeTopFunc(func, *args, **kwargs)
### infer interface
if isinstance(func, _ModuleInstance):
intf = func # already inferred
else:
intf = _analyzeTopFunc(func, *args, **kwargs)
intf.name = name
doc = _makeDoc(inspect.getdoc(func))
self._convert_filter(h, intf, siglist, memlist, genlist)

View File

@ -12,6 +12,7 @@ import myhdl
from myhdl._Simulation import Simulation
from myhdl.conversion._toVHDL import toVHDL
from myhdl.conversion._toVerilog import toVerilog
from myhdl._module import _ModuleInstance
_version = myhdl.__version__.replace('.','')
# strip 'dev' for version
@ -112,6 +113,8 @@ class _VerificationClass(object):
name = toVerilog.name
elif hdl == 'VHDL' and toVHDL.name is not None:
name = toVHDL.name
elif isinstance(func, _ModuleInstance):
name = func.mod.__name__
else:
name = func.__name__
@ -129,10 +132,16 @@ class _VerificationClass(object):
skipchars = hdlsim.skipchars
ignore = hdlsim.ignore
if hdl == "VHDL":
inst = toVHDL(func, *args, **kwargs)
if isinstance(func, _ModuleInstance):
if hdl == "VHDL":
inst = toVHDL(func)
else:
inst = toVerilog(func)
else:
inst = toVerilog(func, *args, **kwargs)
if hdl == "VHDL":
inst = toVHDL(func, *args, **kwargs)
else:
inst = toVerilog(func, *args, **kwargs)
if hdl == "VHDL":
if not os.path.exists("work"):

View File

@ -5,6 +5,7 @@ path = os.path
from myhdl import *
from myhdl.conversion import verify
@module
def bin2gray2(B, G, width):
""" Gray encoder.
@ -22,6 +23,7 @@ def bin2gray2(B, G, width):
G.next[i] = Bext[i+1] ^ Bext[i]
return logic
@module
def bin2gray(B, G, width):
""" Gray encoder.
@ -42,7 +44,7 @@ def bin2gray(B, G, width):
return logic
@module
def bin2grayBench(width, bin2gray):
B = Signal(intbv(0)[width:])
@ -67,8 +69,7 @@ def bin2grayBench(width, bin2gray):
def test1():
assert verify(bin2grayBench, width=8, bin2gray=bin2gray) == 0
assert verify(bin2grayBench(width=8, bin2gray=bin2gray)) == 0
def test2():
assert verify(bin2grayBench, width=8, bin2gray=bin2gray2) == 0
assert verify(bin2grayBench(width=8, bin2gray=bin2gray2)) == 0

View File

@ -12,6 +12,7 @@ t_State_b = enum('SEARCH', 'CONFIRM', 'SYNC')
t_State_oh = enum('SEARCH', 'CONFIRM', 'SYNC', encoding="one_hot")
t_State_oc = enum('SEARCH', 'CONFIRM', 'SYNC', encoding="one_cold")
@module
def FramerCtrl(SOF, state, syncFlag, clk, reset_n, t_State):
""" Framing control FSM.
@ -55,8 +56,7 @@ def FramerCtrl(SOF, state, syncFlag, clk, reset_n, t_State):
return FSM
@module
def FSMBench(FramerCtrl, t_State):
SOF = Signal(bool(0))
@ -110,5 +110,5 @@ def FSMBench(FramerCtrl, t_State):
def test():
assert verify(FSMBench, FramerCtrl, t_State_b) == 0
assert verify(FSMBench(FramerCtrl, t_State_b)) == 0

View File

@ -12,6 +12,7 @@ from myhdl.conversion import verify
ACTIVE_LOW, INACTIVE_HIGH = bool(0), bool(1)
@module
def incRef(count, enable, clock, reset, n):
""" Incrementer with enable.
@ -32,6 +33,7 @@ def incRef(count, enable, clock, reset, n):
count.next = (count + 1) % n
return logic
@module
def inc(count, enable, clock, reset, n):
""" Incrementer with enable.
@ -54,6 +56,7 @@ def inc(count, enable, clock, reset, n):
return incProcess
@module
def inc2(count, enable, clock, reset, n):
@always(clock.posedge, reset.negedge)
@ -69,6 +72,7 @@ def inc2(count, enable, clock, reset, n):
return incProcess
@module
def incFunc(count, enable, clock, reset, n):
def incFuncFunc(cnt, enable):
count_next = intbv(0, min=0, max=n)
@ -87,6 +91,7 @@ def incFunc(count, enable, clock, reset, n):
return incFuncGen
@module
def incTask(count, enable, clock, reset, n):
def incTaskFunc(cnt, enable, reset, n):
@ -109,6 +114,7 @@ def incTask(count, enable, clock, reset, n):
return incTaskGen
@module
def incTaskFreeVar(count, enable, clock, reset, n):
def incTaskFunc():
@ -126,6 +132,7 @@ def incTaskFreeVar(count, enable, clock, reset, n):
return incTaskGen
@module
def IncBench(inc):
NR_CYCLES = 201
@ -163,18 +170,18 @@ def IncBench(inc):
def test_incReg():
assert verify(IncBench, incRef) == 0
assert verify(IncBench(incRef)) == 0
def test_inc():
assert verify(IncBench, inc) == 0
assert verify(IncBench(inc)) == 0
def test_inc2():
assert verify(IncBench, inc2) == 0
assert verify(IncBench(inc2)) == 0
def testIncTask():
assert verify(IncBench, incTask) == 0
assert verify(IncBench(incTask)) == 0
def testIncFunc():
assert verify(IncBench, incFunc) == 0
assert verify(IncBench(incFunc)) == 0