Exemple #1
0
 def is_state(self, state: ast.Node) -> ast.Eq:
     return ast.Eq(left=self.state, right=state)
Exemple #2
0
    def _instantiate_global_fsm(
        self,
        task: Task,
        is_done_signals: List[rtl.Pipeline],
    ) -> None:
        # global state machine

        def is_state(state: ast.IntConst) -> ast.Eq:
            return ast.Eq(left=rtl.STATE, right=state)

        def set_state(state: ast.IntConst) -> ast.NonblockingSubstitution:
            return ast.NonblockingSubstitution(left=rtl.STATE, right=state)

        countdown = ast.Identifier('countdown')
        countdown_width = (self.register_level - 1).bit_length()

        task.module.add_signals([
            ast.Reg(rtl.STATE.name, width=ast.make_width(2)),
            ast.Reg(countdown.name, width=ast.make_width(countdown_width)),
        ])

        state01_action = set_state(STATE10)
        if is_done_signals:
            state01_action = ast.make_if_with_block(
                cond=ast.make_operation(
                    operator=ast.Land,
                    nodes=(x[-1] for x in reversed(is_done_signals)),
                ),
                true=state01_action,
            )

        global_fsm = ast.make_case_with_block(
            comp=rtl.STATE,
            cases=[
                (
                    STATE00,
                    ast.make_if_with_block(
                        cond=self.start_q[-1],
                        true=set_state(STATE01),
                    ),
                ),
                (
                    STATE01,
                    state01_action,
                ),
                (
                    STATE10,
                    [
                        set_state(STATE11 if self.register_level else STATE00),
                        ast.NonblockingSubstitution(
                            left=countdown,
                            right=ast.make_int(max(0,
                                                   self.register_level - 1)),
                        ),
                    ],
                ),
                (
                    STATE11,
                    ast.make_if_with_block(
                        cond=ast.Eq(
                            left=countdown,
                            right=ast.make_int(0, width=countdown_width),
                        ),
                        true=set_state(STATE00),
                        false=ast.NonblockingSubstitution(
                            left=countdown,
                            right=ast.Minus(
                                left=countdown,
                                right=ast.make_int(1, width=countdown_width),
                            ),
                        ),
                    ),
                ),
            ],
        )

        task.module.add_logics([
            ast.Always(
                sens_list=rtl.CLK_SENS_LIST,
                statement=ast.make_block(
                    ast.make_if_with_block(
                        cond=rtl.RST,
                        true=set_state(STATE00),
                        false=global_fsm,
                    )),
            ),
            ast.Assign(left=rtl.IDLE, right=is_state(STATE00)),
            ast.Assign(left=rtl.DONE, right=self.done_q[-1]),
            ast.Assign(left=rtl.READY, right=self.done_q[0]),
        ])

        task.module.add_pipeline(self.start_q, init=rtl.START)
        task.module.add_pipeline(self.done_q, init=is_state(STATE10))
Exemple #3
0
 def is_state(state: ast.IntConst) -> ast.Eq:
     return ast.Eq(left=rtl.STATE, right=state)
Exemple #4
0
    def _instantiate_fifos(self, task: Task) -> None:
        _logger.debug('  instantiating FIFOs in %s', task.name)

        # skip instantiating if the fifo is not declared in this task
        fifos = {
            name: fifo
            for name, fifo in task.fifos.items() if 'depth' in fifo
        }
        if not fifos:
            return

        col_width = max(
            max(len(name), len(util.get_instance_name(fifo['consumed_by'])),
                len(util.get_instance_name(fifo['produced_by'])))
            for name, fifo in fifos.items())

        for fifo_name, fifo in fifos.items():
            _logger.debug('    instantiating %s.%s', task.name, fifo_name)

            # add FIFO instances
            task.module.add_fifo_instance(
                name=fifo_name,
                width=self._get_fifo_width(task, fifo_name),
                depth=fifo['depth'],
            )

            # print debugging info
            debugging_blocks = []
            fmtargs = {
                'fifo_prefix': '\\033[97m',
                'fifo_suffix': '\\033[0m',
                'task_prefix': '\\033[90m',
                'task_suffix': '\\033[0m',
            }
            for suffixes, fmt, fifo_tag in zip(
                (rtl.ISTREAM_SUFFIXES, rtl.OSTREAM_SUFFIXES),
                ('DEBUG: R: {fifo_prefix}{fifo:>{width}}{fifo_suffix} -> '
                 '{task_prefix}{task:<{width}}{task_suffix} %h',
                 'DEBUG: W: {task_prefix}{task:>{width}}{task_suffix} -> '
                 '{fifo_prefix}{fifo:<{width}}{fifo_suffix} %h'),
                ('consumed_by', 'produced_by')):
                display = ast.SingleStatement(statement=ast.SystemCall(
                    syscall='display',
                    args=(ast.StringConst(value=fmt.format(
                        width=col_width,
                        fifo=fifo_name,
                        task=(util.get_instance_name(fifo[fifo_tag])),
                        **fmtargs)),
                          ast.Identifier(
                              name=rtl.wire_name(fifo_name, suffixes[0])))))
                debugging_blocks.append(
                    ast.Always(
                        sens_list=rtl.CLK_SENS_LIST,
                        statement=ast.make_block(
                            ast.IfStatement(
                                cond=ast.Eq(
                                    left=ast.Identifier(name=rtl.wire_name(
                                        fifo_name, suffixes[-1])),
                                    right=rtl.TRUE,
                                ),
                                true_statement=ast.make_block(display),
                                false_statement=None))))
            task.module.add_logics(debugging_blocks)