Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

MLX90640 Eval Board I2C #86

Open
calvinfoo opened this issue Jul 4, 2021 · 1 comment
Open

MLX90640 Eval Board I2C #86

calvinfoo opened this issue Jul 4, 2021 · 1 comment

Comments

@calvinfoo
Copy link

Hi,

I am trying to use the VDD, GND and SCL, SDA pins on the Melexis evaluation board for ML90640.

VCC=3.3V
GND =GND
SCL & SDA with pull up 3.3k resisters
But I can't seems to get any address with I2C scanner on ESP32. (I tried with VL53L0X and can get I2C address).

Anyone manage to get this working?

@karelv
Copy link

karelv commented Jul 5, 2021

At first I would add a decoupling capacitor on VDD/GND.
Also in this driver the I2C functions still need an implementation.

You might compare your MLX90640_I2C_Driver.c with this content:

/**
 * @copyright (C) 2017 Melexis N.V.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 *
 */
#include "MLX90640_I2C_Driver.h"

#include "esp_log.h"
#include "driver/i2c.h"
#define ACK_CHECK_EN 0x1                        /*!< I2C master will check ack from slave*/
#define ACK_CHECK_DIS 0x0                       /*!< I2C master will not check ack from slave */
#define ACK_VAL I2C_MASTER_ACK                             /*!< I2C ack value */
#define NACK_VAL I2C_MASTER_NACK                            /*!< I2C nack value */


    // I2C_MASTER_ACK = 0x0,        /*!< I2C ack for each byte read */
    // I2C_MASTER_NACK = 0x1,       !< I2C nack for each byte read
    // I2C_MASTER_LAST_NACK = 0x2,   /*!< I2C nack for the last byte*/


// #define _I2C_NUMBER(num) I2C_NUM_##num
// #define I2C_NUMBER(num) _I2C_NUMBER(num)

i2c_port_t g_i2c_num = I2C_NUM_0;



void MLX90640_I2CInit()
{
  // send 8 clock pulses and a STOP condition.
  i2c_cmd_handle_t cmd = i2c_cmd_link_create();
  i2c_master_write_byte(cmd, (0x7F << 1) | I2C_MASTER_WRITE, ACK_CHECK_EN);
  i2c_master_stop(cmd);
  i2c_master_cmd_begin(g_i2c_num, cmd, 1000 / portTICK_RATE_MS);
  i2c_cmd_link_delete(cmd);
}


int MLX90640_I2CRead(uint8_t slaveAddr, uint16_t startAddress, uint16_t nMemAddressRead, uint16_t *data)
{



  if (nMemAddressRead == 0) return 0;

  i2c_cmd_handle_t cmd = i2c_cmd_link_create();
  i2c_master_start(cmd);
  i2c_master_write_byte(cmd, (slaveAddr << 1) | I2C_MASTER_WRITE, ACK_CHECK_EN);
  i2c_master_write_byte(cmd, startAddress >> 8, ACK_CHECK_EN);
  i2c_master_write_byte(cmd, startAddress, ACK_CHECK_EN);

  i2c_master_start(cmd); // repeated start
  i2c_master_write_byte(cmd, (slaveAddr << 1) | I2C_MASTER_READ, ACK_CHECK_EN);

  uint8_t *data_rd = (uint8_t *)data;

  uint16_t bytes2Read = nMemAddressRead * 2;

  i2c_master_read(cmd, data_rd, bytes2Read - 1, ACK_VAL);
  i2c_master_read_byte(cmd, data_rd + bytes2Read - 1, NACK_VAL);
  i2c_master_stop(cmd);
  esp_err_t ret = i2c_master_cmd_begin(g_i2c_num, cmd, 3000 / portTICK_RATE_MS); // 3 sec timeout
  i2c_cmd_link_delete(cmd);
  // ESP_LOGE("MLX90640-I2C-Driver", "ret = %d (%d, %d, %d, %d, %d)", ret, ESP_OK, ESP_ERR_INVALID_ARG, ESP_FAIL, ESP_ERR_INVALID_STATE, ESP_ERR_TIMEOUT);

  if (ret == ESP_OK)
  {
    for (uint16_t i=0; i<nMemAddressRead; i++)
    { // swap low & high byte!
      data[i] = (data[i]>>8) | (data[i]<<8);
    }
  }


  return ret != ESP_OK;
}


void MLX90640_I2CFreqSet(int freq)
{
  ESP_LOGE("MLX90640-I2C-Driver", "set I2C master SCL frequency directly in i2c master functions!!!");
}


int MLX90640_I2CWrite(uint8_t slaveAddr, uint16_t writeAddress, uint16_t data)
{
  i2c_cmd_handle_t cmd = i2c_cmd_link_create();
  i2c_master_start(cmd);
  i2c_master_write_byte(cmd, (slaveAddr << 1) | I2C_MASTER_WRITE, ACK_CHECK_EN);
  i2c_master_write_byte(cmd, writeAddress >> 8, ACK_CHECK_EN);
  i2c_master_write_byte(cmd, writeAddress, ACK_CHECK_EN);
  i2c_master_write_byte(cmd, data >> 8, ACK_CHECK_EN);
  i2c_master_write_byte(cmd, data, ACK_CHECK_EN);
  i2c_master_stop(cmd);
  esp_err_t ret = i2c_master_cmd_begin(g_i2c_num, cmd, 1000 / portTICK_RATE_MS);
  i2c_cmd_link_delete(cmd);
  if (ret == ESP_OK)
  {
    return 0;
  }


  uint16_t dataCheck;
  MLX90640_I2CRead(slaveAddr, writeAddress, 1, &dataCheck);
  if (dataCheck != data)
  {
    return -2;
  }
  return -1;
}

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants