我有一个与从numeric_std转换为std_logic_vector相关的问题。我正在使用移动平均滤波器代码,我在网上看到并过滤我的ADC值以稳定值。
过滤器包代码是:
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
package filterpack is
subtype number is unsigned(27 downto 0);
type numbers is array(natural range <>) of number;
function slv_to_num(signal slv: in std_logic_vector) return number;
procedure MAF_filter(
signal x: in number;
signal h: inout numbers;
signal y: out number
);
end filterpack;
package body filterpack is
function slv_to_num(signal slv: in std_logic_vector) return number is
variable x: number := (others => '0');
begin
for i in slv'range loop
if slv(i) = '1' then
x(i+4) := '1';
end if;
end loop;
return x;
end function slv_to_num;
procedure MAF_filter(
signal x: in number;
signal h: inout numbers;
signal y: out number
) is
begin
h(0) <= x + h(1); -- h[n] = x[n] + h[n-1]
y <= h(0) - h(h'high); -- y[n] = h[n] - h[n-M]
end MAF_filter;
end package body filterpack;
在我的顶级文件中,我调用了MAF_filter过程。
Asign_x: x <= slv_to_num(adc_dat);
Filter: MAF_filter(x,h,y);
adc_dat定义为:
adc_dat : out std_logic_vector (23 downto 0);
我想将MAF_Filter的输出转换为std_logic_vector(23 downto 0)。任何人都可以告诉我如何将过滤器输出'y'转换为'std_logic_vector'?
非常感谢!
答案 0 :(得分:1)
你想用4个额外的位做什么?您的类型number
有28位,但您的信号adc_dat
只有24位。
如果可以丢弃它们,您可以使用:
adc_dat <= std_logic_vector(y(adc_dat'range));
另外,是否有理由不编写您的函数slv_to_num
,如下所示?
function slv_to_num(signal slv: in std_logic_vector) return number is
begin
return number(slv & "0000");
end function slv_to_num;
答案 1 :(得分:0)
转换必须解决2个问题:您注意到的类型差异,以及这两个字的大小不同的事实。
类型差异很简单:std_logic_vector (y)
会为您提供正确的类型。因为这两种类型是相关类型,所以这只是一个演员。
尺寸差异......只有你有这方面的知识。
adc_dat <= std_logic_vector(y(23 downto 0))
将给出Y的LSB - 即Y本身的值,但可以溢出。或者正如Rick所说,adc_dat <= std_logic_vector(y(adc_dat'range));
通常更好,但我想揭露细节。
adc_dat <= std_logic_vector(y(27 downto 4))
不会溢出,但实际上会给你y / 16。