-
Notifications
You must be signed in to change notification settings - Fork 0
/
sar_adc.v
74 lines (59 loc) · 1.22 KB
/
sar_adc.v
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
module sar_adc #(
// adc bits
parameter p_bit_cnt = 8
)(
input i_clk,
input i_reset,
// control port
input i_start,
output o_busy,
// result port
output o_valid,
output [p_bit_cnt - 1:0] o_res,
// ports for DAC and comparator
output [p_bit_cnt - 1:0] o_dac,
input i_cmp
);
localparam p_top_bit = p_bit_cnt - 1;
// states
localparam
s_idle = 2'b0,
s_samp = 2'b1,
s_conv = 2'b2,
s_done = 2'b3;
reg [1:0] r_state;
reg [p_bit_cnt - 1:0] r_cur, r_res;
wire w_last = r_res[0];
assign o_busy =
r_state == s_samp |
r_state == s_conv;
assign o_valid = r_state == s_done;
assign o_res = r_res;
assign o_dac = r_res | r_cur;
initial
r_state <= s_idle;
always @(posedge i_clk) begin
if (i_reset)
r_state <= s_idle;
else
case (r_state)
s_idle, s_done:
if (i_start)
r_state <= s_samp;
s_samp:
begin
r_state <= s_conv;
r_cur <= 1 << p_bit_cnt;
r_res <= 0;
end
s_conv:
begin
if (i_cmp)
r_res <= r_res | r_cur;
if (w_last)
r_state <= s_done;
r_cur <= r_cur >> 1;
end
endcase
end
endmodule