melexis / mlx90632-library

MLX90632 library for the Melexis 90632 Infra Red temperature sensor.
Apache License 2.0
42 stars 15 forks source link

EEPROM write issue #41

Open domko99 opened 2 years ago

domko99 commented 2 years ago

Hi. I have an issue with EEPROM writing with sensor MLX90632SLD-DCB-000-SP. I am using framework ESP-IDF and microcontroller ESP32.

The first think I want to say is I think I am 100% able to read EEPROM memory from sensor. The normal mode program is working well and i2c_read and i2c_read32 functions dont return ret<0. Also my sensor should be supporting Extended mode because function mlx90632_init() returns ERANGE.

The problem is when I am trying to use MEDICAL mode or EXTENDED mode with appropiate code, Function mlx90632_read_temp_raw_extended() is returning ret<0. As I know in normal mode there is no need to write to EEPROM memory so the code is working.... But in other modes there is so I assume this can be an issue.

For I2C write I am using this code

int32_t mlx90632_i2c_write(int16_t register_address, uint16_t value){
    uint8_t reg_add[] = { (register_address >> 8) & 0xff, register_address & 0xff, 0, 0};
    i2c_master_write_to_device(I2C_MASTER_NUM, MLX90632_I2C_ADDR,reg_add,sizeof(reg_add),1000 / portTICK_PERIOD_MS);
    uint8_t data[2] = { 0 };
    data[0] = value >> 8;
    data[1] = value;
    uint8_t write_buf[] = { (register_address >> 8) & 0xff, register_address & 0xff , data[1], data[0]};
    i2c_master_write_to_device(I2C_MASTER_NUM, MLX90632_I2C_ADDR,write_buf,sizeof(write_buf),1000 / portTICK_PERIOD_MS);
    return 0;
}

and I think I am doing everything what is said in datasheet, erasing memory before write and then write to memory.

Code which I am using to implement extended mode is:

    // i2c init
    mlx90632_read_eeprom(&PR, &PG, &PO, &PT, &Ea, &Eb, &Fa, &Fb, &Ga, &Gb, &Ha, &Hb, &Ka);
    mlx90632_init();                    // returns ERANGE
    mlx90632_set_meas_type(MLX90632_MTYP_EXTENDED);
    mlx90632_start_measurement();
    mlx90632_read_temp_raw_extended(&ambient_new_raw, &ambient_old_raw, &object_new_raw);  // returns ret<0
    /* Now start calculations (no more i2c accesses) */
    /* Calculate ambient temperature */
    ambient = mlx90632_calc_temp_ambient_extended(ambient_new_raw, ambient_old_raw, 
                                                  PT, PR, PG, PO, Gb);
    /* Get preprocessed temperatures needed for object temperature calculation */
    pre_ambient = mlx90632_preprocess_temp_ambient_extended(ambient_new_raw,
                                                                   ambient_old_raw, Gb);
    pre_object = mlx90632_preprocess_temp_object_extended(object_new_raw, ambient_new_raw,
                                                                 ambient_old_raw, Ka);
    /* Calculate object temperature assuming the reflected temperature equals ambient*/
    object = mlx90632_calc_temp_object_extended(pre_object, pre_ambient, ambient, Ea, Eb, Ga, Fa, Fb, Ha, Hb);

I think no function is missing to successfully execute extended measurement. The return value of object and ambient variables is "nan". Also it is taking a long time to get this output (I mean "nan"). And when I want to execute new code with normal mode measurement I need to reset power supply of external PCB board with MLX90632 and after that sensor is producing good data of temperature. I was also looking at example code available here: https://github.com/melexis/mlx90632-example and there is no special implementation of mlx90632_i2c_write function.

If there is someone who can help to solve this problem or had a similar problem and was able to solve it I would be happy for any help. Thanks.

Letme commented 2 years ago

You didn't mention if you defined BITS_PER_LONG = 32 as a compiler flag (-D)? I think it is a 32bit processor right...

Letme commented 2 years ago

Also if you look at exapmle code for extended mode in readme, you have the start_measurement() function before the read_temp_raw_extended. That could be a reason for the return value (it would be cool to know which it is - might be ETIMEOUT?). So first you can remove that function and second you can print the return code.

domko99 commented 2 years ago

Hi. I deleted start_measurement() function and the problem is the same. The return value of read_temp_raw_extended is -116. I think it is 116 so it should be ETIMEOUT. And I didnt define BITS_PER_LONG = 32 as a compiler flag. I just define it in mlx90632.h library #define BITS_PER_LONG 32. I dont know how to do it in esp-idf framework but when it is needed to add a flag for bits per long I will try to find out how. Thanks.

domko99 commented 2 years ago

And is it necessary to add BITS_PER_LONG = 32 compiler flag? And is it needed only for source files in melexis component (mlx90632.c and mlx90632_extended_meas.c)? Thanks.

domko99 commented 2 years ago

Added BITS_PER_LONG = 32 as compiler flag didnt help. I have got pull-up resistors for I2C wires with value of 10 kOhm (integrated in PCB) and in datasheet there is pull-up resistors value of 1 kOhm. Can be this an issue?

Letme commented 2 years ago

I don't think so, your communication should be fine at least you wrote above you received register values. How about making a longer delay with that mdelay function?

Letme commented 1 year ago

Any updates on this? I hope you solved the issue meanwhile...

mm66 commented 2 months ago

Hello, I'm having similar problems, mlx90632_read_temp_raw_extended() is also returning ret<0, also it seems that measurement type does not get set correctly, i call mlx90632_get_meas_type() and it seems it is still set to default even though i set it to mlx90632_set_meas_type(MLX90632_MTYP_EXTENDED) beforehand. I set the BITS_PER_LONG to 32 for my system. I don't think there is a problem with my i2c functions since i can read good temperature values in normal mode from the chip as well as calibration constants.

Letme commented 2 months ago

Your write function has correct endianness for the sensor? Are you able to check stuff with scope?

Based on your comment it seems write is not working.

mm66 commented 2 months ago

It does have correct endiannes, I mean as I said, measuring in standard mode works good for me. I can try checking what happens with scope. Can you confirm that eeprom version number 0x8505 supports extended mode?

Letme commented 2 months ago

Yes, I also assume Init function also returns ERANGE right? If you can measure in standard mode that does not mean write function works as expected - because you do not write much unless you work in burst mode for example. That is why I asked. Can you change refresh_rate? Then with burst mode you would see the difference without the scope....