Problem with I2C Master

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

cross mob
Anonymous
Not applicable

Hello,

   

I have some trouble in I2C. My I2C_I2CMasterSendStart() returns I2C_I2C_MSTR_ERR_LB_NAK. According to the description of the datasheet, this constant indicates "Last byte was NAKed". I don't know how to solve this problem. Can you help me?

   

My I2C master is PSoC 4 BLE and slave is MAX30100(here is datasheet link, https://www.maximintegrated.com/en/products/analog/sensors-and-sensor-interface/MAX30100.html)

   

Here is code that I try to read temperature value:

   

        static uint16 temp1,temp2;
        static double temp = 30;        
        
        // Mode Configuration
        I2C_I2CMasterSendStart(0xae,I2C_I2C_WRITE_XFER_MODE); // MAX30100 WRITE ADDRESS is 0xae        
        I2C_I2CMasterWriteByte(0x06);         //Mode Configuration's register address is 0x06       
        I2C_I2CMasterWriteByte(0x0a);         // the value I write
        I2C_I2CMasterSendStop();
        
        // wait a momment
        CyDelay(20);
        
        // read integer value of temperature
        I2C_I2CMasterSendStart(0xae,I2C_I2C_WRITE_XFER_MODE);
        I2C_I2CMasterWriteByte(0x16);        //Integer Value's reg_addr is 0x16
        I2C_I2CMasterSendRestart(0xaf,I2C_I2C_READ_XFER_MODE); //MAX30100 READ ADDRESS is 0xaf
        temp1 = I2C_I2CMasterReadByte(I2C_I2C_NAK_DATA);    // read integer value
        I2C_I2CMasterSendStop();   

   

        
        // read  fraction value of temperature
        I2C_I2CMasterSendStart(0xae,I2C_I2C_WRITE_XFER_MODE); 
        I2C_I2CMasterWriteByte(0x17);       //Fraction Value's reg_addr is 0x17
        I2C_I2CMasterSendRestart(0xaf,I2C_I2C_READ_XFER_MODE);
        temp2 = I2C_I2CMasterReadByte(I2C_I2C_NAK_DATA);
        I2C_I2CMasterSendStop();
  
        temp = temp1 + (temp2 / 100);

   

        CyDelay(100);

   

 

   

 

   

Any guidance would be greatly appreciated! Thank you.

0 Likes
1 Solution
Bob_Marlowe
Level 10
Level 10
First like given 50 questions asked 10 questions asked

Welcome in the forum.

   

Your slave address is wrong. I2C uses 7-bit addresses and an additional bit indicating read or write access. This bit is inserted automatically.

   

So your address should read 0x57

   

Keep in mind that most of the APIs (except those for reading a byte) return a status byte which, when non-zero indicate an error condition. I always suggest to check those values at least while debugging.

   

 

   

Bob

View solution in original post

0 Likes
12 Replies
Bob_Marlowe
Level 10
Level 10
First like given 50 questions asked 10 questions asked

Welcome in the forum.

   

Your slave address is wrong. I2C uses 7-bit addresses and an additional bit indicating read or write access. This bit is inserted automatically.

   

So your address should read 0x57

   

Keep in mind that most of the APIs (except those for reading a byte) return a status byte which, when non-zero indicate an error condition. I always suggest to check those values at least while debugging.

   

 

   

Bob

0 Likes
Anonymous
Not applicable

Hi,Bob

   

Thanks for your advice, my master device could read temperature value.

   

Wang 

0 Likes
lock attach
Attachments are accessible only for community members.
Anonymous
Not applicable

Hi Bob,

   

thanks I read max30100 temp data. But I need continuous temp data. I want to read one temp value every second. Could you help with this. Once the cycle is read, then it stops. 

   

I need help

   

Thanks.

0 Likes
Bob_Marlowe
Level 10
Level 10
First like given 50 questions asked 10 questions asked

You are always welcome, Wang.

   

 

   

Bob

0 Likes
lock attach
Attachments are accessible only for community members.
Anonymous
Not applicable

Hi Bob,

   

I was faced with a new problem: the sample value of heart value of cannot be read correctly from MAX30100's FIFO. Could you please give me some advise?

   

Looking forward to your reply.

   

Best,Wang

   

The following is my code:

0 Likes
Bob_Marlowe
Level 10
Level 10
First like given 50 questions asked 10 questions asked

Can you please post your complete project, so that we all can have a look at all of your settings. To do so, use
Creator->File->Create Workspace Bundle (minimal)
and attach the resulting file.

   

 

   

Bob

0 Likes
lock attach
Attachments are accessible only for community members.
Anonymous
Not applicable

Hi Bob,

   

Here is complete project.

0 Likes
Bob_Marlowe
Level 10
Level 10
First like given 50 questions asked 10 questions asked

All I2C functions except I2CMasterReadByte() deliver a status that indicates an error when non-zero. I strongly suggest to check for that at least until the project runs correctly.

   

Easiest will be to put your writes and reads into functions.

   

Provide a function void I2CError(void) and change all your I2C functions except I2CMasterReadByte() to

   

if(I2CMasterfunction(..) != 0) I2CError();

   

Now you can set a breakpoint in I2CError and check with the call stack window where the error happened.

   

 

   

Bob

0 Likes
Bob_Marlowe
Level 10
Level 10
First like given 50 questions asked 10 questions asked

Welcome in the forum, Wang Sen.

   

I do not have got your temp-measure device, so I can only have a look.

   

Every I2C_I2CMasterxxx() API returns a status byte which when non-zero indicates an error . so you can see when debugging which of your calls hang.

   

I would suggest some more changes:

   

Set UART to byte mode and increase read and write buffers to 80.

   

The line

   

     temp = temp1 + (temp2 / 100);

   


will not work as expected: Temp is a float and thmp1 and temp2 are 16 bit integers. Change them to int8 and

   

     temp = (double)temp1 + ((double)temp2 * 0.0625); // See datasheet page 23

   

Datasheet shows that registers for temperature are 0x1f and 0x20, am I wrong with that?

   

 

   

Bob

0 Likes
lock attach
Attachments are accessible only for community members.
Anonymous
Not applicable

Hey Bob 

   

Thanks you for answering me. I solved the problem with contiuonus read data. But I am new sensor MAX30102.

   

I am adding DIE_TEMP_RDY(Internal Temperature Ready Flag) and I am reading contiunonus temp value 🙂

   

Muhammed Gulcu

0 Likes
Bob_Marlowe
Level 10
Level 10
First like given 50 questions asked 10 questions asked

Congratulations!

   

 

   

Bob

0 Likes
Anonymous
Not applicable

Hey, can you suggest us what could be the possible changes in the above project for SpO2 implementation using the same sensor i.e MAX30100?

0 Likes