I2C Nacking Address unless sample project is used

Tip / Sign in to post questions, reply, level up, and achieve exciting badges. Know more

cross mob
lock attach
Attachments are accessible only for community members.
KevinE
Level 3
Level 3
10 sign-ins 10 replies posted 5 sign-ins

I am working with CY8CKIT-059 and need help discerning the differences between my custom project and one of the projects provided under "Find code example..." dialogue. 

I have a device that is acting as an I2C Master and is connected to the CY8CKIT-059 acting as an I2C slave. 

If I use the sample project: "DelSig_I2CS" I can  successfully perform a Write operation from the external device and the CY8CKIT-059 running the sample project can successfully ACK the address and receive the 2 bytes being written to it.  No issues here, I2C slave is working as expected. 

However when I generate a new project, and reuse the code from the sample I2C project and set up the I2C peripheral in the same way the sample project has it configured, the CY8CKIT-059 NACKs the address and no data is received. 

Perhaps I am not setting up the custom project in the same way, but I think I have checked everything. 

What are some probable causes as to why the CY8CKIT-059 would NACK when being addressed?

I will attach both projects: DelSig_I2CS is working just fine with no issues and "Roadrunner2_Eval which I believe is setup in the same way. 

In general, both projects have the same code:

At this point Delays are being used to have a line of code to attach breakpoints to. 

I2CS_Start();

/* Set up slave read data buffer */
I2CS_SlaveInitReadBuf((uint8 *) sample_segment, RD_BUFFER_SIZE);
I2CS_SlaveInitWriteBuf((uint8 *) sample_segment, RD_BUFFER_SIZE);

/* Enable global interrupts - needed for I2C operation */
CyGlobalIntEnable;

Enter Main Loop:

