复合文件/组件实例化

时间:2019-02-10 03:16:17

标签: vhdl

我是VHDL的新手。我试图了解如何使用不同的组件.vhd文件来构建完整的结构。我正在使用Digilent PmodA7,并且希望两个LED交替闪烁。

我尝试过的是Inverter.vhd和LedBlink.vhd

Inverter.vhd:

function setup() {
  createCanvas(600, 600);
  background(200);
  noLoop();
}

function draw() {
  translate(width/2, height/2);
  loadPixels();
  for (let x=0; x<=width; x++) {
    for (let y=0; y<=height; y++) {
      a=map(x, 0, width, -2.5, 1);
      b=map(y, 0, height, -1, 1);
      z=new Complex(a, b);
      f = (mand(z))
      //i = map(f,1,100,0,255);
      pixels[(x+y*width)*4]=sqrt(f/100);
      pixels[(x+y*width)*4+1]=255;
      pixels[(x+y*width)*4+2]=150;

    }
  }
  updatePixels();
}

var Complex = function(a, b) {
  this.re=a;
  this.im=b;
  this.modSq=(a*a+b*b);
}

Complex.prototype.square = function() {
  a=sq(this.re)-sq(this.im);
  b=2*this.re*this.im;
  return new Complex(a, b);
}

function mand(c) {
  oldZ=new Complex(0, 0);
  for (let i=1; i<=100; i++) {
    newZ=oldZ.square();
    newZ.re+=c.re;
    newZ.im+=c.im;
    //newZ.re+= -0.70176;
    //newZ.im+= -0.3842;
    oldZ=newZ;
    if (oldZ.modSq>=4) {
      return i
    }
  }
  return 0
}

Ledblink-1.vhd:

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
entity Inverter is
Port (
      Inv_in  : in  std_logic;
      Inv_out : out std_logic
      );
end Inverter;
architecture Behavioral of Inverter is
begin
    Inv_out <= not Inv_in;
end Behavioral;

要了解如何合并文件,我想替换一行 blink_1 <= blink_0; 与逆变器组件(即7404)一起使用,但无法确定如何执行此操作。我要遵循的示例未使用库,因此我对该方法最感兴趣,尽管如何使用库来完成此操作会有所帮助。 我所拥有的是:

1 个答案:

答案 0 :(得分:2)

您尚未提供带有错误的最小,完整和可验证的示例。在堆栈溢出方面寻求编程帮助的问题是实际的,而不是理论上的。这意味着这里有一个特定的问题。

在未标记的过程中,架构主体或组件实例中缺少is会导致分析(编译)失败。

您不能实例化流程(只能包含顺序语句)中的组件(并发语句)。将组件实例移到流程之外。

触发器输出blink_0inverter的输入。然后将其输出blink_1分配给流程中的blink_0而不是not blink_0

blink_1仅在inverter体系结构中的并发赋值语句的详细过程中赋值。设计层次结构中的每个流程都有一个驱动程序。在仿真过程中可以解析多个驱动程序的值。等效的后期合成具有两个驱动相同信号的设备,并且会产生合成误差。

在详细介绍LedBlink之前分析Inverter.vhd。

cnt必须为增量模拟而重置,对所有'U'加1将得到所有'U'。您不使用软件包std_logic_unsigned。

library ieee;
use ieee.std_logic_1164.all;
-- use ieee.std_logic_unsigned.all;
use ieee.numeric_std.all;

entity ledblink is
    port ( 
        clk:    in  std_logic;
        rst:    in  std_logic;
        led_0:  out std_logic;
        led_1:  out std_logic
    );
end entity ledblink;

architecture behavioral of ledblink is  -- ADDED is
    component inverter is 
        port ( 
            inv_in:     in  std_logic;
            inv_out:    out std_logic
        );        
    end component;
    constant clk_freq:      integer := 12500000;
    constant blink_freq:    integer := 1;
    constant cnt_max:       integer := clk_freq/blink_freq/2 - 1;
    signal cnt:             unsigned(24 downto 0);
    signal blink_0:         std_logic := '1';
    signal blink_1:         std_logic := '1';
