Decoder và encoder: mã số, one-hot và quyền ưu tiên

Khoảng 45 phútMức 1/3Bản nháp: một số khẳng định chưa đối chiếu spec

Sau bài này bạn sẽ

  • Dùng enable và mức kích hoạt để đọc đúng decoder
  • Phân biệt encoder thường với priority encoder có valid
  • Xử lý rõ không request, nhiều request và thứ tự ưu tiên

Mã chọn khác tập các yêu cầu

Một bộ giải mã nhận số thứ tự rồi kích hoạt một đường tương ứng. Một bộ mã hóa nhận các đường đang kích hoạt rồi đưa ra số thứ tự.

Hai hướng này không mặc nhiên là hai hàm nghịch đảo cho mọi đầu vào. Khi nhiều request cùng bật, encoder cần giả thiết one-hot hoặc một quy tắc ưu tiên rõ ràng.

Decoder có enable và mức kích hoạt

Decoder active-high 2→4 dùng mã A/B; khi enable E bằng 0 thì mọi đầu ra đều 0.

E A B D3..D0
0 bất kỳ mã 0/1 0000
1 00 0001
1 01 0010
1 10 0100
1 11 1000

Mỗi đầu ra là một minterm của mã và được chặn bởi E. Ví dụ D2 bằng E·A·B'. Khi E bật và mã xác định, đúng một đường ra 1.

Decoder active-low có đầu ra được chọn xuống 0, các đường còn lại lên 1. Tên linh kiện hoặc từ “decoder” chưa xác định được polarity của enable và output; phải đọc hợp đồng cụ thể.

Enable giúp ghép decoder lớn hơn

Để dựng decoder 3→8, dùng hai decoder 2→4. Hai bit thấp cấp cho cả hai khối; bit cao chọn enable của một trong hai khối. Một nhánh nhận bit cao, nhánh còn lại nhận bit đảo của nó.

Giữ đúng thứ tự bit và số thứ tự đầu ra. Nếu hai nhánh cùng được enable do nối sai polarity, tính one-hot toàn cục sẽ hỏng.

Decoder cũng tạo các minterm để ghép thành hàm. Ví dụ hàm ba đầu vào đạt khi ít nhất hai bit bằng 1 có thể OR các đường minterm 3, 5, 6, 7. Cách dựng đúng chức năng chưa chắc là cách mapping hiệu quả nhất.

Encoder thường cần đầu vào one-hot

Với bốn request, encoder OR đơn giản có C1=R3+R2 và C0=R3+R1. Nó đúng số thứ tự khi đúng một request bật.

R3..R0 Code Ý nghĩa
0001 00 Request 0
0010 01 Request 1
0100 10 Request 2
1000 11 Request 3
0000 00 Không phân biệt được với request 0 nếu thiếu valid
0110 11 Trộn mã 1 và 2 thành 3, dù request 3 không bật

“One-hot” nghĩa đúng một bit 1; “one-hot-or-zero” cho phép thêm mẫu tất cả 0. Cờ valid giúp tách trường hợp không có yêu cầu, nhưng chỉ valid chưa giải quyết việc nhiều request.

Priority encoder phải nói ai thắng

Chọn quy tắc chỉ số lớn hơn có ưu tiên cao hơn. Khi R3 bật thì code là 3, không phụ thuộc các request thấp hơn. Nếu R3 tắt mà R2 bật thì code là 2; tiếp tục như vậy.

R3..R0 Valid Code trong ví dụ
0000 0 00 theo quy ước của bài
0001 1 00
0011 1 01
0110 1 10
1011 1 11

Code 00 vẫn có hai khả năng, vì vậy người nhận phải kiểm valid trước khi dùng. Trong nhiều giao diện, code không có ý nghĩa khi valid bằng 0; ví dụ này chọn 00 xác định để dễ kiểm, không áp đặt lên mọi thiết kế.

Ưu tiên thấp nhất thắng cũng là một hợp đồng hợp lệ nếu đã thỏa thuận. Không suy quy tắc từ tên biến hoặc thứ tự chân vẽ trên sơ đồ.

