Три случая из одной зимы. Станция в частном доме: begin прошёл, файл открылся, а через месяц чтение из лога возвращает ровно ноль байт — при том, что Serial каждую минуту отчитывался о записи. Даталоггер на балконе жил до минус десяти, а в двадцатиградусный мороз перестал видеть карту вовсе. Третий случай — сам виноват: вынул карту из работающего логгера «на секундочку», и половина декабря на ней пропала. Общее у всех трёх: проводка и уровни ни при чём — диагностика begin и большой чек-лист были пройдены до того, как железо поехало на место. Ни один из трёх скетчей при этом не менялся — менялись условия, в которых железо жило: питание, температура, порядок обращения с картой.
Здесь — полевая часть жизни карты, после удачного begin. Разбираю три симптома: файл живой, а из него ноль байт — что проверить в скетче и кому поверил каталог; карта молчит на морозе — что говорит паспорт и почему занос в тепло опаснее самого мороза; вынимание под током — что именно ломается в файловой системе за доли секунды. Питание при пиках записи — отдельным пунктом, потому что оно даёт половину загадочных зависаний логгеров. Порядок разбора простой: сначала то, что чинится скетчем, потом то, что лечится паяльником, потом то, что обходится протоколом поведения.
Ноль байт из живого файла
Симптом: SD.open проходит, available() сразу ноль, хотя файл на ПК открывается с содержимым. Первая проверка — кому верит библиотека: каталог хранит запись с именем и текущей длиной, и после обрыва питания между записью секторов и обновлением длины байты лежат на карте, но каталог показывает старую, меньшую границу. Библиотека честно отдаёт столько, сколько написано в каталоге, и ни байтом больше. Живой пример: после отключения света файл открывается, показывает половину недели, а занятое место на карте вдвое больше размера файла — это и есть байты за границей каталога. Механику этого разлома разобрал в уроке про сбой питания и потерянные кластеры; здесь следствие: хвост файла числится призраком, пока проверка диска не сверит цепочки с каталогом.
Вторая причина — запись в воздух: карта отвалилась или её выдернули, а скетч продолжает писать в открытый File. Возврат print библиотека не проверяет, ошибок не печатает, Serial отчитывается об успехах. Диагноз в одну строку: после каждой записи сравнивайте myFile.size() с прошлым значением — не вырос, значит карта отвалилась. Скетч ниже делает это сам и добавляет переинициализацию с паузой: контроллеру карты после сбоя нужны сотни миллисекунд тишины, повторный begin без паузы падает. Короткие сессии открыт-дописал-закрыл из урока про сессию файла закрывают вопрос заранее — между сессиями карта вправе отдыхать без последствий. Мой счётчик таких случаев пошёл с третьего: каждый раз Serial отчитывался бодро, а размер стоял — с тех пор проверка размера вписывается в скетч до того, как логгер уезжает на место.
#include <SPI.h>#include <SD.h> const int CS_PIN = 10; File logFile;unsigned long lastRow = 0;unsigned long lastSize = 0; void setup() { Serial.begin(9600); if (!SD.begin(CS_PIN)) { Serial.println("карта не поднялась"); while (true) delay(500); } logFile = SD.open("log.csv", FILE_WRITE); if (logFile) { logFile.println("sec,lux"); logFile.flush(); lastSize = logFile.size(); }} void loop() { unsigned long ms = millis(); if (ms - lastRow < 3000) return; lastRow = ms; logFile.print(ms / 1000); logFile.print(","); logFile.println(analogRead(A1)); logFile.flush(); unsigned long now = logFile.size(); if (now == lastSize) { // байт на карте не прибавилось Serial.println("размер не вырос: запись ушла в воздух"); logFile.close(); delay(800); // пауза: контроллер карты приходит в себя if (SD.begin(CS_PIN)) { logFile = SD.open("log.csv", FILE_WRITE); if (logFile) { lastSize = logFile.size(); Serial.println("переинициализация удалась, пишем дальше"); } } else { Serial.println("begin снова false: карте нужен ремонт, чек-лист в помощь"); } } else { lastSize = now; }}Питание при пиках и мороз: разные уроки одной зимы
Средний ток модуля SD скромный — десятки миллиампер. Но в момент сброса сектора карта потребляет скачком: у ряда моделей пики доходят до 100-200 миллиампер на десятки миллисекунд, цифры плавают от партии к партии — смотрите паспорт своей карты. Если линия 3,3 В собрана на длинных тонких проводах, а на модуле стоит штатный стабилизатор AMS1117 без конденсаторов рядом, пик просаживает питание, и контроллер карты в лучшем случае зависает до переинициализации, в худшем — недописывает сектор. Провода к модулю — те самые, что живут в ящике с надписью перемычки: на столе они прощают всё, на длинной линии питания прощают втрое меньше.
Симптом узнаваемый: begin проходит, одиночные строки пишутся, а стоит нарастить темп или попасть на пакетный flush — карта замолкает до перезапуска платы. Лечение копеечное: провода короче и толще, электролит 100-470 микрофарад вплотную к модулю, отдельная линия питания от источника вместо хвоста макетки. Просадки и стабильность писал в уроке про питание модуля, уровни 3,3 и 5 вольт — в уроке про согласование; здесь добавлю правило полевика: питание карты проверяют под нагрузкой, а не мультиметром в покое — в покое красиво всегда.
Спецификация SD Association отводит обычным картам рабочую полосу от минус 25 до плюс 75 градусов; индустриальные карты дают от минус 40 до плюс 85, и это не маркетинг, а другой температурный режим чипов и пайки. У дешёвых noname честный диапазон бывает уже паспортного: форумная классика — логгер, который работал до минус десяти и замолчал в двадцатиградусный мороз. Паспорт вашей карты смотрите до первого выноса на улицу: диапазон там указан явно, и это единственная цифра, которая имеет силу. Отсюда же правило покупки: для балконного или уличного проекта я беру карту с явным диапазоном в паспорте, а не самую ёмкую со скидки — гигабайты мороз не вылечат.
Второй морозный грех — конденсат, и он опаснее самого холода. Карта с улицы в тёплой комнате покрывается влагой за минуту: тонкий слой воды на контактах — и ридер видит мусор, а вы честно решаете, что карта умерла. Правило простое: полчаса-час прогрева до раскрытия герметичного пакетика или до вставки в слот. Герметичный пакет работает в обе стороны: в нём карта едет на мороз без влаги и возвращается домой без росы. На заносе в помещение страдает и плата: датчики плывут первые минуты, и показания первого получаса лучше помечать в логе как прогрев.
Вынимание под током и порядок прощания
Вынимание под током ломает не ячейки, а структуру: в момент выдёргивания контроллер карты может стоять посреди записи сектора или обновления FAT. Оборванная цепочка кластеров, потерянные кластеры, размер в каталоге меньше реального — набор уже знакомый, и картина на ПК предсказуемая: файл открывается, но хвост не виден, а проверка диска находит FILE0000.CHK. Парадокс в том, что карта сама остаётся рабочей: разметка чинится переформатированием после того, как архив спасён посекторной копией. Копия раньше лечения — правило без исключений: посекторная копия стоит времени картридера, а утерянный архив не возвращает ничто.
Поэтому в любом проекте с картой нужен протокол прощания, а не привычка «сейчас быстро выдерну». Минимум: пауза между строками в полсекунды, светодиод окна записи на корпусе и правило вынимать карту при ровном свете. Строгая версия — кнопка Стоп: скетч закрывает файл, печатает END, и только тогда карта вправе покинуть слот; такой протокол собран в уроке про логгер света. Граница метода: если симптомы повторяются при комнатной температуре, на коротких проводах и стабильном питании — карта доживает свой ресурс, копируйте архив и меняйте, медицина здесь бессильна.
| Симптом | Первая проверка | Чем лечится |
|---|---|---|
| Ноль байт из файла, begin в порядке | растёт ли myFile.size() после записи | сравнение размера, пауза и повторный begin; сессии короче |
| Карта молчит на морозе | паспорт: рабочая температура | индустриальная карта, утепление, прогрев до чтения |
| Зависает на пакете, строка-в-строку ок | просадка 3,3 В в момент сброса сектора | электролит 100-470 мкФ у модуля, короткие провода, своя линия |
| Хвост лога пропал после выдёргивания | проверка диска на посекторной копии | копия раньше лечения; протокол прощания на плате |
- 1. Файл открыт, available() сразу ноль, на ПК содержимое видно. Что проверяете первым?
- 2. Скетч пишет в File, а размер файла не растёт. Что происходит?
- 3. Пики тока карты при сбросе сектора могут достигать...
- 4. Рабочий диапазон обычной карты по спецификации SD Association:
- 5. Что ломается при вынимании карты под током?
- Ноль байт из живого файла: сначала врёт ли каталог, затем запись в воздух — size() до и после записи ставит диагноз.
- Запись в воздух лечится паузой и повторным SD.begin: контроллеру карты нужна тишина на сотни миллисекунд.
- Пики тока при записи до 100-200 мА: электролит 100-470 мкФ у модуля и короткие провода дешевле ночных отладок.
- Паспорт карты: обычные от минус 25 до плюс 75, индустриальные от минус 40 до плюс 85; конденсат при прогреве опаснее мороза.
- Вынимание под током ломает структуру, а не ячейки: окно записи на светодиоде и протокол прощания обязательны.
Частые вопросы по теме урока
- Файл открыт, available() сразу ноль, на ПК содержимое видно. Что проверяете первым?
- Каталог хранит текущую длину файла; обрыв между записью секторов и обновлением длины оставляет байты на карте, но библиотека отдаёт ровно столько, сколько записано в каталоге. Какой размер показывает каталог: после сбоя он может врать
- Скетч пишет в File, а размер файла не растёт. Что происходит?
- Возврат print библиотека не проверяет: карта отвалилась, а скетч продолжает печатать в открытый поток. Сравнение size() до и после записи ставит диагноз в одну строку. Запись уходит в воздух: карта отвалилась
- Пики тока карты при сбросе сектора могут достигать...
- Средний ток скромный, но сброс сектора тянет скачок; при слабой линии 3,3 В это просадка и зависание контроллера карты. Электролит у модуля и короткие провода снимают вопрос. 100-200 миллиампер на десятки миллисекунд у ряда моделей
- Рабочий диапазон обычной карты по спецификации SD Association:
- Обычным картам спецификация отводит минус 25..плюс 75, индустриальным — минус 40..плюс 85. У дешёвых noname реальный диапазон бывает уже паспортного. Минус 25 до плюс 75, индустриальные шире
- Что ломается при вынимании карты под током?
- Выдёргивание рвёт запись сектора или обновление FAT: оборванные цепочки, потерянные кластеры, старый размер в каталоге. Сама карта остаётся рабочей — разметку чинит переформатирование после спасения архива. Структура: цепочки кластеров и размер в каталоге