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

如何使脉动阵列架构矩阵向量乘法器的数据流控制可综合?

脉动阵列矩阵-向量乘法器综合问题改造方案

问题背景

基于8×8固定脉动阵列(PE总数64)的矩阵-向量乘法器,支持外部动态配置矩阵维度(最大64×64),仿真验证通过,但综合时数据流控制模块报错:

  • ELAB-312:数组越界访问W_reg[64](有效范围[0:63])
  • ELAB-900:循环迭代次数超出综合器分析上限

核心矛盾:使用了运行时可变边界的for循环,综合器无法处理非编译期常量的迭代范围;同时存在数组维度不匹配、索引计算错误等问题。

错误根源分析

  1. 数组维度不匹配:

    • W_reg定义为[0:M-1](仅8个寄存器),但PE总数为64个,导致跨维度访问时触发越界;
    • Ws、Xs的维度与PE阵列数量不匹配,引发索引访问错误。
  2. 动态循环不满足综合要求:
    综合器要求for循环的迭代次数必须是编译期常量,但代码中使用M_val、cycle等运行时变量作为循环边界,导致综合器无法确定循环次数,触发ELAB-900错误。

  3. 索引计算逻辑错误:
    原代码中W_i[(cycle-m) + m*N_val]会出现负数索引(当cycle < m时),引发数组越界。

具体改造步骤

1. 修正数组维度匹配问题

  • 保持W_reg深度对应8行(每行1个权重输入寄存器):
    reg [DW-1:0] W_reg[0:M-1]; // 对应8行,每行1个权重输入寄存器
    
  • 修正Ws、Xs的维度,匹配64个PE的移位链需求:
    wire [DW-1:0] Ws[1:0][0:M*N-1]; // 64个PE的权重输入/输出
    wire [DW-1:0] Xs [0:M*N];       // 向量移位链,64个PE对应65个节点
    

2. 将动态循环改为静态循环+条件赋值

所有使用M_val作为循环边界的代码,改为遍历编译期固定的全部索引,通过条件判断控制是否执行操作,确保循环次数固定:

例1:复位后的W_reg清零

原代码:

for(m = 0; m < M_val; m = m + 1) begin
  W_reg[m] <= 8'd0;
end

改造后:

for(m = 0; m < M; m = m + 1) begin // M是编译期常量8
  if(m < M_val) begin // 仅对前M_val行执行清零
    W_reg[m] <= 8'd0;
  end
end

例2:cycle < N_val时的权重加载

原代码:

for(m = 0; m < M_val; m = m + 1) begin
  W_reg[m] <= W_i[(cycle-m) + m*N_val];
end

改造后(修正索引计算,避免负数):

for(m = 0; m < M; m = m + 1) begin
  if(m < M_val) begin
    // 行优先存储,第m行第cycle列的权重索引为m*N_val + cycle
    W_reg[m] <= W_i[m*N_val + cycle];
  end
end

例3:cycle >= N_val时的权重加载

原代码:

for (m=cycle-N_val+1; m < M_val; m = m + 1) begin
  W_reg[m] <= W_i[(cycle-m) + m*N_val];
end

改造后(增加边界判断,避免负数索引):

for(m = 0; m < M; m = m + 1) begin
  // 仅当cycle >= N_val且m在有效范围内时执行赋值
  if(cycle >= N_val && m >= (cycle - N_val + 1) && m < M_val) begin
    W_reg[m] <= W_i[m*N_val + cycle];
  end
end

3. 修正PE激活信号逻辑

原激活信号逻辑未正确映射到二维PE阵列,改造后确保前M_val行的所有PE被激活:

  • 修正activate_reg赋值:
    always@(posedge reset or posedge start_mult) begin
      if(!reset)
        activate_reg <= 64'hFFFF_FFFF_FFFF_FFFF; // 初始化全激活
      else begin
        // 启用前M_val行,每行N个PE,共M_val*N个PE
        activate_reg <= (64'hFFFF_FFFF_FFFF_FFFF) >> (M*N - M_val*N);
      end
    end
    
  • 修正PE激活信号映射:
    generate
      for (i = 0; i < M; i = i + 1) begin: PE_activators
        for (j = 0; j < N; j = j + 1) begin: COL_activators
          assign activate_pe[i*N + j] = activate_reg[i*N + j];
        end
      end 
    endgenerate
    

4. 修正PE实例化的移位连接

原PE的w_o悬空,需连接到同一行下一个PE的w_i,实现权重的脉动移位:

generate
  for (i = 0; i < M; i = i + 1) begin: ROWs
    for (j = 0; j < N; j = j + 1) begin: COLs
     PE #(DW)
         pe (
            .clk(clk),
            .reset(reset),
            .activate(activate_pe[i*N + j]),
            .w_i(j == 0 ? W_reg[i] : Ws[0][i*N + j - 1]), // 行首PE从W_reg取权重,其余从左邻PE取
            .x_i(Xs[i*N + j]),
            .w_o(Ws[0][i*N + j]), // 权重输出到右邻PE
            .x_o(Xs[i*N + j + 1]),
            .mac(Ys[i*N + j])
         );
    end
  end
endgenerate

验证说明

改造后:

  • 所有for循环的迭代次数均为编译期常量(8行或64个PE),满足综合器要求;
  • 数组索引计算修正,避免越界访问;
  • PE激活信号与权重移位逻辑匹配脉动阵列的数据流要求,仿真结果将与预期一致。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.26 08:37:02