Вы находитесь на странице: 1из 32

-------

Tutorial 1 on using the LCD on the Spartan 3E Starter Kit board


by Claudio Talarico
Eastern Washington University
ctalarico@ewu.edu

--------

The design displays the word VHDL splitted on two lines on the LCD
+----------------+
|VH
|
| DL
|
+----------------+

-cs
-----.
--

The 2 x 16 character LCD on the board has an internal Sitronix ST7066U graphi
controller that is functionally equivalent with the following devices:
* Samsung S6A0069X or KS0066U
* Hitachi HD44780
* SMOS SED1278
To minimize pin icount the FPGA controls the LCD via the 4-bit data interface

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;
entity lcd
port(
clk
:
rst
:
SF_D :
LCD_E :
LCD_RS :
LCD_RW :
SF_CE0 :
end lcd;

is
in std_logic;
in std_logic;
out std_logic_vector(11 downto 8);
out std_logic;
out std_logic;
out std_logic;
out std_logic);

architecture rtl of lcd is


type istate_t is (iidle, iwrite_one, iwait_one, iwrite_two, iwait_two,
iwrite_three, iwait_three, iwrite_four, iwait_four,
function_set, entry_mode, control_display, clear_display,
init_done);
type dstate_t is (didle, set_address_one, write_data_V, write_data_H,
set_address_two, write_data_D, write_data_L, return_home);
signal
signal
sm
signal
signal
signal
signal
SF_D
signal

istate, next_istate
dstate, next_dstate

: istate_t; --state and next state of the init sm


: dstate_t; --state and next state of the display

idone, next_idone
icount, next_icount
dcount, next_dcount
nibble

:
:
:
:

std_logic; --initialization done


integer range 0 to 750000;
integer range 0 to 750000;
std_logic_vector(3 downto 0);--nibble put out to

inibble, next_inibble : std_logic_vector(3 downto 0);

signal
signal
signal
signal
signal
_RS
signal
signal

dnibble, next_dnibble : std_logic_vector(3 downto 0);


enable
: std_logic;--enable signal put out to LCD_E
ienable, next_ienable : std_logic;
denable, next_denable : std_logic;
regsel
: std_logic;--register select signal put out to LCD
iregsel, next_iregsel : std_logic;
dregsel, next_dregsel : std_logic;

begin
-- concurrent assignments
SF_CE0 <= '1'; --disable intel strataflash memory.
--FPGA has full read/write access to LCD.
LCD_RW <= '0'; --write LCD (LCD accepts data).
--putting LCD_RW=0 also prevent the LCD screen from presenting
--undesired data.
SF_D <= nibble;
LCD_E <= enable;
LCD_RS <= regsel;
--- muxing init state machines and data state machine
-mux: process (idone, dnibble, inibble, denable, ienable, dregsel, iregsel)
begin
if (idone = '1') then
nibble <= dnibble;
enable <= denable;
regsel <= dregsel;
else
nibble <= inibble;
enable <= ienable;
regsel <= iregsel;
end if;
end process mux;
--- initialization state machine
--- the purpose of the state machine is to initialize the display.
-- After power-on, the display must be initialized to
-- 1. establish the required communication protocol, and
-- 2. configure the diplay operation
--- 1. Configuration of the Fout-bit Interface Protocol
-- The initialization sequence establishes that the FPGA application wishes to
use the
-- four-bit data interface to the LCD as follows:
-- * Wait 15 ms or longer, although the display is generally ready when the
FPGA
-finishes configuration. The 15 ms interval is 750,000 clock cycles at 5
0 MHz.
-- * Write SF_D<11:8> = 0x3, pulse LCD_E High for 12 clock cycles.
-- * Wait 4.1 ms or longer, which is 205,000 clock cycles at 50 MHz.
-- * Write SF_D<11:8> = 0x3, pulse LCD_E High for 12 clock cycles.
-- * Wait 100 ?s or longer, which is 5,000 clock cycles at 50 MHz.
-- * Write SF_D<11:8> = 0x3, pulse LCD_E High for 12 clock cycles.
-- * Wait 40 ?s or longer, which is 2,000 clock cycles at 50 MHz.
-- * Write SF_D<11:8> = 0x2, pulse LCD_E High for 12 clock cycles.

-- * Wait 40 ?s or longer, which is 2,000 clock cycles at 50 MHz.


--- 2. Display Configuration
-- The four-bit interface is now established. The next part of the sequence
-- configures the display:
-- * Issue a Function Set command, 0x28, to configure the display for operat
ion on
-the Spartan-3E Starter Kit board.
-- * Issue an Entry Mode Set command, 0x06, to set the display to automatica
lly
-increment the address pointer.
-- * Issue a Display On/Off command, 0x0C, to turn the display on and disabl
es the
-cursor and blinking.
-- * Finally, issue a Clear Display command, 0x01. Allow at least 1.64 ms
-(82,000 clock cycles) after issuing this command.
--- NOTE: the sm follows religiously (and without much brain involvement) the S
partan 3E
-Starter Kit Board User Guide (pg.41-52). As can be easily noticed the
actions
-taken in most of the states have only few differences, so by "adding"
a
-little more flexibility in the way the state machine is coded/designe
d it is
-possible to reduce the number of states (and the line of code) consid
erably
-init_sm: process (istate, icount, idone, inibble, ienable )
begin
-- default assignments
next_istate <= istate;
next_icount <= icount;
next_idone <= idone;
next_ienable <= '0';
next_inibble <= "0000";
next_iregsel <= '0';
case istate is
when iidle => -- wait here for 15 ms
next_icount <= icount + 1;
if (icount = 750000) then
next_istate <= iwrite_one;
next_icount <= 0;
next_inibble <= "0011"; -- 0x3
end if;
when iwrite_one =>
next_inibble <= inibble;
next_ienable <= ienable;
next_icount <= icount + 1;
if (icount = 1) then
next_ienable <= '1';
end if;

if (icount = 10) then


