Urgent help: Arduino constantly restarting

Hi,

The urgency of solving this issue, is due to the closing deadline for my project.

Just to give a little background information on my project;

Current components:

Aim of the project:

  • To produce a device (using arduino only) that is able to read the barcode of items and lookup further information on that item (looking at a txt/csv file that is stored locally, ideally on an SD card), that is then displayed on an LCD screen. (Overall this device replicates the functionality of barcode scanners in supermarkets that display certain information regarding that item, onto a screen)

Current progress:

  • Barcode scanner connected correctly and working via a USB host shield (code used is working and is able to display the barcode on a 20x4 I2C LCD screen)

  • SD card adapter is functioning (able to see that the SD card is connected correctly and works as I was able to read and write to a file saved on the microSD)

  • LCD works perfectly (able to display barcode/SD/random information)

Problems & required help:

  • I am trying to implement the seaparately working components (mainly the Barcode scanner and SD card reader) but have come across an exhausting issue.
    The issue that persists is that the arduino continuously restarts every time the file on the SD card is accessed. Funnily enough, when I unplug the barcode scanner, the arduino no longer resets and is able to access the SD. But once plugged back in, the error continuous. Same thing goes for unpluggin the SD adapter and leaving the USB plugged in. Seems to have an issue when both are plugged in at the same time.

(SD focus: The SD is currently being used to match the barcode ID scanned to existing information on a txt file, that then displays information taken from the txt file that is in relation to the matched barcode)

Current Connections:

I am using a breadboard to share the voltage of 5v, between the LCD and microSD card reader.

LCD:
GND -> positive pin (on breadboard)
VCC -> 5v (negative pin on breadboard)
SDA -> A4
SCL -> A5

SD reader:
CS -> 4
MISO -> 12
MOSI -> 11
SCK -> 13
VCC -> 5v (negative pin on breadboard)
GND -> positive pin (on breadboard)
Using a USB host shield for the barcode scanner, so the pin setup is default to a shield host.

Here is the code I have implemented:

//SD SETUP
#include <SD.h>
#include <SPI.h>

int CS_PIN = 4;

File file;

#include <hid.h>
#include <hiduniversal.h>

#include <LiquidCrystal_I2C.h>
#include <avr/pgmspace.h>

#include <Usb.h>
#include <usbhub.h>
#include <avr/pgmspace.h>

#include <hidboot.h>

 
#define DISPLAY_WIDTH 20

LiquidCrystal_I2C lcd(0x27,2, 1, 0, 4, 5, 6, 7, 3, POSITIVE);
 
USB     Usb;
USBHub     Hub(&Usb);
HIDUniversal      Hid(&Usb);
String barcode = "";
char barcodeChar;
bool scanning = false;
int count = 0;
int count2 = 0;

HIDBoot<HID_PROTOCOL_KEYBOARD>    Keyboard(&Usb);
class KbdRptParser : public KeyboardReportParser
{  
  void PrintKey(uint8_t mod, uint8_t key);
protected:
  virtual void OnKeyDown  (uint8_t mod, uint8_t key);
  virtual void OnKeyPressed(uint8_t key);
public:
  void collectBarcode();
};
 
void KbdRptParser::OnKeyDown(uint8_t mod, uint8_t key)  
{
    uint8_t c = OemToAscii(mod, key);
 
    if (c)
        OnKeyPressed(c);
}
 
/* what to do when symbol arrives */
void KbdRptParser::OnKeyPressed(uint8_t key)  
{
static uint32_t next_time = 0;      //watchdog
static uint8_t current_cursor = 0;  //tracks current cursor position  

    lcd.print((char)key); // displays barcode
    barcodeChar = ((char)key);  // saves barcode char
    barcode = barcode + barcodeChar;  // adds barcode char to a string that holds the full barcode ID
    scanning = true; 
   count++;
       
};

KbdRptParser Prs;
 
void setup()
{
    Serial.begin( 9600 );
    Serial.println("Start");
 // USB SETUP
    initializeScanner();
    
 // SD SETUP
    initializeSD();  
}
 
void loop()
{  
  Usb.Task();  
  if(count > 7 && scanning == false && count < 14)
  {
 
    Serial.println(barcode);
    openFile();
    Serial.println(readLine(barcode));
    
    count = 0;
    barcode = "";
  }
    scanning = false;  
}

void initializeScanner()
{
  if (Usb.Init() == -1) {
      Serial.println("OSC did not start.");
  }
  else
  {
    Serial.println("Scanner ready");
  }

  delay( 200 );

  Hid.SetReportParser(0, (HIDReportParser*)&Prs);
  lcd.begin(DISPLAY_WIDTH, 4);
  lcd.clear();
  lcd.noAutoscroll();
  lcd.print("Ready");
  delay( 200 );
}

void initializeSD()
{
 // Serial.println("Initializing SD card...");
  //pinMode(CS_PIN, OUTPUT);

  if (SD.begin(CS_PIN))
  {
    Serial.println("SD card ready");
  } else
  {
    Serial.println("SD card failed");
    return;
  }
}

