Heltec WiFi LoRa 32 (V3) - Ethernet module connection

Hello,
is it possible to use the Ethernet module like W5500 (Ethernet Module W5500 - ProtoSupplies) or LAN8720 (Lan8720 Module ETH Board, For Industrial at Rs 275 in Hyderabad | ID: 22627102262 (indiamart.com)) together with Heltec WiFi LoRa 32 (V3) board so that LoRa can be used at the same time? I need to pass MQTT messages (pubsubclient library) but over ethernet instead of Wi-Fi.

Alternatively, which ethernet module would be compatible with Heltec nodes?

Thanks

Yes, they are compatible and the device can be used by connecting to the network through Ethernet.

Hi - was wondering if you ever got your project working with the Heltec LoRa (V3) and the W5500 Ethernet Module?
I am looking at doing something similar to you. Any advice would be much appreciated.

Thanks.

try this test program

// Heltec LoRa V3  W5500 Ethernet test

/*
 * HelloServer example from the ESP32 WebServer library modified for Ethernet.
 */

#include <EthernetESP32.h>
#include <WebServer.h>
#include <ESPmDNS.h>

// define Heltec LoRa V3 W5500 SPI pins
#define W5500_SCK 40
#define W5500_MISO 42
#define W5500_MOSI 39
#define W5500_CS 41

W5500Driver driver(W5500_CS);  // SPI SS is GPIO34
//ENC28J60Driver driver;
//EMACDriver driver(ETH_PHY_LAN8720);

SPIClass spi(SPI);  // HSPI object used by W5500

WebServer server(80);

const int led = 13;

void handleRoot() {
  digitalWrite(led, 1);
  server.send(200, "text/plain", "hello from esp32!");
  digitalWrite(led, 0);
}

void handleNotFound() {
  digitalWrite(led, 1);
  String message = "File Not Found\n\n";
  message += "URI: ";
  message += server.uri();
  message += "\nMethod: ";
  message += (server.method() == HTTP_GET) ? "GET" : "POST";
  message += "\nArguments: ";
  message += server.args();
  message += "\n";
  for (uint8_t i = 0; i < server.args(); i++) {
    message += " " + server.argName(i) + ": " + server.arg(i) + "\n";
  }
  server.send(404, "text/plain", message);
  digitalWrite(led, 0);
}

void setup(void) {
  pinMode(led, OUTPUT);
  digitalWrite(led, 0);
  Serial.begin(115200);
  delay(2000);
  // setup SPI pins
  spi.begin(W5500_SCK, W5500_MISO, W5500_MOSI, W5500_CS);
  driver.setSPI(spi);    // specify driver SPI interface
  Ethernet.init(driver);  // initialise driver
  Serial.println("Initialize Ethernet with DHCP:");
  if (Ethernet.begin()) {
    Serial.print("  DHCP assigned IP ");
    Serial.println(Ethernet.localIP());
  } else {
    Serial.println("Failed to configure Ethernet using DHCP");
    while (true) {
      delay(1);
    }
  }
  if (MDNS.begin("esp32")) {
    Serial.println("MDNS responder started");
  }
  server.on("/", handleRoot);
  server.on("/inline", []() {
    server.send(200, "text/plain", "this works as well");
  });
  server.onNotFound(handleNotFound);
  server.begin();
  Serial.println("HTTP server started");
}

void loop(void) {
  server.handleClient();
  delay(2);  //allow the cpu to switch to other tasks
}

Arduino serial monitor output

Initialize Ethernet with DHCP:
  DHCP assigned IP 192.168.1.245
MDNS responder started
HTTP server started

web client

photo of setup
image

an alternative would be to communicate using WiFi to a wt32-eth01 ESP32 based ethernet module

Thanks Horace. I’m using a Heltec LoRa (V3.2) board. The code you provided works great by itself, and I think I also managed to get it to use the HSPI bus (as opposed to the VSPI bus which is used by the OLED display).

But the problem starts when I introduce the LoRa logic to the sketch (for example the standard Factory Test V1 example or Ping-Pong example). If I merge these 2 projects it seems the Ethernet.h library (or the ETH.h library) doesn’t compile.
I get errors such as this one:

