I am trying to make an rfid safe. I am using a finite state machine to have 3 states: locked, unlocked, and reprogramming. In the locked state, the arduino scans for either a button press, which changes the state to reprogramming, or a card read by the rfid reader, which changes the state to unlocked if it matches the authorized code stored in eeprom. In the unlocked state, the arduino waits 3 seconds, then relocks the safe and changes its state to locked. In the reprogramming state, the ardsuino stores the next card to be scanned in eeprom (this feature changes the card authorized to open the safe). If no card is scanned within 5 seconds, the state is changed back to locked. To execute the 5 second timeout, i am using millis(). In the code, i had the arduino print "reprograming..." to the serial monitor when the button is pressed, and "locked" when the 5 second timeout is over. The problem is, when the button is pressed, the serial monitor prints "reprogramming...", then "locked" in a cycle that runs 4-5 times in about a second. If the button is held down, it continues the cycle until the button is released.
#include <EEPROM.h>
#include "EEPROMAnything.h"
int val = 0;
char code[11]; //the code read by the RFID reader
char validCode [11]; //code read from EEPROM is stored here
int bytesread = 0;
#define buttonPin 10
int lockState = 0;
unsigned long time;void setup(){
Serial.begin (2400);
pinMode(2,OUTPUT);
pinMode (buttonPin, INPUT);
digitalWrite(2, LOW);
EEPROM_readAnything (0, validCode);
}bool readRFID(){
if(Serial.available() > 0) { // if data available from reader
if((val = Serial.read()) == 10) { // check for header
bytesread = 0;
while(bytesread<10) { // read 10 digit code
if( Serial.available() > 0) {
val = Serial.read();
if((val == 10)||(val == 13)) { // if header or stop bytes before the 10 digit reading
break; // stop reading
}
code[bytesread] = val; // add the digit
bytesread++; // ready to read next digit
}
}
if(bytesread == 10) { // if 10 digit read is complete
bytesread = 0;
digitalWrite(2, HIGH); // deactivate the RFID reader for a moment so it will not flood
delay(1500); // wait for a bit
digitalWrite(2, LOW); // Activate the RFID reader
return true;
}
}
}
return false;
}void loop() {
switch (lockState)
{
case 0: //Locked State
if (digitalRead (buttonPin) == LOW) // check if the button is pressed
{
time = millis();
lockState = 2;
Serial.println ("Reprogramming...");
break;
}
else if(readRFID()== true)
{
if (strcmp (code, validCode) == 0)
{
//unlock...
lockState = 1;
break;
}
}break;
case 1: //Unlocked State
digitalWrite (2, HIGH);
Serial.println ("Unlocked");
delay (3000);
Serial.println ("Locked");
digitalWrite (2, LOW);
//lock...
lockState = 0;
break;
case 2: //Reprogram
if (time + 5000 >= millis())
{
Serial.println ("Locked1");
lockState = 0;
break;
}else if (readRFID())
{
//EEPROM_writeAnything (0, code);
Serial.println ("Locked");
lockState = 0;
break;
}
//break;
}
}
the nature of the problem suggests (to me) that the code is performing the actions inside the
if (time + 5000 >= millis())
statement even when the condition is not true. How can I fox this problem? Is it my code, or is something wrong with my chip? please help...if you have any questions, please ask.