2 Replies Latest reply on Aug 5, 2014 12:33 AM by user_343349849

    SPI code locks attempting to write byte

    user_343349849

      Hi Guys,

         

      I am having some trouble with the SPI. I have looked through the site and found some documents but not a worked example.

         

      The code is ported across from a Microchip project. The Devie is PSOC 5LP and the memory is FM25W256-G.

         

      The code runs until the second line in the ReadByte routine and appears to hang. I have the SPI component set to Mode 0 and 4MHz using internal clock source. Does my code below look correct? Or is there something I need to enable or initialise? Thanks in advance for your help.

         

       

         

      #define WREN 0x06

         

      #define MEMWRITE 0x02

         

      #define MEMREAD 0x03

         

       

         

      unsigned char Muted;

         

      unsigned char testbyte;

         

       

         

      void SendByte(unsigned short MemAddress, unsigned char MemData)  //FM25W256-G Device

         

      {

         

        MEM_EN_Write(false);    //Enable Write function

         

        SPI_WriteByte(WREN);   

         

        MEM_EN_Write(true);

         

        MEM_EN_Write(false);   //Send Write command

         

        SPI_WriteByte(MEMWRITE);  

         

        SPI_WriteByte(MemAddress >> 8);  //Send 16-bit Address, MSB first

         

        SPI_WriteByte(MemAddress);

         

        SPI_WriteByte(MemData);  //Send Data byte

         

        MEM_EN_Write(true);

         

      }

         

       

         

      unsigned char ReadByte(unsigned short MemAddress)

         

      {

         

        unsigned char i;

         

        

         

        MEM_EN_Write(false);   //Send Read Command

         

        SPI_WriteByte(MEMREAD);   //************************ LOCKS UP on this line ********************

         

        SPI_WriteByte(MemAddress >> 8);  //Read Address, MSB fist

         

        SPI_WriteByte(MemAddress);

         

        i = SPI_ReadByte();   //Read the byte ????

         

        MEM_EN_Write(true);

         

        return i;

         

      }

         

       

         

      void init(void)

         

      {

         

          CyGlobalIntEnable; 

         

          PWM_Start();

         

          SPI_Init();

         

      }

         

       

         

      int main()

         

         

        init();

         

          SendByte(0x01, 0x33);

         

          testbyte = ReadByte(0x01);  //Test byte should = 0x33

         

         for(;;) {}

        • 1. Re: SPI code locks attempting to write byte
          user_343349849

           I have played around a bit more, read a couple of documents but still having trouble understanding how to get this working.

             

          My changed code ensures that the last byte was sent from the buffer before attempting to send the next one. This time the code does not hang anywhere but I keep reading back "0" on the RX buffer.

             

          I am assuming that I put a byte into the TX buf and it sends it, while sending it shifts any received data into RX buf and once done the SPI_DONE flag is set and I can go to next byte???

             

          There seem to be very few worked example of how to use the component in this manner. Tomorrow I will put a logic analyser on the pins and see what the hardware is doing to help narrow it doen to hardware or software issue.

             

          I am hoping someone would not mind taking a quick look at the code below and let me know if there is anything glaringly obvious (stupid) I have done or grossly misunderstood. Thanks again

             

          unsigned char Send_SPI(unsigned char sData)

             

          {

             

             SPI_WriteTxData(sData); 

             

             while(!(SPI_ReadTxStatus() & SPI_STS_SPI_DONE));

             

             return SPI_ReadRxData();

             

          }

             

           

             

          void PutMemByte(unsigned short MemAddress, unsigned char MemData)  //FM25W256-G Device

             

          {

             

            MEM_EN_Write(false);      //Enable Write

             

            Send_SPI(WREN);  

             

            MEM_EN_Write(true);

             

           

             

            MEM_EN_Write(false);

             

            Send_SPI(MEMWRITE);  

             

            Send_SPI(MemAddress >> 8);

             

            Send_SPI(MemAddress);

             

            Send_SPI(MemData);

             

            MEM_EN_Write(true);

             

          }

             

           

             

          unsigned char GetMemByte(unsigned short MemAddress)

             

          {

             

            unsigned char i;

             

            

             

            MEM_EN_Write(false);

             

            Send_SPI(MEMREAD);   //0x03

             

            Send_SPI(MemAddress >> 8);

             

            Send_SPI(MemAddress);

             

            i = Send_SPI(0);

             

            MEM_EN_Write(true);

             

            return i;

             

          }

             

           

             

          void init(void)

             

          {

             

              CyGlobalIntEnable; 

             

              PWM_Start();

             

              SPI_Start();

             

              SPI_ClearRxBuffer();

             

              SPI_ClearTxBuffer();

             

           }

             

           

             

          int main()

             

             

            init();

             

            for(;;)

             

            {

             

              PutMemByte(0x01, 0x33);

             

              testbyte = GetMemByte(0x01);  //Returns 0, expecting 0x33

          • 2. Re: SPI code locks attempting to write byte
            user_343349849

             It seems there is so much information on this site but when I attempt to do something specific, I have trouble finding the exact information I need. Today I checked the hardware and can see the write signal is working correctly but not reply fromt he IC, I tried a second hardware target and exactly the same thing. If I set the MISO pin to pull up resistor, I get nothing at all returned, If I leave high impedance then I see glitches in the MISO line. The MOSI line, clock and CS are all ok (I software select CS).

               

            It is as if the PSOC is pulling the MISO up strong when the IC wants to send data.The datasheet talks about API functions Write_TXData() but any examples I found use WriteByte (which I used as I assume it writes directly to the SPI register instead of the buffer? Not sure what this does really. The module should be shifting bits out MOSI and back into MISO.

               

            Attached is copy of my current code, waveforms attached.

               

             

               

            void PutMemByte(unsigned short MemAddress, unsigned char MemData)  //FM25W256-G Device

               

            {

               

              MEM_EN_Write(false);      //Enable Write

               

              SPI_WriteByte(WREN);  

               

              while(!(SPI_ReadTxStatus() & SPI_STS_SPI_DONE));

               

              MEM_EN_Write(true);

               

             

               

              MEM_EN_Write(false);

               

              SPI_WriteByte(MEMWRITE);  

               

              SPI_WriteByte(MemAddress >> 8);

               

              SPI_WriteByte(MemAddress);

               

              SPI_WriteByte(MemData);

               

              while(!(SPI_ReadTxStatus() & SPI_STS_SPI_DONE));

               

              MEM_EN_Write(true);

               

            }

               

             

               

            unsigned char GetMemByte(unsigned short MemAddress)

               

            {

               

              unsigned char i;

               

                

               

              MEM_EN_Write(false);

               

              SPI_WriteByte(MEMREAD);   //0x03

               

              SPI_WriteByte(MemAddress >> 8);

               

              SPI_WriteByte(MemAddress);

               

              while(!(SPI_ReadTxStatus() & SPI_STS_SPI_DONE));

               

              i = SPI_ReadByte();

               

              MEM_EN_Write(true);

               

              return i;

               

            }

               

             

               

            void init(void)

               

            {

               

                RTC_EN_Write(true);

               

                MEM_EN_Write(true);

               

                CyGlobalIntEnable; 

               

                PWM_Start();

               

                SPI_Start();

               

                SPI_ClearRxBuffer();

               

                SPI_ClearTxBuffer();

               

                CyDelay(100);

               

             }

               

             

               

            int main()

               

               

              init();

               

              for(;;)

               

              {

               

                PutMemByte(0x01,0x33);

               

                testbyte = GetMemByte(0x01);

               

                CyDelay(1); 

               

              }

               

            }