Rule90
第一次見這東西有點莫名其妙,但是其實看懂了之后就是左移和右移相異或,注意這里使用的是邏輯右移,會自動補零,不能使用算數左移<<<,
module top_module( input clk, input load, input [511:0] data, output reg[511:0] q ); always@(posedge clk) begin if(load) q <= data; else begin q <= (q<<1)^(q>>1); end end endmodule
Rule110
Rule90可以直接根據Left和Right異或得到,而Rule110一定要三個值進行邏輯運算得到,可以畫一個卡諾圖并寫出邏輯運算式并計算,當然不化簡肯定也是可以的,

module top_module( input clk, input load, input [511:0] data, output reg[511:0] q ); always@(posedge clk) begin if(load) q <= data; else begin q <= (q&~(q<<1))|(~(q>>1)&(q<<1))|(~q&(q<<1)); end end endmodule
注意左移之后參與計算的是R,右移之后參與計算的是L,一開始搞反了想了很久,
Conwaylife
需要計算鄰域1的個數,注意這里的邊界比較復雜,每個點都有8個鄰點,成一個環形結構,
方法比較笨,就是把所有情況全部考慮一遍,注意以下幾點:
1、verilog運算自動按位數最多的運算元來計算,所以計算下標時使用i-8'd15而不是i-15,
2、因為我想讓回圈數溢位,所以取的8位i,
網上查了一下,看了別人的做法,大致有以下幾類:
1、和hdlbits提示的一樣使用sv語法,使用二維陣列,可以大大簡化邏輯,
2、將矩陣拓展為18*18,從而減少情況的考慮,
module top_module( input clk, input load, input [255:0] data, output reg[255:0] q ); reg [3:0]neig_cnt; reg [255:0] q_next; always@(posedge clk) begin if(load) q <= data; else begin q <= q_next; end end reg [15:0]loop; reg unsigned[7:0]i; always@(*) begin for(loop=0;loop<256;loop=loop+1) begin i=loop; if(i==255)//左上角 neig_cnt = q[i-8'd15]+q[i+8'd1]+q[i+8'd16]+q[i+8'd15]+q[i-8'd1]+q[i-8'd17]+q[i-8'd16]+q[i-8'd31]; else if(i==240)//右上角 neig_cnt = q[i+8'd1]+q[i+8'd17]+q[i+8'd16]+q[i+8'd31]+q[i+8'd15]+q[i-8'd1]+q[i-8'd16]+q[i-8'd15]; else if(i==15)//左下角 neig_cnt = q[i-8'd15]+q[i+8'd1]+q[i+8'd16]+q[i+8'd15]+q[i-8'd1]+q[i-8'd17]+q[i-8'd16]+q[i-8'd31]; else if(i==0)//右下角 neig_cnt = q[i+8'd1]+q[i+8'd17]+q[i+8'd16]+q[i+8'd31]+q[i+8'd15]+q[i-8'd1]+q[i-8'd16]+q[i-8'd15]; else if(i>240)//上方 neig_cnt = q[i+8'd1]+q[i+8'd17]+q[i+8'd16]+q[i+8'd15]+q[i-8'd1]+q[i-8'd17]+q[i-8'd16]+q[i-8'd15]; else if(i%16==15)//左方 neig_cnt = q[i-8'd15]+q[i+8'd1]+q[i+8'd16]+q[i+8'd15]+q[i-8'd1]+q[i-8'd17]+q[i-8'd16]+q[i-8'd31]; else if(i%16==0)//右方 neig_cnt = q[i+8'd1]+q[i+8'd17]+q[i+8'd16]+q[i+8'd31]+q[i+8'd15]+q[i-8'd1]+q[i-8'd16]+q[i-8'd15]; else if(i<15)//下方 neig_cnt = q[i+8'd1]+q[i+8'd17]+q[i+8'd16]+q[i+8'd15]+q[i-8'd1]+q[i-8'd17]+q[i-8'd16]+q[i-8'd15]; else//中間的點 neig_cnt = q[i+8'd1]+q[i+8'd17]+q[i+8'd16]+q[i+8'd15]+q[i-8'd1]+q[i-8'd17]+q[i-8'd16]+q[i-8'd15]; if(neig_cnt == 0||neig_cnt == 1) q_next[i] = 0; else if(neig_cnt == 2) q_next[i] = q[i]; else if(neig_cnt == 3) q_next[i] = 1; else q_next[i] = 0; end end endmodule
看到題目最后John Conway因為COVID-19并發癥去世了,有些感慨,RIP,
轉載請註明出處,本文鏈接:https://www.uj5u.com/houduan/524902.html
標籤:Verilog
