VHDL - 任何类型数组的函数/过程 [英] VHDL - Function/Procedure for any type of array

查看:32
本文介绍了VHDL - 任何类型数组的函数/过程的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

如果可能,如何声明一个用于任何类型参数的函数 T 其中对 T 的唯一约束是它被定义为一维 <代码>数组如

How does one declare, if possible, a function intended for a parameter of any type T where the only constraint on T is that it was defined as a 1D array as in

type T is array ( integer range <> ) of a_random_type;

其中 a_random_type 可以是任何 type.

以下语法错误的函数是所需的示例

The following syntactically incorrect function is an example of what is desired

function measure_size_of_any_array ( a : array ( integer range <> ) ) return natural is
    variable r : natural := 0;
begin
    for i in a'range loop
        r := r + 1;
    end loop;
    return r;
end function;

然后可以在任何 array

type natural_array is array ( integer range <> ) of natural;
type stdlogv_array is array ( integer range <> ) of std_logic_vector;

[...]

variable some_natural_array : natural_array;
variable some_stdlogv_array : stdlogv_array;

[...]

constant size_1 : natural := measure_size_of_any_array(some_natural_array);
constant size_2 : natural := measure_size_of_any_array(some_stdlogv_array);

显然,这个问题是关于定义函数的方式而不是函数本身:我不是在寻找a'length.

Obviously, this question is about the way of defining the function and not about the function itself: I am not looking for a'length.

来自 Ashenden 的 VHDL-2008:只是新东西

可以为子程序指定通用类型.

Generic types can be specified for subprograms.

我们可以通过以下方式在泛型列表中声明一个正式泛型类型:

We can declare a formal generic type in a generic list in the following way:

type indentifier

具有通用列表的函数采用以下形式:

A function with a generic list takes the form:

function indentifier
    generic   ( ... )
    parameter ( ... ) return result_type is
    ... -- declarations
begin
    ... -- statements
end function identifier

这将允许以下定义

function measure_size_of_any_array
    generic   ( type arr_type )
    parameter ( arr : arr_type );

以及以下使用

function measure_size_of_natural_array is new measure_size_of_any_array
    generic ( arr_type => natural_array );
function measure_size_of_stdlogv_array is new measure_size_of_any_array
    generic ( arr_type => stdlogv_array );

constant size_1 : natural := measure_size_of_natural_array(some_natural_array);
constant size_2 : natural := measure_size_of_stdlogv_array(some_stdlogv_array);

这提供了在不同调用之间共享函数体的所需行为,而不管array 元素的类型如何,但仍然需要一个实例化的函数(可以根据需要是本地的)所以还不错).

This provides the desired behavior of sharing the body of the function among different calls, regardless of the type of the elements of the array but still requires an instantiated function (which can be as local as desired so it isn't that bad).

由于主要供应商对 VHDL-2008 的支持很少(我尝试过的编译器无法理解以前的解决方案),因此首选 VHDL-87、-93 或 -2002 解决方案.

Because of how little support is being provided for VHDL-2008 by the main vendors (the previous solution wasn't understood by the compilers I tried), a VHDL-87, -93 or -2002 solution will be preferred.

前面的信息是我试图找到一种编写 VHDL 子程序的方法,只要它是一个 array (ie 来回答最初的问题).预期的答案不一定应该使用相同的方法(即使用 VHDL-2008 通用子程序)!

The previous information is my attempt to find a way of writing a VHDL subprogram accepting any argument as long as it is an array (i.e. to answer the initial question). The expected answer isn't necessarily supposed to use the same approach (namely using VHDL-2008 generic subprograms)!

推荐答案

2008 年之前,仅允许在实体级别定义泛型.因此,您可以通过为该函数创建一个特殊实体来将泛型传递给该函数.例如

Pre-2008, defining generics was only allowed at entity level. So you could pass generics to a function by making a special entity for that function. E.g.

entity function_ent is
    generic(return_value : natural);
    port(output : out natural);
end entity;

architecture func_def of function_ent is
    function measure_size_of_any_array return natural is
    begin
        return return_value;
    end function;
begin
    output <= measure_size_of_any_array;
end architecture;

但是,您希望将 type 作为通用参数传递...这是不可能的 <2008.因此,您必须使用 VHDL-2008.

However, you want to pass a type as a generic parameter... This is not possible <2008. So, you have to use VHDL-2008.

但是在 VHDL 中使用泛型时,您总是必须将某个值(或在 vhdl-2008 中键入)映射到它们.没有智能(预)编译器会自动检测输入类型,就像在 C++ 中一样.

But when using generics in VHDL, you will always have to map a certain value (or type in vhdl-2008) to them. There is no smart (pre-)compiler that will automatically detect the input type, like in C++.

当您最终决定使用 VHDL-2008 时,您可以问自己:我是否会在不先定义数组的情况下使用 函数?"可能不是.因此,您可以将通用(模板化")包用作与 C++ 类相当的东西.示例:

When you've eventually decided to use VHDL-2008, you can ask yourself: "will I ever use the function without defining an array first?" Likely not. So you might use a generic ("templated") package as something comparable to a C++ class. Example:

package array_pkg is
    generic (type element_type);

    type array_type is array (natural range <>) of element_type;

    function measure_size_of_array(
        arr : array_type) return natural;
end package;

package body array_pkg is
    function measure_size_of_array(
        arr : array_type) return natural is
    begin
        return arr'length;
    end function;
end package body;

entity test is
end entity test;

library ieee;

architecture beh of test is
    package natural_array_pkg is new work.array_pkg
        generic map (element_type => natural);

    signal test_sig1 : natural_array_pkg.array_type(0 to 10);
    constant test_out1 : natural := natural_array_pkg.measure_size_of_array(test_sig1);

    use ieee.std_logic_1164.all;

    package slv_array_pkg is new work.array_pkg
        generic map (element_type => std_logic_vector);

    signal test_sig2 : slv_array_pkg.array_type(0 to 12)(5 downto 0);
    constant test_out2 : natural := slv_array_pkg.measure_size_of_array(test_sig2);
begin

end architecture;

我认为这是当前 VHDL 中最接近模板化参数的方法.

I think this is the closest you can get to templated parameters in current VHDL.

这篇关于VHDL - 任何类型数组的函数/过程的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