Start work on testing ADC driver

This commit is contained in:
Kelvin Ly 2020-01-07 23:57:08 -05:00
parent b95e31eda1
commit faaf9415a0
7 changed files with 173 additions and 31 deletions

1
rtl/.gitignore vendored
View File

@ -2,3 +2,4 @@
*.bin *.bin
*.json *.json
*.rpt *.rpt
*.log

View File

@ -10,7 +10,7 @@ ${FN}_filled.bin: ${FN}.bin
dd if=$< of=$@ conv=notrunc dd if=$< of=$@ conv=notrunc
${FN}.json: ${FN}.v $(shell find library -type f -name '*.v') ${FN}.json: ${FN}.v $(shell find library -type f -name '*.v')
./run_yosys.sh ${FN} ./run_yosys.sh ${FN} | tee bldc.log
${FN}.asc: ${FN}.json ${FN}.pcf ${FN}.asc: ${FN}.json ${FN}.pcf
nextpnr-ice40 ${NEXTPNR_OPTS} --pcf "${FN}.pcf" --json "${FN}.json" --asc "${FN}.asc" nextpnr-ice40 ${NEXTPNR_OPTS} --pcf "${FN}.pcf" --json "${FN}.json" --asc "${FN}.asc"

View File

@ -1,4 +1,9 @@
set_io if_int 32 set_io if_int 32
set_io dbg_tx 48 set_io dbg_tx 48
set_io adc_sck 28
set_io adc_ss 27
set_io adc_si 26
set_io adc_so 25
set_io clk 20 set_io clk 20

View File

@ -1,32 +1,145 @@
module bldc ( module bldc (
input clk, input clk,
output dbg_tx, output dbg_tx,
output if_int output if_int,
output adc_ss,
output adc_sck,
input adc_so,
output adc_si
); );
reg [7:0] dbg_buf = 8'hac; reg [7:0] dbg_buf = 0;
reg dbg_buf_vld = 1; reg dbg_buf_vld = 0;
wire dbg_tx_ack; wire dbg_tx_rdy;
reg [15:0] adc_vals[3:0];
reg [1:0] vals_idx = 0;
initial begin
adc_vals[0] = 0;
adc_vals[1] = 0;
adc_vals[2] = 0;
adc_vals[3] = 0;
end
wire [1:0] adc_channel;
wire [11:0] adc_val;
wire adc_vld;
reg adc_ack = 0;
adc_driver adc0(
.clk(clk),
.rstn(1'b1),
.so(adc_so),
.si(adc_si),
.ss(adc_ss),
.sck(adc_sck),
.channel(adc_channel),
.val(adc_val),
.vld(adc_vld),
.ack(adc_ack)
);
uart_tx_115200 dbg( uart_tx_115200 dbg(
.clk_25mhz(clk), .clk_25mhz(clk),
.rstn(1'b1), .rstn(1'b1),
.tx(dbg_tx), .tx(dbg_tx),
.tx_buf(dbg_buf), .tx_buf(dbg_buf),
.tx_vld(dbg_buf_vld), .vld(dbg_buf_vld),
.tx_ack(dbg_tx_ack) .rdy(dbg_tx_rdy)
); );
reg [3:0] tmp = 0; reg [7:0] tmp3 = 0;
reg [7:0] tmp2 = 0;
reg [7:0] tmp = 0;
assign if_int = tmp[3]; assign if_int = tmp[3];
reg uart_end = 0;
reg uart_bsy = 0;
// stores {cur_channel_idx, cur_nibble}
reg [3:0] cur_idx = 0;
reg [15:0] cur_channel;
reg [3:0] cur_nibble;
reg [7:0] nibble_hex;
always @(posedge clk) begin
cur_channel <= adc_vals[cur_idx[3:2]];
case (cur_idx[1:0])
2'b00: cur_nibble <= cur_channel[3:0];
2'b01: cur_nibble <= cur_channel[7:4];
2'b10: cur_nibble <= cur_channel[11:8];
2'b11: cur_nibble <= cur_channel[15:12];
endcase
case (cur_nibble)
4'h0: nibble_hex <= 48;
4'h1: nibble_hex <= 49;
4'h2: nibble_hex <= 50;
4'h3: nibble_hex <= 51;
4'h4: nibble_hex <= 52;
4'h5: nibble_hex <= 53;
4'h6: nibble_hex <= 54;
4'h7: nibble_hex <= 55;
4'h8: nibble_hex <= 56;
4'h9: nibble_hex <= 57;
4'ha: nibble_hex <= 97;
4'hb: nibble_hex <= 98;
4'hc: nibble_hex <= 99;
4'hd: nibble_hex <= 100;
4'he: nibble_hex <= 101;
4'hf: nibble_hex <= 102;
endcase
end
always @(posedge clk) begin always @(posedge clk) begin
tmp <= tmp + 1; tmp <= tmp + 1;
if (dbg_tx_ack) begin if (&tmp) begin
dbg_buf <= dbg_buf + 1; tmp2 <= tmp2 + 1;
dbg_buf_vld = 1; if (&tmp2)
tmp3 <= tmp3 + 1;
end
// 25 MHz / 2^(8+8+7) = 3 Hz
if (&tmp & &tmp2 & &tmp3[6:0]) begin
uart_bsy <= 1;
cur_idx <= 0;
end
if (dbg_tx_rdy) begin
if (uart_bsy) begin
if (~uart_end) begin
// write the ADC data to the UART
dbg_buf <= nibble_hex;
dbg_buf_vld <= 1;
cur_idx <= cur_idx + 1;
if (&cur_idx)
uart_end <= 1;
end else begin
// write newline
dbg_buf <= 8'h0a;
dbg_buf_vld <= 1;
uart_end <= 0;
uart_bsy <= 0;
end
end
end else begin end else begin
dbg_buf_vld = 0; dbg_buf_vld <= 0;
end
if (adc_vld) begin
adc_ack <= 1;
vals_idx <= vals_idx + 1;
if (~uart_bsy) begin
adc_vals[vals_idx] <= {adc_channel, adc_val};
end
end else begin
adc_ack <= 0;
end end
end end

View File

@ -1,3 +1,7 @@
// driver for the MAX1141 ADC used in the board
// it has 4 analog inputs, and is configured to automatically
// scan them sequentially while being driven by SCK
// it uses
module adc_driver( module adc_driver(
input clk, input clk,
input rstn, input rstn,
@ -15,15 +19,15 @@ module adc_driver(
reg [1:0] channel_ff = 0; reg [1:0] channel_ff = 0;
reg [11:0] adc_val_ff = 0; reg [11:0] adc_val_ff = 0;
reg vld_ff = 0; reg new = 0;
assign channel = channel_ff; assign channel = channel_ff;
assign val = adc_val_ff; assign val = adc_val_ff;
assign vld = vld_ff; assign vld = new & ~ack;
reg [2:0] sck_strobe = 0; reg [1:0] sck_strobe = 0;
wire strobe = &sck_strobe; wire strobe = &sck_strobe;
wire strobe2 = &(sck_strobe^3'b100); wire strobe2 = &(sck_strobe^2'b10);
always @(posedge clk) begin always @(posedge clk) begin
if (rstn) if (rstn)
@ -76,6 +80,7 @@ always @* begin
sck_next = 1; sck_next = 1;
ss_next = 1; ss_next = 1;
si_next = 0;
if (rstn) begin if (rstn) begin
// latch sck and ss state until the strobe happens // latch sck and ss state until the strobe happens
@ -158,11 +163,11 @@ always @(posedge clk) begin
// write the data out when write_out is asserted // write the data out when write_out is asserted
if (write_out) begin if (write_out) begin
{channel_ff, adc_val_ff} <= so_ff_next[13:0]; {channel_ff, adc_val_ff} <= so_ff_next[13:0];
vld_ff <= 1; new <= 1;
end end
// deassert vld when the data is acknowledged // deassert vld when the data is acknowledged
if (ack) if (ack)
vld_ff <= 0; new <= 0;
end end
endmodule endmodule

18
rtl/library/bram512x8.v Normal file
View File

@ -0,0 +1,18 @@
module bram512x8(
input clk,
input [8:0] raddr,
output [7:0] reg rdat,
input [8:0] waddr,
input [7:0] wdat,
input wen
);
reg [7:0] mem[511:0];
always @(posedge clk) begin
if (wen)
mem[waddr] <= wdat;
rdat <= mem[rdat];
end
endmodule

View File

@ -3,12 +3,12 @@ module uart_tx_115200(
input rstn, input rstn,
output reg tx, output reg tx,
input [7:0] tx_buf, input [7:0] tx_buf,
input tx_vld, input vld,
output tx_ack, output rdy,
); );
reg [2:0] bit = 0; reg [2:0] b = 0;
reg [2:0] bit_next; reg [2:0] b_next;
reg [7:0] counter = 0; reg [7:0] counter = 0;
reg [7:0] counter_next; reg [7:0] counter_next;
@ -18,13 +18,13 @@ localparam IDLE = 0, START = 1, TX = 2, STOP = 3;
reg [1:0] state = IDLE; reg [1:0] state = IDLE;
reg [1:0] state_next; reg [1:0] state_next;
assign tx_ack = (state == IDLE); assign rdy = (state == IDLE);
always @* begin always @* begin
case (state) case (state)
IDLE: tx = 1; IDLE: tx = 1;
START: tx = 0; START: tx = 0;
TX: tx = tx_buf[bit]; TX: tx = tx_buf[b];
STOP: tx = 1; STOP: tx = 1;
endcase endcase
end end
@ -32,19 +32,19 @@ end
always @* begin always @* begin
state_next = state; state_next = state;
counter_next = counter; counter_next = counter;
bit_next = bit; b_next = b;
if (rstn) begin if (rstn) begin
if (counter == 216) begin if (counter == 216) begin
counter_next = 0; counter_next = 0;
bit_next = bit + 1; b_next = b + 1;
end else begin end else begin
counter_next = counter + 1; counter_next = counter + 1;
end end
case (state) case (state)
IDLE: begin IDLE: begin
if (tx_vld) begin if (vld) begin
state_next = START; state_next = START;
counter_next = 0; counter_next = 0;
end end
@ -52,11 +52,11 @@ always @* begin
START: begin START: begin
if (counter == 216) begin if (counter == 216) begin
state_next = TX; state_next = TX;
bit_next = 0; b_next = 0;
end end
end end
TX: begin TX: begin
if ((counter == 216) && (bit == 7)) begin if ((counter == 216) && (b == 7)) begin
state_next = STOP; state_next = STOP;
end end
end end
@ -69,14 +69,14 @@ always @* begin
end else begin end else begin
state_next = IDLE; state_next = IDLE;
counter_next = 0; counter_next = 0;
bit_next = 0; b_next = 0;
end end
end end
always @(posedge clk_25mhz) begin always @(posedge clk_25mhz) begin
state <= state_next; state <= state_next;
counter <= counter_next; counter <= counter_next;
bit <= bit_next; b <= b_next;
end end
endmodule endmodule