void openFile()
{
  file = SD.open("Database.txt");
  if (file)
  {
    Serial.println("File opened!");
  } else
  {
    Serial.println("Error opening file...");
  }
}

String readLine(String barcode)
{
 // file = SD.open("Database.txt");
   if (file)
    {
    //String barcode= "180900038";       
    String received = "";  
    String temp = "";
    char ch;
    bool temptest = false;
    Serial.println(F("Reading File"));
    while (file.available()) {
    ch = file.read();
    if (ch == ',') {            // Is the tag starting? / as result this is the tag ending       
      received = "";   
    } else if(ch == '\n') {      // Is the tag ending? / as the result this is the tag start      
      received = "";            // Empty the string, we don't need br      
    } else {                    // Everything's OK, append to the string
      received += ch;     
    }
    if(received == barcode || temptest == true)
    {      
      temp += ch;      
      temptest = true;
    }
    if (temptest == true && ch == ',')
    {
      temp = "";
    }
    if(temptest == true && ch == '\n')
    {
      return String(temp); //returns the barcode ID
      temptest = false;
      temp = "";
    }
    
    }
    file.close();
    //Serial.println("End of file ");
    lcd.setCursor(0, 1);
    lcd.print("End of file  ");
  }
  else
  {
    Serial.println("error opening datalog.txt");
  } 
  Serial.println("End of read function "); 
  
  delay(500);    
}

The result presented in the Serial monitor is below:

Thank you in advance for any help given. My current thought, is that it might be a power or memory issue (my current global variables are using 88% of the dynamic memory) but I am unsure.

 if(temptest == true && ch == '\n')
    {
      return String(temp); //returns the barcode ID
      temptest = false;
      temp = "";
    }

Wrong order (probably)

Which bit of it is in the wrong order?

What does "return" do?

Return, is sending back the extracted information (taken after matching the barcode ID) thats held within the txt file.

It is called and displayed in the line "Serial.println(readLine(barcode));"

The txt file currently has this:

180900038,11111

The first column represents the barcode ID that is to be matched, and the second column is the information wanting to be displayed (currently using fake information for testing)

The problem I'm having is that the code isn't getting far enough to reach the 'return String(temp);' line of code and instead is restarting the entire arduino continuously when trying to open/manipulate the file.

Hi,

The urgency of solving this issue, is due to the closing deadline for my project.

Just to give a little background information on my project;

Current components:

Aim of the project:

  • To produce a device (using arduino only) that is able to read the barcode of items and lookup further information on that item (looking at a txt/csv file that is stored locally, ideally on an SD card), that is then displayed on an LCD screen. (Overall this device replicates the functionality of barcode scanners in supermarkets that display certain information regarding that item, onto a screen)

Current progress:

The following components have been tested separately:

  • Barcode scanner connected correctly and working via a USB host shield (code used is working and is able to display the barcode on a 20x4 I2C LCD screen)

  • SD card adapter is functioning (able to see that the SD card is connected correctly and works as I was able to read and write to a file saved on the microSD)

  • LCD works perfectly (able to display barcode/SD/random information)

Problems & required help:

  • I am trying to implement the separately working components (mainly the Barcode scanner and SD card reader) but have come across an exhausting issue.
    The issue that persists is that the arduino continuously restarts every time the file on the SD card is accessed. Funnily enough, when I unplug the barcode scanner, the arduino no longer resets and is able to access the SD. But once plugged back in, the error continuous. Same thing goes for unpluggin the SD adapter and leaving the USB plugged in. Seems to have an issue when both are plugged in at the same time.

(SD focus: The SD is currently being used to match the barcode ID scanned to existing information on a txt file, that then displays information taken from the txt file that is in relation to the matched barcode)

Current Connections:

I am using a breadboard to share the voltage of 5v, between the LCD and microSD card reader.

LCD:
GND -> positive pin (on breadboard)
VCC -> 5v (negative pin on breadboard)
SDA -> A4
SCL -> A5

SD reader:
CS -> 4
MISO -> 12
MOSI -> 11
SCK -> 13
VCC -> 5v (negative pin on breadboard)
GND -> positive pin (on breadboard)
Using a USB host shield for the barcode scanner, so the pin setup is default to a shield host.

Here is the code I have implemented:

//SD SETUP
#include <SD.h>
#include <SPI.h>

int CS_PIN = 4;

File file;

#include <hid.h>
#include <hiduniversal.h>

#include <LiquidCrystal_I2C.h>
#include <avr/pgmspace.h>

#include <Usb.h>
#include <usbhub.h>
#include <avr/pgmspace.h>

#include <hidboot.h>

 
#define DISPLAY_WIDTH 20

LiquidCrystal_I2C lcd(0x27,2, 1, 0, 4, 5, 6, 7, 3, POSITIVE);
 
USB     Usb;
USBHub     Hub(&Usb);
HIDUniversal      Hid(&Usb);
String barcode = "";
char barcodeChar;
bool scanning = false;
int count = 0;
int count2 = 0;

HIDBoot<HID_PROTOCOL_KEYBOARD>    Keyboard(&Usb);
class KbdRptParser : public KeyboardReportParser
{  
  void PrintKey(uint8_t mod, uint8_t key);
protected:
  virtual void OnKeyDown  (uint8_t mod, uint8_t key);
  virtual void OnKeyPressed(uint8_t key);
public:
  void collectBarcode();
};
 
void KbdRptParser::OnKeyDown(uint8_t mod, uint8_t key)  
{
    uint8_t c = OemToAscii(mod, key);
 
    if (c)
        OnKeyPressed(c);
}
 
/* what to do when symbol arrives */
void KbdRptParser::OnKeyPressed(uint8_t key)  
{
static uint32_t next_time = 0;      //watchdog
static uint8_t current_cursor = 0;  //tracks current cursor position  

    lcd.print((char)key); // displays barcode
    barcodeChar = ((char)key);  // saves barcode char
    barcode = barcode + barcodeChar;  // adds barcode char to a string that holds the full barcode ID
    scanning = true; 
   count++;
       
};

KbdRptParser Prs;
 
void setup()
{
    Serial.begin( 9600 );
    Serial.println("Start");
 // USB SETUP
    initializeScanner();
    
 // SD SETUP
    initializeSD();  
}
 
void loop()
{  
  Usb.Task();  
  if(count > 7 && scanning == false && count < 14)
  {
 
    Serial.println(barcode);
    openFile();
    Serial.println(readLine(barcode));
    
    count = 0;
    barcode = "";
  }
    scanning = false;  
}

void initializeScanner()
{
  if (Usb.Init() == -1) {
      Serial.println("OSC did not start.");
  }
  else
  {
    Serial.println("Scanner ready");
  }

  delay( 200 );

  Hid.SetReportParser(0, (HIDReportParser*)&Prs);
  lcd.begin(DISPLAY_WIDTH, 4);
  lcd.clear();
  lcd.noAutoscroll();
  lcd.print("Ready");
  delay( 200 );
}

void initializeSD()
{
 // Serial.println("Initializing SD card...");
  //pinMode(CS_PIN, OUTPUT);

  if (SD.begin(CS_PIN))
  {
    Serial.println("SD card ready");
  } else
  {
    Serial.println("SD card failed");
    return;
  }
}

void openFile()
{
  file = SD.open("Database.txt");
  if (file)
  {
    Serial.println("File opened!");
  } else
  {
    Serial.println("Error opening file...");
  }
}

String readLine(String barcode)
{
 // file = SD.open("Database.txt");
   if (file)
    {
    //String barcode= "180900038";       
    String received = "";  
    String temp = "";
    char ch;
    bool temptest = false;
    Serial.println(F("Reading File"));
    while (file.available()) {
    ch = file.read();
    if (ch == ',') {            // Is the tag starting? / as result this is the tag ending       
      received = "";   
    } else if(ch == '\n') {      // Is the tag ending? / as the result this is the tag start      
      received = "";            // Empty the string, we don't need br      
    } else {                    // Everything's OK, append to the string
      received += ch;     
    }
    if(received == barcode || temptest == true)
    {      
      temp += ch;      
      temptest = true;
    }
    if (temptest == true && ch == ',')
    {
      temp = "";
    }
    if(temptest == true && ch == '\n')
    {
      return String(temp); //returns the barcode ID
      temptest = false;
      temp = "";
    }
    
    }
    file.close();
    //Serial.println("End of file ");
    lcd.setCursor(0, 1);
    lcd.print("End of file  ");
  }
  else
  {
    Serial.println("error opening datalog.txt");
  } 
  Serial.println("End of read function "); 
  
  delay(500);    
}

The result presented in the Serial monitor is below:

Thank you in advance for any help given. My current thought, is that it might be a power or memory issue (my current global variables are using 88% of the dynamic memory) but I am unsure.

How long have you been working on the project ?

Perhaps you forgot to turn the power off before removing and returning wires?

Paul

I am using a breadboard to share the voltage of 5v, between the LCD and microSD card reader.

What is supplying the 5V? If you are using the Arduino 5v pin, the try a separate power supply. Remember to connect the grounds.

Most likely you are overloading the power supply. Post a wiring diagram (hand drawn, not Fritzing).

The Arduino 5V output is not intended to power more than a couple of LEDs, and the scanner alone requires 100 mA.

@Dopeye, do not cross-post. Threads merged.

Dopeye:
Return, is sending back the extracted information (taken after matching the barcode ID) thats held within the txt file.

It also terminates the function in which it resides. Lines of code after the return() will not be executed.

While I agree with @jremington that the most likely cause is an inadequate power supply the second thing I would suspect is your use of the String class.

It is not a good idea to use the String (capital S) class on an Arduino as it can cause memory corruption in the small memory on an Arduino. This can happen after the program has been running perfectly for some time. Just use cstrings - char arrays terminated with '\0' (NULL).

A third thing to check is whether your code is writing beyond the end of an array and corrupting some other area of memory.

...R