-->
Page 1 of 1

Is favicon.ico request causing server to stick in while loop

PostPosted: Mon Oct 26, 2015 6:06 am
by Barnabybear
Hi, I’m running the following code from IOT-playground. All mostly runs as expected until I’m unable to connect to send requests. This happens every time I run the code, the only variable is the length of time before it becomes unresponsive.
Code: Select all/*
 *  This sketch demonstrates how to set up a simple HTTP-like server.
 *  The server will set a GPIO pin depending on the request
 *    http://server_ip/gpio/0 will set the GPIO2 low,
 *    http://server_ip/gpio/1 will set the GPIO2 high
 *  server_ip is the IP address of the ESP8266 module, will be
 *  printed to Serial when the module is connected.
 */

#include <ESP8266WiFi.h>

const char* ssid = "your-ssid";
const char* password = "your-password";

// Create an instance of the server
// specify the port to listen on as an argument
WiFiServer server(80);

void setup() {
  Serial.begin(115200);
  delay(10);

  // prepare GPIO2
  pinMode(2, OUTPUT);
  digitalWrite(2, 0);
 
  // Connect to WiFi network
  Serial.println();
  Serial.println();
  Serial.print("Connecting to ");
  Serial.println(ssid);
 
  WiFi.begin(ssid, password);
 
  while (WiFi.status() != WL_CONNECTED) {
    delay(500);
    Serial.print(".");
  }
  Serial.println("");
  Serial.println("WiFi connected");
 
  // Start the server
  server.begin();
  Serial.println("Server started");

  // Print the IP address
  Serial.println(WiFi.localIP());
}

void loop() {
  // Check if a client has connected
  WiFiClient client = server.available();
  if (!client) {
    return;
  }
 
  // Wait until the client sends some data
  Serial.println("new client");
  while(!client.available()){
    delay(1);
  }
 
  // Read the first line of the request
  String req = client.readStringUntil('\r');
  Serial.println(req);
  client.flush();
 
  // Match the request
  int val;
  if (req.indexOf("/gpio/0") != -1)
    val = 0;
  else if (req.indexOf("/gpio/1") != -1)
    val = 1;
  else {
    Serial.println("invalid request");
    client.stop();
    return;
  }

  // Set GPIO2 according to the request
  digitalWrite(2, val);
 
  client.flush();

  // Prepare the response
  String s = "HTTP/1.1 200 OK\r\nContent-Type: text/html\r\n\r\n<!DOCTYPE HTML>\r\n<html>\r\nGPIO is now ";
  s += (val)?"high":"low";
  s += "</html>\n";

  // Send the response to the client
  client.print(s);
  delay(1);
  Serial.println("Client disonnected");

  // The client will actually be disconnected
  // when the function returns and 'client' object is detroyed
}

I added some Serial.prints to debug. The code is getting stuck in the ‘while(!client.available())’ statement.
Code: Select all  // Check if a client has connected
  WiFiClient client = server.available();
  if (!client) {
    return;
  }
 
  // Wait until the client sends some data
  Serial.println("new client");
  while(!client.available()){ //<<<<<<<<< gets stuck in loop here
    delay(1);
  }

I commented the '// Wait until the client sends some data' block out & have not had the problem since. If for some reason a request is received that it doesn’t like it falls through to ‘Serial.println("invalid request");’., which is not a problem.
From debugging I noticed that when the code became unresponsive it was always just after a valid request. With this block commented out I now frequently get an ‘invalid request’ directly after a valid one. Which I believe is a 'favicon.ico' request.
Code: Select allSerial prints.
GET /gpoi/0 HTTP/1.1
Client disconnected
GET /favicon.ico HTTP/1.1
Invalid request

Is it possible that the ‘favicon.ico’ request was causing the code to stick in the ‘while(!client.available())’ statement?
Is this the nature of the ‘favicon.ico’ request or the coding?
Any thoughts on the best way to correct this?

Thanks.

Re: Is favicon.ico request causing server to stick in while

PostPosted: Mon Oct 26, 2015 8:11 am
by eduperez
Why do you close the client after receiving and invalid request? I think you should just answer with a HTTP-404 and continue normally.