Странное поведение I2C (MLX90614)

DsKTY
Offline
Зарегистрирован: 30.07.2012

Столкнулся со странным поведением I2C. Подключаю к дуине сенсор MLX90614. Подключение простейшее: питание, земля, SCL, SDA. Про подтягивающие резисторы не забыл - по 4.7к от SDA и SCL к питанию. Всё работает, но крайне нестабильно и странно. 

Собственно в чём проблема: для тестов запускаю скетч i2c-сканера устройств на шине (http://playground.arduino.cc/Main/I2cScanner). В процессе выполнения ловлю примерно вот такие ошибки:

I2C Scanner
Scanning...
Unknow error at address 0x03
Unknow error at address 0x06
Unknow error at address 0x09
Unknow error at address 0x0C
 
При чём, каждый раз, ошибки на разных адресах. Подключал другие датчики (акселерометры попался под руку) - всё распознаётся прекрасно. Делаю вывод, что проблема именно в MLX90614. Думал, проблема в электрическом контакте где-то, передёргал всё, что мог. И Чисто случайно обнаружил странность:
 
Если подключить датчик к I2C, но не подключать SCL, и подключить SCL уже после запуска ардуины, то датчик начинает работать правильно. Т.е. корректно определяется и отзывается на свой адрес по i2с запросам. Но вот при попытке запускать ардуину с подключённом сразу датчиком - датчик "гадит в линию".
 
Складывается ощущение, что самому датчику для старта нужно какое-то время между подачей питания и началом тактирования по SCL. Но как это реализовать ума не приложу. 
 
Может кто сталкивался с подобным? Или ещё какие-то мысли есть?
DsKTY
Offline
Зарегистрирован: 30.07.2012

Подключил лог-анализатор и посмотрел, что собственно происходит в I2C. А происходит вот что:

Судя по всему, сразу же после включения, на линии SDA появляется вот такая вот "гребёнка". Не совсем ясно, кто эту гребёнку генерит - ардуина или MLX90614.

DsKTY
Offline
Зарегистрирован: 30.07.2012

Тихо сам с собою... Вопрос снялся после долгих чтений мануалов. Похоже, что сенсоры пришли в PWM Mode. Что бы их перевести в I2C, нужно каким-то образом в течение 3мс после подачи питания пустить линию SCL в LOW. Проблема в том, что между появлением питания в ардуине и выполнением первой команды проходит около 1.4 секунд. Соответсвенно, программно линию SCL прижать в LOW нет никакой возможности. 

vov4ik
Offline
Зарегистрирован: 10.09.2013

Задействуй лишний пин, на полевой транзисторе запитай датчик, включилась ардуинка пин подал напряжение на датчик и снимай SCL в LOW.

poteh
Offline
Зарегистрирован: 09.06.2015

Скажите, удалось ли решить проблему?

У меня похожая проблема. Сперва MLX90614 отлично работал, затем начал показывать около 1000 градусов, потом вновь начал нормально работать, и сейчас опять перестал работать.

DsKTY
Offline
Зарегистрирован: 30.07.2012

Да, когда показывает около 1000 градусов - очень похоже на PWM Mode. Возможно перезагрзка девайса поможет? 

По факту, проблема была только на одной партии сенсоров. Самые дешёвые. Сложилось ощущение, что это вообще какой-то левак. Купил несколько других вариантов этого же сенсора (в других корпусах и на другое напряжение питания) - работают отлично.

poteh
Offline
Зарегистрирован: 09.06.2015

Ни перезагрузка, ни загрузка другого скетча (в том числе с использованием библиотеки wire вместо i2cmaster) не решают проблемы. Проблема появляется сама и так же сама исчезает.

DsKTY
Offline
Зарегистрирован: 30.07.2012

А что за датчик? Желательно сдалать фото и  выложить сюда, по возможности.

poteh
Offline
Зарегистрирован: 09.06.2015

MLX90614ESF-AAA. Фото сделать могу, но он уже в корпусе и распаянный. Подключен к 4 и 5 аналоговому пинам ардуино уно с подтягивающими резисторами по 4.7 кОм. Запитал от 3.3 вольта, хотя по даташиту ААА должен быть 5 вольтовый... но от 5 вольт показания не появляются.

Использую библиотеку i2cmaster. В .cpp файле поменял значение SCL_CLOCK с 50000L на 100000L. После этого датчик начал работать. Сейчас даже с этим не работает.

Код который использую:

//Simple program to read data from smbus device and convert from degrees kelvin to degrees C and print to serial port.
#include <i2cmaster.h>
void setup()
{
 Serial.begin(9600);
 i2c_init();  //Initialise the i2c bus
}
void loop()
{ 
 int dev = 0x5A<<1;
 int data_low = 0;
 int data_high = 0;
 int pec = 0;
 i2c_start_wait(dev+I2C_WRITE); //send start condition and write bit
 i2c_write(0x07); //send command for device to action
 i2c_rep_start(dev+I2C_READ); //send repeated start condition, device will ack
 data_low = i2c_readAck();  //Read 1 byte and then send ack
 data_high = i2c_readAck(); //Read 1 byte and then send ack
 pec = i2c_readNak(); //Read error check byte and send Nack to tell device no more data to send
 i2c_stop(); //Release bus, end transaction
//This converts high and low bytes together and processes temperature, MSB is a error bit and is ignored for temps
  double tempFactor = 0.02; // 0.02 degrees per LSB
   int tempData = 0x0000;
// This masks off the error bit of the high byte, then moves it left 8 bits and adds the low byte.
   tempData = (int)(((data_high & 0x007F) << 8) + data_low);
   tempData = (tempData * tempFactor)-0.01;
   tempData = tempData - 273.15;
   Serial.println(tempData); //Print temp in degrees C to serial
   delay(1000);
}

И фото датчика:

Картинка со страницы продавца:

Igor36
Offline
Зарегистрирован: 14.06.2014

poteh, удалось ли решить проблему. У того же продавца заказывал 3 датчика MLX90614ESF-AAA почти как с год назад, пролежали да же ни разу не развернул, сегодня решил попробовать. Либо вообще не удается запустить, либо показания более 1000 с библиотекой adafruit и не меняются. I2C Scanner выдает ошибки. Перешерстил интернет по похожей проблеме крайне мало ответов с решением. Если кто столкнулся прошу помощи.

poteh
Offline
Зарегистрирован: 09.06.2015

к сожалению нет, не удалось. заказал второй датчик (уже распаяный на текстолит), попробую с ним.

Igor36
Offline
Зарегистрирован: 14.06.2014

Спасибо огромное за ответ. По ходу дела у продавца на али, где были приобретены датчики вся партия сенсоров неисправная. Долго изучал сеть на этот счет, зарубежные любители то же пострадали купив у этого продавца сенсоры. Даже номер неисправной сери  есть в сети. 

poteh
Offline
Зарегистрирован: 09.06.2015

но ведь работал... потом перестал, потом вновь заработал, потом опять перестал... думаю что всё же беда с переходом в PWM режим.

Igor36
Offline
Зарегистрирован: 14.06.2014

Мои датчики то же вроде работали, причем что бы что либо получить с датчика приходилось по нескольку раз отключать и заново подключать его, и то что они выдавали - абсолютная ерунда, какая даже не рядом с ральными измеряемыми температурами.

medic
Offline
Зарегистрирован: 06.02.2016

К сожалению уже трижды попадал на левые MLX90614. Оригинальные- это с гравировкой модификации на корпусе датчика, левые- с обычным принтом по корпусу.

Причем в случае с китайцами на ebay, они все прекрасно знают, т.к. после открытия диспута быстро возвращают деньги.

Поэтому перед покупкой убедитесь в наличии гравировки! А то что выдаёт 1000 градусов- это минус библиотеке. Она не находит датчик на шине, но чудно продолжает работать.

Левые датчики:

http://www.ebay.com/itm/2Pcs-MLX90614ESF-BAA-MLX90614ESF-MELEXIS-TO-39-ORIGINAL-NEW-/221846576336?hash=item33a7161cd0:g:JDUAAOSw~gRVxIO2 - на фото есть гравировка, пришли с обычным принтом. естественно не работают.

http://www.ebay.com/itm/Non-Contact-Thermometer-IR-Melexis-MLX90614-40C-to-85C-I2C-TWI-3-3V-Arduino-/331498270439?hash=item4d2ed62ee7:m:mqOFtmSWIeuA9HJBpadshgQ - Продавец из США, переплюнул даже барыг из Китая. Отфотошопил фото в описании, чтобы скрыть принт. Подделка не работает.

 

А вот этот - https://www.adafruit.com/product/1748 работает! Но и цена у него 16дол.

pavel_bbb
Offline
Зарегистрирован: 27.01.2014

Подскажите как перевести датчик из PWM-mode в I2C.

Китаец прислал 5 датчиков в ШИМ режиме.

Если у кого есть знания, как это осуществить с помощью ардуино - отблагодарю финансово, ибо жалко датчики выкидывать.

pavel_bbb
Offline
Зарегистрирован: 27.01.2014