Ưu tiên tổ hợp chưa phải bộ phân xử công bằng

Priority encoder chỉ chọn một request của trạng thái đầu vào hiện tại. Nếu request ưu tiên cao luôn bật, request thấp có thể không được chọn. Nó chưa tạo fairness, round-robin hay giao thức giữ grant tới khi giao dịch xong.

Với encoder thường, cần kiểm giả thiết one-hot tại biên. Với priority encoder, cần kiểm từng lớp nhiều request, valid và quy tắc thắng. Với decoder, cần kiểm enable tắt, mọi mã và polarity.

Trong RTL tổ hợp, gán mặc định trước các nhánh rồi ghi đè theo ưu tiên. Bỏ một đầu ra chưa gán ở một nhánh có thể tạo phần tử nhớ ngoài ý muốn.

Các lỗi khiến mã không còn đại diện một request

  • Dùng encoder OR khi nhiều request có thể bật.
  • Quên valid nên nhầm không request với request 0.
  • Đảo thứ tự ưu tiên do đọc từ trái qua phải trên một vector.
  • Nối sai polarity enable của decoder ghép tầng.
  • Coi priority encoder là bằng chứng không có starvation.

Khi debug, ghi cả vector request, valid và code. Chỉ in code sẽ che mất nhiều lỗi hợp đồng.

Thử cả không request và nhiều request

  1. Encoder OR bốn request nhận 0101 cho mã gì? Mã ấy có nhất thiết chỉ một request đang bật không?
  2. Priority encoder chỉ số cao thắng nhận 0101 cho code/valid nào?
  3. Vì sao thêm valid cho encoder OR vẫn chưa đủ xử lý mọi mẫu multi-hot?
  4. Decoder active-low được chọn đường 2 có vector D3..D0 nào?
  5. Muốn tránh request thấp bị đói, còn cần cơ chế nào ngoài priority encoder tổ hợp?

Kiểm tra

Tự kiểm tra: Decoder và encoder: mã số, one-hot và quyền ưu tiên

  1. Priority encoder chỉ số cao thắng nhận 0110 cho kết quả nào?
  2. Vì sao cần valid khi code 00 có thể xuất hiện?
  3. Encoder OR bốn request nhận 0110 cho raw code nào?
  4. Decoder active-high có enable tắt sẽ cho đầu ra nào?
  5. Priority encoder tổ hợp đã bảo đảm request thấp không bị đói chưa?

Bằng chứng kiểm chứng

Expected tính trước chạy: CODEC CHECK priority=16 onehot=4 multi=11 none=1 decoder=8 time_ns=24.

Decoder, plain encoder và priority encoder có valid

Kỳ vọng tính trước chạy: CODEC CHECK priority=16 onehot=4 multi=11 none=1 decoder=8 time_ns=24

