@@ -30,6 +30,7 @@ void esp_schedule();
30
30
}
31
31
32
32
#include < AddrList.h>
33
+ #include < PolledTimeout.h>
33
34
34
35
#define PBUF_ALIGNER_ADJUST 4
35
36
#define PBUF_ALIGNER (x ) ((void *)((((intptr_t )(x))+3 )&~3 ))
@@ -390,14 +391,39 @@ class UdpContext
390
391
return size;
391
392
}
392
393
394
+ void cancelBuffer ()
395
+ {
396
+ if (_tx_buf_head)
397
+ pbuf_free (_tx_buf_head);
398
+ _tx_buf_head = 0 ;
399
+ _tx_buf_cur = 0 ;
400
+ _tx_buf_offset = 0 ;
401
+ }
402
+
393
403
bool send (const ip_addr_t * addr = 0 , uint16_t port = 0 )
404
+ {
405
+ return trySend (addr, port, /* don't keep buffer */ false ) == ERR_OK;
406
+ }
407
+
408
+ bool sendTimeout (const ip_addr_t * addr, uint16_t port,
409
+ esp8266::polledTimeout::oneShotFastMs::timeType timeoutMs)
410
+ {
411
+ err_t err;
412
+ esp8266::polledTimeout::oneShotFastMs timeout (timeoutMs);
413
+ while (((err = trySend (addr, port, /* keep buffer on error */ true )) != ERR_OK) && !timeout)
414
+ delay (0 );
415
+ if (err != ERR_OK)
416
+ cancelBuffer (); // get rid of buffer kept on error after timeout
417
+ return err == ERR_OK;
418
+ }
419
+
420
+ private:
421
+
422
+ err_t trySend (const ip_addr_t * addr, uint16_t port, bool keepBufferOnError)
394
423
{
395
424
size_t data_size = _tx_buf_offset;
396
425
pbuf* tx_copy = pbuf_alloc (PBUF_TRANSPORT, data_size, PBUF_RAM);
397
- if (!tx_copy){
398
- DEBUGV (" failed pbuf_alloc" );
399
- }
400
- else {
426
+ if (tx_copy) {
401
427
uint8_t * dst = reinterpret_cast <uint8_t *>(tx_copy->payload );
402
428
for (pbuf* p = _tx_buf_head; p; p = p->next ) {
403
429
size_t will_copy = (data_size < p->len ) ? data_size : p->len ;
@@ -406,38 +432,32 @@ class UdpContext
406
432
data_size -= will_copy;
407
433
}
408
434
}
409
- if (_tx_buf_head)
410
- pbuf_free (_tx_buf_head);
411
- _tx_buf_head = 0 ;
412
- _tx_buf_cur = 0 ;
413
- _tx_buf_offset = 0 ;
414
- if (!tx_copy){
415
- return false ;
416
- }
417
435
436
+ if (!keepBufferOnError)
437
+ cancelBuffer ();
438
+
439
+ if (!tx_copy){
440
+ DEBUGV (" failed pbuf_alloc" );
441
+ return ERR_MEM;
442
+ }
418
443
419
444
if (!addr) {
420
445
addr = &_pcb->remote_ip ;
421
446
port = _pcb->remote_port ;
422
447
}
423
- #ifdef LWIP_MAYBE_XCC
424
- uint16_t old_ttl = _pcb->ttl ;
425
- if (ip_addr_ismulticast (addr)) {
426
- _pcb->ttl = _mcast_ttl;
427
- }
428
- #endif
448
+
429
449
err_t err = udp_sendto (_pcb, tx_copy, addr, port);
430
450
if (err != ERR_OK) {
431
451
DEBUGV (" :ust rc=%d\r\n " , (int ) err);
432
452
}
433
- #ifdef LWIP_MAYBE_XCC
434
- _pcb->ttl = old_ttl;
435
- #endif
453
+
436
454
pbuf_free (tx_copy);
437
- return err == ERR_OK;
438
- }
439
455
440
- private:
456
+ if (err == ERR_OK)
457
+ cancelBuffer (); // no error: get rid of buffer
458
+
459
+ return err;
460
+ }
441
461
442
462
size_t _processSize (const pbuf* pb)
443
463
{
0 commit comments