diff --git a/net/ESP8266Interface/ESP8266/ATParser/BufferedSerial/BufferedSerial.cpp b/net/ESP8266Interface/ESP8266/ATParser/BufferedSerial/BufferedSerial.cpp index d13424264d..da3cbfa168 100644 --- a/net/ESP8266Interface/ESP8266/ATParser/BufferedSerial/BufferedSerial.cpp +++ b/net/ESP8266Interface/ESP8266/ATParser/BufferedSerial/BufferedSerial.cpp @@ -124,6 +124,10 @@ void BufferedSerial::rxIrq(void) // read from the peripheral and make sure something is available if(serial_readable(&_serial)) { _rxbuf = serial_getc(&_serial); // if so load them into a buffer + // trigger callback if necessary + if (_cbs[RxIrq]) { + _cbs[RxIrq](); + } } return; @@ -138,6 +142,10 @@ void BufferedSerial::txIrq(void) } else { // disable the TX interrupt when there is nothing left to send RawSerial::attach(NULL, RawSerial::TxIrq); + // trigger callback if necessary + if (_cbs[TxIrq]) { + _cbs[TxIrq](); + } break; } } @@ -157,4 +165,8 @@ void BufferedSerial::prime(void) return; } +void BufferedSerial::attach(Callback func, IrqType type) +{ + _cbs[type] = func; +} diff --git a/net/ESP8266Interface/ESP8266/ATParser/BufferedSerial/BufferedSerial.h b/net/ESP8266Interface/ESP8266/ATParser/BufferedSerial/BufferedSerial.h index 3463d15d39..5c58928e72 100644 --- a/net/ESP8266Interface/ESP8266/ATParser/BufferedSerial/BufferedSerial.h +++ b/net/ESP8266Interface/ESP8266/ATParser/BufferedSerial/BufferedSerial.h @@ -79,6 +79,8 @@ private: void rxIrq(void); void txIrq(void); void prime(void); + + Callback _cbs[2]; public: /** Create a BufferedSerial port, connected to the specified transmit and receive pins @@ -135,6 +137,22 @@ public: * @return The number of bytes written to the Serial Port Buffer */ virtual ssize_t write(const void *s, std::size_t length); + + /** Attach a function to call whenever a serial interrupt is generated + * @param func A pointer to a void function, or 0 to set as none + * @param type Which serial interrupt to attach the member function to (Serial::RxIrq for receive, TxIrq for transmit buffer empty) + */ + virtual void attach(Callback func, IrqType type=RxIrq); + + /** Attach a member function to call whenever a serial interrupt is generated + * @param obj pointer to the object to call the member function on + * @param method pointer to the member function to call + * @param type Which serial interrupt to attach the member function to (Serial::RxIrq for receive, TxIrq for transmit buffer empty) + */ + template + void attach(T *obj, M method, IrqType type=RxIrq) { + attach(Callback(obj, method), type); + } }; #endif diff --git a/net/ESP8266Interface/ESP8266/ESP8266.cpp b/net/ESP8266Interface/ESP8266/ESP8266.cpp index 9e39147f7d..e2f0dc5443 100644 --- a/net/ESP8266Interface/ESP8266/ESP8266.cpp +++ b/net/ESP8266Interface/ESP8266/ESP8266.cpp @@ -167,3 +167,7 @@ bool ESP8266::writeable() return _serial.writeable(); } +void ESP8266::attach(Callback func) +{ + _serial.attach(func); +} diff --git a/net/ESP8266Interface/ESP8266/ESP8266.h b/net/ESP8266Interface/ESP8266/ESP8266.h index 808aec3614..40050a429b 100644 --- a/net/ESP8266Interface/ESP8266/ESP8266.h +++ b/net/ESP8266Interface/ESP8266/ESP8266.h @@ -144,6 +144,24 @@ public: */ bool writeable(); + /** + * Attach a function to call whenever network state has changed + * + * @param func A pointer to a void function, or 0 to set as none + */ + void attach(Callback func); + + /** + * Attach a function to call whenever network state has changed + * + * @param obj pointer to the object to call the member function on + * @param method pointer to the member function to call + */ + template + void attach(T *obj, M method) { + attach(Callback(obj, method)); + } + private: BufferedSerial _serial; ATParser _parser; diff --git a/net/ESP8266Interface/ESP8266Interface.cpp b/net/ESP8266Interface/ESP8266Interface.cpp index 82b717b40e..71cc5953f2 100644 --- a/net/ESP8266Interface/ESP8266Interface.cpp +++ b/net/ESP8266Interface/ESP8266Interface.cpp @@ -29,6 +29,9 @@ ESP8266Interface::ESP8266Interface(PinName tx, PinName rx, bool debug) : _esp(tx, rx, debug) { memset(_ids, 0, sizeof(_ids)); + memset(_cbs, 0, sizeof(_cbs)); + + _esp.attach(this, &ESP8266Interface::event); } int ESP8266Interface::connect( @@ -203,4 +206,15 @@ int ESP8266Interface::socket_recvfrom(void *handle, SocketAddress *addr, void *d void ESP8266Interface::socket_attach(void *handle, void (*callback)(void *), void *data) { + struct esp8266_socket *socket = (struct esp8266_socket *)handle; + _cbs[socket->id].callback = callback; + _cbs[socket->id].data = data; +} + +void ESP8266Interface::event() { + for (int i = 0; i < ESP8266_SOCKET_COUNT; i++) { + if (_cbs[i].callback) { + _cbs[i].callback(_cbs[i].data); + } + } } diff --git a/net/ESP8266Interface/ESP8266Interface.h b/net/ESP8266Interface/ESP8266Interface.h index ce26e5ea82..831e027303 100644 --- a/net/ESP8266Interface/ESP8266Interface.h +++ b/net/ESP8266Interface/ESP8266Interface.h @@ -167,6 +167,12 @@ protected: private: ESP8266 _esp; bool _ids[ESP8266_SOCKET_COUNT]; + + void event(); + struct { + void (*callback)(void *); + void *data; + } _cbs[ESP8266_SOCKET_COUNT]; }; #endif