codec_core.sv RTL
`timescale 1ns/1psmodule codec_core(input logic [3:0] requests,input logic enable,input logic [1:0] code, output wire [1:0] plain_code,output logic [1:0] priority_code, output wire valid,onehot,output wire [3:0] decoded); assign plain_code={requests[3]|requests[2],requests[3]|requests[1]}; assign valid=|requests; assign onehot=(requests!=0)&&((requests&(requests-4'b0001))==0); assign decoded=enable?(4'b0001<<code):4'b0000; always_comb begin  priority_code=2'b00;  if(requests[3])priority_code=2'd3;  else if(requests[2])priority_code=2'd2;  else if(requests[1])priority_code=2'd1;  else if(requests[0])priority_code=2'd0; endendmodule
tb.sv testbench
`timescale 1ns/1psmodule tb_a2_codec; logic [3:0] requests;logic enable;logic [1:0] code;wire [1:0] plain_code,priority_code; wire valid,onehot;wire [3:0] decoded;codec_core dut(.*); int priority_count=0,onehot_count=0,multi=0,none_count=0,decoder_count=0,highest,bits_set; initial begin  enable=0;code=0;requests=0;  for(int raw=0;raw<16;raw++)begin   highest=0;bits_set=0;   for(int k=0;k<4;k++)if((raw/(2**k))%2==1)begin highest=k;bits_set++;end   requests=4'(raw);#1;priority_count++;   if(valid!==(raw!=0)||int'(priority_code)!=highest||onehot!==(bits_set==1))$fatal(1,"Priority/valid mismatch raw=%0d",raw);   if(bits_set==1)begin onehot_count++;if(int'(plain_code)!=highest)$fatal(1,"Plain encoder mismatch");end   else if(bits_set==0)begin none_count++;if(plain_code!==2'b00)$fatal(1,"Plain zero contract");end   else multi++;  end  for(int en=0;en<2;en++)for(int i=0;i<4;i++)begin   enable=1'(en);code=2'(i);#1;decoder_count++;   if(int'(decoded)!=(en==0?0:2**i))$fatal(1,"Decoder enable/code mismatch");  end  if(priority_count!=16||onehot_count!=4||multi!=11||none_count!=1||decoder_count!=8||$time!=24)$fatal(1,"Codec contract");  $display("CODEC CHECK priority=%0d onehot=%0d multi=%0d none=%0d decoder=%0d time_ns=%0d",priority_count,onehot_count,multi,none_count,decoder_count,$time);  $finish; endendmodule

Đã kiểm chứng thế nào

  • Phân tích và elaborate theo LRM (pyslang 12.1.0)
  • Lint -Wall (Verilator 5.050)
  • Mô phỏng, exit 0 và output khớp kỳ vọng tính tay (Verilator 5.050, 2-state)
  • Tổng hợp, số cell khớp kỳ vọng (Yosys 0.70)

Output phải khớp: CODEC CHECK priority=16 onehot=4 multi=11 none=1 decoder=8 time_ns=24

Kỳ vọng sau tổng hợp: codec_core: $_*DFF* = 0codec_core: $_*LATCH* = 0

Finite known 0/1 input domains only. Generic synthesis, where claimed, is not technology mapping, STA or PPA. No all-width or X/Z language conformance claim.

Các kiểm tra chạy lúc xây dựng nội dung (2026-11-07), không chạy trong trình duyệt. Kỳ vọng được tính tay trước khi chạy.

Kiểm toàn bộ 16 request pattern: bốn one-hot, 11 multi-hot và một none. Tham chiếu duyệt các vị trí bằng số nguyên để tìm chỉ số cao nhất, khác chuỗi if ưu tiên của DUT. Encoder OR chỉ đối chiếu code trong bốn mẫu thỏa one-hot; mọi mẫu priority đều kiểm valid và code xác định.

Decoder active-high kiểm cả hai trạng thái enable qua bốn mã. Parsed/linted/simulated/synthesized đạt; synthesis generic không có flip-flop/latch. Không claim fairness hoặc triển khai arbiter có trạng thái, không kiểm X/Z.

[1] [2] [3] [4]

Nguồn và mức độ đối chiếu

  1. Digital Encoder Circuit — bản chụp resources.zip, Quick Answer: Binary vs. Priority Encoder; The Binary Encoder; Two Problems With the Plain Encoder; The Priority Encoder. Trích dẫn; nguồn đã đọc các mục liên quan.
  2. Thí nghiệm nguyên bản A2.codec, Sixteen request patterns, independent highest-bit selection and eight enabled-decoder vectors. Trích dẫn; nguồn đã đọc toàn văn.
  3. IEEE 1800-2023 SystemVerilog LRM, Priority procedural selection, combinational completeness and reduction operators — chưa đối chiếu LRM. Chưa đối chiếu với văn bản nguồn (chưa mở).
  4. Digital Decoder Circuit — bản chụp resources.zip, The 2-to-4 Decoder With Enable; Building Bigger Decoders From Smaller Ones; A Decoder Generates Minterms. Trích dẫn; nguồn đã đọc các mục liên quan.