VHDL:为2D数组的特定元素指定新值

VHDL:为2D数组的特定元素指定新值,vhdl,Vhdl,我想将平均变量值复制到2d数组的特定位置。对于该代码,它是array\u new\u signal11(3,2) 谁能指导我怎么做?这段代码在模拟时给了我错误 architecture Behavioral of Correction is type array_new is array (0 to 4, 0 to 4) of integer; signal array_new_signal: array_new; begin array_new_signal11 <= ((1,2

我想将平均变量值复制到2d数组的特定位置。对于该代码,它是
array\u new\u signal11(3,2)

谁能指导我怎么做?这段代码在模拟时给了我错误

architecture Behavioral of Correction is

type array_new is array (0 to 4, 0 to 4) of integer;
signal array_new_signal: array_new;

begin

array_new_signal11 <=  ((1,2,3,4,5),
                        (4,5,6,7,8),
                        (7,8,9,0,1),
                        (1,3,6,5,9),
                        (2,3,5,4,5)); 

  Process(kelvin)
    variable Sum1: integer:= 0;
    Variable Sum2: integer:= 0;
    Variable Total_Sum: integer:= 0;
    Variable Average: integer:= 0;

    begin

        for Row in 0 to 4 loop
          for Column in 0 to 4 loop 

            if(Row = 1 and Column = 1) then
                for Column in 1 to 3 loop
                    sum1 := array_new_signal11(Row, Column) + Sum1;
                end loop;
            end if;

            if(Row = 2 and Column = 1) then
                for Column in 1 to 3 loop
                    sum2 := array_new_signal11(Row, Column) + Sum2;
                end loop;
            end if;   
         end loop;
        end loop;
      Total_Sum := Sum1 + Sum2;
      Average := Total_Sum / 8;
      **array_new_signal11(3,2) <= Average;**
     end Process;
    end Behavioral;
纠正的架构是
类型array_new是整数的数组(0到4,0到4);
信号阵列\新建\信号:阵列\新建;
开始

array_new_signal 11您试图从两个不同的进程驱动
array_new_signal 11
信号。是,您的第一个并发信号分配:

array_new_signal11 <=  ((1,2,3,4,5),
                        (4,5,6,7,8),
                        (7,8,9,0,1),
                        (1,3,6,5,9),
                        (2,3,5,4,5));
注:

  • Average
    作为一个变量,您应该有另一个错误:

    Average <= Total_Sum / 8;
    
  • 在两个嵌套循环中使用相同的循环索引(
    )。不确定你想做什么,但这不是很安全

  • 即使我建议您修复错误,您也会遇到另一个问题:
    array\u new\u signal11
    既是流程的输入(您读取它)又是流程的输出(您分配它)。因此,它也应列在敏感度列表中。在电气工程中,这被称为组合回路,通常是非常不可取的,除非你想创建一个振荡器或一种随机发生器

  • 您的进程对信号
    Kelvin
    敏感,但不使用它。奇怪的情况。您是否清楚您要对哪些硬件进行建模

  • 您可能认为每次流程恢复时(即每次
    Kelvin
    更改),流程变量都会重新初始化为0。事实并非如此:它们保留上次分配的值。可能不是你想要的。您应该在流程主体的开头初始化它们


  • 您正试图从两个不同的进程驱动
    阵列\u新\u信号11
    信号。是,您的第一个并发信号分配:

    array_new_signal11 <=  ((1,2,3,4,5),
                            (4,5,6,7,8),
                            (7,8,9,0,1),
                            (1,3,6,5,9),
                            (2,3,5,4,5));
    
    注:

  • Average
    作为一个变量,您应该有另一个错误:

    Average <= Total_Sum / 8;
    
  • 在两个嵌套循环中使用相同的循环索引(
    )。不确定你想做什么,但这不是很安全

  • 即使我建议您修复错误,您也会遇到另一个问题:
    array\u new\u signal11
    既是流程的输入(您读取它)又是流程的输出(您分配它)。因此,它也应列在敏感度列表中。在电气工程中,这被称为组合回路,通常是非常不可取的,除非你想创建一个振荡器或一种随机发生器

  • 您的进程对信号
    Kelvin
    敏感,但不使用它。奇怪的情况。您是否清楚您要对哪些硬件进行建模

  • 您可能认为每次流程恢复时(即每次
    Kelvin
    更改),流程变量都会重新初始化为0。事实并非如此:它们保留上次分配的值。可能不是你想要的。您应该在流程主体的开头初始化它们


  • 从问题中构造一个最小、完整且可验证的示例:

    entity correction is 
    end correction;
    
    architecture behavioral of correction is
        type array_new is array (0 to 4, 0 to 4) of integer;
        signal array_new_signal11: array_new := ((1,2,3,4,5),
                                                 (4,5,6,7,8),
                                                 (7,8,9,0,1),
                                                 (1,3,6,5,9),
                                                 (2,3,5,4,5));
        signal kelvin: boolean;
    begin
    
        -- array_new_signal11 <=  ((1,2,3,4,5),
        --                         (4,5,6,7,8),
        --                         (7,8,9,0,1),
        --                         (1,3,6,5,9),
        --                         (2,3,5,4,5));
    
        process (kelvin)
            variable sum1: integer:= 0;
            variable sum2: integer:= 0;
            variable total_sum: integer:= 0;
            variable average: integer:= 0;
        begin
            for row in 0 to 4 loop
                for column in 0 to 4 loop 
                    if row = 1 and column = 1 then
                        for column in 1 to 3 loop
                            sum1 := array_new_signal11(row, column) + sum1;
                        end loop;
                    end if;
                    if row = 2 and column = 1 then
                        for column in 1 to 3 loop
                            sum2 := array_new_signal11(row, column) + sum2;
                        end loop;
                    end if;   
                end loop;
            end loop;
          total_sum := sum1 + sum2;
          average := total_sum / 8;
          report "sum1 = " & integer'image(sum1) & ", " &
                 "sum2 = " & integer'image(sum2) & ", " &
                 "average = " & integer'image(average);
          array_new_signal11(3,2) <= average;
        end process;
    MONITOR_PROCESS:
        process
        begin
            wait on array_new_signal11;
            for row in 0 to 4 loop
                report "row" & integer'image(row) & " = " &
                        integer'image(array_new_signal11(row,0)) & ", " &
                        integer'image(array_new_signal11(row,1)) & ", " &
                        integer'image(array_new_signal11(row,2)) & ", " &
                        integer'image(array_new_signal11(row,3)) & ", " &
                        integer'image(array_new_signal11(row,4));
            end loop;
        end process;
    end behavioral;
    
    由平均值指定

    正如Renaud Pacalet所指出的,有两个不同的进程驱动array_new_signal11,这在VHDL中是不合法的,因为它的元素类型integer不是已解析的数据类型

    解决方案是在声明数组的情况下初始化该数组

    否则,对阵列信号元素的每个赋值都必须处于相同的过程中。您的并发信号分配将被细化为等效的过程语句,并在细化时生成错误,如最初所示:

    (对于ghdl模拟器,精化部分(包括链接和加载)是在调用仿真时完成的(r命令,加载部分,其中创建了设计网络))

    Renaud Pacalet建议在进程内分配数组值,但如果没有中间的等待语句,这些值将无法在同一模拟周期中后续使用。新信号值在分配给它们的同一模拟周期中不可用

    每个信号分配计划波形更新,特定模拟时间只有一个条目可用。在这种情况下,它将保证数组(3,2)是整数'left'的八个值的平均值(这是不正确的,在未标记的第三个循环语句第一个循环迭代中累积sum1时,您将得到错误,导致模拟结束)

    这告诉我们需要在读取之前初始化数组

    上面的示例成功的唯一原因是,当将数组元素添加到一起时,不会违反integer类型的值范围和指定的值

    通过使用整数的二进制数组等价物并注意所需的精度,您可以绕过这类问题

    这个故事有几个寓意。首先,VHDL不是一种编程语言,其次它是强类型的,第三个信号赋值在生成它们的模拟周期中永远不可见


    请注意,已将开尔文添加为布尔信号,以触发流程执行一次,而不改变它。

    从以下问题构造一个最小、完整且可验证的示例:

    entity correction is 
    end correction;
    
    architecture behavioral of correction is
        type array_new is array (0 to 4, 0 to 4) of integer;
        signal array_new_signal11: array_new := ((1,2,3,4,5),
                                                 (4,5,6,7,8),
                                                 (7,8,9,0,1),
                                                 (1,3,6,5,9),
                                                 (2,3,5,4,5));
        signal kelvin: boolean;
    begin
    
        -- array_new_signal11 <=  ((1,2,3,4,5),
        --                         (4,5,6,7,8),
        --                         (7,8,9,0,1),
        --                         (1,3,6,5,9),
        --                         (2,3,5,4,5));
    
        process (kelvin)
            variable sum1: integer:= 0;
            variable sum2: integer:= 0;
            variable total_sum: integer:= 0;
            variable average: integer:= 0;
        begin
            for row in 0 to 4 loop
                for column in 0 to 4 loop 
                    if row = 1 and column = 1 then
                        for column in 1 to 3 loop
                            sum1 := array_new_signal11(row, column) + sum1;
                        end loop;
                    end if;
                    if row = 2 and column = 1 then
                        for column in 1 to 3 loop
                            sum2 := array_new_signal11(row, column) + sum2;
                        end loop;
                    end if;   
                end loop;
            end loop;
          total_sum := sum1 + sum2;
          average := total_sum / 8;
          report "sum1 = " & integer'image(sum1) & ", " &
                 "sum2 = " & integer'image(sum2) & ", " &
                 "average = " & integer'image(average);
          array_new_signal11(3,2) <= average;
        end process;
    MONITOR_PROCESS:
        process
        begin
            wait on array_new_signal11;
            for row in 0 to 4 loop
                report "row" & integer'image(row) & " = " &
                        integer'image(array_new_signal11(row,0)) & ", " &
                        integer'image(array_new_signal11(row,1)) & ", " &
                        integer'image(array_new_signal11(row,2)) & ", " &
                        integer'image(array_new_signal11(row,3)) & ", " &
                        integer'image(array_new_signal11(row,4));
            end loop;
        end process;
    end behavioral;
    
    由平均值指定

    正如Renaud Pacalet所指出的,有两个不同的进程驱动array_new_signal11,这在VHDL中是不合法的,因为它的元素类型integer不是已解析的数据类型

    解决方案是在声明数组的情况下初始化该数组

    否则,对阵列信号元素的每个赋值都必须处于相同的过程中。您所拥有的并发信号分配将被细化为一个等效的过程语句,并在细化时生成一个错误,因为它是w
    ghdl -r correction
    for signal: .correction(behavioral).array_new_signal11(3,2)
    ./correction:error: several sources for unresolved signal
    ./correction:error: error during elaboration