44void _asyncudp_async_cb (uv_async_t *handle) {
55 AsyncUDP *udp = (AsyncUDP *)handle->data ;
66 udp->_DO_NOT_CALL_async_cb ();
7- };
7+ }
88
99AsyncUDP::AsyncUDP () {
1010 _handler = NULL ;
1111 _connected = false ;
1212 uv_loop_init (&_loop);
1313 _async.data = this ;
1414 uv_async_init (&_loop, &_async, _asyncudp_async_cb);
15- };
15+ }
16+
17+ AsyncUDP::~AsyncUDP () {
18+ _quit.store (true );
19+ uv_async_send (&_async);
20+ _ioThread.join ();
21+ uv_loop_close (&_loop);
22+ }
23+
24+ asyncUDPSendTask::asyncUDPSendTask (uint8_t *data, size_t len, IPAddress addr, uint16_t port) {
25+ this ->data = (uint8_t *)malloc (len);
26+ memcpy (this ->data , data, len);
27+ this ->len = len;
28+ this ->addr = addr;
29+ this ->port = port;
30+ }
1631
1732void _asyncudp_alloc_buffer_cb (uv_handle_t *handle, size_t suggested_size, uv_buf_t *buf) {
1833 buf->base = (char *)malloc (suggested_size);
1934 buf->len = suggested_size;
20- };
35+ }
2136
2237void _asyncudp_on_read_cb (uv_udp_t *handle, ssize_t nread, const uv_buf_t *buf, const struct sockaddr *addr, unsigned flags) {
2338 AsyncUDP *udp = (AsyncUDP *)handle->data ;
@@ -33,7 +48,7 @@ void AsyncUDP::_DO_NOT_CALL_uv_on_read(uv_udp_t *handle, ssize_t nread, const uv
3348 h (packet);
3449 }
3550 free (buf->base );
36- };
51+ }
3752
3853bool AsyncUDP::listenMulticast (const IPAddress addr, uint16_t port, uint8_t ttl) {
3954 if (_connected) {
@@ -73,7 +88,7 @@ bool AsyncUDP::listenMulticast(const IPAddress addr, uint16_t port, uint8_t ttl)
7388 _listenIP = addr;
7489 _connected = true ;
7590 return true ;
76- };
91+ }
7792
7893size_t AsyncUDP::writeTo (const uint8_t *data, size_t len, const IPAddress addr, uint16_t port) {
7994 auto task = std::make_unique<asyncUDPSendTask>((uint8_t *)data, len, addr, port);
@@ -82,7 +97,7 @@ size_t AsyncUDP::writeTo(const uint8_t *data, size_t len, const IPAddress addr,
8297 _sendQueueMutex.unlock ();
8398 uv_async_send (&_async);
8499 return len;
85- };
100+ }
86101
87102void AsyncUDP::_DO_NOT_CALL_async_cb () {
88103 _sendQueueMutex.lock ();
@@ -104,11 +119,11 @@ void AsyncUDP::_DO_NOT_CALL_async_cb() {
104119 uv_udp_set_membership (&_socket, addr_str, NULL , UV_LEAVE_GROUP);
105120 uv_stop (&_loop);
106121 }
107- };
122+ }
108123
109124void _asyncudp_send_cb (uv_udp_send_t *req, int status) {
110125 free (req);
111- };
126+ }
112127
113128void AsyncUDP::_doWrite (const uint8_t *data, size_t len, const IPAddress addr, uint16_t port) {
114129 // FIXME: don't do bytes → string → bytes IP conversion
@@ -128,4 +143,4 @@ void AsyncUDP::_doWrite(const uint8_t *data, size_t len, const IPAddress addr, u
128143 if (uv_udp_send (req, &_socket, &msg, 1 , (const struct sockaddr *)&uvAddr, _asyncudp_send_cb) < 0 ) {
129144 portduinoError (" FIXME: implement proper error handling; uv_udp_send failed" );
130145 }
131- };
146+ }
0 commit comments