DeterministicESPAsyncWebServer v6.28.0
Zero-allocation, bounded-execution async HTTP server for ESP32
Loading...
Searching...
No Matches
sockpool.cpp
Go to the documentation of this file.
1// Copyright (C) 2026 Douglas Quigg (dstroy0) <dquigg123@gmail.com>
2// SPDX-License-Identifier: AGPL-3.0-or-later
3
4/**
5 * @file sockpool.cpp
6 * @brief Dynamic socket recycling: an LRU connection-slot pool (see sockpool.h).
7 */
8
10
11#if DETWS_ENABLE_SOCKPOOL
12
13void detws_sockpool_init(SockPool *p, SockSlot *slots, size_t n)
14{
15 if (!p)
16 return;
17 p->slots = slots;
18 p->n = slots ? n : 0;
19 for (size_t i = 0; i < p->n; i++)
20 {
21 p->slots[i].in_use = false;
22 p->slots[i].id = 0;
23 p->slots[i].last_used = 0;
24 }
25}
26
27SockAcq detws_sockpool_acquire(SockPool *p, uint32_t id, uint32_t now, size_t *idx, uint32_t *evicted_id)
28{
29 if (!p || !p->slots || p->n == 0)
30 return SockAcq::SOCK_ACQ_FAIL;
31
32 // Prefer a free slot.
33 for (size_t i = 0; i < p->n; i++)
34 {
35 if (!p->slots[i].in_use)
36 {
37 p->slots[i].in_use = true;
38 p->slots[i].id = id;
39 p->slots[i].last_used = now;
40 if (idx)
41 *idx = i;
42 return SockAcq::SOCK_ACQ_FREE;
43 }
44 }
45
46 // Full: recycle the least-recently-used slot.
47 size_t lru = 0;
48 for (size_t i = 1; i < p->n; i++)
49 if (p->slots[i].last_used < p->slots[lru].last_used)
50 lru = i;
51 if (evicted_id)
52 *evicted_id = p->slots[lru].id;
53 p->slots[lru].id = id;
54 p->slots[lru].last_used = now;
55 if (idx)
56 *idx = lru;
57 return SockAcq::SOCK_ACQ_RECYCLED;
58}
59
60void detws_sockpool_touch(SockPool *p, size_t idx, uint32_t now)
61{
62 if (!p || !p->slots || idx >= p->n)
63 return;
64 if (p->slots[idx].in_use)
65 p->slots[idx].last_used = now;
66}
67
68bool detws_sockpool_release(SockPool *p, size_t idx)
69{
70 if (!p || !p->slots || idx >= p->n || !p->slots[idx].in_use)
71 return false;
72 p->slots[idx].in_use = false;
73 return true;
74}
75
76bool detws_sockpool_find(const SockPool *p, uint32_t id, size_t *idx)
77{
78 if (!p || !p->slots)
79 return false;
80 for (size_t i = 0; i < p->n; i++)
81 if (p->slots[i].in_use && p->slots[i].id == id)
82 {
83 if (idx)
84 *idx = i;
85 return true;
86 }
87 return false;
88}
89
90size_t detws_sockpool_in_use(const SockPool *p)
91{
92 if (!p || !p->slots)
93 return 0;
94 size_t c = 0;
95 for (size_t i = 0; i < p->n; i++)
96 if (p->slots[i].in_use)
97 c++;
98 return c;
99}
100
101#endif // DETWS_ENABLE_SOCKPOOL
Dynamic socket recycling: an LRU connection-slot pool (DETWS_ENABLE_SOCKPOOL).