next_ienable <= '0';
end if;
if(icount = 11) then
next_istate <= iwait_one;
next_icount <= 0;
end if;
when iwait_one => -- wait here for 4.1 ms
next_icount <= icount + 1;
if (icount = 205000) then
next_istate <= iwrite_two;
next_icount <= 0;
next_inibble <= "0011"; -- 0x3
end if;
when iwrite_two =>
next_inibble <= inibble;
next_ienable <= ienable;
next_icount <= icount + 1;
if (icount = 1) then
next_ienable <= '1';
end if;
if (icount = 10) then
next_ienable <= '0';
end if;
if(icount = 11) then
next_istate <= iwait_two;
next_icount <= 0;
end if;
when iwait_two => -- wait here for 100 us
next_icount <= icount + 1;
if (icount = 5000) then
next_istate <= iwrite_three;
next_icount <= 0;
next_inibble <= "0011"; -- 0x3
end if;
when iwrite_three =>
next_inibble <= inibble;
next_ienable <= ienable;
next_icount <= icount + 1;
if (icount = 1) then
next_ienable <= '1';
end if;
if (icount = 10) then
next_ienable <= '0';
end if;
if(icount = 11) then
next_istate <= iwait_three;

next_icount <= 0;
end if;
when iwait_three => -- wait here for 40 us
next_icount <= icount + 1;
if (icount = 2000) then
next_istate <= iwrite_four;
next_icount <= 0;
next_inibble <= "0010"; -- 0x2
end if;
when iwrite_four =>
next_inibble <= inibble;
next_ienable <= ienable;
next_icount <= icount + 1;
if (icount = 1) then
next_ienable <= '1';
end if;
if (icount = 10) then
next_ienable <= '0';
end if;
if(icount = 11) then
next_istate <= iwait_four;
next_icount <= 0;
end if;
when iwait_four => -- wait here for 40 us
next_icount <= icount + 1;
if (icount = 2000) then
next_istate <= function_set; -- issue function set command 0x28
next_icount <= 0;
next_inibble <= "0010"; -- 0x2 (upper nibble of 0x28)
end if;
when function_set => -- function set command 0x28
next_inibble <= inibble;
next_ienable <= ienable;
next_icount <= icount + 1;
if (icount = 1) then
next_ienable <= '1';
end if;
if (icount = 10) then
next_ienable <= '0';
end if;
if(icount = 11) then -- done with the upper nibble data
next_inibble <= (others => '0');
end if;
-- the timing between the falling edge of the upper nibble's enable
-- and the rising edge of the lower nibble's rising edge of an
-- operation is 1us (50 clock cycles)

if (icount = 58) then


-next_inibble <= "1000"; -end if;
if (icount = 60) then
next_ienable <= '1';
end if;
if (icount = 69) then
next_ienable <= '0';
end if;
if(icount = 70) then -- done
next_inibble <= (others =>
end if;

10 + 1 + 50 - 2 = 58
0x8 (lower nibble of 0x28)

with the lower nibble data


'0');

-- the timing between the falling edge of the lower nibble's enable
-- and the rising edge of the upper nibble's rising edge
-- of two adjacent operations is 40us (2000 clock cycles)
if (icount = 2068) then -- 69 + 1 + 2000 - 2 =
next_istate <= entry_mode;
next_icount <= 0;
next_inibble <= "0000"; -- 0x0 (lower nibble of 0x06)
end if;
when entry_mode => -- entry mode set command 0x06
next_inibble <= inibble;
next_ienable <= ienable;
next_icount <= icount + 1;
if (icount = 1) then
next_ienable <= '1';
end if;
if (icount = 10) then
next_ienable <= '0';
end if;
if(icount = 11) then -- done with the upper nibble data
next_inibble <= (others => '0');
end if;
-- the timing between the falling edge of the upper nibble's enable
-- and the rising edge of the lower nibble's rising edge of an
-- operation is 1us (50 clock cycles)
if (icount = 58) then
-next_inibble <= "0110"; -end if;
if (icount = 60) then
next_ienable <= '1';
end if;
if (icount = 69) then
next_ienable <= '0';
end if;
if(icount = 70) then -- done
next_inibble <= (others =>
end if;

10 + 1 + 50 - 2 = 58
0x6 (lower nibble of 0x06)

with the lower nibble data


'0');

-- the timing between the falling edge of the lower nibble's enable
-- and the rising edge of the upper nibble's rising edge

-- of two adjacent operations is 40us (2000 clock cycles)


if (icount = 2068) then -- 69 + 1 + 2000 - 2 =
next_istate <= control_display;
next_icount <= 0;
next_inibble <= "0000"; -- 0x0 (lower nibble of 0x0C)
end if;
when control_display => -- display on command 0x0C
-- enable display, disable cursor, disable blinkin
g
next_inibble <= inibble;
next_ienable <= ienable;
next_icount <= icount + 1;
if (icount = 1) then
next_ienable <= '1';
end if;
if (icount = 10) then
next_ienable <= '0';
end if;
if(icount = 11) then -- done with the upper nibble data
next_inibble <= (others => '0');
end if;
-- the timing between the falling edge of the upper nibble's enable
-- and the rising edge of the lower nibble's rising edge of an
-- operation is 1us (50 clock cycles)
if (icount = 58) then
-next_inibble <= "1100"; -end if;
if (icount = 60) then
next_ienable <= '1';
end if;
if (icount = 69) then
next_ienable <= '0';
end if;
if(icount = 70) then -- done
next_inibble <= (others =>
end if;
---if

10 + 1 + 50 - 2 = 58
0xC (lower nibble of 0x0C)

with the lower inibble data


'0');

the timing between the falling edge of the lower nibble's enable
and the rising edge of the upper nibble's rising edge
of two adjacent operations is 40us (2000 clock cycles)
(icount = 2068) then -- 69 + 1 + 2000 - 2 =
next_istate <= clear_display;
next_icount <= 0;
next_inibble <= "0000"; -- 0x0 (lower nibble of 0x01)
end if;
when clear_display
next_inibble <=
next_ienable <=
next_icount <=

=>
inibble;
ienable;
icount + 1;

if (icount = 1) then

next_ienable <= '1';


end if;
if (icount = 10) then
next_ienable <= '0';
end if;
if(icount = 11) then -- done with the upper nibble data
next_inibble <= (others => '0');
end if;
-- the timing between the falling edge of the upper nibble's enable
-- and the rising edge of the lower nibble's rising edge of an
-- operation is 1us (50 clock cycles)
if (icount = 58) then
-next_inibble <= "0001"; -end if;
if (icount = 60) then
next_ienable <= '1';
end if;
if (icount = 69) then
next_ienable <= '0';
end if;
if(icount = 70) then -- done
next_inibble <= (others =>
end if;

10 + 1 + 50 - 2 = 58
0x1 (lower nibble of 0x01)

with the lower nibble data


'0');

