Compare commits
3
Commits
v0.2.0
..
535f7bcc68
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
535f7bcc68 | ||
|
|
b137c646b0 | ||
|
|
792897d3e4 |
+3
-2
@@ -1,12 +1,13 @@
|
||||
[package]
|
||||
name = "urus"
|
||||
version = "0.2.0"
|
||||
version = "0.2.2"
|
||||
edition = "2021"
|
||||
rust-version = "1.95"
|
||||
description = "Cowboy/bandit-style HTTP library for the smarm actor runtime"
|
||||
license = "MIT"
|
||||
|
||||
[dependencies]
|
||||
smarm = { git = "https://git.kalsbeek.dev/Markk116/smarm", tag = "v0.5.0" }
|
||||
smarm = { git = "https://git.kalsbeek.dev/Markk116/smarm", tag = "v0.6.0" }
|
||||
httparse = "1.9"
|
||||
libc = "0.2"
|
||||
sha1_smol = "1"
|
||||
|
||||
@@ -0,0 +1,21 @@
|
||||
MIT License
|
||||
|
||||
Copyright (c) 2026 Mark Kalsbeek
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all
|
||||
copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
SOFTWARE.
|
||||
+22
-4
@@ -57,8 +57,19 @@ pub struct Config {
|
||||
/// (one per CPU). Set this to a small fixed number in tests so multiple
|
||||
/// concurrent test servers don't oversubscribe the host.
|
||||
pub scheduler_threads: Option<usize>,
|
||||
/// Stack reserve (RFC 019 `smarm::SpawnOpts::stack_reserve`) given to
|
||||
/// each per-connection actor. Request handlers routinely pull in
|
||||
/// application code — DB drivers, (de)compression, templating — whose
|
||||
/// stack needs comfortably exceed smarm's bare-actor default of 64 KiB
|
||||
/// (the exact shape of bug this exists to head off; see smarm RFC 019).
|
||||
/// Default: 256 KiB. The reserve is virtual/demand-paged, so raising it
|
||||
/// costs address space, not RSS, until a handler actually uses it.
|
||||
pub conn_stack_reserve: usize,
|
||||
}
|
||||
|
||||
/// Default per-connection actor stack reserve (see [`Config::conn_stack_reserve`]).
|
||||
pub const DEFAULT_CONN_STACK_RESERVE: usize = 256 * 1024;
|
||||
|
||||
impl Config {
|
||||
pub fn new(addr: SocketAddr) -> Self {
|
||||
let pool = std::thread::available_parallelism()
|
||||
@@ -78,6 +89,7 @@ impl Config {
|
||||
max_frame_payload: 1024 * 1024,
|
||||
max_message_bytes: 4 * 1024 * 1024,
|
||||
scheduler_threads: None,
|
||||
conn_stack_reserve: DEFAULT_CONN_STACK_RESERVE,
|
||||
}
|
||||
}
|
||||
|
||||
@@ -125,6 +137,7 @@ fn listener_loop(
|
||||
listener: Arc<OwnedFd>,
|
||||
pipeline: Pipeline,
|
||||
limits: ConnLimits,
|
||||
conn_stack_reserve: usize,
|
||||
registry: GenServerRef<ConnRegistry>,
|
||||
shutdown: Arc<AtomicBool>,
|
||||
) {
|
||||
@@ -157,7 +170,11 @@ fn listener_loop(
|
||||
let p = pipeline.clone();
|
||||
let l = limits;
|
||||
let r = registry.clone();
|
||||
smarm::spawn(move || run_connection(client, p, l, r));
|
||||
let opts = smarm::SpawnOpts {
|
||||
stack_reserve: Some(conn_stack_reserve),
|
||||
..smarm::SpawnOpts::default()
|
||||
};
|
||||
smarm::spawn_with(opts, move || run_connection(client, p, l, r));
|
||||
}
|
||||
Err(e) if e.kind() == ErrorKind::WouldBlock => {
|
||||
// No pending connection. Park until the listener is
|
||||
@@ -305,8 +322,9 @@ pub fn serve_with_shutdown(
|
||||
listener_fds.push(Arc::new(dup));
|
||||
}
|
||||
|
||||
let limits = config.to_conn_limits();
|
||||
let drain_timeout = config.drain_timeout;
|
||||
let limits = config.to_conn_limits();
|
||||
let conn_stack_reserve = config.conn_stack_reserve;
|
||||
let drain_timeout = config.drain_timeout;
|
||||
|
||||
let smarm_cfg = match config.scheduler_threads {
|
||||
Some(n) => smarm::Config::exact(n),
|
||||
@@ -327,7 +345,7 @@ pub fn serve_with_shutdown(
|
||||
let sf = shutdown_flag.clone();
|
||||
sup = sup.child(ChildSpec::new(Restart::Transient, move || {
|
||||
println!("urus: listener {} starting", i);
|
||||
listener_loop(lfd.clone(), p.clone(), limits, r.clone(), sf.clone());
|
||||
listener_loop(lfd.clone(), p.clone(), limits, conn_stack_reserve, r.clone(), sf.clone());
|
||||
}));
|
||||
}
|
||||
// Default intensity (3 per 5s) applies; a listener crash-looping
|
||||
|
||||
Reference in New Issue
Block a user