Глюки SD.h?

Monster
Offline
Зарегистрирован: 18.06.2012

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

LogFile=SD.open(FileName,FILE_WRITE);
    if (LogFile) 
    {
      logtime=((double)micros()/(double)1000);
      LogFile.print(logtime);                 LogFile.print(",");
      LogFile.print(logtime);                 LogFile.print(","); 
      LogFile.print(PassiveLeft_Speed);       LogFile.print(",");
      LogFile.print(PassiveRight_Speed);      LogFile.print(",");
      LogFile.print(PassiveAxleSpeed);        LogFile.print(","); 
      LogFile.print(ActiveLeft_Speed);        LogFile.print(",");
      LogFile.print(ActiveRight_Speed);       LogFile.print(",");
      LogFile.print(ActiveAxleSpeed);         LogFile.print(",");
      LogFile.print(DeltaSpeed);              LogFile.print(",");
      LogFile.print(Fx);                      LogFile.print(",");  //
      LogFile.print(Fy);                      LogFile.print(",");  // вектор общего ускорения
      LogFile.print(Fz);                      LogFile.print(",");  //
      LogFile.print(F);                       LogFile.print(",");
      LogFile.print(Gx);                      LogFile.print(",");  //
      LogFile.print(Gy);                      LogFile.print(",");  // вектор гравитации
      LogFile.print(Gz);                      LogFile.print(",");  //
      LogFile.print(G);                       LogFile.print(",");
      LogFile.print(Ax);                      LogFile.print(",");  //
      LogFile.print(Ay);                      LogFile.print(",");  // вектор чистого ускорения
      LogFile.print(Az);                      LogFile.print(",");  //
      LogFile.print((double)A*(double)9.81);  LogFile.print(",");  // ускорение в м/с^2
      LogFile.print(Retard_Flag);             LogFile.print(",");
      LogFile.print(Passive_VSS_Interval);    LogFile.print(",");
      LogFile.print(Active_VSS_Interval);     LogFile.println(",");
      LogFile.close();
    }

Наглядный пример с выпавшими пакетами:

Есть ли способ не иметь подобных багов?  Может есть новая версия библиотеки у кого? Или проблема не в ней?
Спасибо.

Monster
Offline
Зарегистрирован: 18.06.2012

Забыл сказать, что все переменные на время тестов = 0 и никаких вычислений не производится нигде!

AlexFisher
AlexFisher аватар
Offline
Зарегистрирован: 20.12.2011

Не, нужен весь текст 

Monster
Offline
Зарегистрирован: 18.06.2012

Это и есть весь текст.
В сетапе() только инит каналов как вход/выход и все.

step962
Offline
Зарегистрирован: 23.05.2011

Monster пишет:
Это и есть весь текст.
В сетапе() только инит каналов как вход/выход и все.

а инклюды?
а информация об источниках используемых библиотек?
а объявления переменных?
А оберточная функция для приведенного огрызка кода?
Неужели ничего этого нет?

Monster
Offline
Зарегистрирован: 18.06.2012
#include <SD.h>

uint32_t i,j;
File LogFile;

void setup() 
{    
  SD.begin(4);
  LogFile=SD.open("test.csv",FILE_WRITE);
  LogFile.println("Time,i,j,");
  LogFile.close();
} 

void loop() 
{
  LogFile=SD.open("test.csv",FILE_WRITE);
  i=(micros());
  ++j;
  LogFile.print(i);                 LogFile.print(",");
  LogFile.print(i);                 LogFile.print(","); 
  LogFile.print(j);                 LogFile.println(",");
  LogFile.close();
}
Monster
Offline
Зарегистрирован: 18.06.2012

Результат:

AlexFisher
AlexFisher аватар
Offline
Зарегистрирован: 20.12.2011

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

Monster
Offline
Зарегистрирован: 18.06.2012

В коде библиотеки указан параметр аля SPI_HALF_SPEED.

Поэтому судя по всему скорость там не максимальная, а половина от оной.

Так понимать надо ждать новую версию библиотеки, либо отказаться от нее и гонять по SPI данные самостоятельно?

AlexFisher
AlexFisher аватар
Offline
Зарегистрирован: 20.12.2011

Я имел в виду не максимальную скорость SPI, а Ваш скетч! У Вас нет никакой синхронизации выборок по времени.

Monster
Offline
Зарегистрирован: 18.06.2012

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

AlexFisher
AlexFisher аватар
Offline
Зарегистрирован: 20.12.2011

Может быть и криво...

Где-то может быть кэширование... Попробуйте не закрывать файл, пользоваться методом flash()...

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

Типа того.

Monster
Offline
Зарегистрирован: 18.06.2012

Наверное flush()?

Напрямую - используя memory-mapping, работая с картой по отзеркаленному куску памяти с оной?

AlexFisher
AlexFisher аватар
Offline
Зарегистрирован: 20.12.2011

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

Monster
Offline
Зарегистрирован: 18.06.2012

Возможно у Вас есть какой-то пример?

Буду признателен. :)

AlexFisher
AlexFisher аватар
Offline
Зарегистрирован: 20.12.2011

Нет, примера нет. Это просто "размышления на тему", основанные на чтении хедеров и сишных файлов библиотек.

Monster
Offline
Зарегистрирован: 18.06.2012

Писать по адресам - довольно просто, надо только знать область куда отзеркалена карта.

Но сложность в том, что тогда придется делать форматированный файл, а это неудобно и будет жрать время МК...

Да и есть как есть - тоже неплохо, и не парит в целом т.к. ни на чем не отражается для анализа лога.

Просто было интересно в чем проблемка и есть ли простые решения оной простым апдейтом SD.h.

Спасибо. :)