--- After the command is complete allow 1.64 ms (82,000 clock cycles)
-- before issuing another command
if (icount = 82071) then -- 70 + 1 + 82000 = 82071
next_istate <= init_done;
next_idone <= '1'; -- flag to signal that initialization is done
next_icount <= 0;
end if;
when init_done =>
-- by default idone will be hold at '1'
-- and the state machine will remain in
-- init_done for good
when others => -- nothing to do
end case;
end process init_sm;
--- display state machine
--- Once the LCD has been properly initialized finally the display sm kicks in
and
-- it makes possible to display characters on the screen.
-- The character code to be displayed on the screen are first stored in the Di
splay
-- Data RAM (DDRAM).
-- There are 32 character locations on the display. The upper line of characte

rs
-- is stored between addresses 0x00 and 0x0F of the DDRAM. The second line of
-- characters is stored between addresses 0x40 and 0x4F of the DDRAM.
-- The character code stored in a DDRAM location "references" a specific chara
cter
-- bitmap stored in the predefined Character Generator ROM (CGROM) character s
et.
-- The CGROM contains the font bitmap for each of the predefined characters th
at
-- the LCD screen can display.
-- The sequence of commands to display characters to the screen is as follows:
-- 1. Set DDRAM Address command
-Set the initial DDRAM address by initializing an internal address counte
r.
-The DDRAM address counter either remains constant or auto-increments or
-auto-decrements by one location, as defined by the I/D set bit of the
-Entry Mode Set command.
-- 2. Write Data to DDRAM command
-Write data into DDRAM if the command follows a previous Set DDRAM Addres
s.
-- 3. Return Cursor Home command
-Return the cursor to the home position, the top-left corner. DDRAM conte
nts are
-unaffected.
--- NOTE: the sm follows religiously (and without much brain involvement) the S
partan 3E
-Starter Kit Board User Guide (pg.41-52). As can be easily noticed the
actions
-taken in most of the states have only few differences, so by "adding"
a
-little more flexibility in the way the state machine is coded/designe
d it is
-possible to reduce the number of states (and the line of code) consid
erably
-display_sm: process(dstate, dcount, dregsel, dnibble, denable, idone)
begin
next_dstate
next_dcount
next_dregsel
next_dnibble
next_denable

<=
<=
<=
<=
<=

dstate;
dcount;
dregsel;
dnibble;
denable;

case dstate is
when didle =>
if (idone = '1') then
next_dstate <= set_address_one; -- set address 0x80
next_dcount <= 0;
next_dnibble <= "1000"; -- 0x8 (upper nibble of 0x80)
end if;
when set_address_one =>
next_dcount

<= dcount + 1;

if (dcount = 1) then
next_denable <= '1';
end if;
if (dcount = 10) then
next_denable <= '0';
end if;
if(dcount = 11) then -- done with the upper nibble data
next_dnibble <= (others => '0');
end if;
-- the timing between the falling edge of the upper nibble's enable
-- and the rising edge of the lower nibble's rising edge of an
-- operation is 1us (50 clock cycles)
if (dcount = 58) then
-next_dnibble <= "0000"; -end if;
if (dcount = 60) then
next_denable <= '1';
end if;
if (dcount = 69) then
next_denable <= '0';
end if;
if(dcount = 70) then -- done
next_dnibble <= (others =>
end if;

10 + 1 + 50 - 2 = 58
0x0 (lower nibble of 0x80)

with the lower nibble data


'0');

-- the timing between the falling edge of the lower nibble's enable
-- and the rising edge of the upper nibble's rising edge
-- of two adjacent operations is 40us (2000 clock cycles)
if (dcount = 2068) then -- 69 + 1 + 2000 - 2 =
next_dstate <= write_data_V;
next_dcount <= 0;
next_dnibble <= "0101"; -- 0x5 (upper nibble of 0x56)
next_dregsel <= '1';
end if;
when write_data_V => -- V = 0x56
next_dcount

<= dcount + 1;

if (dcount = 1) then
next_denable <= '1';
end if;
if (dcount = 10) then
next_denable <= '0';
end if;
if(dcount = 11) then -- done with the upper nibble data
next_dnibble <= (others => '0');
next_dregsel <= '0';
end if;
-- the timing between the falling edge of the upper nibble's enable
-- and the rising edge of the lower nibble's rising edge of an
-- operation is 1us (50 clock cycles)
if (dcount = 58) then
-- 10 + 1 + 50 - 2 = 58
next_dnibble <= "0110"; -- 0x6 (lower nibble of 0x56)

next_dregsel <= '1';


end if;
if (dcount = 60) then
next_denable <= '1';
end if;
if (dcount = 69) then
next_denable <= '0';
end if;
if(dcount = 70) then -- done with the lower nibble data
next_dnibble <= (others => '0');
next_dregsel <= '0';
end if;
-- the timing between the falling edge of the lower nibble's enable
-- and the rising edge of the upper nibble's rising edge
-- of two adjacent operations is 40us (2000 clock cycles)
if (dcount = 2068) then -- 69 + 1 + 2000 - 2 =
next_dstate <= write_data_H;
next_dcount <= 0;
next_dnibble <= "0100"; -- 0x4 (upper nibble of 0x48)
next_dregsel <= '1';
end if;
when write_data_H => -- H = 0x48
next_dcount

<= dcount + 1;

if (dcount = 1) then
next_denable <= '1';
end if;
if (dcount = 10) then
next_denable <= '0';
end if;
if(dcount = 11) then -- done with the upper nibble data
next_dnibble <= (others => '0');
next_dregsel <= '0';
end if;
-- the timing between the falling edge of the upper nibble's enable
-- and the rising edge of the lower nibble's rising edge of an
-- operation is 1us (50 clock cycles)
if (dcount = 58) then
-next_dnibble <= "1000"; -next_dregsel <= '1';
end if;
if (dcount = 60) then
next_denable <= '1';
end if;
if (dcount = 69) then
next_denable <= '0';
end if;
if(dcount = 70) then -- done
next_dnibble <= (others =>
next_dregsel <= '0';
end if;

10 + 1 + 50 - 2 = 58
0x8 (lower nibble of 0x56)

with the lower nibble data


'0');

-- the timing between the falling edge of the lower nibble's enable

-- and the rising edge of the upper nibble's rising edge


-- of two adjacent operations is 40us (2000 clock cycles)
if (dcount = 2068) then -- 69 + 1 + 2000 - 2 =
next_dstate <= set_address_two; -next_dcount <= 0;
next_dnibble <= "1100"; --0xC (upper nibble of 0xC2 - 3rd char of 2nd
line)
end if;
when set_address_two =>
next_dcount

<= dcount + 1;

if (dcount = 1) then
next_denable <= '1';
end if;
if (dcount = 10) then
next_denable <= '0';
end if;
if(dcount = 11) then -- done with the upper nibble data
next_dnibble <= (others => '0');
end if;
-- the timing between the falling edge of the upper nibble's enable
-- and the rising edge of the lower nibble's rising edge of an
-- operation is 1us (50 clock cycles)
if (dcount = 58) then
-next_dnibble <= "0010"; -end if;
if (dcount = 60) then
next_denable <= '1';
end if;
if (dcount = 69) then
next_denable <= '0';
end if;
if(dcount = 70) then -- done
next_dnibble <= (others =>
end if;

10 + 1 + 50 - 2 = 58
0x2 (lower nibble of 0xC2)

with the lower nibble data


'0');

-- the timing between the falling edge of the lower nibble's enable
-- and the rising edge of the upper nibble's rising edge
-- of two adjacent operations is 40us (2000 clock cycles)
if (dcount = 2068) then -- 69 + 1 + 2000 - 2 =
next_dstate <= write_data_D;
next_dcount <= 0;
next_dnibble <= "0100"; -- 0x4 (upper nibble of 0x44)
next_dregsel <= '1';
end if;
when write_data_D => -- D = 0x44
next_dcount

<= dcount + 1;

if (dcount = 1) then
next_denable <= '1';

end if;
if (dcount = 10) then
next_denable <= '0';
end if;
if(dcount = 11) then -- done with the upper nibble data
next_dnibble <= (others => '0');
next_dregsel <= '0';
end if;
-- the timing between the falling edge of the upper nibble's enable
-- and the rising edge of the lower nibble's rising edge of an
-- operation is 1us (50 clock cycles)
if (dcount = 58) then
-next_dnibble <= "0100"; -next_dregsel <= '1';
end if;
if (dcount = 60) then
next_denable <= '1';
end if;
if (dcount = 69) then
next_denable <= '0';
end if;
if(dcount = 70) then -- done
next_dnibble <= (others =>
next_dregsel <= '0';
end if;

10 + 1 + 50 - 2 = 58
0x4 (lower nibble of 0x44)

with the lower nibble data


'0');

-- the timing between the falling edge of the lower nibble's enable
-- and the rising edge of the upper nibble's rising edge
-- of two adjacent operations is 40us (2000 clock cycles)
if (dcount = 2068) then -- 69 + 1 + 2000 - 2 =
next_dstate <= write_data_L; -- 0x4C
next_dcount <= 0;
next_dnibble <= "0100"; --0x4 (upper nibble of 0x4C)
end if;
when write_data_L => -- L = 0x4C
next_dcount

<= dcount + 1;

if (dcount = 1) then
next_denable <= '1';
end if;
if (dcount = 10) then
next_denable <= '0';
end if;
if(dcount = 11) then -- done with the upper nibble data
next_dnibble <= (others => '0');
next_dregsel <= '0';
end if;
-- the timing between the falling edge of the upper nibble's enable
-- and the rising edge of the lower nibble's rising edge of an
-- operation is 1us (50 clock cycles)
if (dcount = 58) then
-- 10 + 1 + 50 - 2 = 58
next_dnibble <= "1100"; -- 0xC (lower nibble of 0x4C)

next_dregsel <= '1';


end if;
if (dcount = 60) then
next_denable <= '1';
end if;
if (dcount = 69) then
next_denable <= '0';
end if;
if(dcount = 70) then -- done with the lower nibble data
next_dnibble <= (others => '0');
next_dregsel <= '0';
end if;
-- the timing between the falling edge of the lower nibble's enable
-- and the rising edge of the upper nibble's rising edge
-- of two adjacent operations is 40us (2000 clock cycles)
if (dcount = 2068) then -- 69 + 1 + 2000 - 2 =
next_dstate <= return_home;
next_dcount <= 0;
next_dnibble <= "0000";
end if;
when
---------

return_home =>
by default the state machine will remain in the
return_home state for good
NOTE: this is not a real return_home command
as specfied in the Spartan 3E starter kit
user guide. Since in this specific case
we know that once we reach this state we
are not sending anything new to the display
we can simply stall the sm in this state

when others => -- nothing to do;


end case;
end process display_sm;
registers: process(rst, clk)
begin
if rst = '1' then
istate <= iidle;
dstate <= didle;
idone <= '0';
icount <= 0;
dcount <= 0;
dnibble <= (others => '0');
inibble <= (others => '0');
ienable <= '0';
denable <= '0';
iregsel <= '0';
dregsel <= '0';
elsif clk = '1' and clk'event then
istate <= next_istate;
dstate <= next_dstate;
idone <= next_idone;
icount <= next_icount;

dcount
dnibble
inibble
ienable
denable
iregsel
dregsel
end if;
end process

<=
<=
<=
<=
<=
<=
<=

next_dcount;
next_dnibble;
next_inibble;
next_ienable;
next_denable;
next_iregsel;
next_dregsel;

registers;

end rtl;

######VERILOG CODE ::

`timescale 1ns / 1ps


module lcd (
input wire clk,
z"
input wire disp_strb,
input wire[8:0] disp_data,
output reg lcd_busy,
output reg lcd_rs,
output wire lcd_rw,
output reg lcd_e,
output reg[3:0] lcd_data,
output wire[7:0] leds
);
localparam INIT=1'b0;

// synthesis attribute PERIOD clk "50 MH

localparam DISPLAY=1'b1;
localparam MAX=26'h3FFFFFF;
localparam N=5'h1A;
reg state=INIT;
reg[3:0] init_cntr=4'h0;
reg nibble_cntr=1'b0;
reg[N-1:0] clk_cntr=0;
assign
assign
assign
assign
assign
assign

lcd_rw=0;
leds[7:4]=lcd_data;
leds[0]=lcd_e;
leds[1]=lcd_rs;
leds[2]=lcd_rw;
leds[3]=lcd_busy;

always @(posedge clk) begin


case(state)
INIT:
case(init_cntr)
0: begin
if(clk_cntr==0) begin
lcd_busy<=1;
lcd_rs<=0;
lcd_data<=4'h3;
end
else if(clk_cntr==MAX)
init_cntr<= init_cntr+ 1;
else
lcd_e<=^clk_cntr[N-1:N-2];
clk_cntr<= clk_cntr+ 1;
end
1: begin
if(clk_cntr==0)
lcd_data<=4'h3;
else if(clk_cntr==MAX)
init_cntr<= init_cntr+ 1;
else
lcd_e<=^clk_cntr[N-1:N-2];
clk_cntr<= clk_cntr+ 1;
end
2: begin
if(clk_cntr==0)
lcd_data<=4'h3;
else if(clk_cntr==MAX)
init_cntr<= init_cntr+ 1;
else
lcd_e<=^clk_cntr[N-1:N-2];
clk_cntr<= clk_cntr+ 1;
end
3: begin
if(clk_cntr==0)
lcd_data<=4'h2;

else if(clk_cntr==MAX)
init_cntr<= init_cntr+ 1;
else
lcd_e<=^clk_cntr[N-1:N-2];
clk_cntr<= clk_cntr+ 1;
end
4: begin
if(clk_cntr==0)
lcd_data<=4'h2;
else if(clk_cntr==MAX)
init_cntr<= init_cntr+ 1;
else
lcd_e<=^clk_cntr[N-1:N-2];
clk_cntr<= clk_cntr+ 1;
end
5: begin
if(clk_cntr==0)
lcd_data<=4'h8;
else if(clk_cntr==MAX)
init_cntr<= init_cntr+ 1;
else
lcd_e<=^clk_cntr[N-1:N-2];
clk_cntr<= clk_cntr+ 1;
end
6: begin
if(clk_cntr==0)
lcd_data<=4'h0;
else if(clk_cntr==MAX)
init_cntr<= init_cntr+ 1;
else
lcd_e<=^clk_cntr[N-1:N-2];
clk_cntr<= clk_cntr+ 1;
end
7: begin
if(clk_cntr==0)
lcd_data<=4'h6;
else if(clk_cntr==MAX)
init_cntr<= init_cntr+ 1;
else
lcd_e<=^clk_cntr[N-1:N-2];
clk_cntr<= clk_cntr+ 1;
end
8: begin
if(clk_cntr==0)
lcd_data<=4'h0;
else if(clk_cntr==MAX)
init_cntr<= init_cntr+ 1;
else
lcd_e<=^clk_cntr[N-1:N-2];

clk_cntr<= clk_cntr+ 1;
end
9: begin
if(clk_cntr==0)
lcd_data<=4'hC;
else if(clk_cntr==MAX)
init_cntr<= init_cntr+ 1;
else
lcd_e<=^clk_cntr[N-1:N-2];
clk_cntr<= clk_cntr+ 1;
end
10: begin
if(clk_cntr==0)
lcd_data<=4'h0;
else if(clk_cntr==MAX)
init_cntr<= init_cntr+ 1;
else
lcd_e<=^clk_cntr[N-1:N-2];
clk_cntr<= clk_cntr+ 1;
end
11: begin
if(clk_cntr==0)
lcd_data<=4'h1;
else if(clk_cntr==MAX) begin
state<= state+ 1;
lcd_busy<=0;
end
else
lcd_e<=^clk_cntr[N-1:N-2];

//

clk_cntr<= clk_cntr+ 1;
end
endcase
DISPLAY:
//

if(lcd_busy)
if(disp_strb|lcd_busy)
case(nibble_cntr)
0: begin
if(clk_cntr==0) begin
lcd_busy<=1;
lcd_rs<=1;//disp_data[8];
lcd_data<=4'h4;//disp_data[7:4];
end
else if(clk_cntr==MAX)
nibble_cntr<= nibble_cntr+ 1;
else
lcd_e<=^clk_cntr[N-1:N-2];
clk_cntr<= clk_cntr+ 1;
end
1: begin
if(clk_cntr==0)
lcd_data<=4'h8;//disp_data[3:0];

else if(clk_cntr==MAX) begin


nibble_cntr<= nibble_cntr+ 1;
lcd_busy<=0;
end
else
lcd_e<=^clk_cntr[N-1:N-2];
clk_cntr<= clk_cntr+ 1;
end
endcase
endcase
end
endmodule

####PART2
# clock
NET "clk" LOC="C9";
# clk
#NET "clk" PERIOD=20.0ns HIGH 50%;
# lcd
NET "lcd_rs" LOC="L18";
NET "lcd_rw" LOC="L17";
NET "lcd_e" LOC="M18";
NET "lcd_data<0>" LOC="R15";
NET "lcd_data<1>" LOC="R16";
NET "lcd_data<2>" LOC="P17";
NET "lcd_data<3>" LOC="M15";
# leds
NET "leds<0>"
NET "leds<1>"
NET "leds<2>"
NET "leds<3>"
NET "leds<4>"
NET "leds<5>"
NET "leds<6>"
NET "leds<7>"

LOC="F12";
LOC="E12";
LOC="E11";
LOC="F11";
LOC="C11";
LOC="D11";
LOC="E9";
LOC="F9";

###PART3
`timescale 1ns / 1ps
module disp (
input wire clk,
output wire lcd_rs,
output wire lcd_rw,
output wire lcd_e,
output wire[3:0] lcd_data,
output wire[7:0] leds
);
localparam CMD=1'b0;

# register select pin


# read/write pin
# enable pin
# io...

#
#
#
#
#
#
#
#

led
led
led
led
led
led
led
led

0
1
2
3
4
5
6
7

localparam CHAR=1'b1;
reg disp_strb=0;
reg[8:0] disp_data;
wire lcd_busy;
lcd disp(.clk(clk), .disp_strb(disp_strb), .disp_data(disp_data), .lcd_b
usy(lcd_busy),
.lcd_rs(lcd_rw), .lcd_rw(lcd_rs), .lcd_e(lcd_e), .lcd_da
ta(lcd_data), .leds(leds));
endmodule

---------------------------------------------------------------------------------- Company:
-- Engineer:
--- Create Date:
14:43:01 05/22/2015
-- Design Name:
-- Module Name:
lcd - Behavioral
-- Project Name:
-- Target Devices:
-- Tool versions:
-- Description:
--- Dependencies:
--- Revision:
-- Revision 0.01 - File Created
-- Additional Comments:
---------------------------------------------------------------------------------library IEEE;

use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;
---- Uncomment the following library declaration if instantiating
---- any Xilinx primitives in this code.
--library UNISIM;
--use UNISIM.VComponents.all;
entity lcd is
Port ( lcd : out STD_LOGIC_vector ( 7 downto 0);
rs : out STD_LOGIC;
rw : out STD_LOGIC;
enable: out std_logic);
end lcd;
architecture Behavioral of lcd is
begin
lcd ( 7 downto 4 ) <= "0010" after 10 ns ;-------- 4 bit interface----------lcd ( 3 downto 0) <= "1000" after 10 ns ;
enable <= '0' after 10 ns;
rw <= '0' after 10 ns;
rs <= '0' after 10 ns;
lcd ( 7 downto 4 ) <= "0010" after 10 ns ;-------- 4 bit interface----------lcd ( 3 downto 0) <= "1000" after 10 ns ;
enable <= '1' after 10 ns ;
rw <= '0' after 10 ns;
rs <= '0' after 10 ns;

lcd ( 7 downto 4 ) <= "0010" after 10 ns ;-------- 4 bit interface----------lcd ( 3 downto 0) <= "1000" after 10 ns ;
enable <= '0' after 10 ns;
rw <= '0' after 10 ns;
rs <= '0' after 10 ns;
----------reset display--------------

lcd ( 7 downto 4 ) <= "0000" after 10 ns ;


lcd ( 3 downto 0) <= "0001" after 10 ns ;
enable <= '0' after 10 ns;
rw <= '0' after 10 ns;
rs <= '0' after 10 ns;

lcd ( 7 downto 4 ) <= "0000" after 10 ns ;


lcd ( 3 downto 0) <= "0001" after 10 ns ;
enable <= '1' after 10 ns;
rw <= '0' after 10 ns;
rs <= '0' after 10 ns;

lcd ( 7 downto 4 ) <= "0000" after 10 ns ;


lcd ( 3 downto 0) <= "0001" after 10 ns ;
enable <= '0' after 10 ns;
rw <= '0' after 10 ns;
rs <= '0' after 10 ns;
-------------- display on-----------------lcd ( 7 downto 4 ) <= "0000" after 10 ns ;
lcd ( 3 downto 0) <= "1110" after 10 ns ;
enable <= '0' after 10 ns;
rw <= '0' after 10 ns;
rs <= '0' after 10 ns;
lcd ( 7 downto 4 ) <= "0000" after 10 ns ;
lcd ( 3 downto 0) <= "1110" after 10 ns ;
enable <= '1' after 10 ns;
rw <= '0' after 10 ns;
rs <= '0' after 10 ns;

lcd ( 7 downto 4 ) <= "0000" after 10 ns ;


lcd ( 3 downto 0) <= "1110" after 10 ns ;
enable <= '0' after 10 ns;
rw <= '0' after 10 ns;
rs <= '0' after 10 ns;
------------------ bring cursor to the 1st position -------------

lcd ( 7 downto 4 ) <= "1000" after 10 ns ;


lcd ( 3 downto 0) <= "0000" after 10 ns ;
enable <= '0' after 10 ns;
rw <= '0' after 10 ns;
rs <= '0' after 10 ns;

lcd ( 7 downto 4 ) <= "1000" after 10 ns ;


lcd ( 3 downto 0) <= "0000" after 10 ns ;
enable <= '1' after 10 ns;
rw <= '0' after 10 ns;
rs <= '0' after 10 ns;

lcd ( 7 downto 4 ) <= "1000" after 10 ns ;


lcd ( 3 downto 0) <= "0000" after 10 ns ;
enable <= '0' after 10 ns;
rw <= '0' after 10 ns;
rs <= '0' after 10 ns;
--------------------- data display--------------------lcd ( 7 downto 4 ) <= "0101" after 10 ns ;--------displaying p----------lcd ( 3 downto 0) <= "0000" after 10 ns ;
enable <= '1' after 10 ns;
rw <= '0' after 10 ns;

rs <= '0' after 10 ns;

lcd ( 7 downto 4 ) <= "0101" after 10 ns ;--------displaying p----------lcd ( 3 downto 0) <= "0000" after 10 ns ;
enable <= '0' after 10 ns;
rw <= '0' after 10 ns;
rs <= '0' after 10 ns;

lcd ( 7 downto 4 ) <= "0101" after 10 ns ;--------displaying p----------lcd ( 3 downto 0) <= "0000" after 10 ns ;
enable <= '1' after 10 ns;
rw <= '0' after 10 ns;
rs <= '0' after 10 ns;
end Behavioral;

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;
entity clock is port (clk1 : in std_logic;
rw: out std_logic;
--read write control
rs:out std_logic;
----command data control
en:out std_logic;
data:out std_logic_vector(7 downto 0)
); end clock;
architecture Behavioral of clock is
component bin_ascii
Port ( bin : in STD_LOGIC_VECTOR (7 downto 0);
ascii : out STD_LOGIC_VECTOR (7 downto 0);
ascii1 : out STD_LOG
IC_VECTOR (7 downto 0)); end component; signal seconds, minutes, hours : std_l
ogic_vector(7 downto 0); signal sec,min,hour : integer range 0 to 60 :=0; signa
l count : integer :=1; signal clk : std_logic :='0'; signal out0,out1,out2,out3,
out4,out5 : std_logic_vector(7 downto 0); begin seconds <= conv_std_logic_vect
or(sec,8); minutes <= conv_std_logic_vector(min,8); hours <= conv_std_logic_vect
or(hour,8);
--clk generation.For 50 MHz clock this generates 1 Hz clock. proc

ess(clk1) begin if(clk1'event and clk1='1') then count <=count+1; if(count = 250
00000) then clk <= not clk; count <=1; end if; end if; end process; process(cl
k) --period of clk is 1 second. begin if(clk'event and clk='1') then
sec
<= sec+ 1;
if(sec = 59) then
sec<=0;
min <= min + 1;
if(min = 59) then
hour <= hour + 1;
min <= 0;
if(hour = 23) then
hour <= 0;
end if;
end if;
end if; end if; end process; p1: bin_ascii port map( seco
nds(7 downto 0), out0, out1); p2: bin_ascii port map( minutes(7 downto 0), out2,
out3); p3: bin_ascii port map( hours(7 downto 0), out4, out5); process(clk1)
variable x,y : integer := 0 ; begin rw<='0'; if clk1'event and clk1 = '1' then
if x <= 160000 then
x := x + 1;
elsif x > 160000 then
x := 0 ;
if y < 43 then
y := y + 1 ;
else
y := 0;
end if;
end if;
case y is
-- as
cii code of data to be displayed
when 1=>
data<="001
11000"; ---38 2 lines and 5x7 matrix
en<='1';
rs<='
0';
when 2=>
rs<='0';
en<='0';
when
3=>
data<="00001100"; ---0C Display on, cursor off
e
n<='1';
rs<='0';
when 4=>
rs<='0';
en<='0';
when 5=>
data<="00000001"; ---clear display
en<='1';
rs<='0';
when 6=>
rs<
='0';
en<='0';
when 7=>
data<="00000110"; --06 Inc cursor(shift right)
en<='1';
rs<='0';
when 8=>
rs<='0';
en<='0';
when 9=>
data<="10000000"; ---80 Force cursor to 1st line
en<='1';
rs<='0';
when 10=>
rs<='0';
e
n<='0'; -------------------------------------------------------------------when 11=>
data<="00100000";
-- SPACE
en<='1
';
rs<='1';
when 12=>
rs<='1';
en<='0';
when 13=>
data<=out5;
-- hr
e
n<='1';
rs<='1';
when 14=>
rs<='1';
en<='0';
when 15=>
data<=out4;
--hr
en<='1';
rs<='1';
when 16=>
rs<='1';
en<='0';
when 17=>
data<="00111010";
-- :
en<='1';
rs<='1';
when 18=>
rs<
='1';
en<='0';
when 19=>
data<=out3;
- min
en<='1';
rs<='1';
when 20=>
rs<='1';
en<='0';
when 21=>
data<=out2;
-- min
en<='1';
rs<='1';
when 22=>
rs<='1';
en<='0';
when 23=>
data<="
00111010"; -- :
rs<='1';
en<='1';
when 24=>
rs<='1';
en<='0';
when 25=>
dat
a<=out1;
-- sec
rs<='1';
en<='1';
when 26
=>
rs<='1';
en<='0';
when 27=>
data<=out0;
-- sec
rs<='1';
en<='1';
when
28=>
rs<='1';
en<='0';
when 2
9=>
data<="00100000";
-- SPACE
en<='1';
rs<='1';
when 30=>
rs<='1';
en<='0';
when 31=>
data<="00100000";
-- SPACE
en<='1';
rs<='1';
when 32=>
rs<='1';
en<='0';
when 33=>
data<="00100000";
-- SPACE
en<='1';
rs<='1';
when 34=>
rs<='1'
;
en<='0';
when 35=>
data<="00100000";
-SPACE
en<='1';
rs<='1';
when 36=>
rs<='1';
en<='0';
when 37=>
data<="0010
0000";
-- SPACE
en<='1';
rs<='1';
when 3
8=>
rs<='1';
en<='0';
when 39=>
data<="00100000";
-- SPACE
en<='1';
rs<='1';
when 40=>
rs<='1';
en<='0';
when 4
1=>
data<="00100000";
-- SPACE
en<='1';
rs<='1';
when 42=>
rs<='1';
en<='0'; ---

-------------------------------------------------------------when oth
ers=>
data<="01000100";
-- ascii code for " "
rs<
='1';
en<='0';
end case; end if; end process; end Behavioral
; - See more at: https://www.pantechsolutions.net/project-kits/implementationof-digital-clock#sthash.bxVh9VEQ.dpuf

Digital clock in VHDL with output on different seven segments


Here is the module will have four outputs Min1,Min10,Hr1 and Hr10 each one will
be outputed on one seven segment display and the clock input clk is the 1Hz clo
ck signal
-------------------------------------------------------------------------------------------------------------Here is the VHDL code for this Module
library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;
---- Uncomment the following library declaration if instantiating
---- any Xilinx primitives in this code.
--library UNISIM;
--use UNISIM.VComponents.all;
entity clockticks is Port (

clk :in std_logic;


ResetL :in std_logic; -- Low true reset to 1:00 AM
Hr1 :out std_logic_vector(3 downto 0); -- 1's place
Hr10 :out std_logic_vector(3 downto 0); -- 10's place
Min1 :out std_logic_vector(3 downto 0); -- 1's place
Min10 :out std_logic_vector(3 downto 0) -- 10's place
);
end clockticks;
architecture Behavioral of clockticks is
signal
signal
signal
signal
signal

sec : integer ;
Min1Temp : integer;
Min10Temp: integer;
Hr1Temp : integer;
Hr10Temp : integer;

begin
--Digital clock in VHDL

process(clk) --period of clk is 1 second.


begin
if(clk'event and clk='1') then
sec <= sec+ 1;
if(sec = 59) then
Min1Temp <= Min1Temp + 1;
end if;
if (Min1Temp=10) then
Min1Temp<=0;
Min10Temp<=Min10Temp+1;
end if;
if(Min10Temp = 6) then
Min10Temp<=0;
Hr1Temp <= Hr1Temp + 1;
Min1Temp <= 1;
end if;
if(Hr10Temp=2 and Hr1Temp = 4) then
Hr1Temp <= 0;
Hr10Temp <= 0;
end if;
if(sec = 60) then
sec <= 1;
end if;
end if;
end process;

Min1 <= conv_std_logic_vector(Min1Temp,4);

Min10 <= conv_std_logic_vector(Min10Temp,4);


Hr1 <= conv_std_logic_vector(Hr1Temp,4);
Hr10 <= conv_std_logic_vector(Hr10Temp,4);
end Behavioral;

The following Verilog code takes in 257 bits of data and sends the data to the L
CD.
`timescale 1ns / 1ps
module LCD(
clk,
chars,
lcd_rs, lcd_rw, lcd_e, lcd_4, lcd_5, lcd_6, lcd_7);
// inputs and outputs
input
clk;
input [256:0] chars;
output
lcd_rs, lcd_rw, lcd_e, lcd_4, lcd_5, lcd_6, lcd_7;
wire [256:0]
reg

chars;
lcd_rs, lcd_rw, lcd_e, lcd_4, lcd_5, lcd_6, lcd_7;

// internal variables
reg [5:0]
lcd_code;
reg [1:0]
write = 2'b10; // write code has 10 for rs rw
// delays
reg [1:0]
reg [3:0]
reg [23:0]

before_delay = 3;
on_delay = 13;
off_delay = 750_001;

// time before on
// time on
// time off

// states and counters


reg [6:0]
Cs = 0;
reg [19:0]
count = 0;
reg [1:0]
delay_state = 0;
// character data
reg [256:0]
chars_hold = "
wire [3:0]
chars_data [63:0];
// redirects characters data to an array
generate

";
// array of characters

genvar i;
for (i = 64; i > 0; i = i-1)
begin : for_name
assign chars_data[64-i] = chars_hold[i*4-1:i*4-4
];
end
endgenerate
always @ (posedge clk) begin
// store character data
if (Cs == 10 && count == 0) begin
chars_hold <= chars;
end
// set time when enable is off
if (Cs < 3) begin
case (Cs)
0: off_delay <=
1: off_delay <=
2: off_delay <=
endcase
end else begin
if (Cs > 12) begin
off_delay
end else begin
off_delay
end
end

750_001;
250_001;
5_001;

// 15ms delay
// 5ms delay
// 0.1ms delay

<= 2_001;

// 40us delay

<= 250_001;

// 5ms delay

// delays during each state


if (Cs < 80) begin
case (delay_state)
0: begin
// enable is off
lcd_e <= 0;
{lcd_rs,lcd_rw,lcd_7,lcd_6,lcd_5,lcd_4}
<= lcd_code;
if (count == off_delay) begin
count <= 0;
delay_state <= delay_state + 1;
end else begin
count <= count + 1;
end
end
1: begin
// data set before enable is on
lcd_e <= 0;
if (count == before_delay) begin
count <= 0;
delay_state <= delay_state + 1;
end else begin
count <= count + 1;
end
end
2: begin
// enable on
lcd_e <= 1;
if (count == on_delay) begin
count <= 0;

delay_state <= delay_state + 1;


end else begin
count <= count + 1;
end
end
3: begin
// enable off with data set
lcd_e <= 0;
if (count == before_delay) begin
count <= 0;
delay_state <= 0;
Cs <= Cs + 1;
// next
case
end else begin
count <= count + 1;
end
end
endcase
end
// set lcd_code
if (Cs < 12) begin
// initialize LCD
case (Cs)
0: lcd_code <= 6'h03;

// power-on initial

ization
1:
2:
3:
4:
5:
6:
7:
8:

lcd_code
lcd_code
lcd_code
lcd_code
lcd_code
lcd_code
lcd_code
lcd_code

<=
<=
<=
<=
<=
<=
<=
<=

6'h03;
6'h03;
6'h02;
6'h02;
6'h08;
6'h00;
6'h06;
6'h00;

// function set
// entry mode set
// display on/off c

ontrol
9: lcd_code <= 6'h0C;
10:lcd_code <= 6'h00;
// display clear
11:lcd_code <= 6'h01;
default: lcd_code <= 6'h10;
endcase
end else begin
// set character data to lcd_code
if (Cs == 44) begin

// change addres

s at end of first line


lcd_code <= {2'b00, 4'b1100};

// 0100 0000 add

ress change
end else if (Cs == 45) begin
lcd_code <= {2'b00, 4'b0000};
end else begin
if (Cs < 44) begin
lcd_code <= {write, chars_data[Cs-12]};
end else begin
lcd_code <= {write, chars_data[Cs-14]};
end
end
end
// hold and loop back

if (Cs == 78) begin


lcd_e <= 0;
if (count == off_delay) begin
Cs
count
<= 0;
end else begin
count <= count + 1;
end
end

<= 10;

end
endmodule

This Verilog code tests the module and show how it works. The last character on
the LCD can be manipulated by the switches on the Spartan-3E board.
`timescale 1ns / 1ps
module LCDtest(
clk,
I3, I2, I1, I0,
lcd_rs, lcd_rw, lcd_e, lcd_4, lcd_5, lcd_6, lcd_7
);
// input and outputs
input clk;
input I3, I2, I1, I0;
output lcd_rs, lcd_rw, lcd_e, lcd_4, lcd_5, lcd_6, lcd_7;
wire
wire

I3, I2, I1, I0;


lcd_rs, lcd_rw, lcd_e, lcd_4, lcd_5, lcd_6, lcd_7;

// internal variables
wire [256:0] chars;
// LCD module

LCD

lcd(

clk,
chars,
lcd_rs, lcd_rw, lcd_e, lcd_4, lcd_5, lcd_6, lcd_7);

// assign character data


assign chars[255:8] = "Hello World!!!!!
Value:
assign chars[7:0] = {4'b0011,I3, I2, I1, I0};

";

endmodule
This is the code for the UCF file for the pin assignments of the Spartan-3E.
# clock
NET "clk" LOC = C9 | IOSTANDARD = LVCMOS33 ;
NET "clk" PERIOD = 20.0ns HIGH 50%;
# LCD control inputs
NET "lcd_e"
LOC = M18 | IOSTANDARD = LVCMOS33 | DRIVE = 4 | SLEW = SLOW ;
NET "lcd_rs"
LOC = L18 | IOSTANDARD = LVCMOS33 | DRIVE = 4 | SLEW = SLOW ;
NET "lcd_rw"
LOC = L17 | IOSTANDARD = LVCMOS33 | DRIVE = 4 | SLEW = SLOW ;
# The LCD four-bit data interface
NET "lcd_4"
LOC = R15 | IOSTANDARD
NET "lcd_5"
LOC = R16 | IOSTANDARD
NET "lcd_6"
LOC = P17 | IOSTANDARD
NET "lcd_7"
LOC = M15 | IOSTANDARD

=
=
=
=

LVCMOS33
LVCMOS33
LVCMOS33
LVCMOS33

# inputs
NET "I0"
NET "I1"
NET "I2"
NET "I3"

=
=
=
=

LVTTL;
LVTTL;
LVTTL;
LVTTL;

LOC
LOC
LOC
LOC

=
=
=
=

L13
L14
H18
N17

|
|
|
|

IOSTANDARD
IOSTANDARD
IOSTANDARD
IOSTANDARD

|
|
|
|

DRIVE
DRIVE
DRIVE
DRIVE

=
=
=
=

4
4
4
4

|
|
|
|

SLEW
SLEW
SLEW
SLEW

=
=
=
=

SLOW
SLOW
SLOW
SLOW

;
;
;
;

Вам также может понравиться