Подключение EEPROM AT24C256 к Arduino по интерфейсу I2C

Подключение EEPROM AT24C256 к Arduino по интерфейсу I2C

В этой статье расскажу, как подключить EEPROM память AT24C256 к Arduino через интерфейс I2C. Разберем, как записывать и читать обычные байты, хранить целые числа, дробные значения ( float), а также запишем в память 16 и 32-битные данные.

Введение

Сначала посмотрим на характеристики самой микросхемы и ее распиновку, затем соберем схему на макетной плате и загрузим рабочий скетч. В итоге у вас будет готовое решение для создания даталоггеров, хранения таблиц калибровки или пользовательских профилей в ваших устройствах.

Технические характеристики

  • Объем памяти: 256 Кбит (общая память 32 КБ);
  • Интерфейс: I2C;
  • Рабочее напряжение: От 1,7 В до 5,5 В;
  • Размер страницы для записи: 64 байта на страницу;
  • Хранение данных: До 100 лет;
  • Долговечность: До 1 миллиона циклов записи / стирания на байт;
  • Скорость: Частота до 1 МГц (в зависимости от напряжения и режима);
  • Рабочая температура: От -40 °C до +85 °C;

Описание

Внутренняя память любого микроконтроллера имеет существенные ограничения: встроенная Flash-память не рассчитана на интенсивную перезапись в процессе работы из-за ограниченного ресурса ячеек (в некоторых микроконтроллерах вообще нет внутренней энергонезависимой памяти), а SRAM является энергозависимой и теряет все данные при отключении питания. Использование внешней микросхемы EEPROM устраняет эти недостатки, обеспечивая сохранность информации без резервного источника тока и гарантируя до миллиона циклов записи

Принципа работы I2C-связи с AT24C256

Протокол I2C — это последовательная шина обмена данными, которая позволяет подключать к микроконтроллеру Arduino множество периферийных устройств (например, датчики, дисплеи или память AT24C256), используя всего две линии: SDA для передачи данных и SCL для синхронизации.

Главное преимущество шины заключается в адресации: каждому ведомому устройству присваивается уникальный идентификатор. Это даёт возможность управлять всей цепочкой компонентов по общим проводам, не расходуя лишние контакты микроконтроллера. Процесс обмена инициирует ведущий узел (Arduino): он формирует стартовое условие на линиях и отправляет адрес конкретного устройства — EEPROM-памяти. Получив свой адрес, ведомый модуль подтверждает готовность сигналом ACK и переходит в режим ожидания команд

Адрес I2C и организация памяти

I2C-адрес микросхемы AT24C256 конфигурируется аппаратно с помощью трех выводов — A0, A1 и A2. Комбинируя их логические уровни (подключая к земле или VCC), можно задать один из восьми уникальных 7-битных адресов в диапазоне от 0x50 до 0x57. Это позволяет подключать до восьми таких чипов на одной шине I2C, увеличивая общий объем доступной энергонезависимой памяти.

Внутренняя архитектура самого кристалла представляет собой массив объемом 32 768 байт (32 КБ). Для управления записью память организована в виде страниц по 64 байта каждая. Ключевое ограничение при работе с ней заключается в том, что операция записи не должна пересекать границу страницы. Если попытаться записать данные за пределы текущего 64-байтового блока, контроллер не перейдет на следующую страницу, а начнет циклически перезаписывать данные с ее начала.

  • Общий объем памяти: 256 Кбит (32 КБ)
  • Размер страницы: 64 байта
  • Количество страниц: 512
  • Диапазон адресов: от 0x0000 до 0x7FFF

Тайминг и размер страницы AT24C256

Эффективность работы с AT25C256 по шине I2C напрямую зависит от соблюдения временных параметров. Микросхема поддерживает тактовую частоту до 1 МГц, однако типичные библиотеки Arduino ограничивают скорость стандартным режимом в 100 кГц или быстрым — в 400 кГц.

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

Кроме того, необходимо строго соблюдать страничный алгоритм: максимальный объем непрерывной передачи ограничен размером физической страницы в 64 байта. Попытка передать больше приведет к циклическому возврату указателя адреса в начало текущей страницы и потере данных. Поэтому массивы информации следует предварительно сегментировать на блоки по 64 байта.

Необходимые детали

№ Компонент Количество Купить
1 Arduino UNO R3 1 шт Авито | AliExpress | RobotChip
2 Провода DuPont 4 шт Авито | AliExpress | RobotChip
3 Модуль памяти AT2C256 1 шт Авито | AliExpress | RobotChip

Подключение

Процесс подключения EEPROM к плате не требует дополнительных компонентов благодаря двухпроводному протоколу. Вам достаточно соединить выводы SDA и SCL микросхемы с соответствующими пинами Arduino A4 и A5, а также подать питание VCC и землю GND.

Таблица подключения

Вывод Arduino UNO AT24C256
1 VCC 3V3
2 SDA A4
3 SCL A5
4 GND GND

Программа 1 — Запись одного байта

В первой программе рассмотрим запись одного байта данных в память AT24C256.

Если все правильно сделали при открытия мониторинга порта увидим результат работы программы.

Описание кода:
Подключаем библиотеку I²C Arduino для связи с EEPROM, затем задает 7-битный I²C-адрес EEPROM (базовый адрес).

В функции setup() инициализируем шину I2C командой Wire.begin(), запускаем последовательный порт командой Serial.begin(9600) и вызываем функцию writeEEPROM(0x000A, 0x55) для записи значения 0x55 в ячейку памяти EEPROM с адресом 0x000A. Добавляем небольшую задержку (например, delay(10)), чтобы цикл записи завершился

В функции loop() зацикливаем программу. Далее, у нас идет функция writeEEPROM(). Она начинает передачу данных по шине I²C в EEPROM, отправляет 16-битный адрес памяти двумя частями (сначала старший байт, затем младший), отправляет байт данных для записи и завершает передачу. После этого программа ожидает завершения записи в течение 5 мс.

Программа 2 — Чтение одного байта

Чтобы получить данные из памяти, необходимо сначала указать где они лежат. Для этого вы передаете ему нужный адрес (два байта). Сразу после этого вы меняете режим шины на чтение и запрашиваете у устройства один байт — EEPROM автоматически отдаст значение из указанной ячейки.

Если все правильно сделали при открытия мониторинга порта увидим результат работы программы.

Описание кода:
Подключаем библиотеку I²C Arduino для связи с EEPROM, затем задает 7-битный I²C-адрес EEPROM (базовый адрес).

В функции setup() инициализируем шину I2C командой Wire.begin(), запускаем последовательный порт командой Serial.begin(9600) и вызывается пользовательская функция чтения byte data = readEEPROM(0x000A). Ей передается 16-битный адрес ячейки 0x000A (10 в десятичной системе). Функция возвращает прочитанный байт, который сохраняется в переменную data.

В функции loop() зацикливаем программу. Далее, у нас идет функция readEEPROM(), которая читает одни байта из внешней памяти. Она принимает 16-битный адрес ячейки и возвращает считанное значение.

Программа 3 — Запись и чтение нескольких байтов.

Вы можете записать в память сразу пачку из 64 байт. Это предел одной страницы. Если вы попытаетесь отправить 65-й байт или больше за тот же раз, память не пойдет дальше по списку. Она вернется в самое начало этой же страницы и начнет записывать новую информацию поверх старой.

Если все правильно сделали при открытия мониторинга порта увидим результат работы программы.

Описание кода:
Подключаем библиотеку I²C Arduino для связи с EEPROM, затем задает 7-битный I²C-адрес EEPROM (базовый адрес).

В функции setup() инициализируем шину I2C командой Wire.begin(), запускаем последовательный порт командой Serial.begin(9600). Далее создается массив writeData со значениями {10, 20, 30, 40, 50}, и вызывается функция writeMultiple(0x0010, writeData, 5) для отправки данных. Затем программа ожидает 10 мс, чтобы микросхема EEPROM успела завершить внутренний цикл записи. После этого создается массив readData для приема пяти байт, и вызывается функция readMultiple(0x0010, readData, 5) для получения данных из памяти по тому же адресу.

В функции loop() программа зацикливается. Далее вызывается функция Wire.beginTransmission() для инициализации передачи данных и функция readMultiple() для чтения данных.

Программа 4 — Сохранение и чтение целочисленных значений.

