diff --git a/content/momentum/4/config-options-summary.md b/content/momentum/4/config-options-summary.md index 7a784f357..effbb7b12 100644 --- a/content/momentum/4/config-options-summary.md +++ b/content/momentum/4/config-options-summary.md @@ -197,7 +197,7 @@ The `Version` column indicated the version(s) of Momentum that support the optio | [http_method](/momentum/4/config/ref-http-method) – Define the HTTP method to use | sending | POST | 4.0 and later | binding, binding_group, domain, global | | [http_uri](/momentum/4/config/ref-http-uri) – Define the HTTP URI that you wish to connect to | sending |   | 4.0 and later | binding, binding_group, domain, global | | [http_version](/momentum/4/config/ref-http-version) – Define the HTTP version to use | sending | 1.1 | 4.0 and later | binding, binding_group, domain, global | -| **idle_time** – Number of seconds of inactivity before a client is disconnected | receiving | 300 | 4.0 and later | esmtp_listener, http_listener, listen, pathway, pathway_group, peer, xmpp_listener | +| [idle_time](/momentum/4/config/ref-idle-time) – Number of seconds of inactivity before a client is disconnected | receiving | 300 | 4.0 and later | esmtp_listener, http_listener, listen, pathway, pathway_group, peer, xmpp_listener | | [idle_timeout](/momentum/4/config/ref-idle-timeout) – Time to maintain idle outbound connections | sending | 5 | 4.0 and later | binding, binding_group, domain, global | | [if_check_interval](/momentum/4/modules/4-modules-cluster#option.if_check_interval) – How often to run through a maintenance cycle (cluster-specific) | na | 30 | 4.0 and later | cluster | | [if_down_limit](/momentum/4/modules/4-modules-cluster#option.if_down_limit) – How long to wait before deciding to bring an IP online (cluster-specific) | na | 4 | 4.0 and later | cluster | @@ -211,7 +211,7 @@ The `Version` column indicated the version(s) of Momentum that support the optio | [license](/momentum/4/config/ref-license) – Specify an alternate license location | na | /opt/msys/ecelerity/etc (*non-dynamic*) | 4.0 and later | global | | [listen](/momentum/4/listeners#listeners.enable.option) *(scope)* – Specify the socket that a listener listens on | receiving |   | 4.0 and later | control_listener, ecstream_listener, esmtp_listener, http_listener, msgcserver_listener, xmpp_listener | | **listen_backlog** – Listen backlog | receiving | 500 (*3.0*) | 4.0 and later | control_listener, eccluster_listener, ecstream_listener, esmtp_listener, http_listener, listen, xmpp_listener | -| **listener_sessions** – Specifies the maximum number of concurrent sessions that can be established to this listener | receiving | 0 | 4.0 and later | esmtp_listener, listen, pathway, pathway_group, peer | +| [listener_sessions](/momentum/4/config/ref-listener-sessions) – Specifies the maximum number of concurrent sessions that can be established to this listener | receiving | 0 | 4.0 and later | esmtp_listener, listen, pathway, pathway_group, peer | | [lmtp_port](/momentum/4/config/ref-lmtp-port) – Configure the port for LMTP deliveries | sending | 2003 | 4.0 and later | binding, binding_group, domain, global | | [local_changes_file](/momentum/4/config/ref-local-changes-file) – File for writing local configuration changes | na | /opt/msys/ecelerity/etc/local_changes.conf | 4.0 and later | global | | [local_changes_only](/momentum/4/config/ref-local-changes-only) – Whether there is a file for writing local configuration change | na | false | 4.0 and later | global | @@ -321,7 +321,7 @@ The `Version` column indicated the version(s) of Momentum that support the optio | [server_max_file_descriptors](/momentum/4/config/ref-server-max-file-descriptors) – Sets the maximum number of file descriptors usable by the system | na | 3000000 | 4.0 and later | global | | [server_max_outbound_connections](/momentum/4/config/ref-server-max-outbound-connections) – Sets the maximum number of outbound connections | sending | 20000 | 4.0 and later | binding, binding_group, global | | [server_reserve_outbound_connections](/momentum/4/config/ref-server-reserve-outbound-connections) – Sets the server-wide connection limit reserve | sending | 200 | 4.0 and later | global | -| **service_sessions** – Specifies the maximum number of concurrent sessions that can be established to all listeners for this service (e.g., ESMTP, ECStream) | receiving | 0 | 4.0 and later | esmtp_listener, listen, pathway, pathway_group, peer | +| [service_sessions](/momentum/4/config/ref-service-sessions) – Specifies the maximum number of concurrent sessions that can be established to all listeners for this service (e.g., ESMTP, ECStream) | receiving | 0 | 4.0 and later | esmtp_listener, listen, pathway, pathway_group, peer | | [signing_stats](/momentum/4/config/ref-signing-stats) – Control how signing statistics are recorded | sending | all | 4.0 and later | global | | [siv_throttle_cache_size](/momentum/4/config/ref-siv-throttle-cache-size) – Set the maximum number of named throttles | both | 100, 1000 (*3.0.24*) | 4.0 and later | global | | [skip_hosts](/momentum/4/config/ref-skip-hosts) – Skip the specified host, but consider other hosts in the domain | sending |   | 4.2.1.6 and later | global | diff --git a/content/momentum/4/config/ref-idle-time.md b/content/momentum/4/config/ref-idle-time.md new file mode 100644 index 000000000..4769fd124 --- /dev/null +++ b/content/momentum/4/config/ref-idle-time.md @@ -0,0 +1,50 @@ +--- +lastUpdated: "06/24/2026" +title: "Idle_Time" +description: "idle time specifies the number of seconds of inactivity before an inbound client connection is disconnected It recycles idle session slots so that concurrency caps such as listener sessions and service sessions are not held by idle connections." +--- + + +## Name + +Idle_Time — number of seconds of inactivity before an inbound client is disconnected. + +## Synopsis + +`Idle_Time = 300` + + +## Description + +`Idle_Time` sets the number of seconds an inbound client connection may remain idle before Momentum disconnects it. It is the primary mechanism for reclaiming session slots held by connections that are no longer doing useful work, and it works hand-in-hand with the inbound concurrency caps [Listener_Sessions](/momentum/4/config/ref-listener-sessions) and [Service_Sessions](/momentum/4/config/ref-service-sessions): because a session slot is held for the entire life of a connection, reaping idle connections frees slots that would otherwise count against those caps. + +The default for this option is `0`, which means connections are never reaped for inactivity. The `ecelerity.conf` file shipped with Momentum sets `Idle_Time` to `300`, which is the recommended value. + +Like the session caps, `Idle_Time` can be set per source block by placing it inside a `Peer` (CIDR) scope — for example, a longer idle window for trusted senders and a shorter one for everyone else: + +``` +ESMTP_Listener { + Idle_Time = 60 + + Peer "10.0.0.0/8" { # trusted senders: longer idle window + Idle_Time = 300 + } + Peer "0.0.0.0/0" { # everyone else: faster reaping + Idle_Time = 30 + } +} +``` + +### Caveats + +`Idle_Time` only reaps connections that the event loop is actively watching, and only when the loop is free. Under saturation it fires late, and it will not reap connections parked for asynchronous work. It recycles idle session slots, but it will not clear every lingering connection — it is not a substitute for addressing connections that fail to close. + + +## Scope + +`Idle_Time` is valid in the esmtp_listener, http_listener, listen, pathway, pathway_group, peer, and xmpp_listener scopes. + + +## See Also + +[Listener_Sessions](/momentum/4/config/ref-listener-sessions), [Service_Sessions](/momentum/4/config/ref-service-sessions), [Listeners](/momentum/4/listeners), [Configuring Inbound Mail Service Using SMTP](/momentum/4/esmtp-listener) diff --git a/content/momentum/4/config/ref-listener-sessions.md b/content/momentum/4/config/ref-listener-sessions.md new file mode 100644 index 000000000..c29461426 --- /dev/null +++ b/content/momentum/4/config/ref-listener-sessions.md @@ -0,0 +1,80 @@ +--- +lastUpdated: "06/24/2026" +title: "Listener_Sessions" +description: "listener sessions specifies the maximum number of concurrent inbound sessions that can be established to this listener When the cap is reached new connections receive a retryable 421 4 4 5 response and are closed Use Peer CIDR scopes to partition the cap per source block." +--- + + +## Name + +Listener_Sessions — maximum number of concurrent inbound sessions for a single listener. + +## Synopsis + +`Listener_Sessions = 0` + + +## Description + +`Listener_Sessions` caps the number of concurrent inbound sessions that may be established to *this* listener (for example, the `ESMTP_Listener`). It is a circuit-breaker that protects a node from being overwhelmed by inbound concurrency. + +A session slot is held for the entire life of a connection — including time spent idle or otherwise lingering — and is only released when the connection is fully closed. While the cap is reached, every new connection in the same scope is rejected, including legitimate mail, until a slot is freed. + +When the cap is reached, the connection is given a clean, retryable response and is closed: + +``` +421 4.4.5 Service unavailable, concurrency limit reached. +``` + +The default value is `0`, which means *no limit*. + +### Scope, fallback, and per-source caps + +`Listener_Sessions` is a *per-scope aggregate*, not a per-IP limit. How the active sessions are counted depends on the scope in which the option is set: + +* When set **outside** a `Peer` scope (directly in the `ESMTP_Listener` or a `Listen` scope), the cap is a single shared budget summed across **all** connecting sources. A few noisy sources can consume the entire budget. + +* When set **inside** a `Peer` (CIDR) scope, sessions are counted **per matching CIDR block**, so each source block gets its own independent budget. + +Because `Peer` scopes use most-specific-match fallback, you can partition a broad cap into narrower per-source budgets, and apply tighter caps to known offenders. For more information about fallback, see [“Configuration Scopes and Fallback”](/momentum/4/4-ecelerity-conf-fallback). + +The following example sets an absolute ceiling on the listener, a larger budget for a trusted subnet, and a tighter budget for everyone else: + +``` +ESMTP_Listener { + Listener_Sessions = 1800 # ceiling for this listener + Idle_Time = 60 + + Peer "10.0.0.0/8" { # trusted senders: larger budget + Listener_Sessions = 1500 + Idle_Time = 300 + } + Peer "0.0.0.0/0" { # everyone else: tighter cap, faster reaping + Listener_Sessions = 600 + Idle_Time = 30 + } + + Listen ":25" { + Listener_Sessions = 1800 + Idle_Time = 60 + } +} +``` + +### Caveats + +* **The cap counts lingering connections too.** A slot is held for the connection's whole life, including while it is stuck. If connections keep lingering, the cap fills with them and then rejects all new connections in that scope. It is a circuit-breaker, not a cure for connections that fail to close. + +* **It is a per-scope aggregate, not per-IP.** A broad cap is one shared budget that a few noisy sources can consume. Partition it with narrower `Peer` scopes, and use specific tight scopes (or upstream firewalling) for known offenders. + +To cap concurrency across *all* listeners for a service rather than a single listener, see [Service_Sessions](/momentum/4/config/ref-service-sessions). + + +## Scope + +`Listener_Sessions` is valid in the esmtp_listener, listen, pathway, pathway_group, and peer scopes. + + +## See Also + +[Service_Sessions](/momentum/4/config/ref-service-sessions), [Idle_Time](/momentum/4/config/ref-idle-time), [Listeners](/momentum/4/listeners), [Configuring Inbound Mail Service Using SMTP](/momentum/4/esmtp-listener) diff --git a/content/momentum/4/config/ref-service-sessions.md b/content/momentum/4/config/ref-service-sessions.md new file mode 100644 index 000000000..5929c0ba5 --- /dev/null +++ b/content/momentum/4/config/ref-service-sessions.md @@ -0,0 +1,75 @@ +--- +lastUpdated: "06/24/2026" +title: "Service_Sessions" +description: "service sessions specifies the maximum number of concurrent inbound sessions that can be established to all listeners for a service such as ESMTP or ECStream When the cap is reached new connections receive a retryable 421 4 4 5 response and are closed Use Peer CIDR scopes to partition the cap per source block." +--- + + +## Name + +Service_Sessions — maximum number of concurrent inbound sessions across all listeners for a service. + +## Synopsis + +`Service_Sessions = 0` + + +## Description + +`Service_Sessions` caps the number of concurrent inbound sessions that may be established across **all** listeners for a given service (for example, ESMTP or ECStream). This differs from [Listener_Sessions](/momentum/4/config/ref-listener-sessions), which limits a single listener: where several listeners serve the same service (for example, an `ESMTP_Listener` bound to ports 25, 587, and a Unix socket), `Service_Sessions` is the shared ceiling across all of them. + +A session slot is held for the entire life of a connection — including time spent idle or otherwise lingering — and is only released when the connection is fully closed. While the cap is reached, every new connection in the same scope is rejected, including legitimate mail, until a slot is freed. + +When the cap is reached, the connection is given a clean, retryable response and is closed: + +``` +421 4.4.5 Service unavailable, concurrency limit reached. +``` + +The default value is `0`, which means *no limit*. + +### Scope, fallback, and per-source caps + +`Service_Sessions` is a *per-scope aggregate*, not a per-IP limit. How the active sessions are counted depends on the scope in which the option is set: + +* When set **outside** a `Peer` scope, the cap is a single shared budget summed across **all** connecting sources for the service. A few noisy sources can consume the entire budget. + +* When set **inside** a `Peer` (CIDR) scope, sessions are counted **per matching CIDR block**, so each source block gets its own independent budget. + +Because `Peer` scopes use most-specific-match fallback, you can partition a broad cap into narrower per-source budgets, and apply tighter caps to known offenders. For more information about fallback, see [“Configuration Scopes and Fallback”](/momentum/4/4-ecelerity-conf-fallback). + +The following example sets a service-wide ceiling, a larger budget for a trusted subnet, and a tighter budget for everyone else: + +``` +ESMTP_Listener { + Service_Sessions = 2000 # absolute ceiling across all ESMTP sockets + Idle_Time = 60 + + Peer "10.0.0.0/8" { # trusted senders: larger budget + Service_Sessions = 1500 + Idle_Time = 300 + } + Peer "0.0.0.0/0" { # everyone else: tighter cap, faster reaping + Service_Sessions = 600 + Idle_Time = 30 + } +} +``` + +### Caveats + +* **The cap counts lingering connections too.** A slot is held for the connection's whole life, including while it is stuck. If connections keep lingering, the cap fills with them and then rejects all new connections in that scope. It is a circuit-breaker, not a cure for connections that fail to close. + +* **It is a per-scope aggregate, not per-IP.** A broad cap is one shared budget that a few noisy sources can consume. Partition it with narrower `Peer` scopes, and use specific tight scopes (or upstream firewalling) for known offenders. + +To cap concurrency for a single listener rather than the whole service, see [Listener_Sessions](/momentum/4/config/ref-listener-sessions). + + +## Scope + +`Service_Sessions` is valid in the esmtp_listener, listen, pathway, pathway_group, and peer scopes. + + +## See Also + +[Listener_Sessions](/momentum/4/config/ref-listener-sessions), [Idle_Time](/momentum/4/config/ref-idle-time), [Listeners](/momentum/4/listeners), [Configuring Inbound Mail Service Using SMTP](/momentum/4/esmtp-listener) diff --git a/content/momentum/4/esmtp-listener.md b/content/momentum/4/esmtp-listener.md index bae8d32aa..0cec1e6c4 100644 --- a/content/momentum/4/esmtp-listener.md +++ b/content/momentum/4/esmtp-listener.md @@ -49,8 +49,18 @@ The `Pool_Name` option associates the `accept-pool` ThreadPool with the listener When using threaded accepts for listeners, you must provision the thread pool you intend to use via the ThreadPool directive. If the thread pool you name is not found or is unspecified, the IO pool will be used and a critical message will appear in your log. +### Limiting Inbound Concurrency + +You can cap the number of concurrent inbound sessions with two options: + +* [Listener_Sessions](/momentum/4/config/ref-listener-sessions) – the maximum concurrent sessions for *this* listener. + +* [Service_Sessions](/momentum/4/config/ref-service-sessions) – the maximum concurrent sessions across *all* listeners for the service (for example, all ESMTP sockets). + +Both default to `0` (no limit). When a cap is reached, new connections receive a clean, retryable `421 4.4.5 Service unavailable, concurrency limit reached.` and are closed. The caps are a *per-scope aggregate*, not a per-IP limit: set them outside a `Peer` scope for a single shared budget, or inside `Peer` (CIDR) scopes to give each source block its own budget. Use [Idle_Time](/momentum/4/config/ref-idle-time) to reap idle session slots. See the linked reference pages for the full behavior and caveats. + For details about the non-module specific configuration options that are valid in the ESMTP_Listener and its nested scopes, refer to [*Configuration Options Summary*](/momentum/4/config-options-summary) . Modules and their configuration options are discussed in the [*Modules Reference*](/momentum/4/modules/) . -For general information regarding listeners, see [“Listeners”](/momentum/4/listeners). \ No newline at end of file +For general information regarding listeners, see [“Listeners”](/momentum/4/listeners).