Open g-philipp opened 3 years ago
The webserver library supports any class derived from the Stream so the Wiznet W5500 should work. I personally have not ever used the ESP32 + Wiznet W5500 combination but the library works fine with other arduino boards and ethernet shields.
See the ethernet example here: https://github.com/lasselukkari/aWOT/blob/master/examples/Ethernet/Ethernet.ino
Is it much effort to programm the ethernet function to exist in the settings and work?
Compared to the WiFi connection management with credential the Ethernet is actually simpler.
well ive tried a couple of things the last days and ive got it kinda working, my problems are that first it loses connection all the time:
and second, when I try to connect via html I only see the follwing:
I of course had to modify the code and I think that the issue is cause by deleting some stuff... The code now looks like this: ``
const int NTP_PACKET_SIZE = 48; // NTP time stamp is in the first 48 bytes of the message. byte packetBuffer[NTP_PACKET_SIZE]; // Buffer for both incoming and outgoing packets.
Preferences preferences; EthernetServer server(80); HardwareSerial UltradriveSerial(2); Ultradrive deviceManager(&UltradriveSerial, RTS_PIN, CTS_PIN); Application app; Router apiRouter("/api");
char basicAuth[BASIC_AUTH_LENGTH]; char softApSsid[SOFT_AP_SSID_LENGTH]; char softApPassword[SOFT_AP_PASSWORD_LENGTH]; char mdnsName[MDDNS_NAME_LENGTH]; bool flowControl; bool autoDisableAP;
char authBuffer[AUTH_BUFFER_LENGHT]; char ssidBuffer[SSID_MAX_LENGTH]; char passwordBuffer[PASSWORD_MAX_LENGHT]; unsigned long lastReconnect; bool shouldRestart = false; unsigned long requestStart;
void WizReset() { Serial.print("Resetting Wiz W5500 Ethernet Board... "); pinMode(RESET_P, OUTPUT); digitalWrite(RESET_P, HIGH); delay(250); digitalWrite(RESET_P, LOW); delay(50); digitalWrite(RESET_P, HIGH); delay(350); Serial.println("Done."); }
void logRequestStart(Request &req, Response &res) { unsigned long now = millis(); Serial.print(now); Serial.print(": HTTP ");
switch (req.method()) { case Request::GET: { Serial.print("GET "); break; } case Request::POST: { Serial.print("POST "); break; } case Request::PUT: { Serial.print("PUT "); break; } case Request::PATCH: { Serial.print("GET "); break; } case Request::DELETE: { Serial.print("DELETE "); break; } default: {} }
Serial.print(req.path()); Serial.print(" "); requestStart = micros(); }
void logRequestEnd(Request &req, Response &res) { float delta = (micros() - requestStart) / 1000.0; Serial.print(res.bytesSent()); Serial.print(" b "); Serial.print(delta); Serial.println(" ms"); }
void auth(Request &req, Response &res) { char * authHeader = req.get("Authorization");
if (strcmp(authHeader, basicAuth) != 0) { res.set("WWW-Authenticate", "Basic realm=\"Ultradrive\""); res.sendStatus(401); res.end(); } }
void update(Request &req, Response &res) { int contentLength = req.left();
if (!Update.begin(contentLength)) { return res.sendStatus(500); }
if (Update.writeStream(req) != contentLength) { return res.sendStatus(500); }
if (!Update.end()) { return res.sendStatus(500); }
if (!Update.isFinished()) { return res.sendStatus(500); }
shouldRestart = true; res.sendStatus(204); }
void getNetworks(Request &req, Response &res) { Serial.print(""); }
void getSettings(Request &req, Response &res) { res.set("Content-Type", "application/json"); res.print("{");
res.print("\"" SOFT_AP_SSID_KEY "\":"); res.print("\""); res.print(softApSsid); res.print("\", ");
res.print("\"" SOFT_AP_PASSWORD_KEY "\":"); res.print("\""); res.print(softApPassword); res.print("\", ");
res.print("\"" AUTH_KEY "\":"); res.print("\""); res.print(basicAuth); res.print("\", ");
res.print("\"" MDNS_HOST_KEY "\":"); res.print("\""); res.print(mdnsName); res.print("\", ");
res.print("\"" FLOW_CONTROL_KEY "\":"); res.print("\""); res.print(flowControl); res.print("\", ");
res.print("\"" AUTO_DISABLE_AP_KEY "\":"); res.print("\""); res.print(autoDisableAP); res.print("\"");
res.print("}"); }
void getVersion(Request &req, Response &res) { res.set("Content-Type", "application/json"); res.print("{");
res.print("\"version\":"); res.print("\""); res.print(VERSION); res.print("\", ");
res.print("\"buildDate\":"); res.print("\""); res.print(BUILD_DATE); res.print("\"");
res.print("}"); }
void updateSettings(Request &req, Response &res) { char name[15]; char value[BASIC_AUTH_LENGTH]; preferences.begin("duinodcx", false);
while (req.left()) { req.form(name, 15, value, BASIC_AUTH_LENGTH); if (strcmp(name, AUTH_KEY) == 0) { preferences.putString(AUTH_KEY, value); } else if (strcmp(name, SOFT_AP_SSID_KEY) == 0) { preferences.putString(SOFT_AP_SSID_KEY, value); } else if (strcmp(name, SOFT_AP_PASSWORD_KEY) == 0) { preferences.putString(SOFT_AP_PASSWORD_KEY, value); } else if (strcmp(name, MDNS_HOST_KEY) == 0) { preferences.putString(MDNS_HOST_KEY, value); } else if (strcmp(name, FLOW_CONTROL_KEY) == 0) { bool isEnabled = (value[0] != '0'); preferences.putBool(FLOW_CONTROL_KEY, isEnabled); } else if (strcmp(name, AUTO_DISABLE_AP_KEY) == 0) { bool isEnabled = (value[0] != '0'); preferences.putBool(AUTO_DISABLE_AP_KEY, isEnabled); } else { preferences.end(); return res.sendStatus(400); } }
preferences.end(); res.sendStatus(204);
shouldRestart = true; }
void getConnection(Request &req, Response &res) { res.set("Content-Type", "application/json"); res.print("{");
res.print("\"current\":"); res.print("\""); res.print("Ethernet"); res.print("\",");
res.print("\"ip\":"); res.print("\""); res.print(Ethernet.localIP()); res.print("\"");
res.print("}"); }
void updateConnection(Request &req, Response &res) { char name[10]; char value[PASSWORD_MAX_LENGHT]; unsigned long timeout;
while (req.left()) { req.form(name, 10, value, PASSWORD_MAX_LENGHT); if (strcmp(name, POST_PARAM_SSID_KEY) == 0) { strcpy (ssidBuffer, value); } else if (strcmp(name, POST_PARAM_PASSWORD_KEY) == 0) { strcpy (passwordBuffer, value); } else { return res.sendStatus(400); } }
timeout = millis() + CONNECTION_TIMEOUT; }
void removeConnection(Request &req, Response &res) { Serial.print(""); }
void getDevice(Request &req, Response &res) { res.set("Content-Type", "application/binary"); deviceManager.writeDevice(&res); }
void getStatus(Request &req, Response &res) { res.set("Content-Type", "application/binary"); deviceManager.writeDeviceStatus(&res); }
void selectDevice(Request &req, Response &res) { byte buffer[100];
if (!req.readBytes(buffer, 100)) { return res.sendStatus(400); }
int id = atoi((const char *)buffer); deviceManager.setSelected(id); }
void getState(Request &req, Response &res) { res.set("Content-Type", "application/binary"); res.write(deviceManager.getSelected()); deviceManager.writeDevice(&res); deviceManager.writeDevices(&res); }
void createDirectCommand(Request &req, Response &res) { while (req.left()) { deviceManager.processOutgoing(&req); }
res.sendStatus(204); }
void processWebServer() { EthernetClient client = server.available(); app.process(&client); }
void restartIfNeeded() { if (shouldRestart) { delay(5000); ESP.restart(); } }
void loadPreferences() { pinMode(RESET_PIN, INPUT_PULLUP);
preferences.begin("duinodcx", false);
unsigned long now = millis(); while (!digitalRead(RESET_PIN)) { if (millis() - now > 1000) { preferences.clear(); break; } }
if (!preferences.getString(AUTH_KEY, basicAuth, BASIC_AUTH_LENGTH)) { strcpy(basicAuth, DEFAULT_AUTH); }
if (!preferences.getString(SOFT_AP_SSID_KEY, softApSsid, SOFT_AP_SSID_LENGTH)) { strcpy(softApSsid, DEFAULT_SOFT_AP_SSID); }
if (!preferences.getString(SOFT_AP_PASSWORD_KEY, softApPassword, SOFT_AP_PASSWORD_LENGTH)) { strcpy(softApPassword, DEFAULT_SOFT_AP_PASSWORD); }
if (!preferences.getString(MDNS_HOST_KEY, mdnsName, MDDNS_NAME_LENGTH)) { strcpy(mdnsName, DEFAULT_MDNS_NAME); }
flowControl = preferences.getBool(FLOW_CONTROL_KEY, DEFAULT_FLOW_CONTROL);
autoDisableAP = preferences.getBool(AUTO_DISABLE_AP_KEY, DEFAULT_AUTO_DISABLE_AP);
preferences.end(); }
void setupHttpServer() { app.header("Authorization", authBuffer, AUTH_BUFFER_LENGHT);
apiRouter.get("/state", &getState); apiRouter.get("/status", &getStatus); apiRouter.put("/selected", &selectDevice); apiRouter.post("/commands", &createDirectCommand); apiRouter.get("/connection", &getConnection); apiRouter.patch("/connection", &updateConnection); apiRouter.del("/connection", &removeConnection); apiRouter.get("/settings", &getSettings); apiRouter.patch("/settings", &updateSettings); apiRouter.get("/networks", &getNetworks); apiRouter.post("/update", &update); apiRouter.get("/version", &getVersion);
app.use(&logRequestStart); app.use(&auth); app.route(&apiRouter); app.route(staticFiles()); app.use(&logRequestEnd); }
void setup() { Ethernet.init(5); // GPIO5 on the ESP32. WizReset(); Serial.begin(38400); UltradriveSerial.begin(38400);
loadPreferences();
if (flowControl) { deviceManager.enableFlowControl(true); pinMode(RTS_PIN, OUTPUT); pinMode(CTS_PIN, INPUT_PULLUP); }
Ethernet.begin(eth_MAC, eth_IP, eth_DNS, eth_GW, eth_MASK); delay(200); Ethernet.begin(eth_MAC, eth_IP); server.begin();
setupHttpServer();
MDNS.begin(mdnsName); MDNS.addService("http", "tcp", 80); }
void loop() { unsigned long now = millis(); deviceManager.processIncoming(now); processWebServer(); restartIfNeeded(); } ``
The new file "local_config.h" looks like the following:
`` /*
/*
const uint16_t localPort = 55432; // Local port for UDP packets.
/*
const uint8_t SLEEP_SECS = 15; // Number of seconds to sleep between queries to the time // server. Please don't set this any lower than 10 unless // timeServer[] is a local NTP server on -your- network. ``
Its my first time using an ethernet board and i dont fully understand your code so forgive me...
Hope you can help me
~Philipp
Hi. I have never tested ESP 32 + Wiznet W5500 combination myself. With the ESP32 WiFi the WifiClient destructor stops the client automatically when it goes away from the scope. The EthernetClient in Ethernet2 library does not define a destructor.
So you will need to at least change the
void processWebServer() {
EthernetClient client = server.available();
app.process(&client);
}
to
void processWebServer() {
EthernetClient client = server.available();
if (client.connected()) {
app.process(&client);
client.stop(); // add the client stop here
}
}
I have the same ethernet module somewhere. I could try it out tomorrow if I find it.
with the change in "processWebServer()" its working! But it would be awesome if you could check the code, you may implement this into your code? Merry Christmas!
Edit: Ive got the problem that sometimes it kicks me out of the settings and is searching again for some time until it picks back up, do you know something about this? Could it be a problem with my cable? its just a normal rs232 to rs232 cable but i switched and soldered two pins and made it male2male instead of fm2m but the shielding is connected to both jacks....
I'm glad you got the Ethernet connection working! It sounds like your RS232 connection is not reliable for some reason. This is not normal and I have not seen the connection to behave like that.
I would try another set of cabling first. If that does not work I would try another MAX3232 module. I have read from old forum discussions that the chinese fake copies can be unreliable especially at higher baud rates. You can also make sure it's not the changes that you have made by switching back to the wifi code.
Feel free to create a pull request. I can add the support for the Ethernet to codebase but I need to find my Ethernet module first. I ordered a new one but it will take a couple of weeks to arrive.
I got a new ethernet module today. Let's see how this goes.
Is there a reason you are using the Ethernet2 library? The standard one seems to work as well.
The UDP example worked for me but the webserver didnt, also with many other libs i had the same problem, but with the Ethernet2 (there are different Eth2 libs, only one worked for me) ist worked as it should
And did you get the RS232 working reliably? I bought a module and board that does not expose any extra pins. If you got the rs232 connection working I would not have to test the changes together with the rs232 module. I can hook up the module to another board but it would be more convenient if I do not have to.
No sadly i didnt get it working reliably but I found out, that sometime (only sometimes) when the music stops, it "catches itself" and I can use the webinterface like normal, but then if the music starts, it is endless looping with loading.
It is very strange :(
OK. I will let you know if I get it working properly.
The ESP32 core has a non standard definition for the server that is not compatible with the rest of the Arduino ecosystem. If you want to use the normal Ethernet library you have to do a simple modification to the ESP32 core files.
You need to change this: https://github.com/espressif/arduino-esp32/blob/master/cores/esp32/Server.h#L28
from
virtual void begin(int port) =0;
to
virtual void begin() =0;
Unfortunately you can not compile the WiFiServer lib anymore with this change until you change it back. The result is that the WiFiServer and EthernetServer can not be used simultaneously. Until the esp32 core gets their shit together I will add this functionality to be configured with a feature flag and there will not be a user interface for setting the static ip.
BTW have you tried or considered the lan8710/lan8720 for the Ethernet. It seems to be supported out of the box with the Arduino framework. I'm new to Ethernet options with ESP32 and I'm trying to figure out the pros and cons between these two solutions. The Wiznet chips uses SPI and this may be at least in theory blocking the other IO pins under heavy use. This could explain the problems you are seeing with RS232 port stability. I ordered this board for evaluation https://www.olimex.com/Products/IoT/ESP32/ESP32-GATEWAY/. Not just because of this project but rather to verify the compatibility with the web server library I have been developing.
Hey, its been a long time since my last post. In the meantime i used the ethernet board and i think the only problem is still that the serial converter sometimes looses connection. But i will not change it. Have you tried some testing with your ethernet board?
Ethernet with the Wiznet W5500 Ethernet Board
set up a static ip address and select ethernet instead of wifi in the webinterface