【问题标题】:yielding a coroutine in a list with cocotb使用 cocotb 在列表中产生一个协程
【发布时间】:2018-10-17 12:46:44
【问题描述】:

我有一个等待设置事件的协程:

@cocotb.coroutine
def wb_RXDR_read(self):
    """ waiting util RXDR is read """
    if not self._RXDR_read_flag:
        while True:
            yield self._RXDR_read_event.wait()
            break

我想在超时后“让步”。然后我这样做了:

        RXDR_timeout = Timer(250, units="us")
        ret = yield [RXDR_timeout, self.wb_RXDR_read()]
        if ret == RXDR_timeout:
            self._dut._log.error("Timeout on waiting RXDR to be read")
            raise TestError()

但我收到此错误:

2ns ERROR    Coroutine i2c_write yielded something the scheduler can't handle
                      Got type: <type 'list'> repr: [<cocotb.triggers.Timer object at 0x7f2098cb1350>, <cocotb.decorators.RunningCoroutine object at 0x7f2098cb1610>] str: [<cocotb.triggers.Timer object at 0x7f2098cb1350>, <cocotb.decorators.RunningCoroutine object at 0x7f2098cb1610>]
                      Did you forget to decorate with @cocotb.coroutine?

我的协程用@cocotb.coroutine 装饰。如果我单独产生它就可以了:

yield self.wb_RXDR_read() # <- that works

但我不能把它放在一个列表中。是否可以将协程放在一个列表中以像 unix select() 那样阻塞?还是保留给 Trigger 类?

【问题讨论】:

    标签: python cocotb


    【解决方案1】:

    好的,我找到了解决方案。事实上 Coroutine 不能像时尚本身一样在 select 中触发。它应该首先作为一个线程启动,并且要检测协程的结束,必须将.join()方法放入yield列表中:

        RXDR_timeout = Timer(250, units="us")
        RXDR_readth = cocotb.fork(self.wb_RXDR_read())
        ret = yield [RXDR_timeout, RXDR_readth.join()]
        if ret == RXDR_timeout:
            self._dut._log.error("Timeout on waiting RXDR to be read")
            raise TestError()
    

    要记住的是:

    • 我们可以生成一个协程
    • 要产生几个协程,我们必须 fork()join()

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2018-11-21
      • 1970-01-01
      • 2015-04-22
      • 1970-01-01
      • 2018-05-16
      • 1970-01-01
      • 2023-03-05
      相关资源
      最近更新 更多