Hello everyone!
I have the problem I mentioned in the title.. So I have connected Arudino with Ethernet shield to my website to read data between "<" and ">" using a couple of tutorials I found all over the internet. So when it reads 1 it turns on an LED, when there is 0 it turns off an LED nad this works just fine. The problem is that after a while, sometimes few seconds, sometimes a few minutes the Arduino just freezes and won't do anything. When I start (or restart) Serial monitor Arduino starts working again just fine until it freezes again. Does anyone know what could be the problem?
The code is below.
Thank you in advance!
#include <Ethernet.h>
#include <SPI.h>
////////////////////////////////////////////////////////////////////////
//CONFIGURE
////////////////////////////////////////////////////////////////////////
//byte server[] = { 174,123,231,247 }; //ip Address of the server you will connect to
char server[] = "peho1.byethost24.com";
//The location to go to on the server
//make sure to keep HTTP/1.0 at the end, this is telling it what type of file it is
String location = "/elementi/ HTTP/1.0";
String prosli="0";
IPAddress ip(192,168,0,177);
// if need to change the MAC address (Very Rare)
byte mac[] = {
0xDE, 0xAD, 0xBE, 0xEF, 0xFE, 0xED };
////////////////////////////////////////////////////////////////////////
EthernetClient client;
char inString[32]; // string for incoming serial data
int stringPos = 0; // string index counter
boolean startRead = false; // is reading?
void setup(){
pinMode(6, OUTPUT);
Serial.begin(9600);
if (Ethernet.begin(mac) == 0) {
Serial.println("Failed to configure Ethernet using DHCP");
// no point in carrying on, so do nothing forevermore:
// try to congifure using IP address instead of DHCP:
Ethernet.begin(mac, ip);
}
}
void loop(){
String pageValue = connectAndRead(); //connect to the server and read the output
Serial.println(pageValue); //print out the findings.
if (pageValue == "1" && prosli=="0"){
digitalWrite(6, HIGH);
prosli="1";
Serial.println("Led On");
}
else if (pageValue == "0" && prosli=="1"){
digitalWrite(6, LOW);
prosli="0";
Serial.println("Led Off");
}
else{
Serial.println("Ne radim nista!");
}
delay(3000); //wait 5 seconds before connecting again
}
String connectAndRead(){
//connect to the server
Serial.println("connecting...");
//port 80 is typical of a www page
if (client.connect(server, 80)) {
Serial.println("connected");
client.print("GET ");
client.println(location);
client.println("Host: peho1.byethost24.com");
client.println("Connection: close");
client.println();
//Connected - Read the page
return readPage(); //go and read the output
}
else{
return "connection failed";
}
}
String readPage(){
//read the page, and capture & return everything between '<' and '>'
stringPos = 0;
memset( &inString, 0, 32 ); //clear inString memory
while(true){
if (client.available()) {
char c = client.read();
if (c == '<' ) { //'<' is our begining character
startRead = true; //Ready to start reading the part
}
else if(startRead){
if(c != '>'){ //'>' is our ending character
inString[stringPos] = c;
stringPos ++;
}
else{
//got what we need here! We can disconnect now
startRead = false;
client.stop();
client.flush();
Serial.println("disconnecting.");
return inString;
}
}
}
}
}
Add the serial output below. Does the code lock up after "Reading page" but doesn't display "disconnecting"?
String connectAndRead(){
//connect to the server
Serial.println("connecting...");
//port 80 is typical of a www page
if (client.connect(server, 80)) {
Serial.println("connected");
client.print("GET ");
client.println(location);
client.println("Host: peho1.byethost24.com");
client.println("Connection: close");
client.println();
//Connected - Read the page
// add this serial print
Serial.println(F("Reading page"));
return readPage(); //go and read the output
}
else{
return "connection failed";
}
}
edit: If not, can you be more specific about where in the code you think it is failing. What is the last thing displayed on the serial monitor when it does fail?
As a test, replace your readPage function with this. You can modify it later to retrieve the data you want. Run it for a while to see if this corrects the freezing. If you ever see a "Timeout" message on the serial monitor, your old code would have stopped there.
String readPage() {
// connectLoop controls the hardware fail timeout
int connectLoop = 0;
while(client.connected())
{
while(client.available())
{
char ch = client.read();
Serial.write(ch);
// set connectLoop to zero if a packet arrives
connectLoop = 0;
}
connectLoop++;
// if more than 10000 milliseconds since the last packet
if(connectLoop > 10000)
{
// then close the connection from this end.
Serial.println();
Serial.println(F("Timeout"));
client.stop();
}
// this is a delay for the connectLoop timing
delay(1);
}
Serial.println();
Serial.println(F("disconnecting."));
// close client end
client.stop();
String rtnVal = "Done";
return rtnVal;
}
I haven't checked the out every time, as it's a php script which only reads from database and echos <1> or <0>.
But even if there's nothing written, wouldn't it just disconnect and reconnect, the same as after reading the string?
else{
//got what we need here! We can disconnect now
startRead = false;
client.stop();
client.flush();
Serial.println("disconnecting.");
return inString;
Note that section of code is an "else". If you do not find the '>' character, that section of code is never executed.
if(c != '>'){ //'>' is our ending character
inString[stringPos] = c;
stringPos ++;
}
else{
//got what we need here! We can disconnect now
startRead = false;
client.stop();
client.flush();
Serial.println("disconnecting.");
return inString;
}
Oh yes, that's true.. I haven't noticed that other "if" after "else if".. Do you think it would work if I added another else, like this:
if (client.available()) {
char c = client.read();
if (c == '<' ) { //'<' is our begining character
startRead = true; //Ready to start reading the part
}
else if(startRead){
if(c != '>'){ //'>' is our ending character
inString[stringPos] = c;
stringPos ++;
}
else{
//got what we need here! We can disconnect now
startRead = false;
client.stop();
client.flush();
Serial.println("disconnecting.");
return inString;
}
}
else{
client.stop();
client.flush();
Serial.println("disconnecting.");
return inString;
}
}
Do you think it would work if I added another else, like this:
No.
edit: This should work. I haven't checked it for errors tho. I changed the return type to char. If it returns 0 (not '0'), then it did not find the '<' character. Otherwise, it should return '0' or '1' (ascii 48 or 49).
char readPage() {
char rtnVal = 0;
char startRead = 0;
// connectLoop controls the hardware fail timeout
int connectLoop = 0;
while(client.connected())
{
while(client.available())
{
char ch = client.read();
Serial.write(ch);
if(ch == '<') startRead = 1;
else if(ch == '>') startRead = 0;
else if(startRead == 1) rtnVal = ch;
// set connectLoop to zero if a packet arrives
connectLoop = 0;
}
connectLoop++;
// if more than 10000 milliseconds since the last packet
if(connectLoop > 10000)
{
// then close the connection from this end.
Serial.println();
Serial.println(F("Timeout"));
client.stop();
}
// this is a delay for the connectLoop timing
delay(1);
}
Serial.println();
Serial.println(F("disconnecting."));
// close client end
client.stop();
return rtnVal;
}
I would have posted this earlier, but the arduino websites are choking. Something is going wrong with the servers. It is becoming almost impossible to login or post anything. I can't access the reference pages at all now.
Thank you a lot! This seems to work, at least for now. I'll leave it running until the morning to see what happens..
There have been a couple of errors, but replacing strings with chars solved them..
Thanks a lot again!