Exemplo n.º 1
0
    def construct(s):

        # Interface

        s.xcel = XcelMinionIfcRTL(XcelReqMsg, XcelRespMsg)

        s.mem = MemMasterIfcRTL(*mk_mem_msg(8, 32, 32))

        from os import path
        s.config_placeholder = VerilogPlaceholderConfigs(
            # Path to the Verilog source file
            src_file=path.dirname(__file__) + '/SortXcelVRTL.v',
            # Name of the Verilog top level module
            top_module='lab2_xcel_SortXcelVRTL',
            # Port name map
            port_map={
                'xcel.req.en': 'xcelreq_en',
                'xcel.req.rdy': 'xcelreq_rdy',
                'xcel.req.msg': 'xcelreq_msg',
                'xcel.resp.en': 'xcelresp_en',
                'xcel.resp.rdy': 'xcelresp_rdy',
                'xcel.resp.msg': 'xcelresp_msg',
                'mem.req.en': 'memreq_en',
                'mem.req.rdy': 'memreq_rdy',
                'mem.req.msg': 'memreq_msg',
                'mem.resp.en': 'memresp_en',
                'mem.resp.rdy': 'memresp_rdy',
                'mem.resp.msg': 'memresp_msg',
            },
        )
        s.config_verilog_import = VerilatorImportConfigs(
            # Enable native Verilog line trace through Verilator
            vl_line_trace=True, )
Exemplo n.º 2
0
    def construct(s, nbits=32):

        dtype = mk_bits(32)
        xreq_class, xresp_class = mk_xcel_msg(5, nbits)

        s.xcel = XcelMinionIfcRTL(xreq_class, xresp_class)

        s.xcelreq_q = NormalQueueRTL(xreq_class, 2)
        s.xcelreq_q.enq //= s.xcel.req

        s.xr0 = RegEn(dtype)
        s.xr0.in_ //= s.xcelreq_q.deq.ret.data

        @update
        def up_null_xcel():

            if s.xcelreq_q.deq.rdy & s.xcel.resp.rdy:
                s.xcelreq_q.deq.en @= 1
                s.xcel.resp.en @= 1
                s.xcel.resp.msg.type_ @= s.xcelreq_q.deq.ret.type_

                if s.xcelreq_q.deq.ret.type_ == XcelMsgType.WRITE:
                    s.xr0.en @= 1
                    s.xcel.resp.msg.data @= 0
                else:
                    s.xr0.en @= 0
                    s.xcel.resp.msg.data @= s.xr0.out
            else:
                s.xcelreq_q.deq.en @= 0
                s.xcel.resp.en @= 0
                s.xr0.en @= 0
                s.xcel.resp.msg.data @= 0
                s.xcel.resp.msg.type_ @= 0
Exemplo n.º 3
0
  def construct( s, nbits=32 ):

    dtype = mk_bits(32)
    XcelMsgType_WRITE = XcelMsgType.WRITE
    xreq_class, xresp_class = mk_xcel_msg( 5,nbits )

    s.xcel = XcelMinionIfcRTL( xreq_class, xresp_class )

    s.xcelreq_q = NormalQueueRTL( xreq_class, 2 )( enq = s.xcel.req )

    s.xr0 = RegEn( dtype )( in_ = s.xcelreq_q.deq.msg.data )

    @s.update
    def up_null_xcel():

      if s.xcelreq_q.deq.rdy & s.xcel.resp.rdy:
        s.xcelreq_q.deq.en = b1(1)
        s.xcel.resp.en     = b1(1)
        s.xcel.resp.msg.type_ = s.xcelreq_q.deq.msg.type_

        if s.xcelreq_q.deq.msg.type_ == XcelMsgType_WRITE:
          s.xr0.en             = b1(1)
          s.xcel.resp.msg.data = dtype(0)
        else:
          s.xr0.en            = b1(0)
          s.xcel.resp.msg.data = s.xr0.out
      else:
        s.xcelreq_q.deq.en   = b1(0)
        s.xcel.resp.en       = b1(0)
        s.xr0.en             = b1(0)
        s.xcel.resp.msg.data = dtype(0)
        s.xcel.resp.msg.type_ = b1(0)
