강의

멘토링

로드맵

인프런 커뮤니티 질문&답변

오현택님의 프로필 이미지
오현택

작성한 질문수

verilog 코딩 질문

작성

·

51

·

수정됨

0

대학교 프로젝트 러닝머신 모듈을 구현하려고 하는데요. 스위치,LCD, LED, 7-seg 등을 사용할 건데 스위치를 눌렀을 때 제대로 작동을 하지 않습니다. 대략적으로 스위치 기능만 요약드리자면

1 2 3

4 5 6

7 8 9 라고 할 때

1번- 스위치 모드 변경(LCD에 출력되는 값 변경)

2번-slope 증가

3번-speed 저장

4번-speed 감소

5번- 러닝머신을 작동시키고 작동되는 상태에서 다시 누르면 러닝머신이 일시정지

6번- speed 증가

7번- 저장된 speed로 변경

8번- slope 감소

9번- 러닝머신 종료 및 값 리셋

 

전체적인 스위치 모듈 코드는 다음과 같습니다.

`timescale 1ns / 1ps

module Switch_Handler(

input osc, // 시스템 클럭

input reset, // 리셋 신호

input SW_INPUT0, // 스위치 행 입력

input SW_INPUT1,

input SW_INPUT2,

output reg SW_COMMON0, // 스위치 열 출력

output reg SW_COMMON1,

output reg SW_COMMON2,

output reg [15:0] speed, // 속도 제어

output reg [15:0] slope, // 경사 제어

output reg active, // 활성 상태

output reg paused, // 일시정지 상태

output reg switch_mode, // 모드 전환 신호

output reg reset_distance // 거리 리셋 신호

);

// 내부 변수

reg [2:0] sw_column = 0; // 현재 활성화된 스위치 열

reg [2:0] sw_state = 0; // 스위치 행 입력 저장

reg [31:0] cnt_sw = 0;

reg tick = 0;

reg [15:0] speed_reg;

// Tick generation (5000 clock cycles for debounce/scan interval)

always @(posedge osc) begin

if (cnt_sw >= 5000) begin

tick <= 1;

cnt_sw <= 0;

end else begin

tick <= 0;

cnt_sw <= cnt_sw + 1;

end

end

// Column scanning logic

always @(posedge tick or posedge reset) begin

if (reset) begin

sw_column <= 3'd0;

end else if (sw_column == 4) begin

sw_column <= 3'd1;

end else begin

sw_column <= sw_column + 1'b1;

end

end

 

always @(posedge osc or posedge reset) begin

if (reset) begin

SW_COMMON0 <= 1'b0;

SW_COMMON1 <= 1'b0;

SW_COMMON2 <= 1'b0;

end else begin

case (sw_column)

1: begin

SW_COMMON0 <= 1'b0;

SW_COMMON1 <= 1'b1;

SW_COMMON2 <= 1'b1;

end

2: begin

SW_COMMON0 <= 1'b1;

SW_COMMON1 <= 1'b0;

SW_COMMON2 <= 1'b1;

end

3: begin

SW_COMMON0 <= 1'b1;

SW_COMMON1 <= 1'b1;

SW_COMMON2 <= 1'b0;

end

default: begin

SW_COMMON0 <= 1'b0;

SW_COMMON1 <= 1'b0;

SW_COMMON2 <= 1'b0;

end

endcase

end

end

// Capture switch state

always @(posedge osc or posedge reset) begin

if (reset) begin

sw_state <= 3'd0;

end else begin

sw_state <= {SW_INPUT2, SW_INPUT1, SW_INPUT0};

end

end

initial begin

speed = 0;

speed_reg = 0;

slope = 0;

paused = 0;

active = 0;

switch_mode = 0;

end

 

always @(posedge osc or posedge reset) begin

if (reset) begin

active <= 0;

paused <= 0;

speed <= 0;

slope <= 0;

speed_reg <= 0;

end else begin

case (sw_column)

1:

begin

case (sw_state)

3'b110: if(active == 1) switch_mode <= ~switch_mode;

3'b101: if(active == 1 && slope < 15) slope <= slope + 1;

3'b011: if(active == 1 && speed > 0)speed_reg <= speed;

default: ;

endcase

end

2:

begin

case (sw_state)

3'b110:if(active == 1 && paused && speed > 1) speed <= speed - 1;

3'b101:

begin

if (!active) begin

active <= 1;

speed <= 1;

end

else if(active == 1) paused <= ~paused;

end

3'b011:

if(active == 1 && !paused && speed < 20) speed <= speed + 1;

default: ;

endcase

end

3:

begin

case(sw_state)

3'b110:

if(active == 1 && !paused) speed <= speed_reg;

3'b101:

begin

if(active == 1 && !paused && slope > 0) slope <= slope - 1;

end

3'b011: begin if(active == 1) begin

active <= 0;

speed <=0;

slope <=0;

speed_reg <=0;

paused <=0;

end

end

endcase

end

endcase

end

end

endmodule

 

제발 도와주세요 ㅠㅠ

답변

답변을 기다리고 있는 질문이에요
첫번째 답변을 남겨보세요!
오현택님의 프로필 이미지
오현택

작성한 질문수

질문하기