You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

含事件控制的Task在fork join_none中出现异常行为的技术问询

Verilog线程触发异常:所有ack仅置位最后一位的问题

问题分析

你的代码中所有线程最终都只响应req[3]并置位ack[3],核心原因是**thread任务默认是静态的**,任务的参数j属于静态存储变量。

在initial块的for循环中,你通过fork/join_none创建4个线程时,虽然用automatic int j = i传递当前循环值,但静态任务的参数j会被所有线程共享。循环结束后j的最终值为3,导致所有线程里的@(posedge req[j])实际都指向req[3]的上升沿。当req被置为15(所有位拉高)时,只有req[3]的上升沿触发所有4个线程执行,因此它们都会输出ack 3并重复置位ack[3]。

解决方案

要让每个任务实例拥有独立的参数副本,只需将thread任务声明为automatic即可:

task automatic thread(int j);
    ack[j] = 0;
    $display("rst %d", j);
    @(posedge req[j]);
    $display("ack for req %d", j);
    ack[j] = 1;
endtask

另一种方式是在任务内部将参数赋值给自动变量,确保事件敏感语句引用独立副本:

task thread(int j);
    automatic int local_j = j;
    ack[local_j] = 0;
    $display("rst %d", local_j);
    @(posedge req[local_j]);
    $display("ack for req %d", local_j);
    ack[local_j] = 1;
endtask

修改后,每个线程会独立监听对应位的req上升沿,触发时正确置位对应ack位,预期输出为:

rst 0
rst 1
rst 2
rst 3
ack for req 0
ack for req 1
ack for req 2
ack for req 3

内容的提问来源于stack exchange,提问作者Mahmoud Maarouf

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.15 15:23:24