I've been working on a sketch wherein some data is downloaded from an HTTP server and is then processed on the Arduino (printed, as it happens, but I don't think that's important). In my original sketches, I was occasionally seeing transfers fail midway through.
The original sketch was more complex (the data was being cached to a file on an SD card, and there was code which attempted to handle pauses in the data), but upon whittling the sketch down to a minimal skeleton, I am still seeing around 10% of the transfers fail to download all of the data.
I've attached the sketch and serial monitor log to a gist - https://gist.github.com/1994216 - and I've included the sketch and a snippet of the log here:
#include <SPI.h>
#include <Ethernet.h>
byte mac[] = { 0x90, 0xA2, 0xDA, 0x00, 0x86, 0x67 }; //physical mac address
EthernetClient client;
#define debug(a) Serial.print(millis()); Serial.print(": "); Serial.println(a);
#define debug2(a, b) Serial.print(millis()); Serial.print(": "); Serial.print(a); Serial.println(b);
void setup(){
Serial.begin(9600);
// start the Ethernet connection:
if (Ethernet.begin(mac) == 0) {
debug("DHCP Failed");
// no point in carrying on, so do nothing forevermore:
while(true);
}
// print your local IP address:
debug2("IP address: ", Ethernet.localIP());
}
char* host = "192.168.1.22";
int port = 4567;
char *path = "/";
int totalRequestSize = 8346;
int failures = 0;
int requests = 0;
void loop() {
if (client.connect(host, port)) {
debug("Connected.");
client.print("GET "); client.print(path); client.println(" HTTP/1.0\n");
int length = 0;
while(client.connected() && !client.available()) delay(1); //waits for data
while(client.available()) {
client.read();
length++;
}
client.stop();
requests++;
if (length != totalRequestSize) {
failures++;
}
debug2("Total read: ", length);
Serial.print("Total failures: "); Serial.print(failures); Serial.print("/"); Serial.println(requests);
} else {
debug("Couldn't connect.");
}
}
170569: Connected.
172350: Total read: 8346
Total failures: 6/93
172555: Connected.
174336: Total read: 8346
Total failures: 6/94
174339: Connected.
175706: Total read: 1706
Total failures: 7/95
175709: Connected.
177753: Total read: 4889
Total failures: 8/96
177756: Connected.
179536: Total read: 8346
Total failures: 8/97
179539: Connected.
181321: Total read: 8346
Total failures: 8/98
181324: Connected.
182976: Total read: 7740
Total failures: 9/99
182979: Connected.
184761: Total read: 8346
Total failures: 9/100
184764: Connected.
186546: Total read: 8346
Total failures: 9/101
186549: Connected.
188190: Total read: 2989
Total failures: 10/102
188193: Connected.
189976: Total read: 8346
Total failures: 10/103
189979: Connected.
191762: Total read: 8346
Total failures: 10/104
The data which is being downloaded is simply an ASCII file for 100 rows of 80 '#' characters. As you can see in the logs above, most requests download 8346 bytes (the response headers + the ~8000 byte file), but intermittently there are requests where the data terminates earlier at any point in the stream.
It's running on an Arduino Uno and a recent Ethernet shield (including an SD card slot), using the Arduino 1.0 IDE.
As you can imagine, this is quite frustrating, as I'd like this system to run without much intervention. As I mentioned above, earlier versions of the sketch included code to wait for a certain period of time if there was no data available, checking periodically to see if the data can be resumed before finally closing the connection, but I still see the behaviour with that logic present.
Does anyone have any ideas about what might be going on, or even how I can make this sketch simpler to try and isolate where the issue might be?