This script is supposed to read a file of words. Different lengths. I only want 8 character words. Discard anything else. Remove CR and/or LF
Store 100 passwords in an multidimensional array... password[100][9]
After many hours I get the LCD to say Index = 1 (around line 110).. If I remove "index = 0" a little further down, it does not work at all. Index = never appears on the LCD.
Perhaps someone can look at this and see the problem right away. Right now I am frustrated.
Thanks for the help.
/* Using this for debug messages */
#include <SoftwareSerial.h>
/* Ethernet shield SD Card Reader */
#include <SPI.h>
#include <SD.h>
/* LCD Screen */
#include <Wire.h>
#include <LiquidCrystal_I2C.h>
#define DEBUGSERIALTXPIN 8
#define DEBUGSERIALRXPIN -1
#define SDCHIPSELECT 9
#define FILENAME "passwords1.txt"
#define NUMBEROFPASSWORDS 100
#define PASSWORDLENGTH 8
/* GLOBALS */
unsigned long LineNumber = 0;
char password[NUMBEROFPASSWORDS][PASSWORDLENGTH] = {""};
// I2C LCD
LiquidCrystal_I2C lcd(0x27, 20, 2); // Set LCD address to 0x27 and 20 chars wide by 2 rows tall
/* ***********************
*** SETUP ***
*********************** */
void setup()
{
char tmp;
int x;
// Disable the Ethernet SPI
pinMode(10, OUTPUT);
digitalWrite(10, HIGH);
// Serial ports
Serial.begin(19200);
Serial1.begin(19200);
Serial2.begin(19200);
Serial3.begin(19200);
// Software Serial for Debug messages
SoftwareSerial debugSerial(DEBUGSERIALRXPIN, DEBUGSERIALTXPIN); // RX, TX
debugSerial.begin(9600);
debugSerial.print("Software Serial TX ready on pin = ");
debugSerial.println(DEBUGSERIALTXPIN);
// LCD Init
lcd.init();
lcd.backlight();
lcd.setCursor(1, 0);
lcd.print("LCD Initialized");
lcd.setCursor(1, 1);
// Initialize SD Card
if (!SD.begin(SDCHIPSELECT))
{
lcd.clear();
lcd.print("SD Card Error!");
debugSerial.println("initialization failed.");
while (true);
} // End of IF
} // End of Setup
/* **********************
*** LOOP ***
********************** */
void loop()
{
int CurrentPasswordNumber;
char str[80] = ""; // Assume a word will not be more than 80 chars
byte index = 0;
char nextChar;
File myFile = SD.open(FILENAME);
while (myFile.available() > 0) // File has data
{
while ( CurrentPasswordNumber < NUMBEROFPASSWORDS)
{
nextChar = myFile.read();
while (nextChar != '\r' && nextChar != '\n') {
nextChar = myFile.read();
if (nextChar != '\r' && nextChar != '\n')
{ // nextChar is NOT a CR or LF..
str[index++] = nextChar; // So add nextChar to str[index] (increment index after)
str[index] = '\0'; // Keep last element terminated
}
else
{ // The else executes if nextChar IS a CR or LF...
nextChar = myFile.peek(); // Peek at next char to see if it too is a CR or LF
if ((nextChar == '\n') || (nextChar == '\r'))
{
nextChar = myFile.read(); // Discard the next character in myFile.Read()
}
}
lcd.clear();
lcd.print("index = ");
lcd.setCursor(1,1);
lcd.print(index); // INDEX IS ALWAYS 1
if (index == PASSWORDLENGTH)
{
password[CurrentPasswordNumber][0] = str;
lcd.clear();
lcd.print("Added. x = "); lcd.print(CurrentPasswordNumber);
delay(3000);
CurrentPasswordNumber++;
}
index = 0; // Removing this line seems to cause havoc
LineNumber++;
} // End of while to get next char
} // X Number of passwords while
} // The end of file hit
myFile.close(); // Reached end of file
}
// EOF
is within an if, which is within an if, which is within a while, which is within a while, which is within a while, which is within void loop().
And the result is:
and
which doesn't surprise me.
If you write procedures (which you test as you proceed) and use some indirection, the problem will probably clear itself for you, or at least become much more manageable.
If I knew what this was doing or how to deal with it, please can someone explain?
while (readLine (myFile, str, sizeof (str)))
{
char *p = & password [nPassword++][0];
strncpy (p, str, PASSWORDLENGTH); // destination, source... seems like it should be str, p
}
This appears to copy anything to the "password" array and cuts it at the length??
We need to add to the password array only if it is 8 characters. If it is more than 8 or less than 8, ignore it and move on to the next one in the file.
Nothing happens. I mean the LCD says "LCD Initialized".. that's it. I ran into this last night and wound up putting everything in loop() which led to the spaghetti!! We need to call File after SD.Init and stuff (which is done in setup). So I put File between void setup() {} and void loop() {} .. which made no diff haha
int readLine (File myFile, char *s, int size )
{
int n = 0;
while (myFile.available () > 0)
{
char c = myFile.read ();
charnumber++; // Count the chars
if (c != '\r')
s [n++] = c;
if (size <= n || '\n' == c)
{
s [n-1] = 0;
break;
}
}
return n;
}
// -------------------------------------
void readPasswords (void)
{
File myFile = SD.open (FILENAME);
char str [80];
int currentLoop = 0;
nPassword = 0;
if ( charnumber > 0 ) { // Skip to where we left off!!!!!!
myFile.seek(charnumber);
}
while (readLine (myFile, str, sizeof (str)))
{
char *p = & password [nPassword++][0];
strncpy (p, str, PASSWORDLENGTH); // destination, source
currentLoop++;
if (currentLoop == NUMBEROFPASSWORDS)
{
currentLoop = 0;
break;
}
}
}