使用 1 位 ALU 制作 16 位 ALU

2024-01-19

你好,我正在尝试从几个 1 位 ALU 创建一个 16 位 ALU 我创建了一个名为 basic_alu1 的包,其中包含 1 位 ALU 的组件。其代码是:

library ieee;
use ieee.std_logic_1164.all;
package basic_alu1 is
component alu1
    port (a, b: std_logic_vector(1 downto 0);
            m: in std_logic_vector(1 downto 0);
            result: out std_logic_vector(1 downto 0));
end component;
end package basic_alu1;


library ieee;
use ieee.std_logic_1164.all;
entity alu1 is
    port (a, b: std_logic_vector(1 downto 0);
    m: in std_logic_vector(1 downto 0);
    result: out std_logic_vector(1 downto 0));
end alu1; 
architecture arch1 of alu1 is 
begin
 process(a, b, m)
 begin
 case m is
 when "00" =>
    result <= a + b;
  when "01" =>
    result <= a + (not b) + 1;
  when "10" =>
    result <= a and b;
  when "11" =>
    result <= a or b;
end case
 end process
 end arch1

因此,为了创建 16 位 ALU,我使用 for 生成循环并实例化 alu1 的多个副本。我的问题是如何将柜台取入和取出,以及如何进行溢出检查。我的主要代码是:

library ieee;
use ieee.std_logic_1164.all;
use work.basic_alu1.all;

entity alu16 is
  port (input_a : in std_logic_vector(15 downto 0);
        input_b : in std_logic_vector(15 downto 0);
        mode : in std_logic_vector(1 downto 0)
        result_x4 : out std_logic);
end alu16;

architecture structural of alu16 is
begin
G1 : for i in 0 to 15 generate
begin
    alu_16 : entity work.basic_alu1
    port map (
    a => input_a(i),
    b => input_b(i),
    m => mode,
    result => result_x4(i));
end generate;

以下是如何创建 N 位加法器组件的示例。首先,您需要创建一个全加器,它是一个也考虑进位的加法器。

LIBRARY ieee;
USE ieee.std_logic_1164.ALL;

ENTITY fullAdder IS
    PORT (a     : IN STD_LOGIC;
          b     : IN STD_LOGIC;
          cin   : IN STD_LOGIC;
          y     : OUT STD_LOGIC;
          cout  : OUT STD_LOGIC);
END fullAdder;

ARCHITECTURE arch_fullAdder OF fullAdder IS
BEGIN
    y <= a XOR b XOR cin;
    cout <= (a AND b) OR 
            (b AND cin) OR 
            (a AND cin);
END arch_fullAdder;

当您拥有这个 1 位加法器时,您可以通过生成我们上面的全加器的多个单元来轻松生成 N 位纹波进位。

LIBRARY IEEE;
USE IEEE.STD_LOGIC_1164.ALL;

ENTITY ripple_adder IS 
    GENERIC (WIDTH : NATURAL := 32);
    PORT(a      : IN STD_LOGIC_VECTOR(WIDTH-1 DOWNTO 0);
         b      : IN STD_LOGIC_VECTOR(WIDTH-1 DOWNTO 0);
         cin    : IN STD_LOGIC := '0';
         y      : OUT STD_LOGIC_VECTOR(WIDTH-1 DOWNTO 0);
         cout   : OUT STD_LOGIC);
END ripple_adder;

ARCHITECTURE arch_ripple_adder OF ripple_adder IS

    SIGNAL carry    : STD_LOGIC_VECTOR(WIDTH DOWNTO 0);
    SIGNAL y_temp   : STD_LOGIC_VECTOR(WIDTH-1 DOWNTO 0);

    COMPONENT fullAdder IS
        PORT(a      : IN STD_LOGIC;
             b      : IN STD_LOGIC;
             cin    : IN STD_LOGIC;
             y      : OUT STD_LOGIC;
             cout   : OUT STD_LOGIC);
    END COMPONENT;
BEGIN  

    N_bit_adder_generate : FOR N IN 0 TO WIDTH-1 GENERATE
    N_bit_adder : fullAdder
        PORT MAP(a      => a(N),
                 b      => b (N),
                 cin    => carry(N),
                 y      => y_temp(N),
                 cout   => carry(N + 1));
    END GENERATE;

    carry(0) <= cin;
    cout <= carry(WIDTH);
    y <= y_temp;

END arch_ripple_adder;

当您拥有加法器时,您可以轻松地将加法器组件放入 ALU 中,并指定 ALU 应能够执行的不同操作。

LIBRARY  ieee;
USE  ieee.std_logic_1164.ALL;
USE ieee.numeric_std.ALL;

ENTITY ALU IS 
    GENERIC(WIDTH : NATURAL := 32);
    PORT(Clk    : IN STD_LOGIC := '0';
         Reset  : IN STD_LOGIC := '0';
         A      : IN STD_LOGIC_VECTOR(WIDTH-1 DOWNTO 0) := (OTHERS => '0');
         B      : IN STD_LOGIC_VECTOR(WIDTH-1 DOWNTO 0) := (OTHERS => '0');
         Op     : IN STD_LOGIC_VECTOR(3 DOWNTO 0) := (OTHERS => '0');
         Outs   : OUT STD_LOGIC_VECTOR(WIDTH-1 DOWNTO 0));
END ALU;

ARCHITECTURE arch_ALU OF ALU IS

    COMPONENT ripple_adder
    PORT(a      : IN STD_LOGIC_VECTOR(WIDTH-1 DOWNTO 0);
         b      : IN STD_LOGIC_VECTOR(WIDTH-1 DOWNTO 0);
         cin    : IN STD_LOGIC := '0';
         y      : OUT STD_LOGIC_VECTOR(WIDTH-1 DOWNTO 0);
         cout   : OUT STD_LOGIC);
END COMPONENT;

    SIGNAL RCA_output   : STD_LOGIC_VECTOR(WIDTH-1 DOWNTO 0) := (OTHERS => '0');
    SIGNAL B_neg        : STD_LOGIC_VECTOR(WIDTH-1 DOWNTO 0) := (OTHERS => '0');
    SIGNAL c_flag       : STD_LOGIC := '0';
    SIGNAL c_reg        : STD_LOGIC := '0';
    SIGNAL cin          : STD_LOGIC := '0';

BEGIN

RCA_comp : ripple_adder
   PORT MAP(a => A,
            b => B_neg,
            Cin => cin,
            y => RCA_output,
            Cout => c_flag);        

    WITH Op SELECT 
        B_neg <= NOT(B) WHEN "1000",
                     B  WHEN OTHERS;

    WITH Op SELECT
        cin <= '1'      WHEN "1000", -- SUB
                c_reg   WHEN "0111", -- ADDC
                '0'     WHEN OTHERS; -- ADD/ADDS    

    ALU_Process:
    PROCESS(Clk, Reset)
    BEGIN
        IF Reset = '0' THEN
            Outs <= (OTHERS => '0');
            c_reg <= '0';
        ELSIF rising_edge(Clk) THEN
            CASE Op IS
                WHEN "0001" => Outs <= A AND B;
                WHEN "0010" => Outs <= A OR  B;
                WHEN "0011" => Outs <= A NOR B;
                WHEN "0100" => Outs <= A XOR B;
                WHEN "0101" => Outs <= RCA_output; -- ADD 
                WHEN "0110" => Outs <= RCA_output; -- ADDS
                    c_reg <= c_flag;    
                WHEN "0111" => Outs <= RCA_output; -- ADDC
                WHEN "1000" => Outs <= RCA_output; -- SUB
                WHEN "1001" => Outs <= STD_LOGIC_VECTOR(UNSIGNED(A) SLL to_integer(UNSIGNED(B(4 DOWNTO 0))));
                WHEN "1010" => Outs <= STD_LOGIC_VECTOR(unsigned(A) SRL to_integer(UNSIGNED(B(4 DOWNTO 0))));
                WHEN "1011" => Outs <= STD_LOGIC_VECTOR(shift_right(SIGNED(A),to_integer(UNSIGNED(B(4 DOWNTO 0)))));
                WHEN OTHERS => Outs <= (OTHERS => '0');
            END CASE;
        END IF;
    END PROCESS;
END arch_ALU; 

然而,该 ALU 并不那么复杂,也没有那么多操作,但可以轻松添加该功能。我希望我给您的示例代码对您有所帮助。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

使用 1 位 ALU 制作 16 位 ALU 的相关文章

  • 来自不同进程的VHDL驱动信号

    我对以下 VHDL 代码有一个小问题 process zbroji begin if rising edge zbroji then oduzima lt 0 ucitanPrvi lt 1 broj1 lt ulaz broj end i
  • 在 VHDL 中找到运算符“+”的“0”定义

    首先我想指出 这是我第一次尝试 VHDL 所以请客气一点 我想读取 X1 X4 输入并在输出处生成输入的总和 这是我的代码 library IEEE use IEEE STD LOGIC 1164 ALL entity counter of
  • Altera Quartus 错误 (12007):顶层设计实体“alt_ex_1”未定义

    我看了之前所有的问题 似乎没有人有问题 和我的一样简单 我也在网上搜索过 但找不到解决方案 我是 VHDL 新手 正在尝试编译提供的简单示例 由Altera设计 如下 library ieee use ieee std logic 1164
  • VHDL:使用输入端口是不好的做法吗?

    我有一个程序 我按照以下方式使用 inout 端口 port inout unsigned 9 downto 0 if port gt 10 then port lt port 1 end if 我正在使用 inout 端口 这样我就可以读
  • VHDL:对固定信号值进行零扩展

    如何对固定信号值进行零扩展 我有以下信号 signal shamt std logic vector 4 downto 0 在将其分配给另一个大小为 31 到 0 的变量之前 我必须将 shamt 归零 我有以下代码 但我不确定它是否正确
  • VHDL 中信号何时分配?

    考虑这段代码 architecture synth of my entity is signal a std logic begin a lt c and d b lt a and c end synth 第二行会尊重这一点吗a在其他进程中
  • 使用 VHDL 实例化 FPGA 中的 RAM

    我试图按照中的指导实现双端口 RAM这篇优秀的博文 http danstrother com 2010 09 11 inferring rams in fpgas 然而 ModelSim 在编译时给出以下警告 Warning fifo ra
  • “等待上升沿(clk)”与“如果上升沿(clk)”有什么区别?

    我在 VHDL 中遇到了两种风格的过程语句 process clk begin if rising edge clk do something 另一种是 process begin wait until rising edge clk do
  • VHDL:进程块内的多个上升沿检测

    我对 VHDL 以及一般的数字电路 还很陌生 我正在尝试使用 BCD 样式块实现两位数的计数器 该电路的外部有一些按钮 按下这些按钮时 会将感兴趣的数字加一 很像闹钟 这是一个异步操作 会在某种形式的编辑模式下发生 外部强制 我编写的代码在
  • 同时读取和写入寄存器

    我计划在 FPGA 上用 VHDL 设计一个类似 MIPS 的 CPU CPU 将具有经典的五级管道 没有转发和危险预防 在计算机体系结构课程中 我了解到第一个 MIPS CPU 用于在时钟上升沿读取寄存器文件并在时钟下降沿写入 我使用的F
  • 如何在 Sphinx 运行时预处理源文件?

    我已经为我的项目设置了 Sphinx 文档 并希望提取源文件的文档字符串并将它们嵌入到最终文档中 不幸的是 Sphinx 不支持源文件的语言 VHDL VHDL 似乎没有 Sphinx 域 所以我的想法如下 挂钩 Sphinx 运行并在 S
  • VHDL 上的反转位顺序

    我在做类似的事情时遇到困难 b 0 to 7 lt a 7 downto 0 当我用ghdl编译它时 出现顺序错误 我发现使我的电路工作的唯一方法如下 library ieee use ieee std logic 1164 all ent
  • 错误(10028):无法解析网络的多个常量驱动程序... VHDL 错误

    我正在尝试编写一个代码来检测 din 信号的上升沿 并在发生后将 doout 提高 5 个时钟周期 我在编译时不断收到不同的错误 但我不确定它们的含义 我认为我对 VHDL 中的一些概念缺乏基本的了解 但遗憾的是在网上查找并没有给我带来太大
  • 有没有办法使用 std textio 在 vhdl 中多次读取文件?

    我试图了解如何在 vhdl 中读取文件 如果我打开一个文件 通读它 测试文件结尾 关闭文件 然后重新打开该文件 然后再次开始读取 它会从开头开始吗 文件 非常感谢 向 VHDL 语言的权威寻求答案 IEEE 标准 1076 2008 5 5
  • Lex VHDL '(勾号)令牌

    在 VHDL 中 字符可用于封装字符标记ie 或者它可以作为属性分隔符 类似于 CPP 的 token ie string hello 解析包含字符的属性名称时出现问题ie string a b c 在这种情况下 天真的词法分析器将错误地标
  • VHDL 中的 BRAM_INIT

    我正在模拟基于处理器的设计 其中程序存储器内容保存在 BRAM 中 我正在使用 VHDL 推断 BRAM 实现程序存储器 我试图避免使用 CoreGen 因为我想保持设计的可移植性 最终该设计将进入 FPGA 我想看看是否有一种方法可以使用
  • 全8位加法器,非逻辑输出

    我创建了一个带全加器的 8 位加法器 正如您所看到的 我开始从右到左添加相应的位 对于 cin 信号 t1 和 t2 并按顺序 cout t2 和 t1 第一个 cin 设置为加法器输入 cin 我在实现中没有看到任何问题 但是当我运行它时
  • 赋值语句中的“others=>'0'”是什么意思?

    cmd register process rst n clk begin if rst n 0 then cmd r lt others gt 0 elsif clk event and clk 1 then cmd r lt end if
  • 学习 VHDL 的最佳方法? [关闭]

    就目前情况而言 这个问题不太适合我们的问答形式 我们希望答案得到事实 参考资料或专业知识的支持 但这个问题可能会引发辩论 争论 民意调查或扩展讨论 如果您觉得这个问题可以改进并可能重新开放 访问帮助中心 help reopen questi
  • Simulink/HDL Coder 中的反馈循环

    我有一个 Simulink HDL 编码器系统 请参见下图 我有 3 个输出和 3 个输入 我希望我的系统运行 10 次 每次迭代后 它应该选择输出并将它们用作输入 我怎样才能做到这一点 使用存储器和每个信号的初始值块构建一个循环 内存块允

