<s> import builtins as _builtins <EOL> import collections as _collections <EOL> from migen . fhdl import tracer as _tracer <EOL> from migen . util . misc import flat_iteration as _flat_iteration <EOL> class DUID : <EOL> """<STR_LIT>""" <EOL> __next_uid = <NUM_LIT:0> <EOL> def __init__ ( self ) : <EOL> self . duid = DUID . __next_uid <EOL> DUID . __next_uid += <NUM_LIT:1> <EOL> class _Value ( DUID ) : <EOL> """<STR_LIT>""" <EOL> def __bool__ ( self ) : <EOL> if isinstance ( self , _Operator ) and self . op == "<STR_LIT>" : <EOL> a , b = self . operands <EOL> if isinstance ( a , Constant ) and isinstance ( b , Constant ) : <EOL> return a . value == b . value <EOL> if isinstance ( a , Signal ) and isinstance ( b , Signal ) : <EOL> return a is b <EOL> if ( isinstance ( a , Constant ) and isinstance ( b , Signal ) <EOL> or isinstance ( a , Signal ) and isinstance ( b , Constant ) ) : <EOL> return False <EOL> raise TypeError ( "<STR_LIT>" ) <EOL> def __invert__ ( self ) : <EOL> return _Operator ( "<STR_LIT>" , [ self ] ) <EOL> def __neg__ ( self ) : <EOL> return _Operator ( "<STR_LIT:->" , [ self ] ) <EOL> def __add__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT:+>" , [ self , other ] ) <EOL> def __radd__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT:+>" , [ other , self ] ) <EOL> def __sub__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT:->" , [ self , other ] ) <EOL> def __rsub__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT:->" , [ other , self ] ) <EOL> def __mul__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT:*>" , [ self , other ] ) <EOL> def __rmul__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT:*>" , [ other , self ] ) <EOL> def __lshift__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT>" , [ self , other ] ) <EOL> def __rlshift__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT>" , [ other , self ] ) <EOL> def __rshift__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT>" , [ self , other ] ) <EOL> def __rrshift__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT>" , [ other , self ] ) <EOL> def __and__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT:&>" , [ self , other ] ) <EOL> def __rand__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT:&>" , [ other , self ] ) <EOL> def __xor__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT>" , [ self , other ] ) <EOL> def __rxor__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT>" , [ other , self ] ) <EOL> def __or__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT:|>" , [ self , other ] ) <EOL> def __ror__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT:|>" , [ other , self ] ) <EOL> def __lt__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT:<>" , [ self , other ] ) <EOL> def __le__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT>" , [ self , other ] ) <EOL> def __eq__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT>" , [ self , other ] ) <EOL> def __ne__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT>" , [ self , other ] ) <EOL> def __gt__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT:>>" , [ self , other ] ) <EOL> def __ge__ ( self , other ) : <EOL> return _Operator ( "<STR_LIT>" , [ self , other ] ) <EOL> def __len__ ( self ) : <EOL> from migen . fhdl . bitcontainer import value_bits_sign <EOL> return value_bits_sign ( self ) [ <NUM_LIT:0> ] <EOL> def __getitem__ ( self , key ) : <EOL> n = len ( self ) <EOL> if isinstance ( key , int ) : <EOL> if key >= n : <EOL> raise IndexError <EOL> if key < <NUM_LIT:0> : <EOL> key += n <EOL> return _Slice ( self , key , key + <NUM_LIT:1> ) <EOL> elif isinstance ( key , slice ) : <EOL> start , stop , step = key . indices ( n ) <EOL> if step != <NUM_LIT:1> : <EOL> return Cat ( self [ i ] for i in range ( start , stop , step ) ) <EOL> return _Slice ( self , start , stop ) <EOL> else : <EOL> raise TypeError ( "<STR_LIT>" . format ( <EOL> type ( key ) , repr ( key ) ) ) <EOL> def eq ( self , r ) : <EOL> """<STR_LIT>""" <EOL> return _Assign ( self , r ) <EOL> def __hash__ ( self ) : <EOL> raise TypeError ( "<STR_LIT>" . format ( type ( self ) . __name__ ) ) <EOL> def wrap ( value ) : <EOL> """<STR_LIT>""" <EOL> if isinstance ( value , ( bool , int ) ) : <EOL> value = Constant ( value ) <EOL> if not isinstance ( value , _Value ) : <EOL> raise TypeError ( "<STR_LIT>" + str ( value ) + "<STR_LIT>" ) <EOL> return value <EOL> class _Operator ( _Value ) : <EOL> def __init__ ( self , op , operands ) : <EOL> _Value . __init__ ( self ) <EOL> self . op = op <EOL> self . operands = [ wrap ( o ) for o in operands ] <EOL> def Mux ( sel , val1 , val0 ) : <EOL> """<STR_LIT>""" <EOL> return _Operator ( "<STR_LIT:m>" , [ sel , val1 , val0 ] ) <EOL> class _Slice ( _Value ) : <EOL> def __init__ ( self , value , start , stop ) : <EOL> _Value . __init__ ( self ) <EOL> if not isinstance ( start , int ) or not isinstance ( stop , int ) : <EOL> raise TypeError ( "<STR_LIT>" ) <EOL> self . value = wrap ( value ) <EOL> self . start = start <EOL> self . stop = stop <EOL> class Cat ( _Value ) : <EOL> """<STR_LIT>""" <EOL> def __init__ ( self , * args ) : <EOL> _Value . __init__ ( self ) <EOL> self . l = [ wrap ( v ) for v in _flat_iteration ( args ) ] <EOL> class Replicate ( _Value ) : <EOL> """<STR_LIT>""" <EOL> def __init__ ( self , v , n ) : <EOL> _Value . __init__ ( self ) <EOL> if not isinstance ( n , int ) or n < <NUM_LIT:0> : <EOL> raise TypeError ( "<STR_LIT>" ) <EOL> self . v = wrap ( v ) <EOL> self . n = n <EOL> class Constant ( _Value ) : <EOL> """<STR_LIT>""" <EOL> def __init__ ( self , value , bits_sign = None ) : <EOL> from migen . fhdl . bitcontainer import bits_for <EOL> _Value . __init__ ( self ) <EOL> self . value = int ( value ) <EOL> if bits_sign is None : <EOL> bits_sign = bits_for ( self . value ) , self . value < <NUM_LIT:0> <EOL> elif isinstance ( bits_sign , int ) : <EOL> bits_sign = bits_sign , self . value < <NUM_LIT:0> <EOL> self . nbits , self . signed = bits_sign <EOL> if not isinstance ( self . nbits , int ) or self . nbits <= <NUM_LIT:0> : <EOL> raise TypeError ( "<STR_LIT>" ) <EOL> def __hash__ ( self ) : <EOL> return self . value <EOL> C = Constant <EOL> class Signal ( _Value ) : <EOL> """<STR_LIT>""" <EOL> def __init__ ( self , bits_sign = None , name = None , variable = False , reset = <NUM_LIT:0> , name_override = None , min = None , max = None , related = None ) : <EOL> from migen . fhdl . bitcontainer import bits_for <EOL> _Value . __init__ ( self ) <EOL> if bits_sign is None : <EOL> if min is None : <EOL> min = <NUM_LIT:0> <EOL> if max is None : <EOL> max = <NUM_LIT:2> <EOL> max -= <NUM_LIT:1> <EOL> assert ( min < max ) <EOL> self . signed = min < <NUM_LIT:0> or max < <NUM_LIT:0> <EOL> self . nbits = _builtins . max ( bits_for ( min , self . signed ) , bits_for ( max , self . signed ) ) <EOL> else : <EOL> assert ( min is None and max is None ) <EOL> if isinstance ( bits_sign , tuple ) : <EOL> self . nbits , self . signed = bits_sign <EOL> else : <EOL> self . nbits , self . signed = bits_sign , False <EOL> if not isinstance ( self . nbits , int ) or self . nbits <= <NUM_LIT:0> : <EOL> raise ValueError ( "<STR_LIT>" ) <EOL> self . variable = variable <EOL> self . reset = reset <EOL> self . name_override = name_override <EOL> self . backtrace = _tracer . trace_back ( name ) <EOL> self . related = related <EOL> def __setattr__ ( self , k , v ) : <EOL> if k == "<STR_LIT>" : <EOL> v = wrap ( v ) <EOL> _Value . __setattr__ ( self , k , v ) <EOL> def __repr__ ( self ) : <EOL> return "<STR_LIT>" + ( self . backtrace [ - <NUM_LIT:1> ] [ <NUM_LIT:0> ] or "<STR_LIT>" ) + "<STR_LIT>" + hex ( id ( self ) ) + "<STR_LIT:>>" <EOL> @ classmethod <EOL> def like ( cls , other , ** kwargs ) : <EOL> """<STR_LIT>""" <EOL> from migen . fhdl . bitcontainer import value_bits_sign <EOL> return cls ( bits_sign = value_bits_sign ( other ) , ** kwargs ) <EOL> def __hash__ ( self ) : <EOL> return self . duid <EOL> class ClockSignal ( _Value ) : <EOL> """<STR_LIT>""" <EOL> def __init__ ( self , cd = "<STR_LIT>" ) : <EOL> _Value . __init__ ( self ) <EOL> if not isinstance ( cd , str ) : <EOL> raise TypeError ( "<STR_LIT>" ) <EOL> self . cd = cd <EOL> class ResetSignal ( _Value ) : <EOL> """<STR_LIT>""" <EOL> def __init__ ( self , cd = "<STR_LIT>" , allow_reset_less = False ) : <EOL> _Value . __init__ ( self ) <EOL> if not isinstance ( cd , str ) : <EOL> raise TypeError ( "<STR_LIT>" ) <EOL> self . cd = cd <EOL> self . allow_reset_less = allow_reset_less <EOL> class _Statement : <EOL> pass <EOL> class _Assign ( _Statement ) : <EOL> def __init__ ( self , l , r ) : <EOL> self . l = wrap ( l ) <EOL> self . r = wrap ( r ) <EOL> def _check_statement ( s ) : <EOL> if isinstance ( s , _collections . Iterable ) : <EOL> return all ( _check_statement ( ss ) for ss in s ) <EOL> else : <EOL> return isinstance ( s , _Statement ) <EOL> class If ( _Statement ) : <EOL> """<STR_LIT>""" <EOL> def __init__ ( self , cond , * t ) : <EOL> if not _check_statement ( t ) : <EOL> raise TypeError ( "<STR_LIT>" ) <EOL> self . cond = wrap ( cond ) <EOL> self . t = list ( t ) <EOL> self . f = [ ] <EOL> def Else ( self , * f ) : <EOL> """<STR_LIT>""" <EOL> if not _check_statement ( f ) : <EOL> raise TypeError ( "<STR_LIT>" ) <EOL> _insert_else ( self , list ( f ) ) <EOL> return self <EOL> def Elif ( self , cond , * t ) : <EOL> """<STR_LIT>""" <EOL> _insert_else ( self , [ If ( cond , * t ) ] ) <EOL> return self <EOL> def _insert_else ( obj , clause ) : <EOL> o = obj <EOL> while o . f : <EOL> assert ( len ( o . f ) == <NUM_LIT:1> ) <EOL> assert ( isinstance ( o . f [ <NUM_LIT:0> ] , If ) ) <EOL> o = o . f [ <NUM_LIT:0> ] <EOL> o . f = clause <EOL> class Case ( _Statement ) : <EOL> """<STR_LIT>""" <EOL> def __init__ ( self , test , cases ) : <EOL> self . test = wrap ( test ) <EOL> self . cases = dict ( ) <EOL> for k , v in cases . items ( ) : <EOL> if isinstance ( k , ( bool , int ) ) : <EOL> k = Constant ( k ) <EOL> if ( not isinstance ( k , Constant ) <EOL> and not ( isinstance ( k , str ) and k == "<STR_LIT:default>" ) ) : <EOL> raise TypeError ( "<STR_LIT>" ) <EOL> if not isinstance ( v , _collections . Iterable ) : <EOL> v = [ v ] <EOL> if not _check_statement ( v ) : <EOL> raise TypeError ( "<STR_LIT>" <EOL> "<STR_LIT>" . format ( k ) ) <EOL> self . cases [ k ] = v <EOL> def makedefault ( self , key = None ) : <EOL> """<STR_LIT>""" <EOL> if key is None : <EOL> for choice in self . cases . keys ( ) : <EOL> if ( key is None <EOL> or ( isinstance ( choice , str ) and choice == "<STR_LIT:default>" ) <EOL> or choice . value > key . value ) : <EOL> key = choice <EOL> if not isinstance ( key , str ) or key != "<STR_LIT:default>" : <EOL> key = wrap ( key ) <EOL> stmts = self . cases [ key ] <EOL> del self . cases [ key ] <EOL> self . cases [ "<STR_LIT:default>" ] = stmts <EOL> return self <EOL> class _ArrayProxy ( _Value ) : <EOL> def __init__ ( self , choices , key ) : <EOL> _Value . __init__ ( self ) <EOL> self . choices = [ ] <EOL> for c in choices : <EOL> if isinstance ( c , ( bool , int ) ) : <EOL> c = Constant ( c ) <EOL> self . choices . append ( c ) <EOL> self . key = key <EOL> def __getattr__ ( self , attr ) : <EOL> return _ArrayProxy ( [ getattr ( choice , attr ) for choice in self . choices ] , <EOL> self . key ) <EOL> def __getitem__ ( self , key ) : <EOL> return _ArrayProxy ( [ choice . __getitem__ ( key ) for choice in self . choices ] , <EOL> self . key ) <EOL> class Array ( list ) : <EOL> """<STR_LIT>""" <EOL> def __getitem__ ( self , key ) : <EOL> if isinstance ( key , Constant ) : <EOL> return list . __getitem__ ( self , key . value ) <EOL> elif isinstance ( key , _Value ) : <EOL> return _ArrayProxy ( self , key ) <EOL> else : <EOL> return list . __getitem__ ( self , key ) <EOL> class ClockDomain : <EOL> """<STR_LIT>""" <EOL> def __init__ ( self , name = None , reset_less = False ) : <EOL> self . name = _tracer . get_obj_var_name ( name ) <EOL> if self . name is None : <EOL> raise ValueError ( "<STR_LIT>" ) <EOL> if self . name . startswith ( "<STR_LIT>" ) : <EOL> self . name = self . name [ <NUM_LIT:3> : ] <EOL> if self . name [ <NUM_LIT:0> ] . isdigit ( ) : <EOL> raise ValueError ( "<STR_LIT>" ) <EOL> self . clk = Signal ( name_override = self . name + "<STR_LIT>" ) <EOL> if reset_less : <EOL> self . rst = None <EOL> else : <EOL> self . rst = Signal ( name_override = self . name + "<STR_LIT>" ) <EOL> def rename ( self , new_name ) : <EOL> """<STR_LIT>""" <EOL> self . name = new_name <EOL> self . clk . name_override = new_name + "<STR_LIT>" <EOL> if self . rst is not None : <EOL> self . rst . name_override = new_name + "<STR_LIT>" <EOL> class _ClockDomainList ( list ) : <EOL> def __getitem__ ( self , key ) : <EOL> if isinstance ( key , str ) : <EOL> for cd in self : <EOL> if cd . name == key : <EOL> return cd <EOL> raise KeyError ( key ) <EOL> else : <EOL> return list . __getitem__ ( self , key ) <EOL> ( SPECIAL_INPUT , SPECIAL_OUTPUT , SPECIAL_INOUT ) = range ( <NUM_LIT:3> ) <EOL> class _Fragment : <EOL> def __init__ ( self , comb = None , sync = None , specials = None , clock_domains = None ) : <EOL> if comb is None : comb = [ ] <EOL> if sync is None : sync = dict ( ) <EOL> if specials is None : specials = set ( ) <EOL> if clock_domains is None : clock_domains = _ClockDomainList ( ) <EOL> self . comb = comb <EOL> self . sync = sync <EOL> self . specials = specials <EOL> self . clock_domains = _ClockDomainList ( clock_domains ) <EOL> def __add__ ( self , other ) : <EOL> newsync = _collections . defaultdict ( list ) <EOL> for k , v in self . sync . items ( ) : <EOL> newsync [ k ] = v [ : ] <EOL> for k , v in other . sync . items ( ) : <EOL> newsync [ k ] . extend ( v ) <EOL> return _Fragment ( self . comb + other . comb , newsync , <EOL> self . specials | other . specials , <EOL> self . clock_domains + other . clock_domains ) <EOL> def __iadd__ ( self , other ) : <EOL> newsync = _collections . defaultdict ( list ) <EOL> for k , v in self . sync . items ( ) : <EOL> newsync [ k ] = v [ : ] <EOL> for k , v in other . sync . items ( ) : <EOL> newsync [ k ] . extend ( v ) <EOL> self . comb += other . comb <EOL> self . sync = newsync <EOL> self . specials |= other . specials <EOL> self . clock_domains += other . clock_domains <EOL> return self </s>