Представьте, что ваше число — это двузначное число, где каждая цифра может быть от 0 до 255. Одна ячейка памяти слишком мала, чтобы вместить всё целиком, поэтому мы используем две. В первую мы кладем «десятки» (старший байт), а во вторую — «единицы» (младший байт). Чтобы получить исходное число назад, мы просто достаем обе цифры и ставим их рядом в правильном порядке.

Если все правильно сделали при открытия мониторинга порта увидим результат работы программы.

Описание кода:
Подключаем библиотеку I²C Arduino для связи с EEPROM, затем задает 7-битный I²C-адрес EEPROM (базовый адрес).

В функции setup() инициализируем шину I2C командой Wire.begin(), запускаем последовательный порт командой Serial.begin(9600). Далее создается переменную nuber со значениями 12345 и вызывается функция writeInt(0x0020, number) для отправки данных. Затем программа ожидает 10 мс, чтобы микросхема EEPROM успела завершить внутренний цикл записи. После этого создается переменную readNumber для хранения адреса.

В функции loop() программа зацикливается. Далее вызывается функция vold writeInt()для инициализации передачи данных и функция readIntдля чтения данных.

Программа 5 — Сохранение и считывание чисел с плавающей запятой

Число с плавающей запятой ( float) в четыре раза больше обычного целого числа — целых 4 байта. Чтобы не записывать каждый байт вручную, можно использовать адресную арифметику. Вы берете физический адрес вашей переменной float, сообщаете компилятору, что теперь это адрес массива байтов, и копируете все 4 ячейки памяти в EEPROM одну за другой. При чтении необходимо выполнить обратное действие: прочитать 4 байта из последовательных ячеек во временный буфер типа float.

Если все правильно сделали при открытия мониторинга порта увидим результат работы программы.

Описание кода:
Подключаем библиотеку I²C Arduino для связи с EEPROM, затем задает 7-битный I²C-адрес EEPROM (базовый адрес).

В функции setup() инициализируем шину I2C командой Wire.begin(), запускаем последовательный порт командой Serial.begin(9600). Далее создается переменную temperature значениям 36.78 и вызывается функция writeFloat(0x0030, temperature) для отправки данных. Затем программа ожидает 10 мс, чтобы микросхема EEPROM успела завершить внутренний цикл записи. После этого создается переменную readTemp для хранения адреса.

В функции loop() программа зацикливается. Далее функция writeFloat преобразует 4-байтное число float в массив байтов через указатель и записывает их в EEPROM по I2C, начиная с заданного адреса, а функция readFloat выполняет обратную операцию: запрашивает 4 байта из памяти по тому же адресу и побитово собирает их обратно в переменную float через указатель на байтовый массив, полагаясь на прямой побайтовый доступ к памяти и порядок Little-Endian.

Программа 6 — Сохранение и чтение 16-битных и 32-битных шестнадцатеричных значений

Принцип записи ничем не отличается от работы с целыми числами или float. Если вам нужно сохранить, например, 32-битный MAC-адрес или код цвета, вы просто выделяете под него цепочку из нужного количества адресов (4 байта для 32-битного числа, 2 байта для 16-битного). Для упрощения кода можно использовать универсальную функцию-шаблон, которая принимает любое значение и записывает его по адресу через указатель:

Пример 16-битного HEX:

Пример 32-битного HEX:

Эти инструменты позволяют без лишних усилий записывать в память любые HEX-числа (например, 0x1A2B или 0xFF00AA55), что идеально подходит для хранения настроек калибровки оборудования, ID устройств или адресов в протоколах связи.

В итоге микросхема AT24C256 способна работать абсолютно с любыми типами информации. Неважно, имеете ли вы дело с целыми числами, дробными ( float) или шестнадцатеричными кодами — принцип всегда один: правильно «нарезать» данные на байты перед отправкой и правильно «склеить» их обратно при получении. Благодаря таким простым функциям ваш Arduino получает возможность постоянно хранить не просто разрозненные цифры, а целые массивы и настройки, делая устройство гораздо более автономным и надежным.

О нас Сергей

Посмотреть также

OLED термометр и гигрометр на SHT30\31

OLED термометр и гигрометр на SHT30\31

В этой статье расскажу расскажу как с помощью датчика температуры и влажности SHT32 и OLED …

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *