esp8266 cannot send text over serial to nano

Hello,

I have a nano using soft serial to communicate with an esp8266-01 module. I would use hardware serial but everything I've read says that connecting external hardware to the hardware serial pins can cause problems, so I opted for softSerial.

Baud rate on esp8266 and nano's softserial port is 9600.

Basically everything works as expected EXCEPT when sending text TO the nano over the softserial port FROM the esp8266.

Heres the breakdown:

Send text from serial monitor to esp8266 via USB to serial adapter in both directions ---> WORKS!
Send text from nano to esp8266 via nanos softserial port ---> WORKS!
Send text from esp8266 to nano using nanos softserial port ---> FAIL!

Here is the sketch running on the nano:

#include <Arduino.h>
#include <SoftwareSerial.h>

const int RX        = 3;
const int TX        = 4;

String serialData;
String softSerialData;
boolean serialReceived;
boolean softSerialReceived;

SoftwareSerial softSerial(RX, TX);


void sendSerials(String msg){
    Serial.println(msg);
    softSerial.println(msg);
}

void setup() {
    Serial.begin(115200);
    softSerial.begin(9600);
    sendSerials("\nReady!");
}

void loop() {
    if(softSerialReceived){
        sendSerials("soft: " + softSerialData);
        softSerialData="";
        softSerialReceived=false;
    }
    if(serialReceived) {
        sendSerials("hard: " + serialData);
        serialData="";
        serialReceived=false;
    }
}


void serialEvent() {
    while (Serial.available() > 0) {
        char inChar = (char)Serial.read();
        if (inChar == '\n') {
            serialReceived = true;
        }
        else {
            serialData += inChar;
        }
    }
    while (softSerial.available() > 0) {
        char inChar = (char)Serial.read();
        if (inChar == '\n') {
            softSerialReceived = true;
        }
        else {
            softSerialData += inChar;
        }
    }
}

And here is the sketch running on the esp8266:

#include <SPI.h>         // needed for Arduino versions later than 0018
#include <ESP8266WiFi.h>
#include <WiFiUdp.h>
#include <Arduino.h>
#include <BlockNot.h>

#ifndef STASSID
#define STASSID "Spanky24"
#define STAPSK  "**********" //masked for forum posting
#endif

unsigned int rcvPort = 8787;      // local port to listen on
unsigned int remotePort = 7878;      // remote port to send on

// buffers for receiving and sending data
char packetBuffer[UDP_TX_PACKET_MAX_SIZE + 1]; //buffer to hold incoming packet,
boolean serialReceived;
boolean ping = false;
String serialData;

WiFiUDP udpRcv;
WiFiUDP udpSnd;
BlockNot rcvTimer = BlockNot(3000); //receive timeout timer after sending data over serial
BlockNot pingTimer = BlockNot(10000); //ping timer
IPAddress remoteIP = IPAddress(10,10,10,90); //my laptop running java UDP app

void serialEvent(void);
void sendUDP(String);
void processSerial(void);

void sendSerial(String msg){
    Serial.println(""); //for some reason the data wont hit the serial port unless i do this first
    Serial.println(msg); //This should be sending the data to the nanos softserial port but its not receiving it.
    sendUDP("sent: "+msg);
}

void sendUDP(String message){
    char msg[100];
    message.toCharArray(msg,message.length()+1); //without +1 it cuts off last character
    udpSnd.beginPacket(remoteIP,remotePort);
    udpSnd.write(msg);
    udpSnd.endPacket();
    udpSnd.flush();
}

String getUDP(){
    String response = "";
    int packetSize = udpRcv.parsePacket();
    if(packetSize > 0){
        remoteIP = udpRcv.remoteIP();
        int n = udpRcv.read(packetBuffer, UDP_TX_PACKET_MAX_SIZE);
        packetBuffer[n] = 0;
        response = packetBuffer;
    }
    serialEvent(); //poll for serial data coming in
    return response;
}

void setup() {
    Serial.begin(9600);
    WiFi.mode(WIFI_STA);
    WiFi.begin(STASSID, STAPSK);

    while (WiFi.status() != WL_CONNECTED) {
        Serial.print('.');
        delay(500);
    }
    
    Serial.print("\nConnected! IP address: ");
    Serial.println(WiFi.localIP());
    Serial.print("UDP server on port "+String(rcvPort));
     
    WiFi.setAutoReconnect(true);
    WiFi.setAutoConnect(true);
    WiFi.enableAP(false);
    udpRcv.begin(rcvPort);
    udpSnd.begin(remotePort);
    sendUDP("Ready!");
}

void loop() {
    static String response;
    String inData = getUDP(); //check for data coming in over udp
    boolean dataReceived = inData.length() > 1;
    if(!dataReceived && serialReceived) processSerial();
    else if(dataReceived) {
        inData.toLowerCase();
        if (inData.startsWith("setping")) ping = !ping; //toggle ping if master says so
        else if (!inData.equals("")) {
            rcvTimer.reset();
            sendSerial(inData); // send the data down the serial port
            while (!rcvTimer.done() && !serialReceived) { //wait for a response for three seconds
                serialEvent();
                if (serialReceived) sendUDP(serialData); //if we get response bounce it back to the sender
            }
            if (rcvTimer.done() && !serialReceived) { //let sender know that there was no response
                sendUDP("no response");
            }
            serialData = ""; //clean house
            serialReceived = false; // clean house
        }
    }
    if(pingTimer.doneReset() && ping){ //if ping enabled, send one every 10 seconds (BlockNot timer)
        response = "ping("+String(millis())+")";
        sendUDP(response);
    }
}

void processSerial() {
    sendUDP(serialData); //Bounce serial data to UDP server
    serialData = "";
    serialReceived=false;
}

void serialEvent() {
    if(!serialReceived) {
        while (Serial.available()) {
            char inChar = (char) Serial.read();
            if (inChar == '\n') {
                serialReceived = true;
            } else {
                serialData += inChar;
            }
        }
    }
}

Any ideas?

Thank you,

Mike

Yes, I have an idea. Have you connected a 3.3V device to a 5V device without level-shifting?

serialEvent is only for hardware Serial. it is not executed for the SoftwareSerial. move the code from serialEvent to loop() and delete the useless serialEvent function. it is only a function called after lopp if (Serial.available() > 0)

Juraj:
and delete the useless serialEvent function.

it was while I was doing exactly that, when I saw the problem, in the code that checks for softSerial input, I must have copy and pasted the code for the same routine from the hardware serial because I didnt re-name the Serial object to softSerial ... seems to be working now.

My bad!

TAANK YOU!

PaulRB:
Yes, I have an idea. Have you connected a 3.3V device to a 5V device without level-shifting?

This is how I have it connect ... fyi

I am feeding the esp with 3.3 volts straight from a buck converter.

Good, that voltage divider should protect the esp from the Nano's 5V signal. I guess the 3.3V signal must be enough for the Nano to read.

I suspect once you have tried an esp8266 or esp32 board as the sole controller in one of your projects, you will realise how much easier that is than having two controllers, two sketches, all that extra power circuitry. You will also have made the transition to the pure-3.3V side of "the force".

PaulRB:
Good, that voltage divider should protect the esp from the Nano's 5V signal. I guess the 3.3V signal must be enough for the Nano to read.

I suspect once you have tried an esp8266 or esp32 board as the sole controller in one of your projects, you will realise how much easier that is than having two controllers, two sketches, all that extra power circuitry. You will also have made the transition to the pure-3.3V side of "the force".

I've messed with the nano sized board that has the esp integrated about a year and half ago ... and I cant be sure why, but one of them just stopped working and the other gets extremely hot within a few seconds after applying power to it ... too hot to touch and it doesn't work either. I have no idea what I did to break them.

I am quite shocked at how capable these esp8266's are ... for a couple bucks, you can pretty much create any internet device you can think of. With the exception of being able to handle extremely heavy traffic loads, I'd be hard pressed to think of something you couldn't do with it.

With this project, adding wifi was an after thought. so this little module made sense - I think I bought 5 for $8 or something like that.

Ive also had a DUE in the past (also went tits up and started getting hot for some reason) so I was breaking into the 3.3 world for a while ... what I loved about the DUE is the ADC resolution and the ability to set that to different levels. Very nice board and it makes me wonder why all of the main nano boards don't offer higher resolution in their ADC ... seems like a simple thing, no?

I've actually already designed a circuit for this project and was just getting ready to send in the order ... but now that i'm thinking about it, maybe it would be better to get an 8266 nano sized board and simplify my design and make that PCB smaller - hell Ive got THREE voltage regulators in it, one for my 5v item like LED, IR sensor and IR senders, then a 3.3v for the esp, and a 12v for the nan0, and the DRV8255 feeds straight from 19v right off the main input ... if I go with an integrated wifi board, I'm thinking I could eliminate most of those as well?

This project is a simple stepper motor controller that I have attached to the pot shaft of an analog volume control on a stereo ... so I can control the volume from across the room... it has mute capability with last position recall for un-mutting and when Im out of IR range working on my laptop in the other room, I can set volume over wifi ... or mute ... or whatever. It's been a fun project.

:slight_smile:

Mike

Hi Mike,

It's hard to know for sure what caused the death of your previous esp boards, but my money would be on failed linear regulators. Sounds like you often use power sources with voltages like 12V or 19V. The linear regulators on most esp boards can't accept such high voltages, they will quickly overheat and fail, possibly exposing the rest of the circuit to fatal damage.

I suggest you start using DC-DC step-down "buck" converters. They are very small and cheap on eBay etc, and because they are so much more efficient than linear regulators, they can supply an amp or so at 3.3V from 12V or 19V while barely warming.

Try to limit yourself to as few voltages as possible in a project, for example only 19V and 3.3V. Not sure why you would want to power a Nano from 12V, its regulator is likely to get hot, especially when you have other 5V regulator in the circuit which could let the Nano through its 5V pin.

PaulRB:
Hi Mike,

It's hard to know for sure what caused the death of your previous esp boards, but my money would be on failed linear regulators. Sounds like you often use power sources with voltages like 12V or 19V. The linear regulators on most esp boards can't accept such high voltages, they will quickly overheat and fail, possibly exposing the rest of the circuit to fatal damage.

I suggest you start using DC-DC step-down "buck" converters. They are very small and cheap on eBay etc, and because they are so much more efficient than linear regulators, they can supply an amp or so at 3.3V from 12V or 19V while barely warming.

Try to limit yourself to as few voltages as possible in a project, for example only 19V and 3.3V. Not sure why you would want to power a Nano from 12V, its regulator is likely to get hot, especially when you have other 5V regulator in the circuit which could let the Nano through its 5V pin.

Yeah I use buck converters all the time ... based on your suggestion, I ordered a few ESP 8266 Node MCU boards ... you know the last time I played with those, I don't remember being aware of them only working with 3 volts ... which might explain how they got fried ... LOL

I'll be more careful this time...

I didn't suggest you buy NodeMCU modules, I don't like the design much and prefer Wemos mini, but I guess they will be ok.

Wemos' regulator can handle 5V input max. Some NodeMCU boards claim up to 20V but recommend max 12V. I have serious doubts about those claims. The esp chip draws around 80mA. At 12V input, the regulator must drop 12-3.3=8.7 volts and so must dissipate 8.7x0.080 = 0.7 Watts of heat. That's alot for a tiny regulator on a small crowded board. If you draw more current from the 3.3V pin for sensors or whatever, the situation gets worse.

With a buck convertor set to output 3.3V, you can power the board through the 3V3 pin, bypassing that on board regulator.

PaulRB:
With a buck convertor set to output 3.3V, you can power the board through the 3V3 pin, bypassing that on board regulator.

See ... that makes sense ... Ive never actually thought about it but that makes sense ... .

The very first WiFi Arduino I bought was a WeMos a couple years ago ... I fried that one too... lol In fact now that I think about it ... every WiFi integrated Arduino Ive ever had I some how killed. Since starting with Arduino's about three years ago, Ive managed to kill two Due's, two 2950, at least two Node MCUs and the WeMos. I've got an UNO thats just been solid... The Nanos have been surprisingly resilient but their USB ports are crap ... they tend to die a lot so I end up using the USBASP to program them. I'm not even sure how many OLED screens Ive been through ... and I never was able to get a touch screen to work ... but I haven,t given it a whole lot of effort I suppose.

I've been wanting to make a LiIon battery charger for a while now (Just to do it and learn a few things about that process), but every time I try to get going on that, I can't seem to find a current sensor thats worth a crap.

Hmm... sounds like it might be worth you investing in a bench power supply. You can set them to output any voltage you want, accurately. But the key feature is that you can also set a maximum current. If the current drawn by your circuit exceeds that maximum, it will either drop the voltage to keep the current under the limit, or simply cut the supply altogether and sound an alarm. So when you test a circuit, you can estimate the current you expect it to draw and set the limit just above that. If you made an error, or an accidental blob of solder is causing a short circuit, the power supply will save your circuit and components.