/* Check if the slave buffer has been Written */
if(I2CM_SlaveStatus() & I2CM_SSTAT_WR_CMPLT)
{
     byteCount = I2CM_SlaveGetWriteBufSize();
     I2CM_SlaveClearWriteStatus();
     I2CM_SlaveClearWriteBuf();

/* If both bytes of the read buffer have been read */
if(byteCount == I2C_BUFFER_SIZE)
{
     CyDelay(1);
     return 1;
}
else /* Wrong number of bytes read - place error handling code here */
{
     CyDelay(1);
}


/* Check if the slave buffer has been read */
if(I2CM_SlaveStatus() & I2CM_SSTAT_RD_CMPLT)
{
     byteCount = I2CM_SlaveGetReadBufSize();
     I2CM_SlaveClearReadStatus();
     I2CM_SlaveClearReadBuf();

/* If both bytes of the read buffer have been read */
if(byteCount == I2C_BUFFER_SIZE)
{
     CyDelay(1);
     return 1;
}
else /* Wrong number of bytes read - place error handling code here */
{
     CyDelay(1);
}




 

0 Likes
1 Solution
KevinE
Level 3
Level 3
10 sign-ins 10 replies posted 5 sign-ins

So oddly enough, I think I may have found the issue. 

Looking at the clock scheme, I had arbitrarily set the master clock to be 67MHz

In doing so, I noticed the I2C schematic configuration shows 99.7 kbps when I have the speed set to 100 under data rate. 

KevinE_0-1639089680191.png

 


I messed around with the clock speed a bit and finally ended up on 64MHz

Now when I look at the I2C schematic configuration, setting 100 to the data rate allows the actual data rate to read at 100. 

KevinE_1-1639089749403.png



And this appears to have solved my issue. My guess is that when using "odd" clock values, it causes the I2C peripheral to have a "non - standard" speed and maybe even lends to the need for the extended ACK wait time. 

View solution in original post

0 Likes
8 Replies
BiBi_1928986
Level 7
Level 7
First comment on blog 500 replies posted 250 replies posted

Hello.

I've not looked at your code.  But, just a quick check...

Did you change the slave address to something different from the code example?

If yes, keep in mind, the slave address has to be between 0-127 decimal.  And the I2C 7-bit address used with API's has to match the address used in the I2C component in the schematic.  Otherwise, you will get a bad address NAK.

0 Likes

Yes, I have kept the same default slave address between both projects - 0x08 or decimal 8

0 Likes
KevinE
Level 3
Level 3
10 sign-ins 10 replies posted 5 sign-ins

Using my trusty 12 dollar logic analyzer I can produce the following results using the provided projects

The image below shows the Cy8C Kit properly ACKing the address and receiving 2 bytes  - this is the result of using the DelSig_I2CS sample project.

 

KevinE_0-1638919954762.png

 

The following image is trying to use the custom project "Roadrunner2"

KevinE_1-1638920078630.png

 

 

0 Likes

Hi.

Great logic captures.

It would appear KIT-059 PSoC requires more time to put it's response onto SDA line, based on the example that works.

Is there anyway for Raodrunner2 to extend it's wait-for ack time?
Or, is there something in PSoC slave that needs to be sped up?

There's an excellent 5LP code example written by Motoo, using KIT-059.  This might shed some light.
MCU Tester, a Swiss Army Knife for PSoC (CY8CKIT-0... - Infineon Developer Community

BTW, what I2C sniffer are you using?

edit:  You could try slowing down the I2C transfer rate from Roadrunner2.  If I2C is running 400kbps, slow it down to 100kbps.

0 Likes

Hello, thank you for your input, that's an interesting point about the wait time for ack. 

I have been looking through the generated code from Psoc creator, namely the interrupt source file (In my case: I2CM_INT.c). I am not able to find any thing related to ACK wait time. I will continue looking but if you have any input on that in the meantime, this would be highly appreciated. 

Does the Psoc5 give access to the actual timing and operation of address decoding? I see in the schematic for I2C there is an option for Hardware or Software address decoding. Selecting either of these with no other software modification does not correct the issue. 

One important note to make is:

 I set a breakpoint inside the I2C interrupt handler for the KIT-059 PSoC I2C slave and then issued an I2C write  from the external I2C Master.

I did this under the  "DelSig_I2CS" (working) project and the breakpoint was reached (Expected)

I also tried to do this with the "Roadrunner2" project and the break point is never reached. 

This leads me to believe that I am either not looking in the right place, or this level (address decode and ACK wait time) is not exposed to the developer. 

I'm also going to checkout the code example provided. This seems like a great tool and perhaps another way to solve the issue I'm having. Either way, this is really useful, thanks!

 

Lastly, you might not believe me, but it actually lends to the idea you proposed about the ACK wait time. 

The working project (DelSig_I2CS) did not work until I changed the I2C Slave in the schematic from it's default 100kbps to 400kbps. 

usually reduction in speed seems to make things work better, but in this case, setting the speed higher helped it. Unfortunately I was not able to reproduce this in the Roadrunner project. 



The sniffer I use actually supports more than I2C, you should definitely check it out. It works with Salae's free logic GUI

Sniffer: https://www.amazon.com/HiLetgo-Analyzer-Ferrite-Channel-Arduino/dp/B077LSG5P2/ref=sr_1_10?crid=14QTJ...


GUI: https://support.saleae.com/logic-software

 

 

 

0 Likes
KevinE
Level 3
Level 3
10 sign-ins 10 replies posted 5 sign-ins

So oddly enough, I think I may have found the issue. 

Looking at the clock scheme, I had arbitrarily set the master clock to be 67MHz

In doing so, I noticed the I2C schematic configuration shows 99.7 kbps when I have the speed set to 100 under data rate. 

KevinE_0-1639089680191.png

 


I messed around with the clock speed a bit and finally ended up on 64MHz

Now when I look at the I2C schematic configuration, setting 100 to the data rate allows the actual data rate to read at 100. 

KevinE_1-1639089749403.png



And this appears to have solved my issue. My guess is that when using "odd" clock values, it causes the I2C peripheral to have a "non - standard" speed and maybe even lends to the need for the extended ACK wait time. 

0 Likes

Hello.

Good to see you got it figured out.  And thanks for the tip on your logic probe.  Looks pretty useful.

Good luck with your project.

0 Likes
AlenAn14
Moderator
Moderator
Moderator
500 replies posted 100 solutions authored 250 replies posted

Hi @KevinE ,

Glad that your issue is resolved and thank you for contributing this solution to the community.

Please continue to use our products and feel free to post any queries you may have on the same in the community and we will be happy to help.

Regards
Alen

0 Likes