首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >VHDL综合编码中时钟的两个边沿

VHDL综合编码中时钟的两个边沿
EN

Stack Overflow用户
提问于 2019-01-08 19:43:12
回答 2查看 772关注 0票数 0

综合编码风格将在未来实现吗?或者IEEE-1076.6-200X标准现在允许简化和增强VHDL综合编码能力?

代码语言:javascript
复制
--Multiple Edge Registers
--Copyright © 2004 SynthWorks Design Inc. All Rights Reserved.
DualEdgeFF : process( nReset, Clk1, Clk2)
begin
  if (nReset = '0') then
    Q <= '0' ;
  elsif rising_edge(Clk1) then -- Functional Clock
    Q <= D ;
  elsif rising_edge(Clk2) then -- Scan Clock
    Q <= SD ;
  end if ;
  -- RTL_SYNTHESIS OFF
  if rising_edge(Clk1) and rising_edge(Clk2) then
    report "Warning: . . ." severity warning ;
    Q <= 'X' ;
  end if ;
-- RTL_SYNTHESIS ON
end process;

--Register Using Both Edges of Clk
DualEdge_Proc: process (Clk, Reset) is
begin
  if Reset = '1' then
    Q <= (others => '0');
  elsif rising_edge(Clk) then
    Q <= D4Rise;
  elsif falling_edge(Clk) then
    Q <= D4Fall;
  end if;
end process DualEdge_Proc;
EN

回答 2

Stack Overflow用户

发布于 2019-01-09 00:11:45

if (nReset = '0') then Q <= '0' ; elsif rising_edge(Clk1) then -- Functional Clock Q <= D ; elsif rising_edge(Clk2) then -- Scan Clock Q <= SD ; end if ;

这永远不会映射到现实世界中任何合理的东西。这对于综合来说是无效的设计。

if Reset = '1' then Q <= (others => '0'); elsif rising_edge(Clk) then Q <= D4Rise; elsif falling_edge(Clk) then Q <= D4Fall; end if;

这可以映射到DDR IO输出寄存器。FPGA具有此功能,但这些工具目前无法合成此代码。他们可能会在未来支持这样的东西。还有一些问题,比如D4Fall必须从上升边缘域重新计时。

目前,您必须显式实例化特定于技术的DDR单元。

票数 0
EN

Stack Overflow用户

发布于 2019-01-09 02:49:51

工作组提供了用于创建编码样式的模板和规则。上面的例子展示了一些潜在的用法。诚然,我最近没有看到第一种编码风格,尽管正如我所评论的那样,我认为当时我能够在ASIC库中找到这样的寄存器,将其用于扫描逻辑。

然而,今天,如果我们稍微修改一下显示的代码模板(但仍然与1076.6-2004年兼容),我们就有了一些有用的东西。请注意,我将"elsif“替换为"end if”和单独的"if“,这是我首选的编码方式。

代码语言:javascript
复制
MemProc : process (ClkA, ClkB)
  type MemType is array (0 to 1023) of std_logic_vector(7 downto 0) ;
  variable Mem : MemType ;
begin
  if rising_edge(ClkA) then
    DataOutA <= Mem(to_integer(unsigned(AddrA))) ;
    if WriteA = '1' then
      Mem(to_integer(unsigned(AddrA))) := DataInA ;
    end if ;
  end if ;
  if rising_edge(ClkB) then
    DataOutB <= Mem(to_integer(unsigned(AddrB))) ;
    if WriteB = '1' then
      Mem(to_integer(unsigned(AddrB))) := DataInB ;
    end if ;
  end if ;
end process ;

您可能还认为某些FPGA供应商要求的编码样式不是语言合法的。共享变量的类型必须是受保护类型。普通类型的共享变量在VHDL-93中暂时是合法的,但正如在VHDL-93中指出的那样,这在下一个修订版本VHDL-2000/2002中得到了修复。

如果FPGA供应商想要做一些有效和语言合法的事情,他们可以用OSVVM MemoryPkg代码替换他们的非法代码,将内存模型实现为适当的受保护类型。我之所以说这是高效的,是因为MemoryPkg实现了一种数据结构,该结构只在内存被使用时实现内存。你可以在github和osvvm.org上找到OSVVM。

代码语言:javascript
复制
library OSVVM;
use OSVVM.MemoryPkg.all;

architecture ...
  shared variable ptRam : MemoryPType ;
begin
  ptRam.MemInit(
AddrWidth => Address'length, DataWidth => Data'length
) ;

MemAProc : process (ClkA)
begin
  if rising_edge(ClkA) then
    DataOutA <= ptRam.MemRead(AddrA) ; ;
    if WriteA = '1' then
      ptRam.MemWrite(AddrA, DataInA) ;
    end if ;
  end if ;
end process ;

MemBProc : process (ClkB)
begin
  if rising_edge(ClkB) then
    DataOutB <= ptRam.MemRead(AddrB) ; ;
    if WriteB = '1' then
      ptRam.MemWrite(AddrB, DataInB) ;
    end if ;
  end if ;
end process ;

你可能会说,合成一个受保护的类型太难了。简单的答案是,你不需要这样做。您也无法在std_logic_1164或numeric_std中综合大部分代码--不相信我,试着从rising_edge中提取代码,并在一个if语句中使用所有这些代码来制作触发器。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/54091116

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档