利用I2C总线读写AT24C512的FPGA原创代码
根据上面一篇研究AT24C512的DATASHEET 心得,设计如下利用FPGA读写 AT24C512的原创代码。在本代码中,设计目的,根据指定的页地址,利用随机顺序读方式和页写方式操作AT24C512, 每次读写128字节,即一页数据。
端口定义如下:
clk: 时钟信号,设计为20MHZ;
rst: 复位信号,设计为0复位,1不复位
clk200k: i2c总线读写时钟
clk200k: i2c总线读写时钟
sck: at24c512时钟控制线
sdata: at24c512数据线
page_addr: 读写的页地址
operate_cmd: 读写命令;“00” 表示---读;“01”---表示写
i2c_ram_rd: RAM读信号,该RAM存放从EEPROM读出的128字节数据
i2c_ram_rd_addr: RAM读地址,该RAM存放从EEPROM读出的128字节数据
i2c_ram_rd_data: RAM读数据,该RAM存放从EEPROM读出的128字节数据
i2c_ram_wr: RAM写信号,该RAM存放写入EEPROM的128字节数据
i2c_ram_wr_addr: RAM写地址,该RAM存放写入EEPROM的128字节数据
i2c_ram_wr_data: RAM写数据,该RAM存放写入EEPROM的128字节数据
i2c_en: i2c模块读写使能信号,高有效
i2c_ram_rd_addr: RAM读地址,该RAM存放从EEPROM读出的128字节数据
i2c_ram_rd_data: RAM读数据,该RAM存放从EEPROM读出的128字节数据
i2c_ram_wr: RAM写信号,该RAM存放写入EEPROM的128字节数据
i2c_ram_wr_addr: RAM写地址,该RAM存放写入EEPROM的128字节数据
i2c_ram_wr_data: RAM写数据,该RAM存放写入EEPROM的128字节数据
i2c_en: i2c模块读写使能信号,高有效
update: 数据从EEProm读取完毕标志
err: 从eeprom读取过程中出错故障指示
library ieee;
use ieee.std_logic_1164.all;
use ieee.std_logic_arith.all;
use ieee.std_logic_signed.all;
use ieee.std_logic_1164.all;
use ieee.std_logic_arith.all;
use ieee.std_logic_signed.all;
entity i2c is
port
(
clk: in std_logic;
rst: in std_logic;
clk200k: in std_logic;
sck: out std_logic;
sdata: inout std_logic;
page_addr: in std_logic_vector(7 downto 0);
operate_cmd: in std_logic_vector(1 downto 0);
i2c_ram_rd: in std_logic;
i2c_ram_rd_addr: in std_logic_vector(6 downto 0);
i2c_ram_rd_data: out std_logic_vector(7 downto 0);
i2c_ram_wr: in std_logic;
i2c_ram_wr_addr: in std_logic_vector(6 downto 0);
i2c_ram_wr_data: in std_logic_vector(7 downto 0);
i2c_en: in std_logic;
update: out std_logic ;
err: out std_logic;
rdy: out std_logic
);
end i2c;
port
(
clk: in std_logic;
rst: in std_logic;
clk200k: in std_logic;
sck: out std_logic;
sdata: inout std_logic;
page_addr: in std_logic_vector(7 downto 0);
operate_cmd: in std_logic_vector(1 downto 0);
i2c_ram_rd: in std_logic;
i2c_ram_rd_addr: in std_logic_vector(6 downto 0);
i2c_ram_rd_data: out std_logic_vector(7 downto 0);
i2c_ram_wr: in std_logic;
i2c_ram_wr_addr: in std_logic_vector(6 downto 0);
i2c_ram_wr_data: in std_logic_vector(7 downto 0);
i2c_en: in std_logic;
update: out std_logic ;
err: out std_logic;
rdy: out std_logic
);
end i2c;
architecture arch_i2c of i2c is
component altsyncram
generic (
operation_mode : string;
width_a : natural;
widthad_a : natural;
width_b : natural;
widthad_b : natural;
width_byteena_a : natural;
outdata_reg_b : string;
address_reg_b : string;
rdcontrol_reg_b : string;
read_during_write_mode_mixed_ports : string;
init_file : string
);
port
(
wren_a : in std_logic ;
clock0 : in std_logic ;
clock1 : in std_logic ;
address_a : in std_logic_vector (widthad_a-1 downto 0);
address_b : in std_logic_vector (widthad_b-1 downto 0);
rden_b : in std_logic ;
q_b : out std_logic_vector (width_b-1 downto 0);
data_a : in std_logic_vector (width_a-1 downto 0)
);
end component;
component altsyncram
generic (
operation_mode : string;
width_a : natural;
widthad_a : natural;
width_b : natural;
widthad_b : natural;
width_byteena_a : natural;
outdata_reg_b : string;
address_reg_b : string;
rdcontrol_reg_b : string;
read_during_write_mode_mixed_ports : string;
init_file : string
);
port
(
wren_a : in std_logic ;
clock0 : in std_logic ;
clock1 : in std_logic ;
address_a : in std_logic_vector (widthad_a-1 downto 0);
address_b : in std_logic_vector (widthad_b-1 downto 0);
rden_b : in std_logic ;
q_b : out std_logic_vector (width_b-1 downto 0);
data_a : in std_logic_vector (width_a-1 downto 0)
);
end component;
constant i2c_device_rd:std_logic_vector(7 downto 0):=x"a1";
constant i2c_device_wr:std_logic_vector(7 downto 0):=x"a0";
signal i2c_operate_state: std_logic_vector(7 downto 0);
signal i2c_operate_cnt : integer range 0 to 7;
signal i2c_operate_byte_nums:integer range 0 to 127;
signal i2c_operate_data: std_logic_vector(7 downto 0);
signal i2c_operate_wr: std_logic;
signal i2c_operate_wr_addr: std_logic_vector(6 downto 0);
signal i2c_operate_wr_data: std_logic_vector(7 downto 0);
signal i2c_operate_rd: std_logic;
signal i2c_operate_rd_addr: std_logic_vector(6 downto 0);
signal i2c_operate_rd_data: std_logic_vector(7 downto 0);
constant i2c_device_wr:std_logic_vector(7 downto 0):=x"a0";
signal i2c_operate_state: std_logic_vector(7 downto 0);
signal i2c_operate_cnt : integer range 0 to 7;
signal i2c_operate_byte_nums:integer range 0 to 127;
signal i2c_operate_data: std_logic_vector(7 downto 0);
signal i2c_operate_wr: std_logic;
signal i2c_operate_wr_addr: std_logic_vector(6 downto 0);
signal i2c_operate_wr_data: std_logic_vector(7 downto 0);
signal i2c_operate_rd: std_logic;
signal i2c_operate_rd_addr: std_logic_vector(6 downto 0);
signal i2c_operate_rd_data: std_logic_vector(7 downto 0);
begin
-----------filter cell data---------------------------------------
i2c_ram_rd_ins : altsyncram
generic map
(
operation_mode => "dual_port",
width_a => 8,
widthad_a => 7,
width_b => 8,
widthad_b => 7,
width_byteena_a => 1,
outdata_reg_b => "unregistered",
address_reg_b => "clock1",
rdcontrol_reg_b => "clock1",
read_during_write_mode_mixed_pORts => "old_data",
init_file =>"rx_data_ram.mif"
)
port map (
wren_a => i2c_operate_wr,
clock0 => clk,
clock1 => clk,
address_a => i2c_operate_wr_addr,
address_b => i2c_ram_rd_addr,
rden_b => i2c_ram_rd,
data_a => i2c_operate_wr_data,
q_b => i2c_ram_rd_data
);
i2c_ram_wr_ins : altsyncram
generic map
(
operation_mode => "dual_port",
width_a => 8,
widthad_a => 7,
width_b => 8,
widthad_b => 7,
width_byteena_a => 1,
outdata_reg_b => "unregistered",
address_reg_b => "clock1",
rdcontrol_reg_b => "clock1",
read_during_write_mode_mixed_pORts => "old_data",
init_file =>"rx_data_ram.mif"
)
port map (
wren_a => i2c_ram_wr,
clock0 => clk,
clock1 => clk,
address_a => i2c_ram_wr_addr,
address_b => i2c_operate_rd_addr,
rden_b => i2c_operate_rd,
data_a => i2c_ram_wr_data,
q_b => i2c_operate_rd_data
);
-----------filter cell data---------------------------------------
i2c_ram_rd_ins : altsyncram
generic map
(
operation_mode => "dual_port",
width_a => 8,
widthad_a => 7,
width_b => 8,
widthad_b => 7,
width_byteena_a => 1,
outdata_reg_b => "unregistered",
address_reg_b => "clock1",
rdcontrol_reg_b => "clock1",
read_during_write_mode_mixed_pORts => "old_data",
init_file =>"rx_data_ram.mif"
)
port map (
wren_a => i2c_operate_wr,
clock0 => clk,
clock1 => clk,
address_a => i2c_operate_wr_addr,
address_b => i2c_ram_rd_addr,
rden_b => i2c_ram_rd,
data_a => i2c_operate_wr_data,
q_b => i2c_ram_rd_data
);
i2c_ram_wr_ins : altsyncram
generic map
(
operation_mode => "dual_port",
width_a => 8,
widthad_a => 7,
width_b => 8,
widthad_b => 7,
width_byteena_a => 1,
outdata_reg_b => "unregistered",
address_reg_b => "clock1",
rdcontrol_reg_b => "clock1",
read_during_write_mode_mixed_pORts => "old_data",
init_file =>"rx_data_ram.mif"
)
port map (
wren_a => i2c_ram_wr,
clock0 => clk,
clock1 => clk,
address_a => i2c_ram_wr_addr,
address_b => i2c_operate_rd_addr,
rden_b => i2c_operate_rd,
data_a => i2c_ram_wr_data,
q_b => i2c_operate_rd_data
);
i2c_operate: process(clk,rst)
begin
if (rst='0') then
sck<='0';
sdata<='Z';
i2c_operate_wr_data<=(others=>'0');
i2c_operate_wr_addr<=(others=>'0');
i2c_operate_wr<='0';
i2c_operate_rd_addr<=(others=>'0');
i2c_operate_rd<='0';
i2c_operate_state<=(others=>'0');
update<='0';
err<='0';
rdy<='0';
elsif clk'event and clk='1' then
if (clk200k='1') then
--------------start bit --------------------
if (i2c_operate_state=x"00") then
-- if (i2c_en='1') then
if((operate_cmd="00") or (operate_cmd="10") ) then
i2c_operate_state<=x"01";
end if;
-- end if;
sck<='0';
sdata<='1';
elsif (i2c_operate_state=x"01") then
sck<='1';
i2c_operate_state<=x"02";
elsif (i2c_operate_state=x"02") then
sdata<='0';
i2c_operate_byte_nums<=0;
i2c_operate_state<=x"03";
-------------Device addre. Firt Page addr Second addr--------------------
elsif (i2c_operate_state=x"03") then
sck<='0';
if(i2c_operate_byte_nums=0) then
i2c_operate_data<=i2c_device_wr;
elsif (i2c_operate_byte_nums=1) then
i2c_operate_data<=page_addr;
elsif (i2c_operate_byte_nums=2) then
i2c_operate_data<=x"00";
end if;
i2c_operate_cnt<=0;
i2c_operate_state<=x"04";
elsif (i2c_operate_state=x"04") then
----bit data ready---
sck<='0';
sdata<=i2c_operate_data(7);
i2c_operate_data<=i2c_operate_data(6 downto 0) & '0';
i2c_operate_state<=x"05";
elsif (i2c_operate_state=x"05") then
sck<='1';
if (i2c_operate_cnt=7) then
i2c_operate_cnt<=0;
i2c_operate_state<=x"06";
else
i2c_operate_cnt<=i2c_operate_cnt+1;
i2c_operate_state<=x"04"; -----clocked data
end if;
elsif (i2c_operate_state=x"06") then
-----check eeprom ack bit---
sck<='0';
sdata<='Z';
i2c_operate_state<=x"20";
elsif (i2c_operate_state=x"20") then
sck<='1';
if (sdata='0') then
if(i2c_operate_byte_nums=2) then
i2c_operate_byte_nums<=0;
i2c_operate_state<=x"07";
i2c_operate_rd_addr<=(others=>'0');
i2c_operate_rd<='1';
else
i2c_operate_byte_nums<=i2c_operate_byte_nums+1;
i2c_operate_state<=x"03";
end if;
i2c_operate_cnt<=0;
elsif (i2c_operate_cnt=7) then
i2c_operate_cnt<=0;
-- err<='1';
------err------------------
else
i2c_operate_cnt<=i2c_operate_cnt+1;
end if;
elsif (i2c_operate_state=x"07") then
sck<='0';
if (operate_cmd="00") then ---read;
i2c_operate_state<=x"23";
elsif (operate_cmd="01") then --write;
i2c_operate_state<=x"31";
end if;
i2c_operate_rd<='0';
i2c_operate_byte_nums<=0;
elsif (i2c_operate_state=x"23") then
sck<='0';
sdata<='1';
i2c_operate_state<=x"08";
------------read start bit----------------------
elsif (i2c_operate_state=x"08") then
sck<='1';
i2c_operate_state<=x"09";
elsif (i2c_operate_state=x"09") then
sdata<='0';
i2c_operate_state<=x"0b";
------------tx device addre and control cmd------
elsif (i2c_operate_state=x"0b") then
sck<='0';
i2c_operate_data<=i2c_device_rd;
i2c_operate_state<=x"0c";
i2c_operate_cnt<=0;
elsif (i2c_operate_state=x"0c") then
sck<='0';
sdata<=i2c_operate_data(7);
i2c_operate_data<=i2c_operate_data(6 downto 0) & '0' ;
i2c_operate_state<=x"0d";
elsif (i2c_operate_state=x"0d") then
sck<='1';
if (i2c_operate_cnt=7) then
i2c_operate_cnt<=0;
i2c_operate_state<=x"0e";
else
i2c_operate_cnt<=i2c_operate_cnt+1;
i2c_operate_state<=x"0c";
end if;
elsif (i2c_operate_state=x"0e") then
sck<='0';
sdata<='Z';
i2c_operate_state<=x"21";
elsif (i2c_operate_state=x"21") then
sck<='1';
if (sdata='0') then
-- err<='1';
i2c_operate_cnt<=0;
i2c_operate_state<=x"22";
elsif (i2c_operate_cnt=7) then
i2c_operate_cnt<=0;
-- err<='1';
------err----
else
i2c_operate_cnt<=i2c_operate_cnt+1;
end if;
elsif (i2c_operate_state=x"22") then
sck<='0';
i2c_operate_state<=x"0f";
elsif (i2c_operate_state=x"0f") then
sck<='1';
i2c_operate_data<=i2c_operate_data(6 downto 0) & sdata ;
i2c_operate_wr<='0';
i2c_operate_state<=x"10";
update<='0';
elsif (i2c_operate_state=x"10") then
sck<='0';
if(i2c_operate_cnt=7) then
i2c_operate_cnt<=0;
i2c_operate_wr_data<=i2c_operate_data;
i2c_operate_wr<='1';
i2c_operate_state<=x"24";
else
i2c_operate_cnt<=i2c_operate_cnt+1;
i2c_operate_state<=x"0f";
end if;
elsif (i2c_operate_state=x"24") then
if(i2c_operate_byte_nums=127) then
i2c_operate_state<=x"13";
i2c_operate_byte_nums<=0;
i2c_operate_wr_addr<=(others=>'0');
update<='1';
sdata<='1';
else
i2c_operate_byte_nums<=i2c_operate_byte_nums+1;
i2c_operate_wr_addr<=i2c_operate_wr_addr+"0000001";
i2c_operate_state<=x"11";
sdata<='0';
end if;
--------------------tx ACK bit=zero-------------------
elsif (i2c_operate_state=x"11") then
i2c_operate_wr<='0';
sck<='1';
i2c_operate_state<=x"12";
elsif (i2c_operate_state=x"12") then
sck<='0';
sdata<='Z';
i2c_operate_state<=x"0f"; ----------receive next data
---------------------tx NO ACK bit=one------------------
elsif (i2c_operate_state=x"13") then
update<='0';
i2c_operate_wr<='0';
sck<='1';
i2c_operate_state<=x"14";
elsif (i2c_operate_state=x"14") then
sck<='0';
sdata<='Z';
i2c_operate_state<=x"15";
---------------------write operate------------------------
elsif (i2c_operate_state=x"31") then
sck<='0';
i2c_operate_data<=i2c_operate_rd_data;
-- if (i2c_operate_rd_data="00001111") then
-- err<='1';
-- end if;
i2c_operate_cnt<=0;
i2c_operate_state<=x"32";
elsif (i2c_operate_state=x"32") then
sck<='0';
sdata<=i2c_operate_data(7);
i2c_operate_data<=i2c_operate_data(6 downto 0) & '0';
i2c_operate_state<=x"33";
i2c_operate_rd<='0';
elsif (i2c_operate_state=x"33") then
sck<='1';
if (i2c_operate_cnt=7) then
i2c_operate_cnt<=0;
i2c_operate_state<=x"34";
if (i2c_operate_rd_addr="1111111") then
i2c_operate_rd_addr<=(others=>'0');
else
i2c_operate_rd_addr<=i2c_operate_rd_addr+"0000001";
end if;
i2c_operate_rd<='1';
else
i2c_operate_cnt<=i2c_operate_cnt+1;
i2c_operate_state<=x"32";
end if;
elsif (i2c_operate_state=x"34") then
i2c_operate_rd<='0';
sck<='0';
sdata<='Z';
i2c_operate_state<=x"35";
elsif (i2c_operate_state=x"35") then
sck<='1';
if (sdata='0') then
i2c_operate_cnt<=0;
if ( i2c_operate_byte_nums=127) then
i2c_operate_byte_nums<=0;
i2c_operate_state<=x"15"; -----stop bit
-- err<='1';
else
i2c_operate_byte_nums<=i2c_operate_byte_nums+1;
i2c_operate_state<=x"31";
end if;
elsif (i2c_operate_cnt=7) then
i2c_operate_cnt<=0;
-- err<='1';
----err---
else
i2c_operate_cnt<=i2c_operate_cnt+1;
end if;
--------------------stop bit -------------------------------------
elsif (i2c_operate_state=x"15") then
sdata<='0';
sck<='0';
rdy<='1';
i2c_operate_state<=x"16";
elsif (i2c_operate_state=x"16") then
sck<='1';
i2c_operate_state<=x"17";
elsif (i2c_operate_state=x"17") then
sdata<='1';
i2c_operate_state<=x"18";
elsif (i2c_operate_state=x"18") then
sck<='0';
i2c_operate_state<=x"00";
rdy<='0';
-- err<='1';
else
i2c_operate_data<=(others=>'0');
i2c_operate_cnt<=0;
i2c_operate_byte_nums<=0;
i2c_operate_state<=x"00";
sck<='1';
sdata<='Z';
end if;
end if;
end if;
end process i2c_operate;
end arch_i2c;
begin
if (rst='0') then
sck<='0';
sdata<='Z';
i2c_operate_wr_data<=(others=>'0');
i2c_operate_wr_addr<=(others=>'0');
i2c_operate_wr<='0';
i2c_operate_rd_addr<=(others=>'0');
i2c_operate_rd<='0';
i2c_operate_state<=(others=>'0');
update<='0';
err<='0';
rdy<='0';
elsif clk'event and clk='1' then
if (clk200k='1') then
--------------start bit --------------------
if (i2c_operate_state=x"00") then
-- if (i2c_en='1') then
if((operate_cmd="00") or (operate_cmd="10") ) then
i2c_operate_state<=x"01";
end if;
-- end if;
sck<='0';
sdata<='1';
elsif (i2c_operate_state=x"01") then
sck<='1';
i2c_operate_state<=x"02";
elsif (i2c_operate_state=x"02") then
sdata<='0';
i2c_operate_byte_nums<=0;
i2c_operate_state<=x"03";
-------------Device addre. Firt Page addr Second addr--------------------
elsif (i2c_operate_state=x"03") then
sck<='0';
if(i2c_operate_byte_nums=0) then
i2c_operate_data<=i2c_device_wr;
elsif (i2c_operate_byte_nums=1) then
i2c_operate_data<=page_addr;
elsif (i2c_operate_byte_nums=2) then
i2c_operate_data<=x"00";
end if;
i2c_operate_cnt<=0;
i2c_operate_state<=x"04";
elsif (i2c_operate_state=x"04") then
----bit data ready---
sck<='0';
sdata<=i2c_operate_data(7);
i2c_operate_data<=i2c_operate_data(6 downto 0) & '0';
i2c_operate_state<=x"05";
elsif (i2c_operate_state=x"05") then
sck<='1';
if (i2c_operate_cnt=7) then
i2c_operate_cnt<=0;
i2c_operate_state<=x"06";
else
i2c_operate_cnt<=i2c_operate_cnt+1;
i2c_operate_state<=x"04"; -----clocked data
end if;
elsif (i2c_operate_state=x"06") then
-----check eeprom ack bit---
sck<='0';
sdata<='Z';
i2c_operate_state<=x"20";
elsif (i2c_operate_state=x"20") then
sck<='1';
if (sdata='0') then
if(i2c_operate_byte_nums=2) then
i2c_operate_byte_nums<=0;
i2c_operate_state<=x"07";
i2c_operate_rd_addr<=(others=>'0');
i2c_operate_rd<='1';
else
i2c_operate_byte_nums<=i2c_operate_byte_nums+1;
i2c_operate_state<=x"03";
end if;
i2c_operate_cnt<=0;
elsif (i2c_operate_cnt=7) then
i2c_operate_cnt<=0;
-- err<='1';
------err------------------
else
i2c_operate_cnt<=i2c_operate_cnt+1;
end if;
elsif (i2c_operate_state=x"07") then
sck<='0';
if (operate_cmd="00") then ---read;
i2c_operate_state<=x"23";
elsif (operate_cmd="01") then --write;
i2c_operate_state<=x"31";
end if;
i2c_operate_rd<='0';
i2c_operate_byte_nums<=0;
elsif (i2c_operate_state=x"23") then
sck<='0';
sdata<='1';
i2c_operate_state<=x"08";
------------read start bit----------------------
elsif (i2c_operate_state=x"08") then
sck<='1';
i2c_operate_state<=x"09";
elsif (i2c_operate_state=x"09") then
sdata<='0';
i2c_operate_state<=x"0b";
------------tx device addre and control cmd------
elsif (i2c_operate_state=x"0b") then
sck<='0';
i2c_operate_data<=i2c_device_rd;
i2c_operate_state<=x"0c";
i2c_operate_cnt<=0;
elsif (i2c_operate_state=x"0c") then
sck<='0';
sdata<=i2c_operate_data(7);
i2c_operate_data<=i2c_operate_data(6 downto 0) & '0' ;
i2c_operate_state<=x"0d";
elsif (i2c_operate_state=x"0d") then
sck<='1';
if (i2c_operate_cnt=7) then
i2c_operate_cnt<=0;
i2c_operate_state<=x"0e";
else
i2c_operate_cnt<=i2c_operate_cnt+1;
i2c_operate_state<=x"0c";
end if;
elsif (i2c_operate_state=x"0e") then
sck<='0';
sdata<='Z';
i2c_operate_state<=x"21";
elsif (i2c_operate_state=x"21") then
sck<='1';
if (sdata='0') then
-- err<='1';
i2c_operate_cnt<=0;
i2c_operate_state<=x"22";
elsif (i2c_operate_cnt=7) then
i2c_operate_cnt<=0;
-- err<='1';
------err----
else
i2c_operate_cnt<=i2c_operate_cnt+1;
end if;
elsif (i2c_operate_state=x"22") then
sck<='0';
i2c_operate_state<=x"0f";
elsif (i2c_operate_state=x"0f") then
sck<='1';
i2c_operate_data<=i2c_operate_data(6 downto 0) & sdata ;
i2c_operate_wr<='0';
i2c_operate_state<=x"10";
update<='0';
elsif (i2c_operate_state=x"10") then
sck<='0';
if(i2c_operate_cnt=7) then
i2c_operate_cnt<=0;
i2c_operate_wr_data<=i2c_operate_data;
i2c_operate_wr<='1';
i2c_operate_state<=x"24";
else
i2c_operate_cnt<=i2c_operate_cnt+1;
i2c_operate_state<=x"0f";
end if;
elsif (i2c_operate_state=x"24") then
if(i2c_operate_byte_nums=127) then
i2c_operate_state<=x"13";
i2c_operate_byte_nums<=0;
i2c_operate_wr_addr<=(others=>'0');
update<='1';
sdata<='1';
else
i2c_operate_byte_nums<=i2c_operate_byte_nums+1;
i2c_operate_wr_addr<=i2c_operate_wr_addr+"0000001";
i2c_operate_state<=x"11";
sdata<='0';
end if;
--------------------tx ACK bit=zero-------------------
elsif (i2c_operate_state=x"11") then
i2c_operate_wr<='0';
sck<='1';
i2c_operate_state<=x"12";
elsif (i2c_operate_state=x"12") then
sck<='0';
sdata<='Z';
i2c_operate_state<=x"0f"; ----------receive next data
---------------------tx NO ACK bit=one------------------
elsif (i2c_operate_state=x"13") then
update<='0';
i2c_operate_wr<='0';
sck<='1';
i2c_operate_state<=x"14";
elsif (i2c_operate_state=x"14") then
sck<='0';
sdata<='Z';
i2c_operate_state<=x"15";
---------------------write operate------------------------
elsif (i2c_operate_state=x"31") then
sck<='0';
i2c_operate_data<=i2c_operate_rd_data;
-- if (i2c_operate_rd_data="00001111") then
-- err<='1';
-- end if;
i2c_operate_cnt<=0;
i2c_operate_state<=x"32";
elsif (i2c_operate_state=x"32") then
sck<='0';
sdata<=i2c_operate_data(7);
i2c_operate_data<=i2c_operate_data(6 downto 0) & '0';
i2c_operate_state<=x"33";
i2c_operate_rd<='0';
elsif (i2c_operate_state=x"33") then
sck<='1';
if (i2c_operate_cnt=7) then
i2c_operate_cnt<=0;
i2c_operate_state<=x"34";
if (i2c_operate_rd_addr="1111111") then
i2c_operate_rd_addr<=(others=>'0');
else
i2c_operate_rd_addr<=i2c_operate_rd_addr+"0000001";
end if;
i2c_operate_rd<='1';
else
i2c_operate_cnt<=i2c_operate_cnt+1;
i2c_operate_state<=x"32";
end if;
elsif (i2c_operate_state=x"34") then
i2c_operate_rd<='0';
sck<='0';
sdata<='Z';
i2c_operate_state<=x"35";
elsif (i2c_operate_state=x"35") then
sck<='1';
if (sdata='0') then
i2c_operate_cnt<=0;
if ( i2c_operate_byte_nums=127) then
i2c_operate_byte_nums<=0;
i2c_operate_state<=x"15"; -----stop bit
-- err<='1';
else
i2c_operate_byte_nums<=i2c_operate_byte_nums+1;
i2c_operate_state<=x"31";
end if;
elsif (i2c_operate_cnt=7) then
i2c_operate_cnt<=0;
-- err<='1';
----err---
else
i2c_operate_cnt<=i2c_operate_cnt+1;
end if;
--------------------stop bit -------------------------------------
elsif (i2c_operate_state=x"15") then
sdata<='0';
sck<='0';
rdy<='1';
i2c_operate_state<=x"16";
elsif (i2c_operate_state=x"16") then
sck<='1';
i2c_operate_state<=x"17";
elsif (i2c_operate_state=x"17") then
sdata<='1';
i2c_operate_state<=x"18";
elsif (i2c_operate_state=x"18") then
sck<='0';
i2c_operate_state<=x"00";
rdy<='0';
-- err<='1';
else
i2c_operate_data<=(others=>'0');
i2c_operate_cnt<=0;
i2c_operate_byte_nums<=0;
i2c_operate_state<=x"00";
sck<='1';
sdata<='Z';
end if;
end if;
end if;
end process i2c_operate;
end arch_i2c;