Veloris.
返回索引
FPGA 2025-10-21

多路选择器设计

4 分钟
1.4k words

多路选择器设计

什么是译码器

数字电路中,译码器是一种多输入多输出的组合逻辑电路,将输入的二进制代码转换为特定的输出信号。这些输出信号通常对应着代码特定的含义或者状态。译码器在数字系统中广泛应用,例如在显示器、存储器、编码器等设备中。

译码器的分类

译码器可以分为二进制译码器和BCD译码器。

  • 二进制译码器:二进制译码器将n位二进制输入转换为2^n个输出。每个输出对应一个特定的二进制代码。二进制译码器可以分为普通二进制译码器和优先级二进制译码器。

  • BCD译码器:BCD译码器将4位BCD码转换为10个输出,每个输出对应一个十进制数字。

译码器的应用

最常见的变量译码器为3-8译码器,主要用于端口的扩展。假如我们有8个led灯需要单独控制,理论上我们需要用8个I/O口,普通的单片机也够用,但是如果我们控制的不是8个led灯,而是一个点阵屏,那就可想而知我们要使用的I/O口数量不是一般控制器就能满足的了,即便是I/O资源丰 富的FPGA在面对巨大的点阵屏时也可能面临管脚资源不够用的尴尬境地。此种情况下使用3-8译码器就可以很好的解决这个问题,我们可以通过控制器控制3个I/O输出的8种情况来分别控制8个输出状态,相当于用3个I/O口就可以独立控制8个led灯,即一个3-8译码器就能够节约出来5个I/O口,算起来是相当合算 的。现在的3-8译码器大都做成了独立ASIC芯片,价格也往往非常便宜。

译码器的工作原理是什么

译码器的结构:通常有N位输入和2^N个输出。

  • 输入端(Input):接收二进制代码,例如,一个 3 位二进制译码器有 3 个输入端。
  • 输出端(Output):输出对应于输入的二进制代码,例如,一个 3 位二进制译码器有 8 个输出端。
  • 使能端(Enable):使能端用于控制译码器的输出,当使能端为高电平时,译码器正常工作,当使能端为低电平时,译码器输出为0。
    • 使能端可以用于译码器的扩展(用多个小译码器构成一个大译码器)或控制译码器的工作状态。

译码器的Verilog设计

设计定义

  1. 设计一个3-8译码器
  2. 用3-8译码器构成一个4-16译码器

设计目的

  1. 掌握组合逻辑电路的描述方式
  2. 掌握always语句描述组合逻辑的敏感列表
  3. 掌握case语句的用法
  4. 掌握case语句缺省条件的重要性,避免组合逻辑种产生锁存器
  5. 掌握Verilog的三种描述方式——行为级描述、结构级描述、数据流级描述

设计实现

设计思路

  • 3-8译码器设计思路:本质上就是一个多路选择器,根据输入的二进制代码,选择对应的输出。
  • 4-16译码器设计思路:用3-8译码器构成一个4-16译码器。

3-8译码器模块和端口定义

端口名称端口方向端口位宽端口说明
selinput33位二进制输入
eninput1使能端
outoutput88位二进制输出

3-8译码器接口时序/真值表

sel = 000, en = 1, out = 00000001
sel = 001, en = 1, out = 00000010
sel = 010, en = 1, out = 00000100
sel = 011, en = 1, out = 00001000
sel = 100, en = 1, out = 00010000
sel = 101, en = 1, out = 00100000
sel = 110, en = 1, out = 01000000
sel = 111, en = 1, out = 10000000

3-8译码器设计

`timescale 1ns/1ns

module decoder3_8(
    input   [2:0]   sel,
    input           en,

    output  [7:0]   out
);

reg [7:0] out_temp;

always @(*)begin
    case(sel[2:0])
    3'b000 : out_temp = 8'b0000_0001;
    3'b001 : out_temp = 8'b0000_0010;
    3'b010 : out_temp = 8'b0000_0100;
    3'b011 : out_temp = 8'b0000_1000;
    3'b100 : out_temp = 8'b0001_0000;
    3'b101 : out_temp = 8'b0010_0000;
    3'b110 : out_temp = 8'b0100_0000;
    3'b111 : out_temp = 8'b1000_0000;
    default : out_temp = 8'b0000_0000;
    endcase
end

assign out = en ? out_temp : 8'b0000_0000;

endmodule

3-8译码器功能仿真

image.png

4-16译码器模块和端口定义

端口名称端口方向端口位宽端口说明
selinput44位二进制输入
eninput1使能端
outoutput1616位二进制输出

4-16译码器verilog设计

`timescale 1ns/1ns

module decoder4_16(
    input   [3:0]   sel,
    input           en,

    output  [15:0]  out
);

wire en_u0;
wire en_u1;

assign en_u0 = ~sel[3] & en;
assign en_u1 = sel[3] & en;

decoder3_8 decoder3_8_u0(
    .sel(sel[2:0]),
    .en(en_u0),
    .out(out[7:0])
);

decoder3_8 decoder3_8_u1(
    .sel(sel[2:0]),
    .en(en_u1),
    .out(out[15:8])
);


endmodule

4-16译码器RTL分析

image.png

4-16译码器功能仿真

image.png

Implement

image.png

问题记录和解决

  • 问题描述: 对4-16译码器的仿真中,当sel信号从1111跳变到0000时,out[7]产生了毛刺;当sel信号从0111跳变到1000时,out[15]产生了毛刺。

  • 问题原因

  1. 组合逻辑传播延迟不一致 4到16译码器是纯组合逻辑电路,当sel信号发生变化时,内部各个门电路的传播延迟不完全相同,导致输出信号在短时间内出现错误的中间状态。
  2. 多位信号同时变化导致的竞争冒险 例如当sel从4’b0111(7)变化到4’b1000(8)时: sel[3]从0→1 sel[2:0]从111→000 由于各位信号的传播延迟略有差异,可能会短暂出现4’b0000或4’b1111等中间状态,从而激活错误的输出。
  • 验证: 修改testbench,在sel信号从1111跳变到0000时,改为从1111跳变到1110,避免同时出现三位及以上的变化。再次仿真,发现out[7]和out[15]不再产生毛刺。

  • 解决办法: 波形中的毛刺是组合逻辑电路的正常现象,通常不会影响电路的功能正确性。如果在实际应用中需要避免毛刺,可以考虑添加同步逻辑或使用特殊的编码方式(如格雷码,每次只有一位发生变化,可以减少毛刺)。对于当前的仿真测试,这些毛刺不会影响译码器功能的验证。

End of file.