0
\$\begingroup\$

I want to write 512KByte data on SRAM(IS61/64WV512).I'm using spartan6 lx9 FPGA. In the program routine, the initial step involves writing all the data. Subsequently, upon completion of the writing process, the state transitions to reading. For write state I used a known data stream(AA, BB, CC, DD) to track and validate the code.

The problem according to ChipScope result is, the reading state doesn't work correctly, as the expected data is not being read(always is DD). I'm using 50mhz clock in my design. during reading state I considered an excessive state to put more time for reading but it wasn't helpful. I've put the relevant part here.

note1: The DATA_SRAM is IO bus(IO0-IO7)

note2: sram_datasheet link

note3: s2f means : sram to fpga, f2s is fpga 2 sram

enter image description here

SRAM_READ_WRITE_PROC:process(CLK)
    begin
            if rising_edge(CLK) then
            
            case state_sram_sig is
                when IDLE =>
                    -- Check if writing process should start
                    read_sram_state_status <= "0000";
                    if start_pixel_capturing_sig = '1'  then
                        rw_sig <= '0';   -- Set to WRITE mode
                        state_sram_sig <= WRITE0;  -- Transition to WRITE state
                    end if;
                    
                when WRITE0 =>
                    -- Perform writing process
                    read_sram_state_status <= "0001";
                    we_to_sram_sig <= '0';
                    oe_to_sram_sig <= '1';
                    ce_to_sram_sig <= '0';
                    
                    whole_data_p0  <= X"AA";
                    whole_data_p1  <= X"BB";
                    whole_data_p2  <= X"CC";
                    whole_data_p3  <= X"DD";
                    rw_sig <= '0';
                    
                    
                    ADDRESS_SRAM <= std_logic_vector(address_input_sig);
                    
                    DATA_SRAM    <= data_f2s_sig ;

                    if address_input_sig = X"4" then
                            state_sram_sig <= READ0;
                            address_input_sig_4_read <= (others=>'0');
                            address_input_sig <= (others=>'0');
                            rw_sig <= '1';
                    end if;
                    

                    if cnt = 6 then
                        -- Write data to SRAM at current address

                        address_input_sig <= address_input_sig;
                        we_to_sram_sig <= '0';
                        oe_to_sram_sig <= '1';
                        ce_to_sram_sig <= '0';
                        
                    elsif cnt = 0 then
                        data_f2s_sig <= whole_data_p0;
                        address_input_sig <= address_input_sig + 1;
                        we_to_sram_sig <= '0';
                        oe_to_sram_sig <= '1';
                        ce_to_sram_sig <= '0';
                        DATA_SRAM    <= data_f2s_sig ;
                        ADDRESS_SRAM <= std_logic_vector(address_input_sig);
                        --state_sram_sig <= READ0;
                        --address_input_sig_4_read <= address_input_sig;
                        
                    elsif cnt = 1 then
                        data_f2s_sig <= whole_data_p1;
                        address_input_sig <= address_input_sig + 1;
                        we_to_sram_sig <= '0';
                        oe_to_sram_sig <= '1';
                        ce_to_sram_sig <= '0';
                        DATA_SRAM    <= data_f2s_sig ;
                        ADDRESS_SRAM <= std_logic_vector(address_input_sig);
                        --state_sram_sig <= READ0;
                        --address_input_sig_4_read <= address_input_sig;
                        
                    elsif cnt = 2 then
                        data_f2s_sig <= whole_data_p2;
                        address_input_sig <= address_input_sig + 1;
                        we_to_sram_sig <= '0';
                        oe_to_sram_sig <= '1';
                        ce_to_sram_sig <= '0';
                        DATA_SRAM    <= data_f2s_sig ;
                        ADDRESS_SRAM <= std_logic_vector(address_input_sig);

                        
                    elsif cnt = 3 then
                        data_f2s_sig <= whole_data_p3;
                        address_input_sig <= address_input_sig + 1;
                        we_to_sram_sig <= '0';
                        oe_to_sram_sig <= '1';
                        ce_to_sram_sig <= '0';
                        DATA_SRAM    <= data_f2s_sig ;
                        ADDRESS_SRAM <= std_logic_vector(address_input_sig);
                        

                    else
                        address_input_sig <= address_input_sig;
                        whole_data_p0 <= whole_data_p0;
                        whole_data_p1 <= whole_data_p1;
                        whole_data_p2 <= whole_data_p2;
                        whole_data_p3 <= whole_data_p3;

                        we_to_sram_sig <= ce_to_sram_sig;
                        oe_to_sram_sig <= oe_to_sram_sig;
                        ce_to_sram_sig <= we_to_sram_sig;
                    end if;

                when READ0 =>
                    -- Perform reading process
                    read_sram_state_status <= "0010";

                    we_to_sram_sig <= '1';
                    oe_to_sram_sig <= '0';
                    ce_to_sram_sig <= '0';
                    rw_sig <= '1';
                    
                    if address_input_sig_4_read = X"4" then
                        state_sram_sig <= WRITE0;  -- Transition to IDLE state after reading
                        address_input_sig <= (others=>'0');
                        address_input_sig_4_read <= (others=>'0');
                        rw_sig <= '0';
                    else
                        state_sram_sig    <= WAIT0;
                    end if;                     

                    
                when WAIT0 =>


                    we_to_sram_sig <= '1';
                    oe_to_sram_sig <= '0';
                    ce_to_sram_sig <= '0';
                    
                    data_s2f_sig <= DATA_SRAM;
                    read_sram_state_status <= "0100";
                    state_sram_sig    <= READ0;
                    ADDRESS_SRAM <= std_logic_vector(address_input_sig_4_read);
                    address_input_sig_4_read <= address_input_sig_4_read+ 1;

                    
                when WAIT1 =>
                    read_sram_state_status <= "1000";
                    if address_input_sig_4_read = X"3FFFF" then
                        state_sram_sig <= WRITE0;  -- Transition to IDLE state after reading
                        address_input_sig <= (others=>'0');
                        address_input_sig_4_read <= (others=>'0');
                    else
                        state_sram_sig    <= READ0;
                    end if;
            end case;
        end if;

end process;
\$\endgroup\$
5
  • 1
    \$\begingroup\$ Can you edit the question to clarify what you mean by the reading state doesn't work correctly. Is it that the expected data isn't read from the SRAM, or something else? Also, is the DATA_SRAM variable directly used to connect to the I/O0 to I/O7 pins of the SRAM or is their some intermediate buffering? From the posted VHDL I can't see how the I/O0 to I/O7 pins will be driven as outputs during a SRAM write, and then changed to be inputs during a SRAM read. \$\endgroup\$ Commented May 12 at 15:09
  • \$\begingroup\$ Please clarify your specific problem or provide additional details to highlight exactly what you need. As it's currently written, it's hard to tell exactly what you're asking. \$\endgroup\$
    – Community Bot
    Commented May 12 at 18:57
  • \$\begingroup\$ @Chester Gillon thanks for your help, Yes, in read mode, I always see the same value, as depicted in this example (DD). Also, you're right, DATA_SRAM represents the SRAM IO bus. \$\endgroup\$ Commented May 13 at 5:15
  • \$\begingroup\$ Please edit your question to provide a link to the data sheet of the SRAM. It looks wrong to me to keep /WE enabled all the time, while address and data change. \$\endgroup\$ Commented May 13 at 5:30
  • \$\begingroup\$ datasheet link added. \$\endgroup\$ Commented May 13 at 5:48

1 Answer 1

2
\$\begingroup\$

The SRAM does not work like you use it. You need to end the write cycle for each word you write.

See the data sheet pages 7 to 9. During the write cycle no change in the address is expected. Notice \$t_{AW}\$ and \$t_{SD}\$, too. Apparently the data write is triggered by the edge at the end of the write cycle.

In contrast, you can change the address in read cycles while /CE and /OE are active, according to the figure on page 6 ("READ CYCLE NO. 1").

Unfortunately this does not explain why you read 0xDD from all words. But since you work outside the specification, undefined things happen.

\$\endgroup\$
1
  • \$\begingroup\$ Thanks for the reply. You're right; I used two clock cycles for each byte to read and write: one clock cycle for enabling and one clock cycle for disabling and getting data. \$\endgroup\$ Commented May 19 at 8:11

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.