C:\Users\Mike\Documents\Arduino\libraries\EthernetESP32\src\Ethernet.cpp:198:11: error: 'gpio_install_isr_service' was not declared in this scope
  198 |     ret = gpio_install_isr_service(0);
      |           ^~~~~~~~~~~~~~~~~~~~~~~~

Is there some known issue between the Heltec Lora boards and the Ethernet (or ETH) libraries?

Or would you have an example sketch of W5500 on HSPI bus with some basic LoRa ping-pong logic executing at the same time?

Thanks

The Heltec framework is running an older version of Arduino-ESP32. If you combine that with newer libraries, I think you get these clashing results. A solution could be to use other LoRa libraries such as RadioLib that work for the newer ESP32 core and therefore won’t clash with your other newer libraries.

1 Like

try the following which uses the RadioLib Library
I try to keep code for different modules in separate files in the same directory

LoRa P2P transmit file Heltec_V3_SX126x_LoRa_Transmit_W550_HSPI.ino

// Heltec LoRa SX1262 transmit test

// File>Examples>RadioLib>SX126x>SX126x_Transmit_Interrupt

// EDITs:
//  radio.begin frequency set to 868.0
//  transmitting byte array and printing it

/*
  RadioLib SX126x Transmit with Interrupts Example

  This example transmits LoRa packets with one second delays
  between them. Each packet contains up to 256 bytes
  of data, in the form of:
  - Arduino String
  - null-terminated char array (C-string)
  - arbitrary binary data (byte array)

  Other modules from SX126x family can also be used.

  For default module settings, see the wiki page
  https://github.com/jgromes/RadioLib/wiki/Default-configuration#sx126x---lora-modem

  For full API reference, see the GitHub Pages
  https://jgromes.github.io/RadioLib/
*/

// include the library
#include <RadioLib.h>

// Heltec LoRa V3  SX1262 has the following connections:
// NSS pin:   8
// DIO1 pin:  14
// NRST pin:  12
// BUSY pin:  13
SX1262 radio = new Module(8, 14, 12, 13);

// or detect the pinout automatically using RadioBoards
// https://github.com/radiolib-org/RadioBoards
/*
#define RADIO_BOARD_AUTO
#include <RadioBoards.h>
Radio radio = new RadioModule();
*/

// save transmission state between loops
int transmissionState = RADIOLIB_ERR_NONE;

// flag to indicate that a packet was sent
volatile bool transmittedFlag = false;

// this function is called when a complete packet
// is transmitted by the module
// IMPORTANT: this function MUST be 'void' type
//            and MUST NOT have any arguments!
#if defined(ESP8266) || defined(ESP32)
ICACHE_RAM_ATTR
#endif
void setFlag(void) {
  // we sent a packet, set the flag
  transmittedFlag = true;
}

// W5500 Ethernet prototypes
void W5500setup(void);
void W5500loop(void);

void setup() {
  Serial.begin(115200);
  delay(2000);
  W5500setup();    // setup W5500 Erthernet
  // initialize SX1262 with default settings
  Serial.print(F("\n\nHeltec LoRa V3 [SX1262] Initializing ... "));
  int state = radio.begin(868.0);
  if (state == RADIOLIB_ERR_NONE) {
    Serial.println(F("success!"));
  } else {
    Serial.print(F("failed, code "));
    Serial.println(state);
    while (true) { delay(10); }
  }

  // set the function that will be called
  // when packet transmission is finished
  radio.setPacketSentAction(setFlag);

  // start transmitting the first packet
  Serial.print(F("[SX1262] Sending first packet ... "));

  // you can transmit C-string or Arduino string up to
  // 256 characters long
  transmissionState = radio.startTransmit("Hello World!");

  // you can also transmit byte array up to 256 bytes long
  /*
    byte byteArr[] = {0x01, 0x23, 0x45, 0x67,
                      0x89, 0xAB, 0xCD, 0xEF};
    state = radio.startTransmit(byteArr, 8);
  */
}

// counter to keep track of transmitted packets
int count = 0;

