• Уважаемые посетители сайта esp8266.ru!
    Мы отказались от размещения рекламы на страницах форума для большего комфорта пользователей.
    Вы можете оказать посильную поддержку администрации форума. Данные средства пойдут на оплату услуг облачных провайдеров для сайта esp8266.ru
  • Система автоматизации с открытым исходным кодом на базе esp8266/esp32 микроконтроллеров и приложения IoT Manager. Наша группа в Telegram

Как конфигурировать GPIO для I2C?

Aviator

New member
Хочу перезадать пины i2c в библиотеке i2c_master, чтобы было как в библиотеке Wire Ардуино (GPIO 4 и 5 ). Модуль у меня 12E Witty Cloud. Изменил в i2_master.h , как показано ниже, но не работает. Где и что ещё нужно исправить?

Код:
/*
#define I2C_MASTER_SDA_MUX PERIPHS_IO_MUX_GPIO2_U
#define I2C_MASTER_SCL_MUX PERIPHS_IO_MUX_MTMS_U
#define I2C_MASTER_SDA_GPIO 2
#define I2C_MASTER_SCL_GPIO 14
#define I2C_MASTER_SDA_FUNC FUNC_GPIO2
#define I2C_MASTER_SCL_FUNC FUNC_GPIO14
*/

#define I2C_MASTER_SDA_MUX PERIPHS_IO_MUX_GPIO4_U
#define I2C_MASTER_SCL_MUX PERIPHS_IO_MUX_GPIO5_U
#define I2C_MASTER_SDA_GPIO 4
#define I2C_MASTER_SCL_GPIO 5
#define I2C_MASTER_SDA_FUNC FUNC_GPIO4
#define I2C_MASTER_SCL_FUNC FUNC_GPIO5
Хотя бы подскажите, как вместо GPIO2 задать GPIO15 в примере blinky?
 

vad7

Active member
vad7, а как правилбьно подключить вашу библиотеку?
скопировал i2c.c i2c.h в папку user, в user_main написал #include "i2c.h", в void ICACHE_FLASH_ATTR user_init(void) пишу i2c_init(100);
и при all выдаёт
implicit declaration of function 'i2c_init'
разобрался с этим. теперь выдаются ошибки
Код:
user/i2c.c:40:33: error: implicit declaration of function 'ets_get_cpu_frequency' [-Werror=implicit-function-declaration]
   i2c_delay_time = 35750 / 80 * ets_get_cpu_frequency() / freq; // 89=400Khz, 250=143Khz, 357=100Khz, 500=75Khz
                                 ^
user/i2c.c:42:2: error: implicit declaration of function 'ets_intr_lock' [-Werror=implicit-function-declaration]
  ets_intr_lock();
  ^
user/i2c.c:43:2: error: implicit declaration of function 'GPIOx_PIN' [-Werror=implicit-function-declaration]
  GPIOx_PIN(I2C_SDA_PIN) = GPIO_PIN_DRIVER; // Open-drain
  ^
user/i2c.c:43:27: error: 'GPIO_PIN_DRIVER' undeclared (first use in this function)
  GPIOx_PIN(I2C_SDA_PIN) = GPIO_PIN_DRIVER; // Open-drain
                           ^
user/i2c.c:43:27: note: each undeclared identifier is reported only once for each function it appears in
user/i2c.c:45:2: error: implicit declaration of function 'SET_PIN_FUNC' [-Werror=implicit-function-declaration]
  SET_PIN_FUNC(I2C_SDA_PIN, (MUX_FUN_IO_PORT(I2C_SDA_PIN) | (1 << GPIO_MUX_PULLUP_BIT))); // Pullup
  ^
user/i2c.c:45:29: error: implicit declaration of function 'MUX_FUN_IO_PORT' [-Werror=implicit-function-declaration]
  SET_PIN_FUNC(I2C_SDA_PIN, (MUX_FUN_IO_PORT(I2C_SDA_PIN) | (1 << GPIO_MUX_PULLUP_BIT))); // Pullup
                             ^
user/i2c.c:45:66: error: 'GPIO_MUX_PULLUP_BIT' undeclared (first use in this function)
  SET_PIN_FUNC(I2C_SDA_PIN, (MUX_FUN_IO_PORT(I2C_SDA_PIN) | (1 << GPIO_MUX_PULLUP_BIT))); // Pullup
                                                                  ^
user/i2c.c:47:2: error: 'GPIO_OUT_W1TS' undeclared (first use in this function)
  GPIO_OUT_W1TS = (1<<I2C_SDA_PIN) | (1<<I2C_SCL_PIN); // Set HI (WO)
  ^
user/i2c.c:48:2: error: 'GPIO_ENABLE_W1TS' undeclared (first use in this function)
  GPIO_ENABLE_W1TS = (1<<I2C_SDA_PIN) | (1<<I2C_SCL_PIN); // Enable output (WO)
  ^
user/i2c.c:49:2: error: implicit declaration of function 'ets_intr_unlock' [-Werror=implicit-function-declaration]
  ets_intr_unlock();
  ^