Exemplo n.º 4
0
  def construct( s ):

    MemReqMsg, MemRespMsg = mk_mem_msg( 8,32,32 )
    MEM_TYPE_READ  = b4(MemMsgType.READ)
    MEM_TYPE_WRITE = b4(MemMsgType.WRITE)

    # Interface

    s.xcel = XcelMinionIfcRTL( XcelReqMsg, XcelRespMsg )

    s.mem  = MemMasterIfcRTL( *mk_mem_msg(8,32,32) )
Exemplo n.º 5
0
  def construct( s, nbits=32 ):
    dtype = mk_bits(nbits)

    # Interface

    s.xcel = XcelMinionIfcRTL( XcelReqMsg, XcelRespMsg )
    s.mem  = MemMasterIfcRTL( *mk_mem_msg(8,nbits,32) )

    # Queues

    s.xcelreq_q = NormalQueueRTL( XcelReqMsg, 2 )( enq = s.xcel.req )

    # Single accelerator register

    s.xr0 = RegEn( Bits32 )

    # Direct connections for xcelreq/xcelresp

    s.xr0.in_             //= s.xcelreq_q.deq.ret.data
    s.xcel.resp.msg.type_ //= s.xcelreq_q.deq.ret.type_

    # Even though memreq/memresp interface is not hooked up, we still
    # need to set the output ports correctly.

    s.mem.req.en   //= 0
    s.mem.req.msg  //= mk_mem_msg(8,nbits,32)[0]()
    s.mem.resp.rdy //= 0

    # Combinational block

    @s.update
    def block():

      # Mux to force xcelresp data to zero on a write

      if s.xcelreq_q.deq.ret.type_ == XCEL_TYPE_WRITE:
        s.xcel.resp.msg.data = dtype(0)
      else:
        s.xcel.resp.msg.data = s.xr0.out

      # Logic for register enable
      both_rdy = s.xcelreq_q.deq.rdy & s.xcel.resp.rdy

      s.xr0.en = (s.xcelreq_q.deq.ret.type_ == XCEL_TYPE_WRITE) & both_rdy

      s.xcelreq_q.deq.en = both_rdy
      s.xcel.resp.en     = both_rdy
  def construct( s, image_column,image_row,window_size,window_size_ext):
  #def construct( s ):

    
    # Interface

    s.xcel = XcelMinionIfcRTL( XcelReqMsg, XcelRespMsg )

    s.mem  = MemMasterIfcRTL( *mk_mem_msg(8,32,32) )

    from os import path
    s.config_placeholder = VerilogPlaceholderConfigs(
      # Path to the Verilog source file
      src_file = path.dirname(__file__) + '/Optical_flowVRTL.v',
      # Name of the Verilog top level module
      top_module = 'Final_Project_Optical_flowVRTL',
      # Port name map
      params={
       'image_column':image_column,
       'image_row'   :image_row,
       'window_size' :window_size,
       'window_size_ext':window_size_ext,
      },
      port_map = {
        'xcel.req.en'   : 'xcelreq_en',
        'xcel.req.rdy'  : 'xcelreq_rdy',
        'xcel.req.msg'  : 'xcelreq_msg',

        'xcel.resp.en'  : 'xcelresp_en',
        'xcel.resp.rdy' : 'xcelresp_rdy',
        'xcel.resp.msg' : 'xcelresp_msg',

        'mem.req.en'   : 'memreq_en',
        'mem.req.rdy'  : 'memreq_rdy',
        'mem.req.msg'  : 'memreq_msg',

        'mem.resp.en'  : 'memresp_en',
        'mem.resp.rdy' : 'memresp_rdy',
        'mem.resp.msg' : 'memresp_msg',
      },
    )
    s.config_verilog_import = VerilatorImportConfigs(
      # Enable native Verilog line trace through Verilator
      vl_line_trace = True,
    )
Exemplo n.º 7
0
    def construct(s):
        # FIXME gc??
        # s.x = bytearray(2**25)

        # Interface

        ReqType, RespType = mk_xcel_msg(5, 32)
        s.xcel = XcelMinionIfcRTL(ReqType, RespType)

        # State encoding

        s.XCFG = b2(0)
        s.WAIT = b2(1)
        s.BUSY = b2(2)

        # Local parameters

        s.RD = XcelMsgType.READ
        s.WR = XcelMsgType.WRITE

        # Components

        s.in_q = NormalQueueRTL(ReqType, num_entries=2)
        s.reg_file = [Reg(Bits32) for _ in range(6)]
        s.checksum_unit = ChecksumRTL()

        s.state = Wire(Bits2)
        s.state_next = Wire(Bits2)
        s.start_pulse = Wire(Bits1)

        # Connections

        connect(s.xcel.req, s.in_q.enq)
        connect(s.checksum_unit.recv.msg[0:32], s.reg_file[0].out)
        connect(s.checksum_unit.recv.msg[32:64], s.reg_file[1].out)
        connect(s.checksum_unit.recv.msg[64:96], s.reg_file[2].out)
        connect(s.checksum_unit.recv.msg[96:128], s.reg_file[3].out)

        # Logic

        @s.update
        def up_start_pulse():
            s.start_pulse = (s.xcel.resp.en and s.in_q.deq.msg.type_ == s.WR
                             and s.in_q.deq.msg.addr == b5(4))

        @s.update
        def up_state_next():
            if s.state == s.XCFG:
                s.state_next = (s.WAIT if s.start_pulse
                                & ~s.checksum_unit.recv.rdy else
                                s.BUSY if s.start_pulse
                                & s.checksum_unit.recv.rdy else s.XCFG)

            elif s.state == s.WAIT:
                s.state_next = s.BUSY if s.checksum_unit.recv.rdy else s.WAIT

            else:  # s.state == s.BUSY
                s.state_next = s.XCFG if s.checksum_unit.send.en else s.BUSY

        @s.update_on_edge
        def up_state():
            if s.reset:
                s.state = s.XCFG
            else:
                s.state = s.state_next

        @s.update
        def up_fsm_output():
            if s.state == s.XCFG:
                s.in_q.deq.en = s.in_q.deq.rdy
                s.xcel.resp.en = s.in_q.deq.rdy
                s.checksum_unit.recv.en = s.start_pulse & s.checksum_unit.recv.rdy
                s.checksum_unit.send.rdy = b1(1)

            elif s.state == s.WAIT:
                s.in_q.deq.en = b1(0)
                s.xcel.resp.en = b1(0)
                s.checksum_unit.recv.en = s.checksum_unit.recv.rdy
                s.checksum_unit.send.rdy = b1(1)

            else:  # s.state == s.BUSY:
                s.in_q.deq.en = b1(0)
                s.xcel.resp.en = b1(0)
                s.checksum_unit.recv.en = b1(0)
                s.checksum_unit.send.rdy = b1(1)

        @s.update
        def up_resp_msg():
            s.xcel.resp.msg.type_ = s.in_q.deq.msg.type_
            s.xcel.resp.msg.data = b32(0)
            if s.in_q.deq.msg.type_ == s.RD:
                s.xcel.resp.msg.data = s.reg_file[s.in_q.deq.msg.addr[0:3]].out

        @s.update
        def up_wr_regfile():
            for i in range(6):
                s.reg_file[i].in_ = s.reg_file[i].out

            if s.in_q.deq.en and s.in_q.deq.msg.type_ == s.WR:
                for i in range(6):
                    s.reg_file[i].in_ = (s.in_q.deq.msg.data
                                         if b5(i) == s.in_q.deq.msg.addr else
                                         s.reg_file[i].out)

            if s.checksum_unit.send.en:
                s.reg_file[5].in_ = s.checksum_unit.send.msg
