This is an automated email from the ASF dual-hosted git repository.
spetz pushed a commit to branch torn_wal_on_kernel_version
in repository https://gitbox.apache.org/repos/asf/iggy.git
The following commit(s) were added to refs/heads/torn_wal_on_kernel_version by
this push:
new c86dcc0a8 fix
c86dcc0a8 is described below
commit c86dcc0a8af88ee838609c76279aed55f4e770cf
Author: spetz <[email protected]>
AuthorDate: Tue Sep 1 07:43:40 2026 +0200
fix
---
core/journal/src/file_storage.rs | 18 +++++------
core/message_bus/src/client_listener/mod.rs | 5 +++
core/server_common/src/diagnostics.rs | 49 ++++++++++++++++++++---------
helm/charts/iggy/README.md | 15 +++++----
helm/charts/iggy/README.md.gotmpl | 15 +++++----
5 files changed, 67 insertions(+), 35 deletions(-)
diff --git a/core/journal/src/file_storage.rs b/core/journal/src/file_storage.rs
index 4db386fec..7153548bc 100644
--- a/core/journal/src/file_storage.rs
+++ b/core/journal/src/file_storage.rs
@@ -61,12 +61,12 @@ impl FileStorage {
/// Truncate the file to `len` bytes and make the new length durable.
///
/// Synchronous `std::fs` on a separate descriptor, not compio: compio's
- /// `set_len` submits `IORING_OP_FTRUNCATE`, which landed in kernel 6.9.
- /// Below that the driver falls back to its blocking pool, and shard
- /// proactors run with `thread_pool_limit(0)`, so the fallback panics the
- /// shard instead of repairing the WAL. `std::fs` needs neither the opcode
- /// nor the pool. The sole caller is boot-time torn-tail repair, so
- /// blocking the shard thread here costs nothing.
+ /// `set_len` submits `IORING_OP_FTRUNCATE`, which landed in mainline Linux
+ /// 6.9. When the opcode is unavailable, the driver falls back to its
+ /// blocking pool, and shard proactors run with `thread_pool_limit(0)`, so
+ /// the fallback panics the shard instead of repairing the WAL. `std::fs`
+ /// needs neither the opcode nor the pool. The sole caller is boot-time
+ /// torn-tail repair, so blocking the shard thread here costs nothing.
///
/// `sync_all` makes the durable-truncation contract explicit and matches
/// segment recovery. Its additional metadata synchronization is acceptable
@@ -197,9 +197,9 @@ mod tests {
/// Torn-tail repair runs on a shard executor, which builds its proactor
/// with `thread_pool_limit(0)`. Any truncate that reaches compio's
/// blocking pool panics that shard rather than repairing the WAL, which
- /// is what every kernel below 6.9 did while `set_len` was an `io_uring`
- /// submission. Driving the repair through a real shard executor is the
- /// only way to keep the no-blocking-pool constraint pinned.
+ /// is what mainline Linux did before 6.9 while `set_len` was an `io_uring`
+ /// submission. Driving the repair through a real shard executor is the
only
+ /// way to keep the no-blocking-pool constraint pinned.
#[test]
fn
given_a_shard_executor_with_no_blocking_pool_when_truncating_should_repair_the_file()
{
let runtime = create_shard_executor().unwrap();
diff --git a/core/message_bus/src/client_listener/mod.rs
b/core/message_bus/src/client_listener/mod.rs
index 1ed966bd2..60d36faec 100644
--- a/core/message_bus/src/client_listener/mod.rs
+++ b/core/message_bus/src/client_listener/mod.rs
@@ -108,6 +108,11 @@ pub mod wss;
/// `TIME_WAIT`); `SO_REUSEPORT` is intentionally not set: only shard 0
/// binds the client listeners (see each caller).
///
+/// On Linux, compio submits this path's bind and listen as
+/// `IORING_OP_BIND` and `IORING_OP_LISTEN`. Mainline Linux added both in
+/// 6.11. Shard 0 has no blocking fallback pool, so an older kernel without
+/// vendor backports panics during listener startup.
+///
/// # Errors
///
/// Returns [`IggyError::CannotBindToSocket`] if the bind/listen fails.
diff --git a/core/server_common/src/diagnostics.rs
b/core/server_common/src/diagnostics.rs
index 2b745d7e4..6d5044e56 100644
--- a/core/server_common/src/diagnostics.rs
+++ b/core/server_common/src/diagnostics.rs
@@ -65,9 +65,11 @@ pub fn enrich_runtime_create_error(error: std::io::Error) ->
std::io::Error {
RUNTIME_CREATE_DIAGNOSTIC.call_once(print_invalid_io_uring_args_info);
format!(
"the kernel rejected io_uring setup flags shard executors
require \
- (IORING_SETUP_COOP_TASKRUN + IORING_SETUP_TASKRUN_FLAG need
Linux \
- >= {MIN_KERNEL_MAJOR}.{MIN_KERNEL_MINOR} with full io_uring
support; \
- WSL2 kernels are often incomplete)"
+ (IORING_SETUP_COOP_TASKRUN + IORING_SETUP_TASKRUN_FLAG
entered \
+ mainline Linux in
{SHARD_SETUP_MIN_KERNEL_MAJOR}.{SHARD_SETUP_MIN_KERNEL_MINOR}, \
+ while current listener startup also needs IORING_OP_BIND and \
+ IORING_OP_LISTEN from
{MAINLINE_MIN_KERNEL_MAJOR}.{MAINLINE_MIN_KERNEL_MINOR}. \
+ WSL2 and vendor kernels may provide a different feature set)"
)
}
_ => return error,
@@ -206,11 +208,18 @@ pub fn print_io_uring_permission_info() {
print_discord_link();
}
-/// Minimum kernel version for IORING_SETUP_COOP_TASKRUN and
IORING_SETUP_TASKRUN_FLAG.
+/// Mainline Linux version providing every io_uring feature Iggy currently
+/// requires during startup, including `IORING_OP_BIND` and `IORING_OP_LISTEN`.
#[cfg(target_os = "linux")]
-const MIN_KERNEL_MAJOR: u32 = 5;
+const MAINLINE_MIN_KERNEL_MAJOR: u32 = 6;
#[cfg(target_os = "linux")]
-const MIN_KERNEL_MINOR: u32 = 19;
+const MAINLINE_MIN_KERNEL_MINOR: u32 = 11;
+
+/// Mainline Linux version that introduced the shard ring setup flags.
+#[cfg(target_os = "linux")]
+const SHARD_SETUP_MIN_KERNEL_MAJOR: u32 = 5;
+#[cfg(target_os = "linux")]
+const SHARD_SETUP_MIN_KERNEL_MINOR: u32 = 19;
/// Minimum kernel version for kernel.io_uring_disabled sysctl.
#[cfg(target_os = "linux")]
@@ -236,7 +245,10 @@ pub fn print_invalid_io_uring_args_info() {
eprintln!(" - IORING_SETUP_COOP_TASKRUN (cooperative task running)");
eprintln!(" - IORING_SETUP_TASKRUN_FLAG (task runner flag
notification)");
eprintln!(
- " These flags require Linux kernel >=
{MIN_KERNEL_MAJOR}.{MIN_KERNEL_MINOR} with full io_uring support."
+ " Mainline Linux added these flags in
{SHARD_SETUP_MIN_KERNEL_MAJOR}.{SHARD_SETUP_MIN_KERNEL_MINOR}."
+ );
+ eprintln!(
+ " Current listener startup also needs IORING_OP_BIND and
IORING_OP_LISTEN from mainline Linux
{MAINLINE_MIN_KERNEL_MAJOR}.{MAINLINE_MIN_KERNEL_MINOR}."
);
eprintln!();
@@ -265,8 +277,11 @@ pub fn print_incomplete_io_uring_ops_info() {
eprintln!(" io_uring setup succeeded (shards started), but at runtime
compio");
eprintln!(" probed the kernel and a required opcode was absent. This is
common");
eprintln!(" on WSL2 and on older or cut-down kernels whose io_uring
support is");
- eprintln!(" incomplete. Some opcodes need a kernel newer than the
shard-setup");
- eprintln!(" floor below.");
+ eprintln!(" incomplete. Some opcodes require a newer kernel than the
ring");
+ eprintln!(" setup flags.");
+ eprintln!();
+ eprintln!(" Current Iggy listener startup submits IORING_OP_BIND and");
+ eprintln!(" IORING_OP_LISTEN through compio. Mainline Linux added both in
6.11.");
eprintln!();
report_io_uring_environment();
@@ -300,9 +315,11 @@ fn report_io_uring_environment() {
if let Some((major, minor)) = parse_kernel_version(&release) {
kernel_version = Some((major, minor));
- if (major, minor) < (MIN_KERNEL_MAJOR, MIN_KERNEL_MINOR) {
+ if (major, minor) < (MAINLINE_MIN_KERNEL_MAJOR,
MAINLINE_MIN_KERNEL_MINOR) {
detected_issues.push(format!(
- "Kernel {major}.{minor} is too old (need >=
{MIN_KERNEL_MAJOR}.{MIN_KERNEL_MINOR})"
+ "Kernel {major}.{minor} predates the mainline Linux \
+ {MAINLINE_MIN_KERNEL_MAJOR}.{MAINLINE_MIN_KERNEL_MINOR}
feature set. \
+ Verify whether the vendor kernel backports the required
io_uring features"
));
}
} else {
@@ -318,8 +335,8 @@ fn report_io_uring_environment() {
if release_is_wsl || proc_version_is_wsl {
eprintln!(" Environment: WSL2 (Microsoft kernel fork detected)");
detected_issues.push(
- "WSL2 kernels often ship incomplete io_uring: missing setup
flags or \
- opcodes even at version >= 5.19"
+ "WSL2 kernels may ship incomplete io_uring support even when
their \
+ reported version is new enough"
.to_string(),
);
}
@@ -386,8 +403,9 @@ fn report_io_uring_environment() {
eprintln!(" To resolve this:");
eprintln!();
eprintln!(
- " 1. Upgrade to Linux kernel >= {MIN_KERNEL_MAJOR}.{MIN_KERNEL_MINOR}
(>=
{SYSCTL_IO_URING_DISABLED_KERNEL_MAJOR}.{SYSCTL_IO_URING_DISABLED_KERNEL_MINOR}
recommended)"
+ " 1. Use mainline Linux >=
{MAINLINE_MIN_KERNEL_MAJOR}.{MAINLINE_MIN_KERNEL_MINOR} or a vendor kernel with
the required io_uring features"
);
+ eprintln!(" Required listener opcodes: IORING_OP_BIND and
IORING_OP_LISTEN");
eprintln!();
eprintln!(" 2. If running under WSL2:");
eprintln!(" - Update WSL: wsl --update (from PowerShell)");
@@ -457,6 +475,9 @@ mod tests {
let raw = std::io::Error::new(std::io::ErrorKind::InvalidInput,
"EINVAL");
let message = enrich_runtime_create_error(raw).to_string();
assert!(message.contains("IORING_SETUP_COOP_TASKRUN"), "{message}");
+ assert!(message.contains("5.19"), "{message}");
+ assert!(message.contains("IORING_OP_BIND"), "{message}");
+ assert!(message.contains("6.11"), "{message}");
}
#[test]
diff --git a/helm/charts/iggy/README.md b/helm/charts/iggy/README.md
index 38885079e..72a91eb33 100644
--- a/helm/charts/iggy/README.md
+++ b/helm/charts/iggy/README.md
@@ -15,14 +15,17 @@ A Helm chart for Apache Iggy server and web-ui
Iggy server uses `io_uring` for high-performance async I/O. This requires:
-1. **Required io_uring setup features** - The node must provide both flags:
+1. **Linux io_uring support on the node**
- * `IORING_SETUP_COOP_TASKRUN`
- * `IORING_SETUP_TASKRUN_FLAG`
+ * Mainline Linux 6.11 or newer provides all io_uring features Iggy
currently needs during startup.
+ * Shard rings require `IORING_SETUP_COOP_TASKRUN` and
`IORING_SETUP_TASKRUN_FLAG` from Linux 5.19.
+ * Listener startup uses `IORING_OP_SOCKET`, `IORING_OP_BIND`, and
`IORING_OP_LISTEN`.
+ * Mainline Linux added bind and listen in 6.11. Vendor kernels may backport
them to an older release.
+ * If an opcode is missing, compio uses a blocking fallback that Iggy
disables on shard threads.
+ * The server then fails during startup. The node kernel matters, not the
container image.
+ * Ubuntu 24.04 GA uses Linux 6.8 and lacks the mainline bind and listen
opcodes.
+ * On Ubuntu 24.04 GA, install `linux-generic-hwe-24.04` before running Iggy.
- Mainline Linux provides both starting in 5.19. Vendor kernels may backport
them to older kernel versions.
-
- The server fails during startup if either is unavailable. Node capabilities
matter, not the container image.
2. **IPC_LOCK capability** - For locking memory required by io_uring
3. **Unconfined seccomp profile** - To allow io_uring syscalls
diff --git a/helm/charts/iggy/README.md.gotmpl
b/helm/charts/iggy/README.md.gotmpl
index edf39d941..e7b4e42d8 100644
--- a/helm/charts/iggy/README.md.gotmpl
+++ b/helm/charts/iggy/README.md.gotmpl
@@ -33,14 +33,17 @@ under the License.
Iggy server uses `io_uring` for high-performance async I/O. This requires:
-1. **Required io_uring setup features** - The node must provide both flags:
+1. **Linux io_uring support on the node**
- * `IORING_SETUP_COOP_TASKRUN`
- * `IORING_SETUP_TASKRUN_FLAG`
+ * Mainline Linux 6.11 or newer provides all io_uring features Iggy
currently needs during startup.
+ * Shard rings require `IORING_SETUP_COOP_TASKRUN` and
`IORING_SETUP_TASKRUN_FLAG` from Linux 5.19.
+ * Listener startup uses `IORING_OP_SOCKET`, `IORING_OP_BIND`, and
`IORING_OP_LISTEN`.
+ * Mainline Linux added bind and listen in 6.11. Vendor kernels may backport
them to an older release.
+ * If an opcode is missing, compio uses a blocking fallback that Iggy
disables on shard threads.
+ * The server then fails during startup. The node kernel matters, not the
container image.
+ * Ubuntu 24.04 GA uses Linux 6.8 and lacks the mainline bind and listen
opcodes.
+ * On Ubuntu 24.04 GA, install `linux-generic-hwe-24.04` before running Iggy.
- Mainline Linux provides both starting in 5.19. Vendor kernels may backport
them to older kernel versions.
-
- The server fails during startup if either is unavailable. Node capabilities
matter, not the container image.
2. **IPC_LOCK capability** - For locking memory required by io_uring
3. **Unconfined seccomp profile** - To allow io_uring syscalls