XBee will now "cache" the IP address if it has already looked up a host

This commit is contained in:
Sara Damiano
2019-01-30 15:14:03 -05:00
parent ec6b475959
commit 3cb71a54be

View File

@@ -78,6 +78,12 @@ public:
} }
public: public:
// NOTE: The XBee saves all paramter information in flash. When you turn it
// on it immediately begins to re-connect to whatever was last connected to.
// All the modemConnect() function does is tell it the paramters to put into
// flash. The connection itself happens automatically after that.
// Because everything is saved, it is possible (or likely) that you will be
// connected even if you haven't "made" any connection
virtual int connect(const char *host, uint16_t port) { virtual int connect(const char *host, uint16_t port) {
at->streamClear(); // Empty anything in the buffer before starting at->streamClear(); // Empty anything in the buffer before starting
if (at->commandMode()) { // Don't try if we didn't successfully get into command mode if (at->commandMode()) { // Don't try if we didn't successfully get into command mode
@@ -85,8 +91,8 @@ public:
at->writeChanges(); at->writeChanges();
at->exitCommand(); at->exitCommand();
} }
else // After setting connection information, check if we're actually connected
sock_connected = false; sock_connected = at->modemGetConnected();
return sock_connected; return sock_connected;
} }
@@ -97,8 +103,8 @@ public:
at->writeChanges(); at->writeChanges();
at->exitCommand(); at->exitCommand();
} }
else // After setting connection information, check if we're actually connected
sock_connected = false; sock_connected = at->modemGetConnected();
return sock_connected; return sock_connected;
} }
@@ -119,7 +125,8 @@ public:
at->writeChanges(); at->writeChanges();
at->exitCommand(); at->exitCommand();
at->streamClear(); // Empty anything remaining in the buffer at->streamClear(); // Empty anything remaining in the buffer
sock_connected = false; // sock_connected = false;
// Note: because settings are saved in flash, the XBEE may immediately attempt to reconnect
} }
virtual size_t write(const uint8_t *buf, size_t size) { virtual size_t write(const uint8_t *buf, size_t size) {
@@ -139,51 +146,57 @@ public:
virtual int available() { virtual int available() {
TINY_GSM_YIELD(); TINY_GSM_YIELD();
return at->stream.available(); return at->stream.available();
// if (!rx.size() || at->stream.available()) { /*
// at->maintain(); if (!rx.size() || at->stream.available()) {
// } at->maintain();
// return at->stream.available() + rx.size(); }
return at->stream.available() + rx.size();
*/
} }
virtual int read(uint8_t *buf, size_t size) { virtual int read(uint8_t *buf, size_t size) {
TINY_GSM_YIELD(); TINY_GSM_YIELD();
return at->stream.readBytes((char *)buf, size); return at->stream.readBytes((char *)buf, size);
// size_t cnt = 0; /*
// uint32_t _startMillis = millis(); size_t cnt = 0;
// while (cnt < size && millis() - _startMillis < _timeout) { uint32_t _startMillis = millis();
// size_t chunk = TinyGsmMin(size-cnt, rx.size()); while (cnt < size && millis() - _startMillis < _timeout) {
// if (chunk > 0) { size_t chunk = TinyGsmMin(size-cnt, rx.size());
// rx.get(buf, chunk); if (chunk > 0) {
// buf += chunk; rx.get(buf, chunk);
// cnt += chunk; buf += chunk;
// continue; cnt += chunk;
// } continue;
// // TODO: Read directly into user buffer? }
// if (!rx.size() || at->stream.available()) { // TODO: Read directly into user buffer?
// at->maintain(); if (!rx.size() || at->stream.available()) {
// } at->maintain();
// } }
// return cnt; }
return cnt;
*/
} }
virtual int read() { virtual int read() {
TINY_GSM_YIELD(); TINY_GSM_YIELD();
return at->stream.read(); return at->stream.read();
// uint8_t c; /*
// if (read(&c, 1) == 1) { uint8_t c;
// return c; if (read(&c, 1) == 1) {
// } return c;
// return -1; }
return -1;
*/
} }
virtual int peek() { return at->stream.peek(); } virtual int peek() { return at->stream.peek(); }
// virtual int peek() { return -1; } //TODO
virtual void flush() { at->stream.flush(); } virtual void flush() { at->stream.flush(); }
virtual uint8_t connected() { virtual uint8_t connected() {
if (available()) { if (available()) {
return true; return true;
} }
sock_connected = at->modemGetConnected();
return sock_connected; return sock_connected;
} }
virtual operator bool() { return connected(); } virtual operator bool() { return connected(); }
@@ -219,8 +232,8 @@ public:
at->writeChanges(); at->writeChanges();
at->exitCommand(); at->exitCommand();
} }
else // After setting connection information, check if we're actually connected
sock_connected = false; sock_connected = at->modemGetConnected();
return sock_connected; return sock_connected;
} }
@@ -231,8 +244,8 @@ public:
at->writeChanges(); at->writeChanges();
at->exitCommand(); at->exitCommand();
} }
else // After setting connection information, check if we're actually connected
sock_connected = false; sock_connected = at->modemGetConnected();
return sock_connected; return sock_connected;
} }
}; };
@@ -246,6 +259,8 @@ public:
beeType = XBEE_UNKNOWN; // Start not knowing what kind of bee it is beeType = XBEE_UNKNOWN; // Start not knowing what kind of bee it is
guardTime = TINY_GSM_XBEE_GUARD_TIME; // Start with the default guard time of 1 second guardTime = TINY_GSM_XBEE_GUARD_TIME; // Start with the default guard time of 1 second
resetPin = -1; resetPin = -1;
ipAddr = IPAddress(0,0,0,0);
host = "";
memset(sockets, 0, sizeof(sockets)); memset(sockets, 0, sizeof(sockets));
} }
@@ -255,6 +270,8 @@ public:
beeType = XBEE_UNKNOWN; // Start not knowing what kind of bee it is beeType = XBEE_UNKNOWN; // Start not knowing what kind of bee it is
guardTime = TINY_GSM_XBEE_GUARD_TIME; // Start with the default guard time of 1 second guardTime = TINY_GSM_XBEE_GUARD_TIME; // Start with the default guard time of 1 second
this->resetPin = resetPin; this->resetPin = resetPin;
ipAddr = IPAddress(0,0,0,0);
host = "";
memset(sockets, 0, sizeof(sockets)); memset(sockets, 0, sizeof(sockets));
} }
@@ -742,7 +759,7 @@ public:
protected: protected:
bool modemConnect(const char* host, uint16_t port, uint8_t mux = 0, bool ssl = false) { IPAddress getHostIP(const char* host) {
String strIP; strIP.reserve(16); String strIP; strIP.reserve(16);
unsigned long startMillis = millis(); unsigned long startMillis = millis();
bool gotIP = false; bool gotIP = false;
@@ -758,13 +775,31 @@ protected:
delay(2500); // wait a bit before trying again delay(2500); // wait a bit before trying again
} }
if (gotIP) { // No reason to continue if we don't know the IP address if (gotIP) { // No reason to continue if we don't know the IP address
IPAddress ip = TinyGsmIpFromString(strIP); return TinyGsmIpFromString(strIP);
return modemConnect(ip, port, mux, ssl); }
else return IPAddress(0,0,0,0);
}
bool modemConnect(const char* host, uint16_t port, uint8_t mux = 0, bool ssl = false) {
// If requested host is the same as the previous one and we already
// have a valid IP address, we don't have to do anything.
if (this->host == String(host) && ipAddr != IPAddress(0,0,0,0)) {
return true;
}
// Otherwise, set the new host and mark the IP as invalid
this->host = String(host);
ipAddr == getHostIP(host); // This will return 0.0.0.0 if lookup fails
// If we now have a valid IP address, use it to connect
if (ipAddr != IPAddress(0,0,0,0)) { // Only re-set connection information if we have an IP address
return modemConnect(ipAddr, port, mux, ssl);
} }
else return false; else return false;
} }
bool modemConnect(IPAddress ip, uint16_t port, uint8_t mux = 0, bool ssl = false) { bool modemConnect(IPAddress ip, uint16_t port, uint8_t mux = 0, bool ssl = false) {
ipAddr = ip; // Set the newly requested IP address
bool success = true; bool success = true;
String host; host.reserve(16); String host; host.reserve(16);
host += ip[0]; host += ip[0];
@@ -794,12 +829,41 @@ protected:
return len; return len;
} }
bool modemGetConnected(uint8_t mux = 0) { bool modemGetConnected() {
if (!commandMode()) return false;
sendAT(GF("AI")); if (!commandMode()) return false; // Return immediately
int16_t res = waitResponse(GF("0"));
// If the IP address is 0, it's not valid so we can't be connected
if (ipAddr == IPAddress(0,0,0,0)) return false;
// Verify that we're connected to the *right* IP address
// We might be connected - but to the wrong thing
// NOTE: In transparent mode, there is only one connection possible - no multiplex
String strIP; strIP.reserve(16);
sendAT(GF("DL"));
strIP = stream.readStringUntil('\r'); // read result
if (TinyGsmIpFromString(strIP) != ipAddr) return exitAndFail();
if (beeType == XBEE_UNKNOWN) getSeries(); // Need to know the bee type to interpret response
switch (beeType){ // The wifi be can only say if it's connected to the netowrk
case XBEE_S6B_WIFI: {
RegStatus s = getRegistrationStatus();
if (s != REG_OK) {
sockets[0]->sock_connected = false;
}
return (s == REG_OK); // if it's connected, we hope the sockets are too
}
default: {
sendAT(GF("CI"));
int16_t intRes = readResponseInt();
exitCommand(); exitCommand();
return 1 == res; if (intRes != 0) {
sockets[0]->sock_connected = false;
}
return (0 == intRes);
}
}
} }
public: public:
@@ -968,6 +1032,8 @@ protected:
int16_t guardTime; int16_t guardTime;
int8_t resetPin; int8_t resetPin;
XBeeType beeType; XBeeType beeType;
IPAddress ipAddr;
String host;
GsmClient* sockets[TINY_GSM_MUX_COUNT]; GsmClient* sockets[TINY_GSM_MUX_COUNT];
}; };