You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
Commit eb641fe
Browse filesBrowse the repository at this point in the historyBrowse files
p2plimits: a stream budget carries the memory its streams reserve
yamux reserves one 256 KiB receive window per stream it opens, through
the resource manager, and releases it with the stream; the bytes are
allocated only as data arrives. With the node dialling TCP first, every
member's hub link runs over yamux, and a router's memory budget, which
libp2p scales from host memory and nothing here had set, filled at 1500
members: 1.17 GB reserved of 1.18 GB on the testnet's routers, after
which the relay refused every circuit with RESOURCE_LIMIT_EXCEEDED (3200
to 3400 per router in one ladder step) while every stream counter stayed
at zero, since a refused memory reservation is not a refused stream.
Streams(n) now carries the memory its 2n streams reserve, one window
each, so the system, transient, service and protocol budgets built from
it follow the connection budget as the streams do; the router's and the
node's peer scope get the same budget as the per-peer circuits, since the
peer scope for a service many members call carries one stop stream per
caller. The reporter counts refused memory reservations in
agentmesh_{router,node}_memory_reservations_refused_total and logs them
once a minute, naming the libp2p gauges that show which scope is full.
Tests pin the budgets and check that a manager built from Streams(n)
admits 2n windows and refuses the next.
returnfmt.Sprintf("[Stream] Refused %d stream(s) %s since the last report; the peer sees its stream reset", n, what)
89
+
})
90
+
}
91
+
92
+
// BlockMemory is a memory reservation the manager refused: the muxer's
93
+
// window for a new stream, or the relay's buffers for a connection it
94
+
// would relay. The budget it ran into is libp2p_rcmgr_limit{resource=
95
+
// "memory"} on the scope libp2p_rcmgr_memory shows full.
96
+
func (s*StreamRefusals) BlockMemory(sizeint) {
97
+
ifs.memoryRefused!=nil {
98
+
s.memoryRefused.Inc()
99
+
}
100
+
s.report("memory", func(nuint64) string {
101
+
returnfmt.Sprintf("[Memory] Refused %d memory reservation(s) since the last report, the last for %d bytes: the resource manager's memory budget is full (libp2p_rcmgr_memory against libp2p_rcmgr_limit{resource=\"memory\"}); a new stream or a relayed connection that needs it is refused", n, size)
102
+
})
103
+
}
104
+
105
+
// report counts one refusal under key and, once per RefusalLogInterval,
106
+
// logs the line for the count since the last report.
Copy file name to clipboardExpand all lines: site/content/docs/guides/scalability.md
+17Lines changed: 17 additions & 0 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -101,6 +101,22 @@ from host memory. A refused stream is counted in
101
101
`agentmesh_router_streams_refused_total{protocol}` and
102
102
`agentmesh_node_streams_refused_total{protocol}`.
103
103
104
+
A stream over TCP also reserves memory. yamux reserves one receive window
105
+
(256 KiB) per stream it opens, through the resource manager, and releases
106
+
it when the stream closes; the memory is allocated only as data arrives
107
+
and waits to be read, so an idle stream holds a reservation and no bytes.
108
+
The memory budget therefore follows the stream budget, one window per
109
+
stream the budget admits, on the system scope and on the scope of each
110
+
peer. libp2p's own default for the system scope is scaled from host
111
+
memory and was 1.1 GiB on the testnet's routers, full at 1500 members
112
+
over TCP, at which point the relay refused every circuit with
113
+
`RESOURCE_LIMIT_EXCEEDED` and no stream counter moved. A refused
114
+
reservation is counted in
115
+
`agentmesh_router_memory_reservations_refused_total` and
116
+
`agentmesh_node_memory_reservations_refused_total`, and the scope that is
117
+
full reads from `libp2p_rcmgr_memory{scope}` against
118
+
`libp2p_rcmgr_limit{resource="memory",scope}`.
119
+
104
120
### Hub links and peer links
105
121
106
122
A member's connection to a router is a hub link. It carries the member's
@@ -367,6 +383,7 @@ The router and the control plane serve Prometheus metrics on
367
383
|`libp2p_relaysvc_reservations_total{type="opened"}` minus `{type="closed"}`, against `agentmesh_router_relay_limit{limit="reservations"}`| Reservations in use against the budget. |
368
384
|`libp2p_relaysvc_connection_rejections_total{reason="resource limit exceeded"}`| A service has more callers than `--relay-max-circuits`. |
369
385
|`libp2p_rcmgr_blocked_resources`| libp2p refused a connection or stream on a scope. On a router this should stay flat. |
386
+
|`agentmesh_router_memory_reservations_refused_total`, `agentmesh_node_memory_reservations_refused_total`, with `libp2p_rcmgr_memory{scope}` against `libp2p_rcmgr_limit{resource="memory",scope}`| The resource manager's memory budget on some scope is full. Over TCP every open stream holds a 256 KiB reservation, so this is the stream budget met from the other side: new streams and relayed connections are refused, with `RESOURCE_LIMIT_EXCEEDED` at the relay and nothing in the stream counters. The scope whose `libp2p_rcmgr_memory` is at its limit names the budget. |
370
387
|`agentmesh_router_streams_refused_total{scope,protocol}`, `agentmesh_node_streams_refused_total{scope,protocol}`| The streams behind that gauge, by protocol. `/mesh/kad/1.0.0` or `/meshsub/*` at the `protocol` scope on a router is members past the stream budget of a protocol, which keeps them out of discovery; `agentmesh_router_dht_routing_table_size` falls with it. |
371
388
|`agentmesh_router_auth_handshakes_total{result="read_failed"}`| Members that timed out mid-handshake: the router is slow, usually CPU. |
372
389
|`agentmesh_router_draining`| The router is stopping. Exclude it from capacity sums. |
0 commit comments