随机推荐

  • AnyDac 又名 FireDac 无法生成更新查询

    我已经使用 UniDac 很长时间了 决定转向 FireDac 因为它具有良好的异步方法 在继续使用后 我发现我的数据编辑不再起作用 它给了我一个错误 FireDAC 物理 330 无法生成更新查询 更新表未定义 我在这里想做的是我有一个
  • Spring单例和Java单例(设计模式)有什么区别? [复制]

    这个问题在这里已经有答案了 我正在学习 Spring 框架 目前正在阅读一本关于它的书 这本书里说Spring单例与Java单例不同 这意味着什么以及有什么区别 谢谢 Java 单例的作用域是 Java 类加载器 Spring 单例的作用域
  • 严重:泄漏:在垃圾收集之前未调用 ByteBuf.release()。内蒂

    我已经创建了一些游戏服务器 并且刚刚与大约 10 个伙伴进行了测试 一切都很顺利 我们玩了大约 10 分钟 在游戏的某个时刻 游戏服务器停止为客户端提供服务 断开了每个人的连接 而且我连接到运行游戏的 VPS 的 SSH 也断开了连接 我不
  • Excel VBA 函数检查文件名是否包含该值

    我需要一个可以输出如下内容的公式 如果特定文件夹中的文件名包含 因为文件名在 字符后会有一个附加字符串 因此如果文件名包含单元格值 AB1 则在单元格 AC1 中添加完整文件名 用VBA可以实现吗 非常感谢 这在VBA中可行吗 当然 这是我
  • 如何反序列化 ArrayObject

    Note 我尝试过使用反序列化函数 但它说第一个参数应该是字符串而不是对象 所以我的问题 Q 如何在 php 中反序列化 ArrayObject 我的 ArrayObject 包含 O 11 ArrayObject 2 s 14 shopp
  • 将 WebKit 用于桌面应用程序 [关闭]

    就目前情况而言 这个问题不太适合我们的问答形式 我们希望答案得到事实 参考资料或专业知识的支持 但这个问题可能会引发辩论 争论 民意调查或扩展讨论 如果您觉得这个问题可以改进并可能重新开放 访问帮助中心 help reopen questi
  • UIImage:调整大小,然后裁剪

    几天来 我一直在努力解决这个问题 尽管我一直觉得自己正处于启示的边缘 但我根本无法实现我的目标 在设计的概念阶段之前 我认为从 iPhone 的相机或库中抓取图像 使用相当于宽高比填充UIImageView 的选项 完全在代码中 然后cro
  • 是什么导致我的 WP7 应用程序崩溃?

    我在模拟器和手机本身上都发生过一些无法解释的崩溃 基本上 当我的应用程序崩溃时 我不会看到任何对话框 并且手机会返回主屏幕 我有以下代码来显示消息框 但这在某种程度上被绕过了 Code to execute if a navigation
  • 明星算法:距离启发式

    我正在使用 A 星算法 如此处所示 取自http code activestate com recipes 578919 python a pathfinding with binary heap http code activestate
  • 将等高线与等高线填充图对齐不规则网格极坐标图(半圆)

    我看到有几个人回答了使用不规则网格绘图的问题 我无法使轮廓线与填充轮廓对齐 此外 需要在绘图上显示数据点位置 以及以 30 度增量显示的径向辐条 以及在 10 20 30 处显示的半圆 Ref 在不规则网格上绘制等高线 https stac
  • 有没有一种快速方法可以在音频文件中查找(不一定识别)人类语音?

    我想编写一个程序 自动同步未同步的字幕 我想到的解决方案之一是以某种方式通过算法找到人类语音并根据其调整字幕 我发现的 API Google Speech API Yandex SpeechKit 与服务器一起工作 这对我来说不太方便 并且
  • SwiftUI 模态演示仅在 navigationBarItems 中工作一次

    当您从导航栏项目内的按钮显示模式时 SwiftUI 中存在一个错误 在下面的代码中 按钮 1 按预期工作 但按钮 2 只工作一次 struct DetailView View Binding var isPresented Bool Env
  • 为什么不能使用具有多态返回类型的原始类型?

    考虑以下两个类 public interface Foo
  • 将 Java BigInteger 用于巨大位掩码的性能影响

    我们面临着一个有趣的挑战 我们必须控制对驻留在 容器 中的数据的访问 可能会有数十万个 垃圾箱 对每个垃圾箱的访问是单独控制的 但限制可能而且可能会重叠 我们正在考虑为每个 bin 分配位掩码中的一个位置 1 2 3 4 等 然后 当用户登
  • 使用参数 [null, 2, 3] 执行“INSERT INTO events (user_id, ET1, ET2) VALUES (?, ?, ?)”时发生异常:

    我正在尝试从默认控制器内部创建表单 我希望主页中两个下拉列表中的值都存储在事件表的 ET1 和 ET2 列中 我能够做到这一点 但是我希望登录用户的 user id 也应该存储在事件表的 user id 列中 当尝试这样做时 它给了我错误
  • 方法 Illuminate\Database\Eloquent\Collection::links 不存在

    我创建了用户和消息之间的模型关系 我想为经过身份验证的用户实现消息列表 但出现以下错误 方法 Illuminate Database Eloquent Collection links 不存在 控制器 public function ind
  • 当我使用快捷键时获取我的ContextMenuStrip的SourceControl

    我有单身ContextMenuStrip连接到两个控件 DataGridView In the ToolStripMenuItem单击事件 我设法得到原始调用者 DataGridView 用这个代码 var menu ToolStripDr
  • 查找 Excel 电子表格的模板路径

    我有一个带有 VBA 代码的 Excel 电子表格模板 xltm 文件 我想在模板打开的电子表格中找到模板的路径 问题示例 用户通过双击 C My Stuff 中的模板文件打开一个新电子表格 他们填写单元格 然后在询问他们的名称后单击一个按
  • MySQL所有父子关系

    我有一个名为table 它有一个名为id与类型INT 11 代表行的标识符 它还有其他字段 但我认为它们与这个问题无关 我有另一个表名为table children 它有一个名为parent与类型INT 11 指的是table id作为外键
  • 使用 1 位 ALU 制作 16 位 ALU

    你好 我正在尝试从几个 1 位 ALU 创建一个 16 位 ALU 我创建了一个名为 basic alu1 的包 其中包含 1 位 ALU 的组件 其代码是 library ieee use ieee std logic 1164 all