user/i2c.c:50:6: error: "DEBUGSOO" is not defined [-Werror=undef]
  #if DEBUGSOO > 2
      ^
user/i2c.c: In function 'i2c_Stop':
user/i2c.c:24:23: error: 'GPIO_OUT_W1TC' undeclared (first use in this function)
#define SET_SDA_LOW   GPIO_OUT_W1TC = (1<<I2C_SDA_PIN)
                       ^
user/i2c.c:62:2: note: in expansion of macro 'SET_SDA_LOW'
  SET_SDA_LOW;
  ^
user/i2c.c:28:22: error: 'GPIO_OUT_W1TS' undeclared (first use in this function)
#define SET_SCL_HI   GPIO_OUT_W1TS = (1<<I2C_SCL_PIN)
                      ^
user/i2c.c:65:2: note: in expansion of macro 'SET_SCL_HI'
  SET_SCL_HI; // release
  ^
user/i2c.c: In function 'i2c_WriteBit':
user/i2c.c:25:22: error: 'GPIO_OUT_W1TS' undeclared (first use in this function)
#define SET_SDA_HI   GPIO_OUT_W1TS = (1<<I2C_SDA_PIN)
                      ^
user/i2c.c:76:3: note: in expansion of macro 'SET_SDA_HI'
   SET_SDA_HI;
   ^
user/i2c.c:24:23: error: 'GPIO_OUT_W1TC' undeclared (first use in this function)
#define SET_SDA_LOW   GPIO_OUT_W1TC = (1<<I2C_SDA_PIN)
                       ^
user/i2c.c:78:3: note: in expansion of macro 'SET_SDA_LOW'
   SET_SDA_LOW;
   ^
user/i2c.c:26:21: error: 'GPIO_IN' undeclared (first use in this function)
#define GET_SDA    (GPIO_IN & (1<<I2C_SDA_PIN))
                     ^
user/i2c.c:83:14: note: in expansion of macro 'GET_SDA'
   if(bit && (GET_SDA) == 0) return 1; // other master active
              ^
user/i2c.c: In function 'i2c_ReadBit':
user/i2c.c:25:22: error: 'GPIO_OUT_W1TS' undeclared (first use in this function)
#define SET_SDA_HI   GPIO_OUT_W1TS = (1<<I2C_SDA_PIN)
                      ^
user/i2c.c:91:2: note: in expansion of macro 'SET_SDA_HI'
  SET_SDA_HI;
  ^
user/i2c.c:26:21: error: 'GPIO_IN' undeclared (first use in this function)
#define GET_SDA    (GPIO_IN & (1<<I2C_SDA_PIN))
                     ^
user/i2c.c:95:17: note: in expansion of macro 'GET_SDA'
  uint8_t bit = (GET_SDA) != 0;
                 ^
user/i2c.c:27:23: error: 'GPIO_OUT_W1TC' undeclared (first use in this function)
#define SET_SCL_LOW   GPIO_OUT_W1TC = (1<<I2C_SCL_PIN)
                       ^
user/i2c.c:96:2: note: in expansion of macro 'SET_SCL_LOW'
  SET_SCL_LOW;
  ^
user/i2c.c: In function 'i2c_Start':
user/i2c.c:25:22: error: 'GPIO_OUT_W1TS' undeclared (first use in this function)
#define SET_SDA_HI   GPIO_OUT_W1TS = (1<<I2C_SDA_PIN)
                      ^
user/i2c.c:135:3: note: in expansion of macro 'SET_SDA_HI'
   SET_SDA_HI;
   ^
user/i2c.c:26:21: error: 'GPIO_IN' undeclared (first use in this function)
#define GET_SDA    (GPIO_IN & (1<<I2C_SDA_PIN))
                     ^
user/i2c.c:139:7: note: in expansion of macro 'GET_SDA'
   if((GET_SDA) == 0) {
       ^
user/i2c.c:24:23: error: 'GPIO_OUT_W1TC' undeclared (first use in this function)
#define SET_SDA_LOW   GPIO_OUT_W1TC = (1<<I2C_SDA_PIN)
                       ^
user/i2c.c:142:3: note: in expansion of macro 'SET_SDA_LOW'
   SET_SDA_LOW;
   ^
я понимаю что не ватает подкючения какогото хидера, можешь подсказать какого?
 
Последнее редактирование:

vad7

Active member
Это все на вебсвалке работает, нужно либо использовать ее, либо все описания и дописанные функции перенести.
 
Это все на вебсвалке работает, нужно либо использовать ее, либо все описания и дописанные функции перенести.
А можно поподробнее, какие файлы и функции перенести?
Эту либу беру потомучто можно для i2c любые выводы использовать.
Компилятор упираелся в определения gpio. Перенёс хидеры со свалки в проект, теперь uint32 в каждой функции не принимает.
 

vad7

Active member
Ставите рядом исходный проект, ищете в нем символ на который в вашем проекте ругается компилятор, жмете на нем ctrl+кн.мыши и видите модуль, в котором он описан.
и т.д.
 

Сергей_Ф

Moderator
Команда форума
@vad7 мне кажется, Вы все слишком усложняете. Я запускал i2c на разных пинах под Ардуино ИДЕ без проблем и даже без правок хидера. Сейчас нет под рукой компьютера (до понедельника), посмотреть не могу. Но точно на ESP-Easy запускал на tx, rx.
 
Ставите рядом исходный проект, ищете в нем символ на который в вашем проекте ругается компилятор, жмете на нем ctrl+кн.мыши и видите модуль, в котором он описан.
и т.д.
отличный метод, спасибо!

теперь вся понятно: в качестве донора я использовал проект esphttpd. у него файл esp8266.h почти пустой (вложение) и второй с кучей нужных определений.
простым копированием содержимого совместить не получается....
буду думать. кто какие советы может дать?
upd: товарищ vad7, а можете объяснить почему всё завязано на папочку bios и файл bios.h и чем тие файлы сильно отличаются от тех что есть в SDK и UDK?
 

Вложения

Последнее редактирование:

vad7

Active member
@Сергей_Ф, если вы про i2c драйвер из примеров UDK, то он мне не нравится - не оптимально написано, нет контроля ошибок, нет возможности выбора скорости на лету.
 
vad7, разобрался я со свалкой теперь за библиоекту I2C взялся.
поправьте если что-то где то ошибаюсь(а я ошибаюсь ибо не работает):
подключил к PCF8583 (адрес 0xA0), подтягивающие резисторы 10кОм.
определил выводы:
Код:
#define I2C_SDA_PIN 12 // SDA on GPIO12
#define I2C_SCL_PIN 13 // SCL on GPIO13
инициализацию i2c_init(0); делаю в процедуре void ICACHE_FLASH_ATTR user_init(void);
затем просто ради проверки делаю так(в той же инициализации но после поднятия и2ц):
Код:
void ICACHE_FLASH_ATTR SaClockUartTx (void)
{
    uint8_t ClockBuffer[3] = {5,6,7};
    uart0_tx(0x00);
    uart0_tx(i2c_eeprom_read_block( 0xA0, 0x02, ClockBuffer, 3)); // адрес, начальная ячейка памяти откуда читаем, куда складываем, сколько байт читаем.//
    uart0_tx(0x00);
    uart0_tx(ClockBuffer[0]);
    uart0_tx(ClockBuffer[1]);
    uart0_tx(ClockBuffer[2]);
}
вывод в терминал: 0,3,0,5,6,7 а должно быть по идее 0,0,0,SS,MM,HH

то есть функция не отработала. в чём может быть косяк?
 
Последнее редактирование:

vad7

Active member
SDA читается как 0, а должен как 1 при старте.
i2c_init можно попробовать сразу перед вашей функцией.
esp на 80Мгц?
 
SDA читается как 0, а должен как 1 при старте.
i2c_init можно попробовать сразу перед вашей функцией.
esp на 80Мгц?
про SDA я так и понял. не понял отчего только именно так, вроде 10kOm резисторы стоят (плата отладочная).
i2c_init сунул в общую кучу инициализаций аппаратных, следом идут пользовательские. для удобства чтения кода.
нет - 160
#define USE_CPU_SPEED 160 // установить частоту CPU по умолчанию 80 или 160 MHz

нарисую 80, попробую, посмотрю что получится
 

vad7

Active member
если логического анализатора нет, то проверяется просто оставить только i2c_init(100) и померять вольтметром на SDA, если не 3V, то смотреть дальше железо или в коде где-то изменились настройки портов.
 
если логического анализатора нет, то проверяется просто оставить только i2c_init(100) и померять вольтметром на SDA, если не 3V, то смотреть дальше железо или в коде где-то изменились настройки портов.
всё сработало! спасибо!
теперь осталось только понять почему вместо простого чтения времени (шести байт) происходит сброс первого байта в очереди?
читаю вот так(не судить это всего лишь отладка):
Код:
void ICACHE_FLASH_ATTR SaClockUartTx (void)
{
    uint8_t ClockBuffer[6] = {6,5,4,3,2,1};
    uart0_tx(0x00);
    uart0_tx(i2c_eeprom_read_block( 0x68, 0x00, ClockBuffer, 6));
    uart0_tx(0x00);
    uart0_tx(ClockBuffer[0]);
    uart0_tx(ClockBuffer[1]);
    uart0_tx(ClockBuffer[2]);
    uart0_tx(ClockBuffer[3]);
    uart0_tx(ClockBuffer[4]);
    uart0_tx(ClockBuffer[5]);

}
и при этом постоянно обнуляется байт секунд. или байт времени если сделать [inline]uart0_tx(i2c_eeprom_read_block( 0x68, 0x01, ClockBuffer, 6));[/inline]
 

vad7

Active member
Для PCF8583 эти функции (i2c_eeprom_*_block) не подходят.
Они для eeprom с 2-х байтной адресацией.
 

vad7

Active member
Sam_Arcanum, так функция то отсылает двух-байтный адрес, а вышеуказанные чипы ждут один.
Плюс протокол отличается от доступа к eeprom.
 
Сверху Снизу