SD модуль. Запись в файл.

victora.mark
Offline
Зарегистрирован: 18.04.2018

Здравствуйте. 
К Arduino Nano подключен SD модуль. Возникла проблема с записью в файл. Вернее запись то идет, а потом код следующий за записью не проходит и цикл loop заново не начинается.
Если убрать кусок кода где идет запись, то все работает как надо. Такое ощущение, что там бесконечная запись идет в файл.
Подскажите, что может быть?

#include <SD.h>
#include <SPI.h>;

File myFile;

volatile boolean check = 0; //флаг для фиксирования совпадения ключа с базой

void setup() {
  Serial.begin(9600); // инициализация последовательного порта
  
  Serial.print("Initializing SD card..."); //инициальзация sd карты
  pinMode(4, OUTPUT);
  if (!SD.begin(4)) {
    Serial.println("initialization failed!");
    return;
  }
  Serial.println("initialization done.");
}

void loop() {
  String dataUID = "";
  
/*здесь кусок кода не относящийся к модулю SD, в зависимости от результата check = 0, либо check = 1*/

  if(check == 1) {
    Serial.println("OPEN");
  }
  else {
    Serial.println("CLOSE");
  }

  dataUID += String(uidDec);
  dataUID += ";";
  myFile = SD.open("log.txt");
  if (myFile) {
    myFile.println(dataUID);
    myFile.close();
    return;
  }
  else {
    Serial.println("error opening log.csv");
  }
  delay(2000);
}

 

victora.mark
Offline
Зарегистрирован: 18.04.2018

Подправила строчку:
 

myFile = SD.open("log.txt");

На:
 

myFile = SD.open("log.txt", FILE_WRITE);

Не помогло.

ЕвгенийП
ЕвгенийП аватар
Offline
Зарегистрирован: 25.05.2015

victora.mark пишет:
Вернее запись то идет, а потом код следующий за записью не проходит и цикл loop заново не начинается.

Какая у Вас версия IDE и что за библиотека SD, родная или откуда-то скачанная? Потому как если у Вас IDE и библиотека примерно как у меня, то ... сдаётся мне, что Вы что-то от нас скрываете. Либо у Вас на самом деле работает другой код, либо никакой записи идти не может, т.к. этот код не может компилироваться. Он должен выдавать ошибку:

'uidDec' was not declared in this scope

 

InfoTechDep
Offline
Зарегистрирован: 18.04.2018

В 38 строчке return производит возврат из функции, т.е. останавливает выполнение loop().

Ворота
Ворота аватар
Offline
Зарегистрирован: 10.01.2016

InfoTechDep пишет:

останавливает выполнение loop().

В смысле? loop() он на то и loop, чтобы сразу после возврата быть вызванным снова.

InfoTechDep
Offline
Зарегистрирован: 18.04.2018
Ворота
Ворота аватар
Offline
Зарегистрирован: 10.01.2016

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

InfoTechDep
Offline
Зарегистрирован: 18.04.2018

Ворота пишет:

Как прочитаешь, приходи, дальше говорить будем.

Не нужно переходить на личности. Это совсем не красит профессионала, скорее проявляет оппонента-самоучку с ЧСВ. Или здесь так принято?

Чем Ваши придирки к формулировке цикличности выполнения loop помешают return остановить текущее выполнение кода и начать loop заново?

victora.mark
Offline
Зарегистрирован: 18.04.2018

И правда, loop должен занова начаться. Причем return он же в if {} стоит. Да даже я пробовала и без этого return, все по старому.

victora.mark
Offline
Зарегистрирован: 18.04.2018

Библиотека родная. Версия 1.8.5.
Да, я там вырезала некоторую часть кода и uidDec у меня объявлено как unsigned long.
Может обновление нужно? Или скачать какую-нибудь стороннюю библиотеку.

ЕвгенийП
ЕвгенийП аватар
Offline
Зарегистрирован: 25.05.2015

victora.mark пишет:

Да, я там вырезала некоторую часть кода и uidDec у меня объявлено как unsigned long.
Может обновление нужно?

Для начала, сделайте пожалуйста код, который можно было бы запустить и увидеть Вашу проблему. Я понимаю, почему Вы вырезали - полный код часто перегружен мелочами и объёмен. Но когда возникает затык - очень полезно сделать маленький (как можно компактнее) код, который выполняется, демнстрирует проблему и достаточно мал для быстрого анализа. Очень часто в процессе выделения такого куска кода, проблема решается сама собой, т.к. автор видит, что беда исчезает и начинает понимать почему. Но даже если проблема не решится - покажите нам компактный, работающий код, чтобы мы могли на него посмотреть и попытаться Вам помочь.

arduinec
Offline
Зарегистрирован: 01.09.2015

victora.mark пишет:

И правда, loop должен занова начаться. Причем return он же в if {} стоит. Да даже я пробовала и без этого return, все по старому.

В приведенном фрагменте return не нужен, так как loop() и без него заново запускается. Непонятно чему равно uidDec и соответственно каким получится dataUID.

Совет: вывести dataUID в Serial (перед записью в файл).

victora.mark
Offline
Зарегистрирован: 18.04.2018
#include <SD.h>
#include <MFRC522.h>
#include <Servo.h>
#include <SPI.h>;

// константы подключения контактов SS и RST для RFID
#define RST_PIN 9
#define SS_PIN 10

File myFile;

volatile boolean check = 0; //флаг для фиксирования совпадения ключа с базой
volatile boolean flag = 0; //флаг для фиксирования прерывания

// Инициализация MFRC522
MFRC522 rfid(SS_PIN, RST_PIN); // Create MFRC522 instance.
unsigned long uidDec, uidDecTemp;  // для храниения номера метки в десятичном формате

void setup() {
  Serial.begin(9600); // инициализация последовательного порта
  
  SPI.begin(); // инициализация SPI

  
  Serial.print("Initializing SD card..."); //инициальзация sd карты
  pinMode(4, OUTPUT);
  if (!SD.begin(4)) {
    Serial.println("initialization failed!");
    return;
  }
  Serial.println("initialization done.");

  rfid.PCD_Init(); // инициализация MFRC522
  Serial.println("Scan PICC");

}

void loop() {
  String dataUID = "";
  
  }*/
  digitalWrite(4, HIGH); //SD отключаем
  digitalWrite(10, LOW); //включаем RFID
  
  if (!rfid.PICC_IsNewCardPresent()) { //если карты нету, выходим, начинаем заново
    return;
  }

  // чтение карты
  if (!rfid.PICC_ReadCardSerial()) { //если данные не считаются
    return;
  }

  //если карта прочиталась:
  uidDec = 0;
  for (byte i = 0; i < rfid.uid.size; i++) {
    uidDecTemp = rfid.uid.uidByte[i];
    uidDec = uidDec * 256 + uidDecTemp;
  }
  Serial.println("Card UID: ");
  Serial.println(uidDec); // выводим UID метки в консоль
  
  digitalWrite(10, HIGH); //выключаем RFID
  digitalWrite(4, LOW); //включаем SD
 
  //поиск ключа в базе
  File myFile = SD.open("users.csv");
  if(myFile) {
    unsigned long buff = 0;
    while (myFile.available()) {
      char ch = myFile.read();
      if(ch == ';') {
        //Serial.println("In File: ");
        //Serial.println(buff);
        if(buff == uidDec) {
       //   Serial.println("Check!");
          check = 1; //если код карты в базе есть
          break;
        }
        else {
         // Serial.println("No check :(");
          check = 0; //если кода карты в базе нет
          buff = 0;
        }
      }
      else if(ch >= 48 && ch <= 57) {   //коды цифр в таблице ASCII
        buff *= 10;
        buff += ch - 48;
        //Serial.println(buff);
      }
    }
    myFile.close();
  } 
  else Serial.println("error opening users.csv");

  if(check == 1) {
    Serial.println("OPEN");
  }
  else {
    Serial.println("CLOSE");
  }
  
  dataUID += String(uidDec);
  dataUID += ";";
  myFile = SD.open("log.txt");
  if (myFile) {
    myFile.println(dataUID);
    myFile.close();
  }
  else {
    Serial.println("error opening log.txt");
  }
  digitalWrite(4, HIGH); //выключаем SD
  //////////////////////////////////////////////////////////////////////////
  delay(2000);
}
   


 

ЕвгенийП
ЕвгенийП аватар
Offline
Зарегистрирован: 25.05.2015

Хорошо. Пока я не вижу где бы она могла зацикливаться. Давайте сделаем следующее:

1.
Вы вставите

Serial.print("Line:"); Serial.println(__LINE__);

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

2.
Смоделируете затык и выложите получившийся код вместе с копипастой напечатанного лога.