void loop() {
  // check W5500 Ethernet
  W5500loop();
  // check if the previous LoRa transmission finished
  if (transmittedFlag) {
    // reset flag
    transmittedFlag = false;

    if (transmissionState == RADIOLIB_ERR_NONE) {
      // packet was successfully sent
      Serial.println(F("transmission finished!"));

      // NOTE: when using interrupt-driven transmit method,
      //       it is not possible to automatically measure
      //       transmission data rate using getDataRate()

    } else {
      Serial.print(F("failed, code "));
      Serial.println(transmissionState);
    }

    // clean up after transmission is finished
    // this will ensure transmitter is disabled,
    // RF switch is powered down etc.
    radio.finishTransmit();

    // wait a second before transmitting again
    delay(1000);

    // send another one
    Serial.print(F("[SX1262] Sending another packet ... "));

    // you can transmit C-string or Arduino string up to
    // 256 characters long
    //String str = "Hello World! #" + String(count++);
    //transmissionState = radio.startTransmit(str);

    // you can also transmit byte array up to 256 bytes long
    static byte byteArr[] = { 0x01, 0x23, 0x45, 0x67,
                              0x89, 0xAB, 0xCD, 0xEF };
    for (int i = 0; i < sizeof(byteArr); i++)
      Serial.printf("%d ", byteArr[i]);
    transmissionState = radio.startTransmit(byteArr, 8);
    byteArr[0]++;
  }
}

W5500 Ethernet file HelloServer_HSPI.ino (in same directory as above .ino file)

// Heltec LoRa V3  W5500 Ethernet test

/*
 * HelloServer example from the ESP32 WebServer library modified for Ethernet.
 */

#include <EthernetESP32.h>
#include <WebServer.h>
#include <ESPmDNS.h>

// define Heltec LoRa V3 W5500 SPI pins
#define W5500_SCK 40
#define W5500_MISO 42
#define W5500_MOSI 39
#define W5500_CS 41

W5500Driver driver(W5500_CS);  // SPI SS is GPIO34
//ENC28J60Driver driver;
//EMACDriver driver(ETH_PHY_LAN8720);

SPIClass hspi(HSPI);  // HSPI object used by W5500

WebServer server(80);

const int led = 13;

void handleRoot() {
  digitalWrite(led, 1);
  server.send(200, "text/plain", "hello from esp32!");
  digitalWrite(led, 0);
}

void handleNotFound() {
  digitalWrite(led, 1);
  String message = "File Not Found\n\n";
  message += "URI: ";
  message += server.uri();
  message += "\nMethod: ";
  message += (server.method() == HTTP_GET) ? "GET" : "POST";
  message += "\nArguments: ";
  message += server.args();
  message += "\n";
  for (uint8_t i = 0; i < server.args(); i++) {
    message += " " + server.argName(i) + ": " + server.arg(i) + "\n";
  }
  server.send(404, "text/plain", message);
  digitalWrite(led, 0);
}

void W5500setup(void) {
  pinMode(led, OUTPUT);
  digitalWrite(led, 0);
  Serial.begin(115200);
  delay(2000);
  // setup SPI pins
  hspi.begin(W5500_SCK, W5500_MISO, W5500_MOSI, W5500_CS);
  driver.setSPI(hspi);    // specify driver SPI interface
  Ethernet.init(driver);  // initialise driver
  Serial.println("Initialize Ethernet with DHCP:");
  if (Ethernet.begin()) {
    Serial.print("  DHCP assigned IP ");
    Serial.println(Ethernet.localIP());
  } else {
    Serial.println("Failed to configure Ethernet using DHCP");
    while (true) {
      delay(1);
    }
  }
  if (MDNS.begin("esp32")) {
    Serial.println("MDNS responder started");
  }
  server.on("/", handleRoot);
  server.on("/inline", []() {
    server.send(200, "text/plain", "this works as well");
  });
  server.onNotFound(handleNotFound);
  server.begin();
  Serial.println("HTTP server started");
}

void W5500loop(void) {
  server.handleClient();
  delay(2);  //allow the cpu to switch to other tasks
}

Heltec LoRa V3 serial monitor output

Initialize Ethernet with DHCP:
  DHCP assigned IP 192.168.1.245
MDNS responder started
HTTP server started


Heltec LoRa V3 [SX1262] Initializing ... success!
[SX1262] Sending first packet ... transmission finished!
[SX1262] Sending another packet ... 1 35 69 103 137 171 205 239 transmission finished!
[SX1262] Sending another packet ... 2 35 69 103 137 171 205 239 transmission finished!
[SX1262] Sending another packet ... 3 35 69 103 137 171 205 239 transmission finished!
[SX1262] Sending another packet ... 4 35 69 103 137 171 205 239 transmission finished!
[SX1262] Sending another packet ... 5 35 69 103 137 171 205 239 transmission finished!
[SX1262] Sending another packet ... 6 35 69 103 137 171 205 239 transmission finished!

the Helloserver output appears on 192.168.1.245 OK

the data transmitted by the Heltec LoRa V3 ir received by a Heltec LoRa V2

Heltec LoRa V2  SX1276  [SX1276] Initializing ... success!
[SX1276] Starting to listen ... success!
[SX1276] Received packet!
[SX1276] Data:		3 35 69 103 137 171 205 239 
[SX1276] RSSI:		-52.00 dBm
[SX1276] SNR:		12.75 dB
[SX1276] Frequency error:	-1696.60 Hz
[SX1276] Received packet!
[SX1276] Data:		4 35 69 103 137 171 205 239 
[SX1276] RSSI:		-51.00 dBm
[SX1276] SNR:		12.50 dB
[SX1276] Frequency error:	-1692.40 Hz
[SX1276] Received packet!
[SX1276] Data:		5 35 69 103 137 171 205 239 
[SX1276] RSSI:		-52.00 dBm
[SX1276] SNR:		12.75 dB
[SX1276] Frequency error:	-1692.40 Hz
[SX1276] Received packet!
[SX1276] Data:		6 35 69 103 137 171 205 239 
[SX1276] RSSI:		-52.00 dBm
[SX1276] SNR:		12.50 dB
[SX1276] Frequency error:	-1688.21 Hz
[SX1276] Received packet!
[SX1276] Data:		7 35 69 103 137 171 205 239 
[SX1276] RSSI:		-52.00 dBm

what Ethernet functionality are you looking at using?

2 Likes

Thanks bns - this is a revelation.
Does that mean that if I select board “Heltec WiFi LoRa 32(V3) Version 3.0.2” I can not use libraries such as ETH.h or EthernetESP32.h together with LoRaWan_APP.h ?
It means a bit of re-development for me :grimacing:

This is a bit surprising since both ETH.h and LoRaWan_APP.h are used in the Heltec included examples, but they are used in separate sketches.

If I use your proposed solution and use RadioLib instead of LoRaWan_APP, should I still select the board as ‘WiFi LoRa 32 (V3)’ or something else?

Thanks again !! and if you have any other tips to avoid potential problems I’d be very apreciative.

Thanks horace - really easy to read and clean code :slightly_smiling_face:
Having the separate .ino files like you did with function prototypes makes the code so much neater.

Looks like you and ‘bns’ both knew to use the RadioLib library instead of the Heltec LoRaWan_APP.h
I’m just curious how you discovered this? Because I took for granted the libraries included in the Heltec examples (using LoRaWan_APP.h, ETH.h, Ethernet.h) would work nicely together.

In arduino-ide do you still select board type: WiFi Lora 32(V3), or do you choose something else?

Have you had any other issues with library incompatibility and the Heltec Wifi LoRa V3 board?

My project involves sending/receiving LoRa, wifi client, plus pub/sub MQTT over W5500 ethernet.
I also have a RTC and using the PCNT function on one of the GPIO pins.

Thanks again.

when implementing a complex project I test each component (sensor, IO device, etc) in a separate program which then become .cpp and .h files for including in the final program - in practice a large project may have twenty or thirty .cpp and .h files plus library files

I have a Heltec LoRa V2 where the LoRaWAN license was lost (I probably erased all the flash) - getting no response from Heltec support I switched to RadioLib (which I had used for other radio modules)

yes - it has the pin definitions etc for the V3 module

I have not had any problems - just make sure the GPIO pins you use don’t clash with any of the module functionality

keep in mind the module uses 3.3V logic - don’t directly input 5V signals

1 Like

If you are using a WiFi LoRa 32 v3, why would you choose different hardware? This is the bit that defines the processor to compile for and how all the pins are connected.

1 Like

Thanks - all good advice.

I’m not sure exactly how the board selection ties in with the whole compilation process but now it makes more sense.My original post started because I could get 2 of the Heltec example projects to compile ‘individually’, but when I combined the projects I got compilation errors. I did spend LOTS of time trying to resolve before resorting to this forum. The 2 projects were ‘Ping-Pong’ and ‘W5500 Ethernet SPI’. One using the LoraWan_APP.h library, and the other using ETH.h. I just assumed the example projects would play nicely together but it wasn’t the case.

From this forum I later found out that the Heltec framework somehow uses older versions of the ESP32 processor which can cause incompatability problems. Maybe I’m the only one that doesn’t know about the library problems, but I did struggle to find this documented anywhere.

Have you had similar incompatability issues with the common libraries, in particular LoraWan_APP and ETH.h (or Ethernet.h)?

Is there a list of the more common libraries which are known to work with Heltec Lora V3 boards? By common I mean: LoRa, Ethernet, WiFi, MQTT, RTC.

To answer your question, I wasn’t sure that by selecting another board (and maybe having to define all the pins) the compiler would use a more up-to-date framework and libraries would be compatible.
You never know until you ask.

recently there has been an upgrade of the ESP32 core from version 2 to version 3 which has caused problem with many libraries
see Espressif Migration from 2.x to 3.0

in some cases projects have had to revert to Version 2.0.17 to use specific libraries which are not compatible with version 3
if using multiple libraries one can then get the problem that some libraries have been updated to version 3 and some have not

In name, the Heltec core is running on v3.0.2, but I have the feeling like certain parts of the core are still using 2.x

I am having another library conflict this time when I add “HT_SSD1306Wire.h” to the sketch and the compiler gives me this error message:

C:\Users\Mike\AppData\Local\Arduino15\packages\Heltec-esp32\hardware\esp32\3.0.2\libraries\Ethernet\src\ETH.cpp: In member function 'bool ETHClass::beginSPI(eth_phy_type_t, int32_t, uint8_t*, int, int, int, SPIClass*, int, int, int, spi_host_device_t, uint8_t)':
C:\Users\Mike\AppData\Local\Arduino15\packages\Heltec-esp32\hardware\esp32\3.0.2\libraries\Ethernet\src\ETH.cpp:571:9: error: 'gpio_install_isr_service' was not declared in this scope
  571 |   ret = gpio_install_isr_service(0);
  |         ^~~~~~~~~~~~~~~~~~~~~~~~

It is exactly the same error message I got with the last library conflict when I tried to add LoRaWan_APP.h . Just to clarify, the compile error occurs when I just add the libraries without any additional code.
Do you know if there is a known solution for this compile error, or is it a matter of keep changing libraries?

I really want to keep using the ETH.h library - I got it working on HSPI using my custom pins and has a nice event handler. I couldn’t get the equivalent working using EthernetESP32.h.
I’m asking the forum brains trust should anyone know the solution? Thanks.

Perhaps try a different SSD1306 display library - there are many to choose from.

using ESP32 core 3.3.2 tried ETH.h library running File>Examples>Ethernet>ETH_W5500_Arduino_SPI

works OK
as soon as I included “HT_SSD1306Wire.h” got same error message as you reported
must be some clash between libraries

tried Adafruit_SSD1306.h library and it worked OK with ETH.h using setup

#define SCREEN_ADDRESS 0x3C  //0x3D ///< See datasheet for Address; 0x3D for 128x64, 0x3C for 128x32
Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, RST_OLED);

void setup() {
  Serial.begin(115200);
  delay(2000);
  Wire.begin(SDA_OLED, SCL_OLED);
  // SSD1306_SWITCHCAPVCC = generate display voltage from 3.3V internally
  if (!display.begin(SSD1306_SWITCHCAPVCC, SCREEN_ADDRESS)) {


2 Likes

The cause is the same: as soon as you use the Heltec stuff (denoted by HT_ in this case), you end up with the mismatch between the Heltec framework and the general ESP32 Arduino framework

1 Like

Thanks - will try this tomorrow once finished venting from an unproductive day of library conflicts :roll_eyes: