
포트를 절약하기 위해 선 줄이기, 각각 하면 16개 필요하지만 8개의 포트로 동작포트로 동작
버튼 pdt 고려
상승엣지에서 col, row 둘다 읽으면 input(row)을 제대로 읽을 수 없다, 8ms주기의 클락에서 하이레벨 로우레벨 각각 4ms이다 따라서 col이든 row든 하나는 상승엣지 하나는 하강엣지로 하면 제대로 읽을 수 있다.

module key_pad_cntr(
input clk, reset_p,
input [3:0] row,
output reg [3:0] col,
output reg [3:0] key_value,
output reg key_valid);
//채터링 방지를 위해 한 버튼당 8ms
reg [19:0] clk_div; //분주를 위해 20번 비트 사용
always @(posedge clk) clk_div = clk_div + 1;
wire clk_8msec_p, clk_8msec_n;
edge_detector_p ed_btn(.clk(clk), .reset_p(reset_p),
.cp(clk_div[19]), .n_edge(clk_8msec_n), .p_edge(clk_8msec_p));
always @(posedge clk or posedge reset_p)begin
if(reset_p) col=4'b0001; //링카운터가 계속돌아 다시 버튼을 누른 행으로 돌아오면 엣지 2번발생
else if(clk_8msec_p && !key_valid)begin //따라서 버튼이 눌렸을때는 링카운터 멈춤
case(col)
4'b0001: col = 4'b0010;
4'b0010: col = 4'b0100;
4'b0100: col = 4'b1000;
4'b1000: col = 4'b0001;
default: col = 4'b0001;
endcase
end
end
always @(posedge clk or posedge reset_p)begin
if(reset_p)begin
key_value = 0;
key_valid = 0; //키가 눌렸을때를 알려주는 값
end
else begin
if(clk_8msec_n)begin //버튼 pdt고려하여 버튼의 n엣지에서 읽음
if(row)begin
key_valid = 1;
case({col, row})
8'b0001_0001: key_value = 4'h0;
8'b0001_0010: key_value = 4'h1;
8'b0001_0100: key_value = 4'h2;
8'b0001_1000: key_value = 4'h3;
8'b0010_0001: key_value = 4'h4;
8'b0010_0010: key_value = 4'h5;
8'b0010_0100: key_value = 4'h6;
8'b0010_1000: key_value = 4'h7;
8'b0100_0001: key_value = 4'h8;
8'b0100_0010: key_value = 4'h9;
8'b0100_0100: key_value = 4'ha;
8'b0100_1000: key_value = 4'hb;
8'b1000_0001: key_value = 4'hc;
8'b1000_0010: key_value = 4'hd;
8'b1000_0100: key_value = 4'he;
8'b1000_1000: key_value = 4'hf;
endcase
end
else begin
key_valid = 0;
//key_vlaue = 0; // 버튼을 떼면 다시 0으로 초기화
end
end
end
end
endmodule
module keypad_test_top(
input clk, reset_p,
input [3:0] row,
output [3:0] col,
output [3:0] com,
output [7:0] seg_7,
output led_key_valid
);
wire [3:0] key_value;
key_pad_cntr(.clk(clk), .reset_p(reset_p),
.row(row), .col(col),
.key_value(key_value),
.key_valid(led_key_valid));
fnd_cntr fnd (.clk(clk), .reset_p(reset_p),
.value({12'b0, key_value}), .com(com), .seg_7(seg_7));
endmodule
#Pmod Header JB
set_property -dict { PACKAGE_PIN A14 IOSTANDARD LVCMOS33 } [get_ports {col[0]}];#Sch name = JB1
set_property -dict { PACKAGE_PIN A16 IOSTANDARD LVCMOS33 } [get_ports {col[1]}];#Sch name = JB2
set_property -dict { PACKAGE_PIN B15 IOSTANDARD LVCMOS33 } [get_ports {col[2]}];#Sch name = JB3
set_property -dict { PACKAGE_PIN B16 IOSTANDARD LVCMOS33 } [get_ports {col[3]}];#Sch name = JB4
set_property -dict { PACKAGE_PIN A15 IOSTANDARD LVCMOS33 PULLDOWN TRUE} [get_ports {row[0]}];#Sch name = JB7
set_property -dict { PACKAGE_PIN A17 IOSTANDARD LVCMOS33 PULLDOWN TRUE} [get_ports {row[1]}];#Sch name = JB8
set_property -dict { PACKAGE_PIN C15 IOSTANDARD LVCMOS33 PULLDOWN TRUE} [get_ports {row[2]}];#Sch name = JB9
set_property -dict { PACKAGE_PIN C16 IOSTANDARD LVCMOS33 PULLDOWN TRUE} [get_ports {row[3]}];#Sch name = JB10
set_property -dict { PACKAGE_PIN E19 IOSTANDARD LVCMOS33 } [get_ports {led_key_valid}]

FSM은 유한한 수의 상태를 가지며, 입력에 따라 상태 간 전이가 일어나는 추상적인 기계입니다.
module key_pad_cntr_FSM(
input clk, reset_p,
input [3:0] row,
output reg [3:0] col,
output reg [3:0] key_value,
output reg key_valid);
reg [19:0] clk_div; //분주를 위해 20번 비트 사용
always @(posedge clk) clk_div = clk_div + 1;
wire clk_8msec;
edge_detector_p ed_btn(.clk(clk), .reset_p(reset_p),
.cp(clk_div[19]), .p_edge(clk_8msec));
reg [3:0] state, next_state;
//FSM 동작
always @(posedge clk or posedge reset_p)begin
if(reset_p) state = 4'b0001;
else if(clk_8msec) state = next_state;
end
always @* begin //와일드카드:case, if등 조건문에 사용되는 변수들과 우변에있는 변수들
case(state)
4'b0001: begin
if(row == 0) next_state = 4'b0010; //key_valid==1이면 바뀌지않고 (else)현상태 유지
else next_state = 4'b0001;
end
4'b0010: begin
if(row == 0) next_state = 4'b0100;
else next_state = 4'b0010;
end
4'b0100: begin
if(row == 0) next_state = 4'b1000;
else next_state = 4'b0100;
end
4'b1000: begin
if(row == 0) next_state = 4'b0001;
else next_state = 4'b1000;
end
default: next_state = 4'b0001;
endcase
end
always @(posedge clk or posedge reset_p) begin
if(reset_p)begin
key_value = 0;
key_valid = 0;
col = 0;
end
else if(clk_8msec)begin
if(row)begin
key_valid = 1;
case({col, row})
8'b0001_0001: key_value = 4'h0;
8'b0001_0010: key_value = 4'h1;
8'b0001_0100: key_value = 4'h2;
8'b0001_1000: key_value = 4'h3;
8'b0010_0001: key_value = 4'h4;
8'b0010_0010: key_value = 4'h5;
8'b0010_0100: key_value = 4'h6;
8'b0010_1000: key_value = 4'h7;
8'b0100_0001: key_value = 4'h8;
8'b0100_0010: key_value = 4'h9;
8'b0100_0100: key_value = 4'ha;
8'b0100_1000: key_value = 4'hb;
8'b1000_0001: key_value = 4'hc;
8'b1000_0010: key_value = 4'hd;
8'b1000_0100: key_value = 4'he;
8'b1000_1000: key_value = 4'hf;
endcase
end
else key_valid = 0;
end
else begin
case(state)
4'b0001:col = 4'b0001;
4'b0010:col = 4'b0010;
4'b0100:col = 4'b0100;
4'b1000:col = 4'b1000;
endcase
end
end
endmodule
FSM
module key_pad_cntr_FSM(
input clk, reset_p,
input [3:0] row,
output reg [3:0] col,
output reg [3:0] key_value,
output reg key_valid);
parameter SCAN0 = 5'b00001;
parameter SCAN1 = 5'b00010;
parameter SCAN2 = 5'b00100;
parameter SCAN3 = 5'b01000;
parameter KEY_PROCESS = 5'b10000;
reg [19:0] clk_div; //분주를 위해 20번 비트 사용
always @(posedge clk) clk_div = clk_div + 1;
wire clk_8msec;
edge_detector_p ed_btn(.clk(clk), .reset_p(reset_p),
.cp(clk_div[19]), .p_edge(clk_8msec));
reg [4:0] state, next_state;
//FSM 동작
always @(posedge clk or posedge reset_p)begin
if(reset_p) state = SCAN0;
else if(clk_8msec) state = next_state;
end
always @* begin //뭐든 입력이 변하면 동작하라
case(state)
SCAN0: begin
if(row == 0) next_state = SCAN1; //key_valid==1이면 바뀌지않고 (else)현상태 유지
else next_state = KEY_PROCESS;
end
SCAN1: begin
if(row == 0) next_state = SCAN2;
else next_state = KEY_PROCESS;
end
SCAN2: begin
if(row == 0) next_state = SCAN3;
else next_state = KEY_PROCESS;
end
SCAN3: begin
if(row == 0) next_state = SCAN3;
else next_state = KEY_PROCESS;
end
default: state = SCAN0;
endcase
end
always @(posedge clk or posedge reset_p) begin
if(reset_p)begin
key_value = 0;
key_valid = 0;
col = 0;
end
else begin
case(state)
SCAN0:begin col = 4'b0001; key_valid = 0; end
SCAN1:begin col = 4'b0010; key_valid = 0; end
SCAN2:begin col = 4'b0100; key_valid = 0; end
SCAN3:begin col = 4'b1000; key_valid = 0; end
KEY_PROCESS: begin
key_valid = 1;
case({col, row})
8'b0001_0001: key_value = 4'h0;
8'b0001_0010: key_value = 4'h1;
8'b0001_0100: key_value = 4'h2;
8'b0001_1000: key_value = 4'h3;
8'b0010_0001: key_value = 4'h4;
8'b0010_0010: key_value = 4'h5;
8'b0010_0100: key_value = 4'h6;
8'b0010_1000: key_value = 4'h7;
8'b0100_0001: key_value = 4'h8;
8'b0100_0010: key_value = 4'h9;
8'b0100_0100: key_value = 4'ha;
8'b0100_1000: key_value = 4'hb;
8'b1000_0001: key_value = 4'hc;
8'b1000_0010: key_value = 4'hd;
8'b1000_0100: key_value = 4'he;
8'b1000_1000: key_value = 4'hf;
endcase
end
// else if(clk_8msec)begin
// if(row)begin
// key_valid = 1;
// case({col, row})
// 8'b0001_0001: key_value = 4'h0;
// 8'b0001_0010: key_value = 4'h1;
// 8'b0001_0100: key_value = 4'h2;
// 8'b0001_1000: key_value = 4'h3;
// 8'b0010_0001: key_value = 4'h4;
// 8'b0010_0010: key_value = 4'h5;
// 8'b0010_0100: key_value = 4'h6;
// 8'b0010_1000: key_value = 4'h7;
// 8'b0100_0001: key_value = 4'h8;
// 8'b0100_0010: key_value = 4'h9;
// 8'b0100_0100: key_value = 4'ha;
// 8'b0100_1000: key_value = 4'hb;
// 8'b1000_0001: key_value = 4'hc;
// 8'b1000_0010: key_value = 4'hd;
// 8'b1000_0100: key_value = 4'he;
// 8'b1000_1000: key_value = 4'hf;
// endcase
// end
// else key_valid = 0;
// end
// else begin
// case(state)
// 4'b0001:col = 4'b0001;
// 4'b0010:col = 4'b0010;
// 4'b0100:col = 4'b0100;
// 4'b1000:col = 4'b1000;
// endcase
// end
endcase
end
end
endmodule
동작 코드
module keypad_test_top(
input clk, reset_p,
input [3:0] row,
output [3:0] col,
output [3:0] com,
output [7:0] seg_7,
output led_key_valid
);
wire [3:0] key_value;
key_pad_cntr_FSM(.clk(clk), .reset_p(reset_p),
.row(row), .col(col),
.key_value(key_value),
.key_valid(led_key_valid));
fnd_cntr fnd (.clk(clk), .reset_p(reset_p),
.value({12'b0, key_value}), .com(com), .seg_7(seg_7));
endmodule
module key_pad_cntr_FSM (
input clk, reset_p,
input [3:0] row,
output reg [3:0] col,
output reg [3:0] key_value,
output reg key_valid );
parameter SCAN0 = 5'b00001;
parameter SCAN1 = 5'b00010;
parameter SCAN2 = 5'b00100;
parameter SCAN3 = 5'b01000;
parameter KEY_PROCESS = 5'b10000;
// chattering 현사을 방지하기 위해 8ms delay_time을 갖고 button 값을 받겠다.
reg [19:0] clk_div;
always @(posedge clk or posedge reset_p) begin
if(reset_p) clk_div = 0;
else clk_div = clk_div + 1;
end
// Get One Cycle Pulse of Button.
// clk_8msec : Positive edge (버튼이 눌렸을 때를 감지)
wire clk_8msec;
edge_detector_p ed_0(.clk(clk), .reset_p(reset_p), .cp(clk_div[19]), .p_edge(clk_8msec));
// 8ms 마다 state 값을 nex_state 입력받는다.
reg [4:0] state, next_state;
// D- Flip Flop
always @(posedge clk or posedge reset_p) begin
if(reset_p) state = SCAN0;
else if(clk_8msec) state = next_state;
end
// state 값에 따라 변화하기 때문에 조합 회로이다.
// row == 0 이면 다음 행으로 이동하고,
// row == 1 이면 현재 행에서 유지한다.
// row == 0 키 입력이 없음을 의미
// row == 1 이면 키 입력이 있음을 의미
always @(*) begin
case (state)
SCAN0: begin
if(row == 0) next_state = SCAN1;
else next_state = KEY_PROCESS;
end
SCAN1: begin
if(row == 0) next_state = SCAN2;
else next_state = KEY_PROCESS;
end
SCAN2: begin
if(row == 0) next_state = SCAN3;
else next_state = KEY_PROCESS;
end
SCAN3: begin
if(row == 0) next_state = SCAN0;
else next_state = KEY_PROCESS;
end
KEY_PROCESS: begin
if(row == 0) next_state = SCAN0;
else next_state = KEY_PROCESS;
end
default : next_state = SCAN0;
endcase
end
//
// always @(posedge clk or posedge reset_p) begin
// if(reset_p) begin
// key_value = 0;
// key_valid = 0;
// col = 0;
// end
// else if(clk_8msec) begin
// if(row) begin
// key_valid = 1;
// case({col, row})
// 8'b0001_0001 : key_value = 4'h0;
// 8'b0001_0010 : key_value = 4'h1;
// 8'b0001_0100 : key_value = 4'h2;
// 8'b0001_1000 : key_value = 4'h3;
// 8'b0010_0001 : key_value = 4'h4;
// 8'b0010_0010 : key_value = 4'h5;
// 8'b0010_0100 : key_value = 4'h6;
// 8'b0010_1000 : key_value = 4'h7;
// 8'b0100_0001 : key_value = 4'h8;
// 8'b0100_0010 : key_value = 4'h9;
// 8'b0100_0100 : key_value = 4'ha;
// 8'b0100_1000 : key_value = 4'hb;
// 8'b1000_0001 : key_value = 4'hc;
// 8'b1000_0010 : key_value = 4'hd;
// 8'b1000_0100 : key_value = 4'he;
// 8'b1000_1000 : key_value = 4'hf;
// default : key_value = key_value;
// endcase
// end
// else key_valid = 0;
// end
// case(state)
// 4'b0001 : col = 4'b0001;
// 4'b0010 : col = 4'b0010;
// 4'b0100 : col = 4'b0100;
// 4'b1000 : col = 4'b1000;
// endcase
// end
always @(posedge clk or posedge reset_p) begin
if(reset_p) begin
key_value = 0;
key_valid = 0;
col = 0;
end
else begin
case(state)
SCAN0 : begin col = 4'b0001; key_valid = 0; end
SCAN1 : begin col = 4'b0010; key_valid = 0; end
SCAN2 : begin col = 4'b0100; key_valid = 0; end
SCAN3 : begin col = 4'b1000; key_valid = 0; end
KEY_PROCESS : begin
key_valid = 1;
case({col, row})
8'b0001_0001 : key_value = 4'h0;
8'b0001_0010 : key_value = 4'h1;
8'b0001_0100 : key_value = 4'h2;
8'b0001_1000 : key_value = 4'h3;
8'b0010_0001 : key_value = 4'h4;
8'b0010_0010 : key_value = 4'h5;
8'b0010_0100 : key_value = 4'h6;
8'b0010_1000 : key_value = 4'h7;
8'b0100_0001 : key_value = 4'h8;
8'b0100_0010 : key_value = 4'h9;
8'b0100_0100 : key_value = 4'ha;
8'b0100_1000 : key_value = 4'hb;
8'b1000_0001 : key_value = 4'hc;
8'b1000_0010 : key_value = 4'hd;
8'b1000_0100 : key_value = 4'he;
8'b1000_1000 : key_value = 4'hf;
default : key_value = key_value;
endcase
end
endcase
end
end
endmodule
상승엣지 하강엣지 추가
module key_pad_cntr_FSM (
input clk, reset_p,
input [3:0] row,
output reg [3:0] col,
output reg [3:0] key_value,
output reg key_valid );
parameter SCAN0 = 5'b00001;
parameter SCAN1 = 5'b00010;
parameter SCAN2 = 5'b00100;
parameter SCAN3 = 5'b01000;
parameter KEY_PROCESS = 5'b10000;
// chattering 현사을 방지하기 위해 8ms delay_time을 갖고 button 값을 받겠다.
reg [19:0] clk_div;
always @(posedge clk or posedge reset_p) begin
if(reset_p) clk_div = 0;
else clk_div = clk_div + 1;
end
// Get One Cycle Pulse of Button.
// clk_8msec : Positive edge (버튼이 눌렸을 때를 감지)
wire clk_8msec;
edge_detector_p ed_0(.clk(clk), .reset_p(reset_p),
.cp(clk_div[19]), .p_edge(clk_8msec_p), .n_edge(clk_8msec_n));
// 8ms 마다 state 값을 nex_state 입력받는다.
reg [4:0] state, next_state;
// D- Flip Flop
always @(posedge clk or posedge reset_p) begin
if(reset_p) state = SCAN0;
else if(clk_8msec_n) state = next_state; //하강엣지로 변경
end
// state 값에 따라 변화하기 때문에 조합 회로이다.
// row == 0 이면 다음 행으로 이동하고,
// row == 1 이면 현재 행에서 유지한다.
// row == 0 키 입력이 없음을 의미
// row == 1 이면 키 입력이 있음을 의미
always @(*) begin
case (state)
SCAN0: begin
if(row == 0) next_state = SCAN1;
else next_state = KEY_PROCESS;
end
SCAN1: begin
if(row == 0) next_state = SCAN2;
else next_state = KEY_PROCESS;
end
SCAN2: begin
if(row == 0) next_state = SCAN3;
else next_state = KEY_PROCESS;
end
SCAN3: begin
if(row == 0) next_state = SCAN0;
else next_state = KEY_PROCESS;
end
KEY_PROCESS: begin
if(row == 0) next_state = SCAN0;
else next_state = KEY_PROCESS;
end
default : next_state = SCAN0;
endcase
end
//
// always @(posedge clk or posedge reset_p) begin
// if(reset_p) begin
// key_value = 0;
// key_valid = 0;
// col = 0;
// end
// else if(clk_8msec) begin
// if(row) begin
// key_valid = 1;
// case({col, row})
// 8'b0001_0001 : key_value = 4'h0;
// 8'b0001_0010 : key_value = 4'h1;
// 8'b0001_0100 : key_value = 4'h2;
// 8'b0001_1000 : key_value = 4'h3;
// 8'b0010_0001 : key_value = 4'h4;
// 8'b0010_0010 : key_value = 4'h5;
// 8'b0010_0100 : key_value = 4'h6;
// 8'b0010_1000 : key_value = 4'h7;
// 8'b0100_0001 : key_value = 4'h8;
// 8'b0100_0010 : key_value = 4'h9;
// 8'b0100_0100 : key_value = 4'ha;
// 8'b0100_1000 : key_value = 4'hb;
// 8'b1000_0001 : key_value = 4'hc;
// 8'b1000_0010 : key_value = 4'hd;
// 8'b1000_0100 : key_value = 4'he;
// 8'b1000_1000 : key_value = 4'hf;
// default : key_value = key_value;
// endcase
// end
// else key_valid = 0;
// end
// case(state)
// 4'b0001 : col = 4'b0001;
// 4'b0010 : col = 4'b0010;
// 4'b0100 : col = 4'b0100;
// 4'b1000 : col = 4'b1000;
// endcase
// end
always @(posedge clk or posedge reset_p) begin
if(reset_p) begin
key_value = 0;
key_valid = 0;
col = 0;
end
else if(clk_8msec_p)begin //상승엣지로 변경
case(state)
SCAN0 : begin col = 4'b0001; key_valid = 0; end
SCAN1 : begin col = 4'b0010; key_valid = 0; end
SCAN2 : begin col = 4'b0100; key_valid = 0; end
SCAN3 : begin col = 4'b1000; key_valid = 0; end
KEY_PROCESS : begin
key_valid = 1;
case({col, row})
8'b0001_0001 : key_value = 4'h7; //계산기 키패드 배열로 변경
8'b0001_0010 : key_value = 4'h8;
8'b0001_0100 : key_value = 4'h9;
8'b0001_1000 : key_value = 4'hA;
8'b0010_0001 : key_value = 4'h4;
8'b0010_0010 : key_value = 4'h5;
8'b0010_0100 : key_value = 4'h6;
8'b0010_1000 : key_value = 4'hb;
8'b0100_0001 : key_value = 4'h1;
8'b0100_0010 : key_value = 4'h2;
8'b0100_0100 : key_value = 4'h3;
8'b0100_1000 : key_value = 4'hE;
8'b1000_0001 : key_value = 4'hC;
8'b1000_0010 : key_value = 4'h0;
8'b1000_0100 : key_value = 4'hF;
8'b1000_1000 : key_value = 4'hd;
// 8'b0001_0001 : key_value = 4'h0;
// 8'b0001_0010 : key_value = 4'h1;
// 8'b0001_0100 : key_value = 4'h2;
// 8'b0001_1000 : key_value = 4'h3;
// 8'b0010_0001 : key_value = 4'h4;
// 8'b0010_0010 : key_value = 4'h5;
// 8'b0010_0100 : key_value = 4'h6;
// 8'b0010_1000 : key_value = 4'h7;
// 8'b0100_0001 : key_value = 4'h8;
// 8'b0100_0010 : key_value = 4'h9;
// 8'b0100_0100 : key_value = 4'ha;
// 8'b0100_1000 : key_value = 4'hb;
// 8'b1000_0001 : key_value = 4'hc;
// 8'b1000_0010 : key_value = 4'hd;
// 8'b1000_0100 : key_value = 4'he;
// 8'b1000_1000 : key_value = 4'hf;
default : key_value = key_value;
endcase
end
endcase
end
end
endmodule
module keypad_test_top(
input clk, reset_p,
input [3:0] row,
output [3:0] col,
output [3:0] com,
output [7:0] seg_7,
output led_key_valid
);
wire [3:0] key_value;
wire key_valid;
key_pad_cntr_FSM(.clk(clk), .reset_p(reset_p),
.row(row), .col(col),
.key_value(key_value),
.key_valid(led_key_valid));
assign led_key_valid = key_valid;
wire key_valid_p;
edge_detector_p ed(.clk(clk), .reset_p(reset_p),
.cp(key_valid), .p_edge(key_valid_p));
reg [15:0] key_count;
always @(posedge clk or posedge reset_p)begin
if(reset_p)key_count = 0;
else if(key_valid_p)begin
key_count = key_count + 1;
end
end
fnd_cntr fnd (.clk(clk), .reset_p(reset_p),
.value(key_count), .com(com), .seg_7(seg_7));
endmodule
module keypad_test_top(
input clk, reset_p,
input [3:0] row,
output [3:0] col,
output [3:0] com,
output [7:0] seg_7,
output led_key_valid
);
wire [3:0] key_value;
wire key_valid;
key_pad_cntr_FSM(.clk(clk), .reset_p(reset_p),
.row(row), .col(col),
.key_value(key_value),
.key_valid(led_key_valid));
assign led_key_valid = key_valid;
wire key_valid_p;
edge_detector_p ed(.clk(clk), .reset_p(reset_p),
.cp(key_valid), .p_edge(key_valid_p));
reg [15:0] key_count;
always @(posedge clk or posedge reset_p)begin
if(reset_p)key_count = 0;
else if(key_valid_p)begin
if(key_value == 1)key_count = key_count + 1;
else if(key_value == 2)key_count = key_count - 1;
else if(key_value == 3)key_count = key_count + 2;
end
end
fnd_cntr fnd (.clk(clk), .reset_p(reset_p),
.value(key_count), .com(com), .seg_7(seg_7));
endmodule


풀업저항 필요

풀업저항이 달려있는 센서
DHT11 데이터시트 참조

전체적인 통신 과정

첫 구간 : 약속된 프로토콜에 의한 시간만큼 0과1을 보내 통신 확인


0과1을 보내는데 약속된 시간동안 1을 보내면서 한 비트에 해당하는 신호가 0인지 1인지 정함
이것을 40비트동안 반복한뒤 신호를 임피던스 상태로 끊음, 하나의 데이터선을 공유하기 때문