Exemplo n.º 8
0
  def construct( s ):

    MemReqMsg, MemRespMsg = mk_mem_msg( 8,32,32 )
    MEM_TYPE_READ  = b4(MemMsgType.READ)
    MEM_TYPE_WRITE = b4(MemMsgType.WRITE)

    # Interface

    s.xcel = XcelMinionIfcRTL( XcelReqMsg, XcelRespMsg )

    s.mem  = MemMasterIfcRTL( *mk_mem_msg(8,32,32) )

    # ''' LAB TASK ''''''''''''''''''''''''''''''''''''''''''''''''''''''
    # Create RTL model for sorting xcel
    # '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''\/

    # Queues

    s.xcelreq_q = PipeQueueRTL( XcelReqMsg, 1 )( enq = s.xcel.req )
    s.memresp_q = PipeQueueRTL( MemRespMsg, 1 )( enq = s.mem.resp )

    # Internal state

    s.base_addr   = Reg( Bits32 )
    s.size        = Reg( Bits32 )
    s.inner_count = Reg( Bits32 )
    s.outer_count = Reg( Bits32 )
    s.a           = Reg( Bits32 )

    # Line tracing

    s.prev_state = 0
    s.xcfg_trace = "  "

    #=====================================================================
    # State Update
    #=====================================================================

    s.STATE_XCFG    = b8(0)
    s.STATE_FIRST0  = b8(1)
    s.STATE_FIRST1  = b8(2)
    s.STATE_BUBBLE0 = b8(3)
    s.STATE_BUBBLE1 = b8(4)
    s.STATE_LAST    = b8(5)

    s.state         = Wire(Bits8)
    s.go            = Wire()

    @s.update_ff
    def block0():

      if s.reset:
        s.state <<= s.STATE_XCFG

      elif s.state == s.STATE_XCFG:
        if s.go & s.xcel.resp.rdy:
          s.state <<= s.STATE_FIRST0

      elif s.state == s.STATE_FIRST0:
        if s.mem.req.rdy:
          s.state <<= s.STATE_FIRST1

      elif s.state == s.STATE_FIRST1:
        if s.mem.req.rdy and s.memresp_q.deq.rdy:
          s.state <<= s.STATE_BUBBLE0

      elif s.state == s.STATE_BUBBLE0:
        if s.mem.req.rdy and s.memresp_q.deq.rdy:
          s.state <<= s.STATE_BUBBLE1

      elif s.state == s.STATE_BUBBLE1:
        if s.mem.req.rdy and s.memresp_q.deq.rdy:
          if s.inner_count.out+1 < s.size.out:
            s.state <<= s.STATE_BUBBLE0
          else:
            s.state <<= s.STATE_LAST

      elif s.state == s.STATE_LAST:
        if s.mem.req.rdy and s.memresp_q.deq.rdy:
          if s.outer_count.out+1 < s.size.out:
            s.state <<= s.STATE_FIRST1
          else:
            s.state <<= s.STATE_XCFG

    #=====================================================================
    # State Outputs
    #=====================================================================

    @s.update
    def block1():

      s.xcelreq_q.deq.en = b1(0)
      s.xcel.resp.en     = b1(0)
      s.mem.req.en       = b1(0)
      s.mem.req.msg      = MemReqMsg()
      s.memresp_q.deq.en = b1(0)
      s.go               = b1(0)

      s.outer_count.in_ = s.outer_count.out
      s.inner_count.in_ = s.inner_count.out
      s.a.in_           = s.a.out
      s.size.in_        = s.size.out
      s.base_addr.in_   = s.base_addr.out

      #-------------------------------------------------------------------
      # STATE: XCFG
      #-------------------------------------------------------------------

      if s.state == s.STATE_XCFG:

        if s.xcelreq_q.deq.rdy & s.xcel.resp.rdy:
          s.xcelreq_q.deq.en = b1(1)
          s.xcel.resp.en     = b1(1)

          if s.xcelreq_q.deq.ret.type_ == XCEL_TYPE_WRITE:

            if   s.xcelreq_q.deq.ret.addr == b5(0):
              s.outer_count.in_ = b32(0)
              s.inner_count.in_ = b32(0)
              s.go              = b1(1)

            elif s.xcelreq_q.deq.ret.addr == b5(1):
              s.base_addr.in_ = s.xcelreq_q.deq.ret.data

            elif s.xcelreq_q.deq.ret.addr == b5(2):
              s.size.in_ = s.xcelreq_q.deq.ret.data

            # Send xcel response message

            s.xcel.resp.msg = XcelRespMsg( XCEL_TYPE_WRITE, b32(0) )

          else:

            # Send xcel response message, obviously you only want to
            # send the response message when accelerator is done

            s.xcel.resp.msg = XcelRespMsg( XCEL_TYPE_READ, b32(1) )

      #-------------------------------------------------------------------
      # STATE: FIRST0
      #-------------------------------------------------------------------
      # Send the first memory read request for the very first
      # element in the array.

      elif s.state == s.STATE_FIRST0:
        if s.mem.req.rdy:
          s.mem.req.en      = s.mem.req.rdy
          s.mem.req.msg     = MemReqMsg( MEM_TYPE_READ, b8(0), s.base_addr.out + 4*s.inner_count.out, b2(0), b32(0) )
          s.inner_count.in_ = b32(1)

      #-------------------------------------------------------------------
      # STATE: FIRST1
      #-------------------------------------------------------------------
      # Wait for the memory response for the first element in the array,
      # and once it arrives store this element in a, and send the memory
      # read request for the second element.

      elif s.state == s.STATE_FIRST1:

        if s.mem.req.rdy and s.memresp_q.deq.rdy:
          s.memresp_q.deq.en = b1(1)
          s.mem.req.en       = b1(1)

          s.a.in_ = s.memresp_q.deq.ret.data

          s.mem.req.msg = MemReqMsg( MEM_TYPE_READ, b8(0), s.base_addr.out + 4*s.inner_count.out, b2(0), b32(0) )

      #-------------------------------------------------------------------
      # STATE: BUBBLE0
      #-------------------------------------------------------------------
      # Wait for the memory read response to get the next element,
      # compare the new value to the previous max value, update b with
      # the new max value, and send a memory request to store the new min
      # value. Notice how we decrement the write address by four since we
      # want to store to the new min value _previous_ element.

      elif s.state == s.STATE_BUBBLE0:
        if s.mem.req.rdy and s.memresp_q.deq.rdy:
          s.memresp_q.deq.en = b1(1)
          s.mem.req.en       = b1(1)

          if s.a.out > s.memresp_q.deq.ret.data:
            s.a.in_ = s.a.out
            s.mem.req.msg = MemReqMsg( MEM_TYPE_WRITE, b8(0),
                                       s.base_addr.out + 4*(s.inner_count.out-1), b2(0),
                                       s.memresp_q.deq.ret.data )
          else:
            s.a.in_ = s.memresp_q.deq.ret.data
            s.mem.req.msg = MemReqMsg( MEM_TYPE_WRITE, b8(0),
                                       s.base_addr.out + 4*(s.inner_count.out-1), b2(0),
                                       s.a.out )

      #-------------------------------------------------------------------
      # STATE: BUBBLE1
      #-------------------------------------------------------------------
      # Wait for the memory write response, and then check to see if we
      # have reached the end of the array. If we have not reached the end
      # of the array, then make a new memory read request for the next
      # element; if we have reached the end of the array, then make a
      # final write request (with value from a) to update the final
      # element in the array.

      elif s.state == s.STATE_BUBBLE1:
        if s.mem.req.rdy and s.memresp_q.deq.rdy:
          s.memresp_q.deq.en = b1(1)
          s.mem.req.en       = b1(1)

          s.inner_count.in_ = s.inner_count.out + 1

          if s.inner_count.out+1 < s.size.out:
            s.mem.req.msg = MemReqMsg( MEM_TYPE_READ, b8(0),
                                       s.base_addr.out + 4*(s.inner_count.out+1), b2(0), b32(0) )

          else:
            s.mem.req.msg = MemReqMsg( MEM_TYPE_WRITE, b8(0),
                                       s.base_addr.out + 4*s.inner_count.out, b2(0),
                                       s.a.out )

      #-------------------------------------------------------------------
      # STATE: LAST
      #-------------------------------------------------------------------
      # Wait for the last response, and then check to see if we need to
      # go through the array again. If we do need to go through array
      # again, then make a new memory read request for the very first
      # element in the array; if we do not need to go through the array
      # again, then we are all done and we can go back to accelerator
      # configuration.

      elif s.state == s.STATE_LAST:
        if s.mem.req.rdy and s.memresp_q.deq.rdy:
          s.memresp_q.deq.en = b1(1)

          s.outer_count.in_ = s.outer_count.out + b32(1)

          if s.outer_count.out + b32(1) < s.size.out:

            s.mem.req.en      = b1(1)
            s.mem.req.msg     = MemReqMsg( MEM_TYPE_READ, b8(0), s.base_addr.out, b2(0), b32(0) )
            s.inner_count.in_ = b32(1)