begin
    process (clk)  -- contains counter cnt and flip flop blink_0
    begin
        if rst = '1' then
            blink_0 <= '0';
            -- blink_1 <= '0';  -- ONLY one driver for blink_1, the component
            cnt <= (others => '0'); -- ADD cnt to reset
        elsif  clk = '1' and clk'event then -- OR rising_edge(clk)
            if cnt = cnt_max then
                cnt <= (others => '0');          
                -- blink_1 <= blink_0;
                -- a1: inverter   MOVED to architecture body
                --     port map ( inv_in => blink_0, inv_out => blink_1);
                -- blink_0 <= not blink_0;  CHANGED
                blink_0 <= blink_1;                
            else
                cnt <= cnt + 1;
            end if; 
        end if;
    end process;
a1: 
    inverter   -- MOVED to architecture body a place for concurrent statements
        port map ( inv_in => blink_0, inv_out => blink_1);

    led_0 <= blink_0;
    led_1 <= blink_1;
end architecture behavioral;

之后,您的设计将进行分析,并通过提供时钟和复位功能的测试平台进行详细说明和仿真:

ledblink_tb simulation

注意cnt仅要求长度为23(22降至0),cnt(24)和cnt(23)始终为0,时钟为12.5 MHz(12500000)。

问题提示:“我要遵循的示例未使用库,因此我对这种方法最感兴趣,尽管如何使用库来完成此操作会有所帮助。”

第一个子句并不完全准确。参见IEEE Std 1076-2008 13.2设计库:

  

设计库是以前分析的设计单元的依赖于实现的存储工具。支持任何数量的设计库都需要给定的实现。
  ...
  设计库分为两类:工作库和资源库。工作库是将设计单元分析产生的库单元放入其中的库。资源库是包含要分析的设计单元中引用的库单元的库。在分析任何给定设计单元时,只有一个库是工作库;相反,在这种分析过程中,任何数量的库(包括工作库本身)都可以是资源库。

     

除上下文声明和程序包STANDARD之外,每个设计单元均假定包含以下隐式上下文项作为其上下文子句的一部分:

     

STD,工作; 使用 STD.STANDARD。全部

     

库逻辑名STD表示包含STANDARD,TEXTIO和ENV包的设计库(请参见第16章)。 (use子句使程序包STANDARD中的所有声明在相应的设计单元中直接可见;请参见12.4。)库逻辑名WORK表示在给定分析期间的当前工作库。库逻辑名IEEE表示设计库,其中包含数学,多值逻辑和综合包以及综合上下文声明(请参见第16章)。

将设计规范分析到工作库中,work可以引用该设计规范,并且可以重定向与实现相关的方法。

有一些规则来确定默认绑定指示(代替配置规范中的绑定指示,作为包含组件实例化的块(包括体系结构主体)或配置声明(未广泛使用)中的块声明项(如果有的话,则通过综合工具)。请参见11.7组件实例化和3.4.3组件配置。

这里没有显式绑定指示,VHDL依赖于默认绑定指示(7.3.3默认绑定指示):

  

在某些情况下,默认绑定指示将在没有显式绑定指示的情况下应用。默认绑定指示包括默认实体方面,以及适当的默认通用映射方面和默认端口映射方面。

     

如果没有可见的实体声明具有与实例化组件相同的简单名称,则默认实体方面将打开。可见的实体声明是以下列表中的第一个实体声明(如果有):

     
    

a)具有与实例化组件相同的简单名称且直接可见的实体声明(请参见12.3),
    b)具有与实例化组件相同的简单名称的实体声明,并且在缺少具有与实体声明相同的简单名称的直接可见(参见12.3)组件声明的情况下将直接可见的实体声明,或< br />     c)用L.C表示的实体声明,其中L是目标库,C是实例化组件的简单名称。目标库是包含在其中声明了组件C的设计单元的库的库逻辑名。

  
     

这些可见性检查是在缺少显式绑定指示的点进行的,该指示使默认绑定指示得以应用。

在这种情况下,因为根据规则b)将inverter分析到相同的资源库中(不变的work)。您可能会注意到,这些规则设置得尽可能轻松。库中只能有一个同名的主要单位(这里是一个实体)。

无论如何,关键是原始帖子的代码中包含库。在这里,没有配置规范inverter的情况下,期望在库work中找到它,无论它在实现定义的庄园中引用了哪个资源库。

它不在标记的范围内,原始文章并未标识特定的工具实现,并且VHDL工具在将工作库和资源库与库逻辑名相关联的方法上也有所不同。

对于由库子句可见的资源库,使用形式为“ use library_logical_name。全部”的use子句。可以使资源库中的所有命名实体直接可见(请参见12.4使用子句,12.3可见性,12.5过载解析的上下文)。否则,可以使用实例化实体的选定名称(8.3选定名称)。