hellerchr / esp8266-websocketclient

ESP8266 WebsocketClient

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

Drop in firmware when connecting to a non-existing server.

RVelichko opened this issue · comments

Thank you for your library, it was very useful to me in the ESP32 project, but there is a problem:
when I connect to a non-existing server, the firmware crashes. In your code, there is no verification after calling WiFiClient :: connect (...) and reading is performed in a loop until the "\ 0" appears, but this is a guaranteed way out of the available address space. I fixed it myself and everything works fine. Correct this for all who will continue to use your library.

Thanks for reporting this!
Would you like to your fix through a pull request?

I do not have permissions to work with your repository, even to add my branches.

bool WebSocketClient::connect(String host, String path, int port) {
// success criteria
bool hasCorrectStatus = false;
bool isUpgrade = false;
bool isWebsocket = false;
bool hasAcceptedKey = false;
bool isConnected = this->client->connect(host.c_str(), port);

if (isConnected) {
	// send handshake
	String handshake = "GET " + path + " HTTP/1.1\r\n"
			"Host: " + host + "\r\n"
			"Connection: Upgrade\r\n"
			"Upgrade: websocket\r\n"
			"Sec-WebSocket-Version: 13\r\n"
			"Sec-WebSocket-Key: " + generateKey() + "=\r\n";

	if (authorizationHeader != "")
		handshake += "Authorization: " + authorizationHeader + "\r\n";

	handshake += "\r\n";

	DEBUG_WS("[WS] sending handshake");
	DEBUG_WS(handshake);

	client->write(handshake.c_str());

	bool endOfResponse = false;

	// handle response headers
	String s;
	while (!endOfResponse && (s = client->readStringUntil('\n')).length() > 0) {
		DEBUG_WS("[WS][RX] " + s);
		// HTTP Status
		if (s.indexOf("HTTP/") != -1) {
			auto status = s.substring(9, 12);
			if (status == "101")
				hasCorrectStatus = true;
			else {
				DEBUG_WS("[WS] wrong status: " + status);
				return false;
			}
		}
		// Headers
		else if (s.indexOf(":") != -1) {
			auto col = s.indexOf(":");
			auto key = s.substring(0, col);
			auto value = s.substring(col + 2, s.length() - 1);

			if (key == "Connection" && (value == "Upgrade" || value == "upgrade"))
				isUpgrade = true;

			else if (key == "Sec-WebSocket-Accept")
				hasAcceptedKey = true;

			else if (key == "Upgrade" && value == "websocket")
				isWebsocket = true;
		}

		else if (s == "\r")
			endOfResponse = true;
	}
}

bool success = hasCorrectStatus && isUpgrade && isWebsocket && hasAcceptedKey;

if (success)
	DEBUG_WS("[WS] sucessfully connected");
else {
	DEBUG_WS("[WS] could not connect");
}

return success;

}

Method with fix.

I want to note that your library is the only one that is freely available on the network — it correctly sends messages to a remote server via websocket. The rest do not fulfill the conditions rfc6455 - do not disguise messages, which leads to the server’s refusal to service the ESP client.

It's finally merged thanks @Estradiaz @RVelichko.