Skip to content

virtiofs: negotiate FUSE_MAX_PAGES for larger I/O requests#3582

Open
benhillis wants to merge 1 commit into
microsoft:mainfrom
benhillis:reapply-fuse-max-pages
Open

virtiofs: negotiate FUSE_MAX_PAGES for larger I/O requests#3582
benhillis wants to merge 1 commit into
microsoft:mainfrom
benhillis:reapply-fuse-max-pages

Conversation

@benhillis
Copy link
Copy Markdown
Member

Reapplies #3447, which was reverted in #3467.

The original revert was motivated by ERROR_NOT_ENOUGH_QUOTA stalls in the wsldevicehost HDV path: the 8x larger FUSE requests amplified per-access aperture churn against a 512-handle VID PPM table while the HDV aperture cache was disabled (DISABLE_CACHE = true).

This is safe to reapply because all of the per-request guest memory accesses get bounced through the same memory range / aperture, so the larger requests do not multiply the number of distinct aperture handles in flight.

Original benefit

Without FUSE_MAX_PAGES the Linux kernel uses FUSE_DEFAULT_MAX_PAGES_PER_REQ (32 pages = 128 KiB) as the maximum request size. With the flag, the kernel uses min(fuse_max_pages_limit, virtqueue_size - 4) which is typically 252 pages (~1008 KiB) — an ~8x increase, significantly reducing per-request overhead for sequential I/O.

See #3447 for full benchmark numbers (sequential read +37–83%, sequential write +59–68%; random I/O unaffected as expected).

Reapply the FUSE_MAX_PAGES negotiation flag previously reverted in microsoft#3467.

The original concern was that increasing the max FUSE request size from
128 KiB (32 pages) to ~1008 KiB (252 pages) caused an 8x increase in
guest memory accesses per request, which combined with the disabled
HDV aperture cache (DISABLE_CACHE = true) and the 512-handle VID PPM
table limit, produced ERROR_NOT_ENOUGH_QUOTA stalls under concurrent
I/O in the wsldevicehost path.

This is safe to reapply because all of the per-request guest memory
accesses get bounced through the same memory range / aperture, so the
larger requests do not multiply the number of distinct aperture
handles in flight.

Without this flag the Linux kernel uses FUSE_DEFAULT_MAX_PAGES_PER_REQ
(32 pages = 128 KiB) as the maximum request size. With the flag, the
kernel uses min(fuse_max_pages_limit, virtqueue_size - 4) which is
typically 252 pages (~1008 KiB) — an ~8x increase, significantly
reducing per-request overhead for sequential I/O.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Copilot AI review requested due to automatic review settings May 28, 2026 15:55
@benhillis benhillis requested a review from a team as a code owner May 28, 2026 15:55
Copy link
Copy Markdown
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR reapplies the virtiofs/FUSE negotiation change that advertises FUSE_MAX_PAGES, allowing Linux guests to issue larger FUSE requests and reduce per-request overhead for sequential I/O.

Changes:

  • Adds FUSE_MAX_PAGES to the default FUSE init flags.
  • Keeps existing max-write/max-pages sizing behavior unchanged.

@github-actions
Copy link
Copy Markdown

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants