Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Temporary memory drain stalls wifi client #4487

Closed
s0170071 opened this issue Mar 9, 2018 · 2 comments
Closed

Temporary memory drain stalls wifi client #4487

s0170071 opened this issue Mar 9, 2018 · 2 comments

Comments

@s0170071
Copy link

s0170071 commented Mar 9, 2018

Basic Infos

  • [x ] This issue complies with the issue POLICY doc.

  • [x ] I have read the documentation at readthedocs and the issue is not addressed there.

  • [x ] I have tested that the issue is present in current master branch (aka latest git).

  • [x ] I have searched the issue tracker for a similar issue.

  • [ x] If there is a stack dump, I have decoded it.

  • [x ] I have filled out all fields below.

Platform

  • Hardware: [ESP-12]
  • Core Version: latest
  • Development Env: [Arduino IDE]
  • Operating System: [Ubuntu]

Settings in IDE

  • Module: [Wemos D1 mini r2]
  • Flash Mode: [dio]
  • Flash Size: [4MB]
  • lwip Variant: [v2 Lower Memory]
  • Reset Method: [ck|nodemcu]
  • Flash Frequency: [40Mhz]
  • CPU Frequency: [80Mhz]
  • Upload Using: [SERIAL]
  • Upload Speed: [115200] (serial upload only)

Problem Description

  • wifi client loses memory at first but works,
  • when memory is very low it stalls, memory returns partly but cannot receive any more.
  • then more memory loss until 900 bytes free. it stays there

MCVE Sketch


#include <ESP8266WiFi.h>
#include <WiFiClient.h>
 

const char *ssid = "xxx";
const char *password = "xxx";
const char *P097_IPaddress="192.168.1.41"; 

 enum sma_states_t {SMA_START_TX, SMA_RECEIVE, SMA_WAIT_FOR_TX};
 
class SMA
{
  public:
    SMA();
    int16_t powerReading;
    uint64_t accumulatedPower; // resets at midnight, requires NTP
    uint64_t accumulatedPowerTimestamp;
    bool handleTXRX();
    unsigned int errcnt; 

  private:
    const char request[12] = {0, 1, 0, 0, 0, 6, 0x7e, 4, 0x9d, 7, 0, 1};
    WiFiClient ModbusClient;
    String LogString = "";
    unsigned long timeout;
    sma_states_t TXRXstate;
    
};

volatile char dummy[35000]; 

 SMA *mySMA;

SMA::SMA() {
  TXRXstate = SMA_START_TX;
  accumulatedPower = 0;
  accumulatedPowerTimestamp = 0;
  powerReading = 0;
  timeout =0;
  errcnt=0; 
}

bool SMA::handleTXRX() {
  unsigned int RXavailable=0; 
  LogString = "";
  int16_t high,low; 
  switch ( TXRXstate ) {
    case SMA_START_TX:
      LogString+=F("connect ");
      LogString+=P097_IPaddress;
      timeout = millis();
      if ( !ModbusClient.connect(P097_IPaddress, 502)) {
        LogString+=F(" fail. ");
        TXRXstate = SMA_WAIT_FOR_TX;
        errcnt++;
        break;
      }
      ModbusClient.write(&request[0], sizeof(request));
      timeout = millis();
      LogString += F(" OK, sending: ");
      for (int i = 0; i < sizeof(request); i++) {
        LogString += ((unsigned int)(request[i]));
        LogString += (" ");
      }
      TXRXstate = SMA_RECEIVE;
      break;

    case SMA_RECEIVE:
      RXavailable = ModbusClient.available();
      if ((RXavailable > 11) || ( ( (millis() - timeout) > 10000))) { // too many bytes or timeout
        LogString+=F("timeout while receiving or too many bytes. "); LogString +=RXavailable;
        errcnt++;
        while (ModbusClient.available())         // empty RX buffer
          ModbusClient.read();
        TXRXstate = SMA_WAIT_FOR_TX;
        break;
      }

      if (RXavailable == 11) {
        LogString += F("reading bytes: "); 
        for (int a = 0; a < RXavailable - 2; a++) {
          LogString += (ModbusClient.read());  LogString += F(" ");
        }
        high = ModbusClient.read();  LogString += (high, HEX);  LogString += (" ");
        low = ModbusClient.read();   LogString += (low, HEX);   LogString += (" ");
        powerReading =   (int16_t) (((int16_t) high << 8) | (int16_t) low); 
        
        LogString +="pow: "; LogString +=powerReading;
        if (powerReading<0) 
            powerReading=0; 
        else
            powerReading=powerReading*10; 
          uint64_t newTimeStamp = millis();
          uint64_t ms= newTimeStamp - accumulatedPowerTimestamp;
          
          //Serial.print("ms"); Serial.println(ms); 
          accumulatedPower +=  (uint64_t) ms * (uint64_t) powerReading; // in Wms
          accumulatedPowerTimestamp =  newTimeStamp;
       
         TXRXstate = SMA_WAIT_FOR_TX;
        break;
      }
      break;

    case SMA_WAIT_FOR_TX:
        if ((millis() - timeout) > 1000){
            TXRXstate = SMA_START_TX;
         }
        break;

    default:
        LogString+=F("default. ");
        TXRXstate = SMA_START_TX;
    break;
    
   }
   if (LogString.length()>1 ) 
      Serial.println( LogString);
}

void setup ( void ) {
  Serial.begin ( 115200 );
  WiFi.mode ( WIFI_STA );
  WiFi.begin ( ssid, password );
  Serial.println ( "" );

  // Wait for connection
  while ( WiFi.status() != WL_CONNECTED ) {
    delay ( 500 );
    Serial.print ( "." );
  }

  Serial.println ( "" );
  Serial.print ( "Connected to " );
  Serial.println ( ssid );
  Serial.print ( "IP address: " );
  Serial.println ( WiFi.localIP() );

  mySMA = new SMA;
  dummy[1]=0;
}

void loop ( void ) {
 
  delay(100); 
  Serial.println(ESP.getFreeHeap());
  mySMA->handleTXRX();
}


Debug Messages

....
Connected to MNET
IP address: 192.168.1.44
11104
connect 192.168.1.41 OK, sending: 0 1 0 0 0 6 126 4 157 7 0 1 
10808
10640
reading bytes: 0 1 0 0 0 5 126 4 2 16 16 pow: 77
10808
10808
10808
10808
10808
10808
10808
10808
10808
connect 192.168.1.41 OK, sending: 0 1 0 0 0 6 126 4 157 7 0 1 
10584
10416
reading bytes: 0 1 0 0 0 5 126 4 2 16 16 pow: 77
10584
10584
10584
10584
10584
10584
10584
10584
10584
connect 192.168.1.41 OK, sending: 0 1 0 0 0 6 126 4 157 7 0 1 
10080
reading bytes: 0 1 0 0 0 5 126 4 2 16 16 pow: 77
10360
10360
10360
10360
10360
10360
10360
10360
10360
10360
connect 192.168.1.41 OK, sending: 0 1 0 0 0 6 126 4 157 7 0 1 
10136
9968
reading bytes: 0 1 0 0 0 5 126 4 2 16 16 pow: 76
10136

... much later ...


1120
1120
1120
connect 192.168.1.41 OK, sending: 0 1 0 0 0 6 126 4 157 7 0 1 
808
728
reading bytes: 0 1 0 0 0 5 126 4 2 16 16 pow: 75
896
896
896
896
896
896
896
896
896
connect 192.168.1.41 OK, sending: 0 1 0 0 0 6 126 4 157 7 0 1 
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
672
timeout while receiving or too many bytes. 0
672
672
connect 192.168.1.41 fail. 
536
536
connect 192.168.1.41 fail. 
536
536
connect 192.168.1.41 fail. 
536
536
connect 192.168.1.41 fail. 
536
536
connect 192.168.1.41 fail. 
536
536
connect 192.168.1.41 fail. 
536
536
connect 192.168.1.41 fail. 
536
536
connect 192.168.1.41 fail. 
536
536
connect 192.168.1.41 fail. 
536
536
connect 192.168.1.41 fail. 
536
536
connect 192.168.1.41 fail. 
536
536
connect 192.168.1.41 OK, sending: 0 1 0 0 0 6 126 4 157 7 0 1 
1488
1488
1488
1488
1488
1488
1488
1488
1488
1656
1656
1656
1656
1656
1656
1656
1656
1656
1656
1824
1824
1824
1824
1824
1824
1824
1824
1824
1824
1992
1992
1992
1992
1992
1992
1992
1992
1992
1992
1992
1992
1992
1992
1992
1992
2160
2160
2160
2160
2160
2160
2160
2160
2160
2160
2328
2328
2328
2328
2328
2328
2328
2328
2328
2328
2496
2496
2496
2496
2496
2496
2496
2496
2496
2496
2664
2664
2664
2664
2664
2664
2664
2664
2664
2664
2664
2664
2664
2664
2664
2832
2832
2832
2832
2832
2832
2832
2832
2832
2832
timeout while receiving or too many bytes. 0
3000
3000
connect 192.168.1.41 OK, sending: 0 1 0 0 0 6 126 4 157 7 0 1 
3448
3448
3448
3448
3616
3616
3616
3616
3616
3616
3616
3616
3616
3616
3616
3784
3784
3784
3784
3784
3784
3784
3784
3784
3784
3952
3952
3952
3952
3952
3952
3952
3952
3952
3952
4120
4120
4120
4120
4120
4120
4120
4120
4120
4120
4120
4120
4120
4120
4120
4288
4288
4288
4288
4288
4288
4288
4288
4288
4288
4456
4456
4456
4456
4456
4456
4456
4456
4456
4456
4624
4624
4624
4624
4624
4624
4624
4624
4624
4792
4792
4792
4792
4792
4792
4792
4792
4792
4792
4792
4792
4792
4792
4792
4960
4960
4960
4960
4960
4960
timeout while receiving or too many bytes. 0
4960
4960
connect 192.168.1.41 OK, sending: 0 1 0 0 0 6 126 4 157 7 0 1 
5880



... much later ...


952
952
952
952
952
1120
1120
1120
1120
1120
timeout while receiving or too many bytes. 0
1120
1120
connect 192.168.1.41 OK, sending: 0 1 0 0 0 6 126 4 157 7 0 1 
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
896
1064
1064
1064
1064
1064
timeout while receiving or too many bytes. 0
1064
1064
connect 192.168.1.41 OK, sending: 0 1 0 0 0 6 126 4 157 7 0 1 
840
840
840
840
840
840
840
840
840
840


@debsahu
Copy link

debsahu commented Mar 10, 2018

Try this, client.setTimeout(time) before client.connect(). time is in milliseconds. Seems to solve my exception 29 issues.

@igrr
Copy link
Member

igrr commented Mar 14, 2018

Closing, will track in #4497. Please follow the link to that issue and click "subscribe" to receive notifications.

@igrr igrr closed this as completed Mar 14, 2018
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants