📄 lcm240128zk03_interface.v
字号:
/****************************************Copyright (c)**************************************************
** 张敏 西北核技术研究所一室 2008
**
**--------------File Info-------------------------------------------------------------------------------
** File name: lcm240128zk03.v
** Last modified Date: 2008-7-26
** Last Version: 1.0
** Descriptions: lcm240128zk03控制逻辑
**------------------------------------------------------------------------------------------------------
** Created by: 张敏 西北核技术研究所一室
** Created date: 2008-7-26
** Version: 1.0
** Descriptions: The original version
**
**------------------------------------------------------------------------------------------------------
** Modified by:
** Modified date:
** Version:
** Descriptions:
**
**------------------------------------------------------------------------------------------------------
********************************************************************************************************/
module lcm240128zk03_interface(
//模块输入
clk,
reset_n,
lcd_int,
chipselect,
read,
write,
lcd_busy,
address,
writedata,
//模块输出
lcd_rs,
lcd_rw,
lcd_en,
lcd_cs1,
lcd_cs2,
lcd_rst,
irq, //LCD 中断信号
readdata,
lcd_data //lcd 数据线
);
//Inputs
input clk; //Input Clock
input reset_n; //Reset
input lcd_int; //lcd 中断
input chipselect; //Avalon Chip select signal
input read; //Avalon read
input write; //Avalon read signal
input lcd_busy; //lcd busy
input [1:0] address;//Avalon Address bus
input [7:0] writedata;//Avalon ritedata
//Outputs
output lcd_rs; //lcd 指令、数据控线
output lcd_rw; //lcd 读写线
output lcd_en; //lcd 使能线
output lcd_cs1; //lcd cs1
output lcd_cs2; //lcd cs2
output lcd_rst; //lcd rst
output irq; //lcd 中断
output reg [7:0] readdata; //IP的输出,LCD寄存器的值
//inout
inout reg [7:0] lcd_data;//lcd 数据线
//中间寄存器声明
reg lcd_rs_r; //lcd rs
reg lcd_rw_r; //lcd rw
reg lcd_en_r; //lcd en
reg lcd_rst_r; //lcd rst
reg [10:0] timecount; //状态机状态变量
//寄存器输出
assign irq = lcd_int; //直接将LCD中断向上报告
assign lcd_cs1 = 1'h0; //直接将LCD cs1 置0
assign lcd_cs2 = 1'h1; //直接将LCD cs2 置1
assign lcd_rs = lcd_rs_r;
assign lcd_rw = lcd_rw_r;
assign lcd_en = lcd_en_r;
assign lcd_rst = lcd_rst_r;
//初始化状态
initial
begin
readdata<=8'h0;
lcd_rs_r<= 1'h1;
lcd_rw_r<= 1'h1;
lcd_en_r<= 1'h0;
lcd_rst_r<= 1'h1;
lcd_data<=8'h0;
timecount = 10'h0;
end
//合成读、写控制
wire read_act;
assign read_act = chipselect & read;
wire write_act;
assign write_act = chipselect & write &!lcd_busy;
parameter tcntwritemax = 10'h37;//写LCD比较耗时,一般需要用到55个时钟周期约550ns
//write and read
always @(posedge clk )
begin
if (write_act && !read_act)//AVALON 写数据
begin
case (address)
2'h0: //写指令
begin
/*
LCD_ChkBusy(); //Call LCD_ChkBusy to Check Busy Bit
LCD_Command = Cmd_Data;
P2 = 0x91;
EN = 1;
_nop_();
EN = 0;
P2 = 0x93;
*/
if(timecount==10'h0)//首先配置RS、RW,输出数据
begin
lcd_rs_r<= 1;//指令
lcd_rw_r<= 0;//写入
lcd_data<=writedata;//将指令输出到LCD的数据线
end
else if(timecount==10'h8)//第8个时钟周期输出lcd的enable高电平,以100M计地址、数据的建立时间约80ns,符合63ns的最小要求
begin
lcd_en_r<= 1;
end
else if(timecount==10'h35)//0x35=53输出lcd的enable低电平,以100M计地址、enable的脉宽约450ns,符合400ns的最小要求
begin
lcd_en_r<= 0;
end
else if(timecount==10'h37)//0x37=55可以拆消地址和数据了,以100M计地址、数据的保持时间约20ns,符合10ns的最小要求,至此写数据就已经完成了
begin
lcd_rs_r<= 1;//指令
lcd_rw_r<= 1;//读入
lcd_data<=8'h0;//将LCD的数据线置0
end
else if(timecount>=10'h0 && timecount<=tcntwritemax)
begin
end
else
begin
readdata<=8'h0;
lcd_rs_r<= 1'h1;
lcd_rw_r<= 1'h1;
lcd_en_r<= 1'h0;
lcd_data<=8'h0;
timecount = 10'h0;
end
if(timecount<=tcntwritemax&&timecount>=0) begin timecount = timecount+1; end
else begin timecount =0; end
end
2'h1: //写数据
begin
/*
LCD_ChkBusy(); //Call LCD_ChkBusy to Check Busy Bit
LCD_Data = Data_Data;
P2 = (0x90);
EN = 1;
_nop_();
EN = 0;
P2 = (0x93);
*/
if(timecount==10'h0)//首先拉低RS、RW,输出数据
begin
lcd_rs_r<= 0;//数据
lcd_rw_r<= 0;//写入
lcd_data<=writedata;//将数据输出到LCD的数据线
end
else if(timecount==10'h8)//第8个时钟周期输出lcd的enable高电平,以100M计地址、数据的建立时间约80ns,符合63ns的最小要求
begin
lcd_en_r<= 1;
end
else if(timecount==10'h35)//0x35=53输出lcd的enable低电平,以100M计地址、enable的脉宽约450ns,符合400ns的最小要求
begin
lcd_en_r<= 0;
end
else if(timecount==10'h37)//0x37=55可以拆消地址和数据了,以100M计地址、数据的保持时间约20ns,符合10ns的最小要求,至此写数据就已经完成了
begin
lcd_rs_r<= 1;//指令
lcd_rw_r<= 1;//读入
lcd_data<=8'h0;//将LCD的数据线置0
end
else if(timecount>=10'h0 && timecount<=tcntwritemax)
begin
end
else
begin
readdata<=8'h0;
lcd_rs_r<= 1'h1;
lcd_rw_r<= 1'h1;
lcd_en_r<= 1'h0;
lcd_data<=8'h0;
timecount = 10'h0;
end
if(timecount<=tcntwritemax&&timecount>=0) begin timecount = timecount+1; end
else begin timecount =0; end
end
2'h2: //重启LCK,由于RESET时延要求100ms ,过长,无法由硬件产生这么长的时序,改由上层软件分两次控制
begin
//使用方法为:RESET_LCM240128(base,0),100ms后再RESET_LCM240128(base,1)
lcd_rst_r <= writedata[0];
end
default: //非法地址,将各路信号置为默认状态
begin
//readdata<=8'h0;
lcd_rs_r<= 1'h1;
lcd_rw_r<= 1'h1;
lcd_en_r<= 1'h0;
lcd_data<=8'h0;
timecount = 10'h0;
end
endcase
end if (read_act && !write_act)//AVALON 读数据,读数据只用0个等待周期
begin
case (address)
2'h0: //读指令
begin//未用到,返回0
readdata <= 8'h0;
end
2'h1: //读数据
begin//未用到,返回0
readdata <= 8'h0;
end
2'h2: //读取LCD的BUSY情况
begin
//使用方法为:CHECK_BUSY_LCM240128(base)
readdata <= {7'h0,lcd_busy};
end
default: //非法地址,将各路信号置为默认状态
begin
readdata<=8'h0;
lcd_rs_r<= 1'h1;
lcd_rw_r<= 1'h1;
lcd_en_r<= 1'h0;
lcd_data<=8'h0;
timecount = 10'h0;
end
endcase
end
else if(lcd_busy)//如果处于忙碌状态,则跳过此次操作,严格来讲,应该是busy只影响写操作
begin
end
else//非读、非写、非忙时,将各路信号置为默认状态
begin
readdata<=8'h0;
lcd_rs_r<= 1'h1;
lcd_rw_r<= 1'h1;
lcd_en_r<= 1'h0;
lcd_data<=8'h0;
timecount = 10'h0;
end
end
endmodule
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -