public inbox for linux-kernel@vger.kernel.org
 help / color / mirror / Atom feed
* [PATCH v3 0/4] rust: alloc: add Vec shrinking methods
@ 2026-02-07 11:32 Shivam Kalra via B4 Relay
  2026-02-07 11:32 ` [PATCH v3 1/4] rust: alloc: introduce Shrinkable trait Shivam Kalra via B4 Relay
                   ` (4 more replies)
  0 siblings, 5 replies; 24+ messages in thread
From: Shivam Kalra via B4 Relay @ 2026-02-07 11:32 UTC (permalink / raw)
  To: Danilo Krummrich, Lorenzo Stoakes, Vlastimil Babka,
	Liam R. Howlett, Uladzislau Rezki, Miguel Ojeda, Boqun Feng,
	Gary Guo, Björn Roy Baron, Benno Lossin, Andreas Hindborg,
	Alice Ryhl, Trevor Gross, Greg Kroah-Hartman,
	Arve Hjønnevåg, Todd Kjos, Christian Brauner,
	Carlos Llamas
  Cc: rust-for-linux, linux-kernel, Shivam Kalra

This series adds shrink_to() and shrink_to_fit() methods to Vec<T, A>
(and by extension KVVec, KVec, VVec) to allow explicit capacity
reduction for memory reclamation.

Problem:
When elements are removed from a KVVec, the allocated capacity is not
reduced. The underlying C allocators (krealloc/kvrealloc) don't shrink
memory in-place. This can cause significant memory waste in scenarios
with variable workloads.

Solution:
- Patch 1: Introduces the `Shrinkable` marker trait to identify allocators
  that can meaningfully reclaim memory when shrinking (e.g., Vmalloc but
  not Kmalloc, since Kmalloc uses fixed-size buckets).
- Patch 2: Implements shrink_to(min_capacity, flags) and
  shrink_to_fit(flags)  methods. Shrinking only occurs when
  the allocator is shrinkable AND the operation would free at least
  one page of memory.
- Patch 3: Adds KUnit tests for the new methods across different allocator
  backends (Vmalloc and KVmalloc).
- Patch 4: Uses shrink_to() in the Rust binder driver to reclaim memory
  when processes are deregistered. Shrinking is triggered only when the
  vector capacity exceeds 128 elements and less than half is used.

Testing:
- KUnit tests pass (rust_kvec test suite).
- Kernel boots successfully in QEMU with CONFIG_ANDROID_BINDER_IPC_RUST=y.

Changes since v2:
- Introduced new `Shrinkable` marker trait to distinguish allocators that
  benefit from shrinking (Vmalloc) from those that don't (Kmalloc).
- Shrinking now only occurs for vmalloc-backed buffers when at least one
  page can be freed, avoiding unnecessary work for kmalloc buffers.
  (Suggested by Danilo Krummrich)
- Split into 4 patches: Shrinkable trait introduction is now a
  separate patch to improve reviewability.
- Uses explicit alloc+copy+free since vrealloc doesn't yet support
  in-place shrinking; TODO added for future optimization when vrealloc
  gains that capability. (Discussed with Danilo Krummrich)
- Fixed minor KVVec/KVec terminology (binder uses KVVec not KVec).
- Expanded KUnit tests to cover different allocator backends and
  page-boundary shrinking behavior.

Changes since v1:
- Resend with correct threading (no code changes).
- Removed base-commit.
- Added explicit lore link to dependency in cover letter.

[1] https://lore.kernel.org/lkml/20260130205424.261700-1-shivamklr@cock.li/
[2] https://lore.kernel.org/lkml/20260131154016.270385-1-shivamklr@cock.li/

Signed-off-by: Shivam Kalra <shivamklr@cock.li>
---
Shivam Kalra (4):
      rust: alloc: introduce Shrinkable trait
      rust: kvec: implement shrink_to and shrink_to_fit for Vec
      rust: alloc: add KUnit tests for Vec shrink operations
      rust: binder: shrink all_procs when deregistering processes

 drivers/android/binder/context.rs |  10 ++
 rust/kernel/alloc/allocator.rs    |  48 +++++++
 rust/kernel/alloc/kvec.rs         | 296 +++++++++++++++++++++++++++++++++++++-
 3 files changed, 352 insertions(+), 2 deletions(-)
---
base-commit: 3c4ae63073d84abee5d81ce46d86a94e9dae9c89
change-id: 20260207-binder-shrink-vec-v3-54045d77b0e7

Best regards,
-- 
Shivam Kalra <shivamklr@cock.li>



^ permalink raw reply	[flat|nested] 24+ messages in thread

* [PATCH v3 1/4] rust: alloc: introduce Shrinkable trait
  2026-02-07 11:32 [PATCH v3 0/4] rust: alloc: add Vec shrinking methods Shivam Kalra via B4 Relay
@ 2026-02-07 11:32 ` Shivam Kalra via B4 Relay
  2026-02-07 11:32 ` [PATCH v3 2/4] rust: kvec: implement shrink_to and shrink_to_fit for Vec Shivam Kalra via B4 Relay
                   ` (3 subsequent siblings)
  4 siblings, 0 replies; 24+ messages in thread
From: Shivam Kalra via B4 Relay @ 2026-02-07 11:32 UTC (permalink / raw)
  To: Danilo Krummrich, Lorenzo Stoakes, Vlastimil Babka,
	Liam R. Howlett, Uladzislau Rezki, Miguel Ojeda, Boqun Feng,
	Gary Guo, Björn Roy Baron, Benno Lossin, Andreas Hindborg,
	Alice Ryhl, Trevor Gross, Greg Kroah-Hartman,
	Arve Hjønnevåg, Todd Kjos, Christian Brauner,
	Carlos Llamas
  Cc: rust-for-linux, linux-kernel, Shivam Kalra

From: Shivam Kalra <shivamklr@cock.li>

Introduce the `Shrinkable` trait to identify allocators that can
meaningfully reclaim memory when an allocation is shrunk.

In the kernel, the slab allocator (`Kmalloc`) uses fixed-size buckets,
meaning a "shrink" operation often results in the same bucket size being
used, yielding no actual memory savings. However, page-based allocators
like `Vmalloc` can reclaim physical pages when the size reduction
crosses a page boundary.

This marker trait allows generic containers (like `KVec` or `KVVec`) to
determine at compile-time or run-time (via `is_shrinkable`) if a
shrinking operation is worth performing.

Signed-off-by: Shivam Kalra <shivamklr@cock.li>
---
 rust/kernel/alloc/allocator.rs | 48 ++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 48 insertions(+)

diff --git a/rust/kernel/alloc/allocator.rs b/rust/kernel/alloc/allocator.rs
index 63bfb91b36712..615799b680b55 100644
--- a/rust/kernel/alloc/allocator.rs
+++ b/rust/kernel/alloc/allocator.rs
@@ -251,6 +251,54 @@ unsafe fn realloc(
     }
 }
 
+/// Marker trait for allocators that support meaningful shrinking.
+///
+/// Shrinking is only meaningful for allocators that can actually reclaim memory. The slab
+/// allocator (`Kmalloc`) uses fixed-size buckets and cannot reclaim memory when shrinking,
+/// so it does not implement this trait.
+///
+/// For `Vmalloc`, shrinking always makes sense since it uses page-granularity allocations.
+/// For `KVmalloc`, shrinking only makes sense if the allocation is backed by vmalloc (checked
+/// at runtime via `is_vmalloc_addr`).
+///
+/// # Note
+///
+/// Currently, shrinking vmalloc allocations requires explicit alloc+copy+free because
+/// `vrealloc` does not support in-place shrinking (see TODO at `mm/vmalloc.c:4316`).
+/// Once `vrealloc` gains this capability, the shrink implementation can be simplified.
+///
+/// # Safety
+///
+/// Implementors must ensure that [`Shrinkable::is_shrinkable`] returns `true` only when
+/// shrinking the allocation would actually reclaim memory.
+pub unsafe trait Shrinkable: Allocator {
+    /// Returns whether shrinking an allocation at the given pointer would reclaim memory.
+    ///
+    /// # Safety
+    ///
+    /// `ptr` must be a valid pointer to an allocation made by this allocator.
+    unsafe fn is_shrinkable(ptr: NonNull<u8>) -> bool;
+}
+
+// SAFETY: `Vmalloc` always uses vmalloc, which allocates at page granularity. Shrinking a
+// vmalloc allocation by at least one page will reclaim that memory.
+unsafe impl Shrinkable for Vmalloc {
+    #[inline]
+    unsafe fn is_shrinkable(_ptr: NonNull<u8>) -> bool {
+        true
+    }
+}
+
+// SAFETY: `KVmalloc` may use either kmalloc or vmalloc. We check at runtime using
+// `is_vmalloc_addr` to determine if shrinking would be meaningful.
+unsafe impl Shrinkable for KVmalloc {
+    #[inline]
+    unsafe fn is_shrinkable(ptr: NonNull<u8>) -> bool {
+        // SAFETY: `ptr` is a valid pointer by the safety requirements of this function.
+        unsafe { bindings::is_vmalloc_addr(ptr.as_ptr().cast()) }
+    }
+}
+
 #[macros::kunit_tests(rust_allocator)]
 mod tests {
     use super::*;

-- 
2.43.0



^ permalink raw reply related	[flat|nested] 24+ messages in thread

* [PATCH v3 2/4] rust: kvec: implement shrink_to and shrink_to_fit for Vec
  2026-02-07 11:32 [PATCH v3 0/4] rust: alloc: add Vec shrinking methods Shivam Kalra via B4 Relay
  2026-02-07 11:32 ` [PATCH v3 1/4] rust: alloc: introduce Shrinkable trait Shivam Kalra via B4 Relay
@ 2026-02-07 11:32 ` Shivam Kalra via B4 Relay
  2026-02-07 17:23   ` Danilo Krummrich
  2026-02-07 11:32 ` [PATCH v3 3/4] rust: alloc: add KUnit tests for Vec shrink operations Shivam Kalra via B4 Relay
                   ` (2 subsequent siblings)
  4 siblings, 1 reply; 24+ messages in thread
From: Shivam Kalra via B4 Relay @ 2026-02-07 11:32 UTC (permalink / raw)
  To: Danilo Krummrich, Lorenzo Stoakes, Vlastimil Babka,
	Liam R. Howlett, Uladzislau Rezki, Miguel Ojeda, Boqun Feng,
	Gary Guo, Björn Roy Baron, Benno Lossin, Andreas Hindborg,
	Alice Ryhl, Trevor Gross, Greg Kroah-Hartman,
	Arve Hjønnevåg, Todd Kjos, Christian Brauner,
	Carlos Llamas
  Cc: rust-for-linux, linux-kernel, Shivam Kalra

From: Shivam Kalra <shivamklr@cock.li>

Implement `shrink_to` and `shrink_to_fit` methods for `Vec<T, A>` where
`A` implements the `Shrinkable` trait.

`shrink_to` reduces the vector's capacity to a specified minimum, while
`shrink_to_fit` attempts to shrink capacity to match the current length.

Both methods only perform shrinking when it would be beneficial:
- The allocator must support meaningful shrinking (checked via the
  `Shrinkable` trait bound and `is_shrinkable` runtime check).
- The operation must free at least one page of memory.

This prevents unnecessary allocations (where shrinking provides no
benefit) while allowing to reclaim unused memory.

The implementation uses explicit alloc+copy+free because `vrealloc`
does not yet support in-place shrinking. A TODO note marks this for
future optimization once the kernel's `vrealloc` gains that capability.

Suggested-by: Alice Ryhl <aliceryhl@google.com>
Suggested-by: Danilo Krummrich <dakr@kernel.org>
Signed-off-by: Shivam Kalra <shivamklr@cock.li>
---
 rust/kernel/alloc/kvec.rs | 111 +++++++++++++++++++++++++++++++++++++++++++++-
 1 file changed, 109 insertions(+), 2 deletions(-)

diff --git a/rust/kernel/alloc/kvec.rs b/rust/kernel/alloc/kvec.rs
index ac8d6f763ae81..22a327d69c061 100644
--- a/rust/kernel/alloc/kvec.rs
+++ b/rust/kernel/alloc/kvec.rs
@@ -3,13 +3,13 @@
 //! Implementation of [`Vec`].
 
 use super::{
-    allocator::{KVmalloc, Kmalloc, Vmalloc, VmallocPageIter},
+    allocator::{KVmalloc, Kmalloc, Shrinkable, Vmalloc, VmallocPageIter},
     layout::ArrayLayout,
     AllocError, Allocator, Box, Flags, NumaNode,
 };
 use crate::{
     fmt,
-    page::AsPageIter, //
+    page::{AsPageIter, PAGE_SIZE},
 };
 use core::{
     borrow::{Borrow, BorrowMut},
@@ -735,6 +735,113 @@ pub fn retain(&mut self, mut f: impl FnMut(&mut T) -> bool) {
     }
 }
 
+impl<T, A: Shrinkable> Vec<T, A> {
+    /// Shrinks the capacity of the vector with a lower bound.
+    ///
+    /// The capacity will remain at least as large as both the length and the supplied value.
+    /// If the current capacity is less than the lower limit, this is a no-op.
+    ///
+    /// Shrinking only occurs if:
+    /// - The allocator supports shrinking for this allocation (see [`Shrinkable`]).
+    /// - The operation would free at least one page of memory.
+    ///
+    /// If these conditions are not met, the vector is left unchanged.
+    ///
+    /// # Examples
+    ///
+    /// ```
+    /// use kernel::alloc::allocator::Vmalloc;
+    ///
+    /// // Allocate enough capacity to span multiple pages.
+    /// let elements_per_page = kernel::page::PAGE_SIZE / core::mem::size_of::<u32>();
+    /// let mut v: Vec<u32, Vmalloc> = Vec::with_capacity(elements_per_page * 4, GFP_KERNEL)?;
+    /// v.push(1, GFP_KERNEL)?;
+    /// v.push(2, GFP_KERNEL)?;
+    ///
+    /// v.shrink_to(0, GFP_KERNEL)?;
+    /// # Ok::<(), Error>(())
+    /// ```
+    pub fn shrink_to(&mut self, min_capacity: usize, flags: Flags) -> Result<(), AllocError> {
+        let target_cap = core::cmp::max(self.len(), min_capacity);
+
+        if self.capacity() <= target_cap {
+            return Ok(());
+        }
+
+        if Self::is_zst() {
+            return Ok(());
+        }
+
+        // SAFETY: `self.ptr` is valid by the type invariant.
+        if !unsafe { A::is_shrinkable(self.ptr.cast()) } {
+            return Ok(());
+        }
+
+        // Only shrink if we would free at least one page.
+        let current_size = self.capacity() * core::mem::size_of::<T>();
+        let target_size = target_cap * core::mem::size_of::<T>();
+        let current_pages = current_size.div_ceil(PAGE_SIZE);
+        let target_pages = target_size.div_ceil(PAGE_SIZE);
+
+        if current_pages <= target_pages {
+            return Ok(());
+        }
+
+        if target_cap == 0 {
+            if !self.layout.is_empty() {
+                // SAFETY: `self.ptr` was allocated with `A`, layout matches.
+                unsafe { A::free(self.ptr.cast(), self.layout.into()) };
+            }
+            self.ptr = NonNull::dangling();
+            self.layout = ArrayLayout::empty();
+            return Ok(());
+        }
+
+        // SAFETY: `target_cap <= self.capacity()` and original capacity was valid.
+        let new_layout = unsafe { ArrayLayout::<T>::new_unchecked(target_cap) };
+
+        // TODO: Once vrealloc supports in-place shrinking (mm/vmalloc.c:4316), this
+        // explicit alloc+copy+free can potentially be replaced with realloc.
+        let new_ptr = A::alloc(new_layout.into(), flags, NumaNode::NO_NODE)?;
+
+        // SAFETY: Both pointers are valid, non-overlapping, and properly aligned.
+        unsafe {
+            ptr::copy_nonoverlapping(self.as_ptr(), new_ptr.as_ptr().cast::<T>(), self.len);
+        }
+
+        // SAFETY: `self.ptr` was allocated with `A`, layout matches.
+        unsafe { A::free(self.ptr.cast(), self.layout.into()) };
+
+        // SAFETY: `new_ptr` is non-null because `A::alloc` succeeded.
+        self.ptr = unsafe { NonNull::new_unchecked(new_ptr.as_ptr().cast::<T>()) };
+        self.layout = new_layout;
+
+        Ok(())
+    }
+
+    /// Shrinks the capacity of the vector as much as possible.
+    ///
+    /// This is equivalent to calling `shrink_to(0, flags)`. See [`Vec::shrink_to`] for details.
+    ///
+    /// # Examples
+    ///
+    /// ```
+    /// use kernel::alloc::allocator::Vmalloc;
+    ///
+    /// let elements_per_page = kernel::page::PAGE_SIZE / core::mem::size_of::<u32>();
+    /// let mut v: Vec<u32, Vmalloc> = Vec::with_capacity(elements_per_page * 4, GFP_KERNEL)?;
+    /// v.push(1, GFP_KERNEL)?;
+    /// v.push(2, GFP_KERNEL)?;
+    /// v.push(3, GFP_KERNEL)?;
+    ///
+    /// v.shrink_to_fit(GFP_KERNEL)?;
+    /// # Ok::<(), Error>(())
+    /// ```
+    pub fn shrink_to_fit(&mut self, flags: Flags) -> Result<(), AllocError> {
+        self.shrink_to(0, flags)
+    }
+}
+
 impl<T: Clone, A: Allocator> Vec<T, A> {
     /// Extend the vector by `n` clones of `value`.
     pub fn extend_with(&mut self, n: usize, value: T, flags: Flags) -> Result<(), AllocError> {

-- 
2.43.0



^ permalink raw reply related	[flat|nested] 24+ messages in thread

* [PATCH v3 3/4] rust: alloc: add KUnit tests for Vec shrink operations
  2026-02-07 11:32 [PATCH v3 0/4] rust: alloc: add Vec shrinking methods Shivam Kalra via B4 Relay
  2026-02-07 11:32 ` [PATCH v3 1/4] rust: alloc: introduce Shrinkable trait Shivam Kalra via B4 Relay
  2026-02-07 11:32 ` [PATCH v3 2/4] rust: kvec: implement shrink_to and shrink_to_fit for Vec Shivam Kalra via B4 Relay
@ 2026-02-07 11:32 ` Shivam Kalra via B4 Relay
  2026-02-07 11:32 ` [PATCH v3 4/4] rust: binder: shrink all_procs when deregistering processes Shivam Kalra via B4 Relay
  2026-02-10 13:38 ` [PATCH v3 0/4] rust: alloc: add Vec shrinking methods Shivam Kalra
  4 siblings, 0 replies; 24+ messages in thread
From: Shivam Kalra via B4 Relay @ 2026-02-07 11:32 UTC (permalink / raw)
  To: Danilo Krummrich, Lorenzo Stoakes, Vlastimil Babka,
	Liam R. Howlett, Uladzislau Rezki, Miguel Ojeda, Boqun Feng,
	Gary Guo, Björn Roy Baron, Benno Lossin, Andreas Hindborg,
	Alice Ryhl, Trevor Gross, Greg Kroah-Hartman,
	Arve Hjønnevåg, Todd Kjos, Christian Brauner,
	Carlos Llamas
  Cc: rust-for-linux, linux-kernel, Shivam Kalra

From: Shivam Kalra <shivamklr@cock.li>

Add comprehensive KUnit tests for `shrink_to` and `shrink_to_fit` methods
across different allocator backends (Vmalloc and KVmalloc).

The tests verify:
- Basic shrinking from multiple pages to less than one page
- Data integrity preservation after shrinking
- No-op behavior when shrinking would not free pages
- Empty vector shrinking
- Partial shrinking with min_capacity constraints
- Consecutive shrink operations
- KVVec shrinking behavior for both small (kmalloc-backed) and large
  (vmalloc-backed) allocations

These tests ensure that the shrinking logic correctly identifies when
memory can be reclaimed and that the `Shrinkable` trait implementation
works as expected.

Signed-off-by: Shivam Kalra <shivamklr@cock.li>
---
 rust/kernel/alloc/kvec.rs | 185 ++++++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 185 insertions(+)

diff --git a/rust/kernel/alloc/kvec.rs b/rust/kernel/alloc/kvec.rs
index 22a327d69c06..e7d4ba11c2b0 100644
--- a/rust/kernel/alloc/kvec.rs
+++ b/rust/kernel/alloc/kvec.rs
@@ -1505,4 +1505,189 @@ fn add(value: &mut [bool]) {
             func.push_within_capacity(false).unwrap();
         }
     }
+
+    /// Test basic shrink_to functionality for VVec.
+    ///
+    /// Verifies that:
+    /// - Shrinking from multiple pages to less than one page works correctly.
+    /// - Data integrity is preserved after shrinking.
+    /// - Shrinking an already-optimal vector is a no-op.
+    /// - Requesting a min_capacity larger than current capacity is a no-op.
+    #[test]
+    fn test_shrink_to_vmalloc() {
+        use crate::page::PAGE_SIZE;
+
+        let elements_per_page = PAGE_SIZE / core::mem::size_of::<u32>();
+        let initial_pages = 4;
+        let initial_capacity = elements_per_page * initial_pages;
+
+        let mut v: VVec<u32> = VVec::with_capacity(initial_capacity, GFP_KERNEL).unwrap();
+
+        for i in 0..10 {
+            v.push(i, GFP_KERNEL).unwrap();
+        }
+
+        assert!(v.capacity() >= initial_capacity);
+        assert_eq!(v.len(), 10);
+
+        // Shrink from 4 pages to less than 1 page.
+        v.shrink_to(0, GFP_KERNEL).unwrap();
+
+        // Verify data integrity.
+        assert_eq!(v.len(), 10);
+        for i in 0..10 {
+            assert_eq!(v[i], i as u32);
+        }
+
+        assert!(v.capacity() >= 10);
+        assert!(v.capacity() < initial_capacity);
+
+        // Already optimal: should be a no-op.
+        let cap_after_shrink = v.capacity();
+        v.shrink_to(0, GFP_KERNEL).unwrap();
+        assert_eq!(v.capacity(), cap_after_shrink);
+
+        // min_capacity > capacity: should be a no-op (never grows).
+        v.shrink_to(initial_capacity * 2, GFP_KERNEL).unwrap();
+        assert_eq!(v.capacity(), cap_after_shrink);
+    }
+
+    /// Test that shrink_to is a no-op when no pages would be freed.
+    ///
+    /// Verifies that:
+    /// - When current and target capacity both fit in one page, no shrink occurs.
+    /// - The shrink_to_fit wrapper behaves identically to shrink_to(0).
+    #[test]
+    fn test_shrink_to_vmalloc_no_page_savings() {
+        use crate::page::PAGE_SIZE;
+
+        let elements_per_page = PAGE_SIZE / core::mem::size_of::<u32>();
+
+        let mut v: VVec<u32> = VVec::with_capacity(elements_per_page, GFP_KERNEL).unwrap();
+
+        for i in 0..(elements_per_page / 2) {
+            v.push(i as u32, GFP_KERNEL).unwrap();
+        }
+
+        let cap_before = v.capacity();
+
+        // No page savings: capacity unchanged.
+        v.shrink_to(0, GFP_KERNEL).unwrap();
+        assert_eq!(v.capacity(), cap_before);
+
+        // shrink_to_fit wrapper: same behavior.
+        v.shrink_to_fit(GFP_KERNEL).unwrap();
+        assert_eq!(v.capacity(), cap_before);
+    }
+
+    /// Test shrink_to on an empty VVec.
+    ///
+    /// Verifies that shrinking an empty vector to capacity 0 frees the allocation.
+    #[test]
+    fn test_shrink_to_vmalloc_empty() {
+        use crate::page::PAGE_SIZE;
+
+        let elements_per_page = PAGE_SIZE / core::mem::size_of::<u32>();
+        let initial_capacity = elements_per_page * 2;
+
+        let mut v: VVec<u32> = VVec::with_capacity(initial_capacity, GFP_KERNEL).unwrap();
+        assert!(v.capacity() >= initial_capacity);
+
+        // Shrink empty vector: frees allocation.
+        v.shrink_to(0, GFP_KERNEL).unwrap();
+        assert_eq!(v.capacity(), 0);
+        assert_eq!(v.len(), 0);
+    }
+
+    /// Test partial shrink and consecutive shrink operations.
+    ///
+    /// Verifies that:
+    /// - Shrinking with min_capacity > len but still saving pages works.
+    /// - Consecutive shrink calls maintain data integrity.
+    #[test]
+    fn test_shrink_to_vmalloc_partial_and_consecutive() {
+        use crate::page::PAGE_SIZE;
+
+        let elements_per_page = PAGE_SIZE / core::mem::size_of::<u32>();
+
+        let mut v: VVec<u32> = VVec::with_capacity(elements_per_page * 4, GFP_KERNEL).unwrap();
+
+        // Fill with ~2.5 pages worth of elements.
+        let target_elements = elements_per_page * 2 + elements_per_page / 2;
+        for i in 0..target_elements {
+            v.push(i as u32, GFP_KERNEL).unwrap();
+        }
+
+        // Partial shrink: 4 pages -> 3 pages (min_capacity > len).
+        let min_cap_3_pages = elements_per_page * 3;
+        v.shrink_to(min_cap_3_pages, GFP_KERNEL).unwrap();
+        assert!(v.capacity() >= min_cap_3_pages);
+        assert!(v.capacity() < elements_per_page * 4);
+        assert_eq!(v.len(), target_elements);
+
+        for i in 0..target_elements {
+            assert_eq!(v[i], i as u32);
+        }
+
+        // Consecutive shrink: verify layout remains consistent.
+        let cap_before = v.capacity();
+        v.shrink_to(0, GFP_KERNEL).unwrap();
+        assert!(v.capacity() >= target_elements);
+        assert!(v.capacity() <= cap_before);
+
+        for i in 0..target_elements {
+            assert_eq!(v[i], i as u32);
+        }
+    }
+
+    /// Test KVVec shrink with small allocation (kmalloc-backed).
+    ///
+    /// KVmalloc uses kmalloc for small allocations. Since kmalloc cannot reclaim
+    /// memory when shrinking, shrink_to should be a no-op for small KVVec.
+    #[test]
+    fn test_shrink_to_kvvec_small() {
+        // Small allocation: likely kmalloc-backed, shrink should be no-op.
+        let mut v: KVVec<u32> = KVVec::with_capacity(10, GFP_KERNEL).unwrap();
+        for i in 0..5 {
+            v.push(i, GFP_KERNEL).unwrap();
+        }
+
+        let cap_before = v.capacity();
+        v.shrink_to(0, GFP_KERNEL).unwrap();
+
+        // Kmalloc-backed: capacity unchanged (is_shrinkable returns false).
+        assert_eq!(v.capacity(), cap_before);
+        assert_eq!(v.len(), 5);
+    }
+
+    /// Test KVVec shrink with large allocation (vmalloc-backed).
+    ///
+    /// KVmalloc falls back to vmalloc for large allocations. When vmalloc-backed
+    /// and page savings are possible, shrink_to should actually shrink.
+    #[test]
+    fn test_shrink_to_kvvec_large() {
+        use crate::page::PAGE_SIZE;
+
+        let elements_per_page = PAGE_SIZE / core::mem::size_of::<u32>();
+        let initial_capacity = elements_per_page * 4;
+
+        // Large allocation: likely vmalloc-backed.
+        let mut v: KVVec<u32> = KVVec::with_capacity(initial_capacity, GFP_KERNEL).unwrap();
+        for i in 0..10 {
+            v.push(i, GFP_KERNEL).unwrap();
+        }
+
+        assert!(v.capacity() >= initial_capacity);
+
+        // Shrink from 4 pages to <1 page.
+        v.shrink_to(0, GFP_KERNEL).unwrap();
+
+        // Vmalloc-backed with page savings: should shrink.
+        // Note: If allocation happened to use kmalloc, capacity won't change.
+        // This test verifies the path works; actual behavior depends on allocator.
+        assert_eq!(v.len(), 10);
+        for i in 0..10 {
+            assert_eq!(v[i], i as u32);
+        }
+    }
 }

-- 
2.43.0



^ permalink raw reply related	[flat|nested] 24+ messages in thread

* [PATCH v3 4/4] rust: binder: shrink all_procs when deregistering processes
  2026-02-07 11:32 [PATCH v3 0/4] rust: alloc: add Vec shrinking methods Shivam Kalra via B4 Relay
                   ` (2 preceding siblings ...)
  2026-02-07 11:32 ` [PATCH v3 3/4] rust: alloc: add KUnit tests for Vec shrink operations Shivam Kalra via B4 Relay
@ 2026-02-07 11:32 ` Shivam Kalra via B4 Relay
  2026-02-09 13:54   ` Alice Ryhl
  2026-02-10 13:38 ` [PATCH v3 0/4] rust: alloc: add Vec shrinking methods Shivam Kalra
  4 siblings, 1 reply; 24+ messages in thread
From: Shivam Kalra via B4 Relay @ 2026-02-07 11:32 UTC (permalink / raw)
  To: Danilo Krummrich, Lorenzo Stoakes, Vlastimil Babka,
	Liam R. Howlett, Uladzislau Rezki, Miguel Ojeda, Boqun Feng,
	Gary Guo, Björn Roy Baron, Benno Lossin, Andreas Hindborg,
	Alice Ryhl, Trevor Gross, Greg Kroah-Hartman,
	Arve Hjønnevåg, Todd Kjos, Christian Brauner,
	Carlos Llamas
  Cc: rust-for-linux, linux-kernel, Shivam Kalra

From: Shivam Kalra <shivamklr@cock.li>

When a process is deregistered from the binder context, the all_procs
vector may have significant unused capacity. Add logic to shrink the
vector when capacity exceeds 128 and usage drops below 50%, reducing
memory overhead for long-running systems.

The shrink operation uses GFP_KERNEL and is allowed to fail gracefully
since it is purely an optimization. The vector remains valid and
functional even if shrinking fails.

Signed-off-by: Shivam Kalra <shivamklr@cock.li>
---
 drivers/android/binder/context.rs | 10 ++++++++++
 1 file changed, 10 insertions(+)

diff --git a/drivers/android/binder/context.rs b/drivers/android/binder/context.rs
index 9cf437c025a20..f2505fbf17403 100644
--- a/drivers/android/binder/context.rs
+++ b/drivers/android/binder/context.rs
@@ -94,6 +94,16 @@ pub(crate) fn deregister_process(self: &Arc<Self>, proc: &Arc<Process>) {
         }
         let mut manager = self.manager.lock();
         manager.all_procs.retain(|p| !Arc::ptr_eq(p, proc));
+
+        // Shrink the vector if it has significant unused capacity.
+        // Only shrink if capacity > 128 to avoid repeated reallocations for small vectors.
+        let len = manager.all_procs.len();
+        let cap = manager.all_procs.capacity();
+        if cap > 128 && len < cap / 2 {
+            // Shrink to current length. Ignore allocation failures since this is just an
+            // optimization; the vector remains valid even if shrinking fails.
+            let _ = manager.all_procs.shrink_to(len, GFP_KERNEL);
+        }
     }
 
     pub(crate) fn set_manager_node(&self, node_ref: NodeRef) -> Result {

-- 
2.43.0



^ permalink raw reply related	[flat|nested] 24+ messages in thread

* Re: [PATCH v3 2/4] rust: kvec: implement shrink_to and shrink_to_fit for Vec
  2026-02-07 11:32 ` [PATCH v3 2/4] rust: kvec: implement shrink_to and shrink_to_fit for Vec Shivam Kalra via B4 Relay
@ 2026-02-07 17:23   ` Danilo Krummrich
  2026-02-08 16:11     ` Shivam Kalra
  0 siblings, 1 reply; 24+ messages in thread
From: Danilo Krummrich @ 2026-02-07 17:23 UTC (permalink / raw)
  To: Shivam Kalra via B4 Relay
  Cc: shivamklr, Lorenzo Stoakes, Vlastimil Babka, Liam R. Howlett,
	Uladzislau Rezki, Miguel Ojeda, Boqun Feng, Gary Guo,
	Björn Roy Baron, Benno Lossin, Andreas Hindborg, Alice Ryhl,
	Trevor Gross, Greg Kroah-Hartman, Arve Hjønnevåg,
	Todd Kjos, Christian Brauner, Carlos Llamas, rust-for-linux,
	linux-kernel

On Sat Feb 7, 2026 at 12:32 PM CET, Shivam Kalra via B4 Relay wrote:
> +impl<T, A: Shrinkable> Vec<T, A> {

I don't think we should have a Shrinkable trait with is_shrinkable(). This is a
decision taken by the backing Allocator's realloc() function already.

Instead, shrink_to() should be a normal method of Vec<A, T> and just call
A::realloc().

For the temporary workaround we can have a temporary ShrinkQuirk trait that has
methods that take the same arguments as shrink_to().

In Vec::shrink_to() we can then hook in before calling A::realloc() and apply
the quirk.

	fn shrink_to() {
	    if self.shrink_needs_quirk() {
	        return self.shrink_quirk();
	    }

	    // Allocator backend decides.
	    A::realloc();
	}

> +    pub fn shrink_to(&mut self, min_capacity: usize, flags: Flags) -> Result<(), AllocError> {
> +        let target_cap = core::cmp::max(self.len(), min_capacity);
> +
> +        if self.capacity() <= target_cap {
> +            return Ok(());
> +        }
> +
> +        if Self::is_zst() {
> +            return Ok(());
> +        }
> +
> +        // SAFETY: `self.ptr` is valid by the type invariant.
> +        if !unsafe { A::is_shrinkable(self.ptr.cast()) } {
> +            return Ok(());
> +        }
> +
> +        // Only shrink if we would free at least one page.
> +        let current_size = self.capacity() * core::mem::size_of::<T>();
> +        let target_size = target_cap * core::mem::size_of::<T>();
> +        let current_pages = current_size.div_ceil(PAGE_SIZE);
> +        let target_pages = target_size.div_ceil(PAGE_SIZE);

This is the specific heuristic we use for the Vmalloc shrink workaround
(including when for KVmalloc is_vmalloc_addr() is true) and it doesn't belong
into the common code path.

But this goes away anyways with the above changes.

> +        if current_pages <= target_pages {
> +            return Ok(());
> +        }
> +
> +        if target_cap == 0 {
> +            if !self.layout.is_empty() {
> +                // SAFETY: `self.ptr` was allocated with `A`, layout matches.
> +                unsafe { A::free(self.ptr.cast(), self.layout.into()) };
> +            }
> +            self.ptr = NonNull::dangling();
> +            self.layout = ArrayLayout::empty();
> +            return Ok(());
> +        }
> +
> +        // SAFETY: `target_cap <= self.capacity()` and original capacity was valid.
> +        let new_layout = unsafe { ArrayLayout::<T>::new_unchecked(target_cap) };
> +
> +        // TODO: Once vrealloc supports in-place shrinking (mm/vmalloc.c:4316), this
> +        // explicit alloc+copy+free can potentially be replaced with realloc.
> +        let new_ptr = A::alloc(new_layout.into(), flags, NumaNode::NO_NODE)?;
> +
> +        // SAFETY: Both pointers are valid, non-overlapping, and properly aligned.
> +        unsafe {
> +            ptr::copy_nonoverlapping(self.as_ptr(), new_ptr.as_ptr().cast::<T>(), self.len);
> +        }
> +
> +        // SAFETY: `self.ptr` was allocated with `A`, layout matches.
> +        unsafe { A::free(self.ptr.cast(), self.layout.into()) };
> +
> +        // SAFETY: `new_ptr` is non-null because `A::alloc` succeeded.
> +        self.ptr = unsafe { NonNull::new_unchecked(new_ptr.as_ptr().cast::<T>()) };
> +        self.layout = new_layout;
> +
> +        Ok(())
> +    }
> +
> +    /// Shrinks the capacity of the vector as much as possible.
> +    ///
> +    /// This is equivalent to calling `shrink_to(0, flags)`. See [`Vec::shrink_to`] for details.
> +    ///
> +    /// # Examples
> +    ///
> +    /// ```
> +    /// use kernel::alloc::allocator::Vmalloc;
> +    ///
> +    /// let elements_per_page = kernel::page::PAGE_SIZE / core::mem::size_of::<u32>();
> +    /// let mut v: Vec<u32, Vmalloc> = Vec::with_capacity(elements_per_page * 4, GFP_KERNEL)?;

You can just use VVec<u32>.

> +    /// v.push(1, GFP_KERNEL)?;
> +    /// v.push(2, GFP_KERNEL)?;
> +    /// v.push(3, GFP_KERNEL)?;
> +    ///
> +    /// v.shrink_to_fit(GFP_KERNEL)?;
> +    /// # Ok::<(), Error>(())
> +    /// ```
> +    pub fn shrink_to_fit(&mut self, flags: Flags) -> Result<(), AllocError> {
> +        self.shrink_to(0, flags)
> +    }
> +}
> +
>  impl<T: Clone, A: Allocator> Vec<T, A> {
>      /// Extend the vector by `n` clones of `value`.
>      pub fn extend_with(&mut self, n: usize, value: T, flags: Flags) -> Result<(), AllocError> {
>
> -- 
> 2.43.0


^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH v3 2/4] rust: kvec: implement shrink_to and shrink_to_fit for Vec
  2026-02-07 17:23   ` Danilo Krummrich
@ 2026-02-08 16:11     ` Shivam Kalra
  0 siblings, 0 replies; 24+ messages in thread
From: Shivam Kalra @ 2026-02-08 16:11 UTC (permalink / raw)
  To: Danilo Krummrich, Shivam Kalra via B4 Relay
  Cc: Lorenzo Stoakes, Vlastimil Babka, Liam R. Howlett,
	Uladzislau Rezki, Miguel Ojeda, Boqun Feng, Gary Guo,
	Björn Roy Baron, Benno Lossin, Andreas Hindborg, Alice Ryhl,
	Trevor Gross, Greg Kroah-Hartman, Arve Hjønnevåg,
	Todd Kjos, Christian Brauner, Carlos Llamas, rust-for-linux,
	linux-kernel

On 07/02/26 22:53, Danilo Krummrich wrote:
> This is the specific heuristic we use for the Vmalloc shrink workaround
> (including when for KVmalloc is_vmalloc_addr() is true) and it doesn't belong
> into the common code path.
> 
> But this goes away anyways with the above changes.

Thanks for the review, Danilo!
I understand the suggestion to restructure.
I'll rework the patches accordingly and send v4 in a few days
after giving others time to provide feedback on this version.
Best,
Shivam

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH v3 4/4] rust: binder: shrink all_procs when deregistering processes
  2026-02-07 11:32 ` [PATCH v3 4/4] rust: binder: shrink all_procs when deregistering processes Shivam Kalra via B4 Relay
@ 2026-02-09 13:54   ` Alice Ryhl
  2026-02-10 11:47     ` Shivam Kalra
  0 siblings, 1 reply; 24+ messages in thread
From: Alice Ryhl @ 2026-02-09 13:54 UTC (permalink / raw)
  To: shivamklr
  Cc: Danilo Krummrich, Lorenzo Stoakes, Vlastimil Babka,
	Liam R. Howlett, Uladzislau Rezki, Miguel Ojeda, Boqun Feng,
	Gary Guo, Björn Roy Baron, Benno Lossin, Andreas Hindborg,
	Trevor Gross, Greg Kroah-Hartman, Arve Hjønnevåg,
	Todd Kjos, Christian Brauner, Carlos Llamas, rust-for-linux,
	linux-kernel

On Sat, Feb 07, 2026 at 05:02:50PM +0530, Shivam Kalra via B4 Relay wrote:
> [PATCH v3 4/4] rust: binder: shrink all_procs when deregistering

The usual prefix for Rust Binder changes is rust_binder:, not
rust: binder:.

> From: Shivam Kalra <shivamklr@cock.li>
> 
> When a process is deregistered from the binder context, the all_procs
> vector may have significant unused capacity. Add logic to shrink the
> vector when capacity exceeds 128 and usage drops below 50%, reducing
> memory overhead for long-running systems.
> 
> The shrink operation uses GFP_KERNEL and is allowed to fail gracefully
> since it is purely an optimization. The vector remains valid and
> functional even if shrinking fails.
> 
> Signed-off-by: Shivam Kalra <shivamklr@cock.li>
> ---
>  drivers/android/binder/context.rs | 10 ++++++++++
>  1 file changed, 10 insertions(+)
> 
> diff --git a/drivers/android/binder/context.rs b/drivers/android/binder/context.rs
> index 9cf437c025a20..f2505fbf17403 100644
> --- a/drivers/android/binder/context.rs
> +++ b/drivers/android/binder/context.rs
> @@ -94,6 +94,16 @@ pub(crate) fn deregister_process(self: &Arc<Self>, proc: &Arc<Process>) {
>          }
>          let mut manager = self.manager.lock();
>          manager.all_procs.retain(|p| !Arc::ptr_eq(p, proc));
> +
> +        // Shrink the vector if it has significant unused capacity.
> +        // Only shrink if capacity > 128 to avoid repeated reallocations for small vectors.
> +        let len = manager.all_procs.len();
> +        let cap = manager.all_procs.capacity();
> +        if cap > 128 && len < cap / 2 {
> +            // Shrink to current length. Ignore allocation failures since this is just an
> +            // optimization; the vector remains valid even if shrinking fails.
> +            let _ = manager.all_procs.shrink_to(len, GFP_KERNEL);

Hmm. This way we need to reallocate immediately if one more process is
added. How about:

if len < cap / 4 {
    shrink_to(cap / 2);
}

Alice

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH v3 4/4] rust: binder: shrink all_procs when deregistering processes
  2026-02-09 13:54   ` Alice Ryhl
@ 2026-02-10 11:47     ` Shivam Kalra
  0 siblings, 0 replies; 24+ messages in thread
From: Shivam Kalra @ 2026-02-10 11:47 UTC (permalink / raw)
  To: Alice Ryhl
  Cc: Danilo Krummrich, Lorenzo Stoakes, Vlastimil Babka,
	Liam R. Howlett, Uladzislau Rezki, Miguel Ojeda, Boqun Feng,
	Gary Guo, Björn Roy Baron, Benno Lossin, Andreas Hindborg,
	Trevor Gross, Greg Kroah-Hartman, Arve Hjønnevåg,
	Todd Kjos, Christian Brauner, Carlos Llamas, rust-for-linux,
	linux-kernel

On 09/02/26 19:24, Alice Ryhl wrote:
> 
> Hmm. This way we need to reallocate immediately if one more process is
> added. How about:
> 
> if len < cap / 4 {
>     shrink_to(cap / 2);
> }
> 
> Alice
Good point, that avoids the shrink-then-immediately-regrow pattern.
Will adopt this for v4.

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH v3 0/4] rust: alloc: add Vec shrinking methods
  2026-02-07 11:32 [PATCH v3 0/4] rust: alloc: add Vec shrinking methods Shivam Kalra via B4 Relay
                   ` (3 preceding siblings ...)
  2026-02-07 11:32 ` [PATCH v3 4/4] rust: binder: shrink all_procs when deregistering processes Shivam Kalra via B4 Relay
@ 2026-02-10 13:38 ` Shivam Kalra
  2026-02-10 13:57   ` Alice Ryhl
  4 siblings, 1 reply; 24+ messages in thread
From: Shivam Kalra @ 2026-02-10 13:38 UTC (permalink / raw)
  To: Danilo Krummrich, Lorenzo Stoakes, Vlastimil Babka,
	Liam R. Howlett, Uladzislau Rezki, Miguel Ojeda, Boqun Feng,
	Gary Guo, Björn Roy Baron, Benno Lossin, Andreas Hindborg,
	Alice Ryhl, Trevor Gross, Greg Kroah-Hartman,
	Arve Hjønnevåg, Todd Kjos, Christian Brauner,
	Carlos Llamas
  Cc: rust-for-linux, linux-kernel

This is a follow-up to my v3 series:
https://lore.kernel.org/rust-for-linux/20260207-binder-shrink-vec-v3-v3-0-8ff388563427@cock.li/

Hi all,

Thanks for the feedback on v3. Before I respin, I want to confirm
the direction for v4 to avoid unnecessary iterations.

Proposed changes for v4:

1. Drop the Shrinkable trait entirely. Make shrink_to() a normal
   method on Vec<T, A> that calls A::realloc(). (Danilo)

2. Add a temporary ShrinkQuirk trait to handle the vmalloc workaround
   (page-boundary check + manual alloc+copy+free) until vrealloc
   gains in-place shrinking support. (Danilo)

3. In the binder patch, use a less aggressive shrink strategy to
   avoid shrink-then-regrow oscillation: (Alice)
     if len < cap / 4 {
         shrink_to(cap / 2);
     }

4. Fix commit prefix to rust_binder: instead of rust: binder:. (Alice)

Also noting that starting from v4, I will be sending patches from
a new email address: shivamkalra98@gmail.com

Does this look right? Any other concerns before I send v4?

Thanks,
Shivam

Note: I previously sent patches as shivamklr@cock.li. That account
has run out of quota, so I'm continuing from shivamkalra98@gmail.com
going forward. All future patches (v4+) will come from this address.

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH v3 0/4] rust: alloc: add Vec shrinking methods
  2026-02-10 13:38 ` [PATCH v3 0/4] rust: alloc: add Vec shrinking methods Shivam Kalra
@ 2026-02-10 13:57   ` Alice Ryhl
  2026-02-10 15:05     ` Danilo Krummrich
  0 siblings, 1 reply; 24+ messages in thread
From: Alice Ryhl @ 2026-02-10 13:57 UTC (permalink / raw)
  To: Shivam Kalra
  Cc: Danilo Krummrich, Lorenzo Stoakes, Vlastimil Babka,
	Liam R. Howlett, Uladzislau Rezki, Miguel Ojeda, Boqun Feng,
	Gary Guo, Björn Roy Baron, Benno Lossin, Andreas Hindborg,
	Trevor Gross, Greg Kroah-Hartman, Arve Hjønnevåg,
	Todd Kjos, Christian Brauner, Carlos Llamas, rust-for-linux,
	linux-kernel

On Tue, Feb 10, 2026 at 07:08:09PM +0530, Shivam Kalra wrote:
> This is a follow-up to my v3 series:
> https://lore.kernel.org/rust-for-linux/20260207-binder-shrink-vec-v3-v3-0-8ff388563427@cock.li/
> 
> Hi all,
> 
> Thanks for the feedback on v3. Before I respin, I want to confirm
> the direction for v4 to avoid unnecessary iterations.
> 
> Proposed changes for v4:
> 
> 1. Drop the Shrinkable trait entirely. Make shrink_to() a normal
>    method on Vec<T, A> that calls A::realloc(). (Danilo)
> 
> 2. Add a temporary ShrinkQuirk trait to handle the vmalloc workaround
>    (page-boundary check + manual alloc+copy+free) until vrealloc
>    gains in-place shrinking support. (Danilo)

I don't think you want any new traits at all. What types would even
implement the trait? The special code can go in the realloc() method of
Vmalloc struct in rust/kernel/alloc/allocator.rs.

> 3. In the binder patch, use a less aggressive shrink strategy to
>    avoid shrink-then-regrow oscillation: (Alice)
>      if len < cap / 4 {
>          shrink_to(cap / 2);
>      }
> 
> 4. Fix commit prefix to rust_binder: instead of rust: binder:. (Alice)
> 
> Also noting that starting from v4, I will be sending patches from
> a new email address: shivamkalra98@gmail.com
> 
> Does this look right? Any other concerns before I send v4?
> 
> Thanks,
> Shivam
> 
> Note: I previously sent patches as shivamklr@cock.li. That account
> has run out of quota, so I'm continuing from shivamkalra98@gmail.com
> going forward. All future patches (v4+) will come from this address.

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH v3 0/4] rust: alloc: add Vec shrinking methods
  2026-02-10 13:57   ` Alice Ryhl
@ 2026-02-10 15:05     ` Danilo Krummrich
  2026-02-10 17:42       ` Shivam Kalra
  2026-02-10 20:05       ` Alice Ryhl
  0 siblings, 2 replies; 24+ messages in thread
From: Danilo Krummrich @ 2026-02-10 15:05 UTC (permalink / raw)
  To: Alice Ryhl
  Cc: Shivam Kalra, Lorenzo Stoakes, Vlastimil Babka, Liam R. Howlett,
	Uladzislau Rezki, Miguel Ojeda, Boqun Feng, Gary Guo,
	Björn Roy Baron, Benno Lossin, Andreas Hindborg,
	Trevor Gross, Greg Kroah-Hartman, Arve Hjønnevåg,
	Todd Kjos, Christian Brauner, Carlos Llamas, rust-for-linux,
	linux-kernel

On Tue Feb 10, 2026 at 2:57 PM CET, Alice Ryhl wrote:
> On Tue, Feb 10, 2026 at 07:08:09PM +0530, Shivam Kalra wrote:
>> This is a follow-up to my v3 series:
>> https://lore.kernel.org/rust-for-linux/20260207-binder-shrink-vec-v3-v3-0-8ff388563427@cock.li/
>> 
>> Hi all,
>> 
>> Thanks for the feedback on v3. Before I respin, I want to confirm
>> the direction for v4 to avoid unnecessary iterations.
>> 
>> Proposed changes for v4:
>> 
>> 1. Drop the Shrinkable trait entirely. Make shrink_to() a normal
>>    method on Vec<T, A> that calls A::realloc(). (Danilo)
>> 
>> 2. Add a temporary ShrinkQuirk trait to handle the vmalloc workaround
>>    (page-boundary check + manual alloc+copy+free) until vrealloc
>>    gains in-place shrinking support. (Danilo)
>
> I don't think you want any new traits at all. What types would even
> implement the trait? The special code can go in the realloc() method of
> Vmalloc struct in rust/kernel/alloc/allocator.rs.

I did not propose to move this into the realloc() functions of the corresponding
allocators intentionally, as there is a difference between calling realloc() and
shrink_to().

I don't want that some user of e.g. Vmalloc::realloc() experiences page wise
shrinking by copy. This is acceptable for Vec::shrink_to(), but not for
realloc() in general.

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH v3 0/4] rust: alloc: add Vec shrinking methods
  2026-02-10 15:05     ` Danilo Krummrich
@ 2026-02-10 17:42       ` Shivam Kalra
  2026-02-10 20:05       ` Alice Ryhl
  1 sibling, 0 replies; 24+ messages in thread
From: Shivam Kalra @ 2026-02-10 17:42 UTC (permalink / raw)
  To: Danilo Krummrich, Alice Ryhl
  Cc: Lorenzo Stoakes, Vlastimil Babka, Liam R. Howlett,
	Uladzislau Rezki, Miguel Ojeda, Boqun Feng, Gary Guo,
	Björn Roy Baron, Benno Lossin, Andreas Hindborg,
	Trevor Gross, Greg Kroah-Hartman, Arve Hjønnevåg,
	Todd Kjos, Christian Brauner, Carlos Llamas, rust-for-linux,
	linux-kernel

On 10/02/26 20:35, Danilo Krummrich wrote:
> On Tue Feb 10, 2026 at 2:57 PM CET, Alice Ryhl wrote:
>> On Tue, Feb 10, 2026 at 07:08:09PM +0530, Shivam Kalra wrote:
>>> This is a follow-up to my v3 series:
>>> https://lore.kernel.org/rust-for-linux/20260207-binder-shrink-vec-v3-v3-0-8ff388563427@cock.li/
>>>
>>> Hi all,
>>>
>>> Thanks for the feedback on v3. Before I respin, I want to confirm
>>> the direction for v4 to avoid unnecessary iterations.
>>>
>>> Proposed changes for v4:
>>>
>>> 1. Drop the Shrinkable trait entirely. Make shrink_to() a normal
>>>    method on Vec<T, A> that calls A::realloc(). (Danilo)
>>>
>>> 2. Add a temporary ShrinkQuirk trait to handle the vmalloc workaround
>>>    (page-boundary check + manual alloc+copy+free) until vrealloc
>>>    gains in-place shrinking support. (Danilo)
>>
>> I don't think you want any new traits at all. What types would even
>> implement the trait? The special code can go in the realloc() method of
>> Vmalloc struct in rust/kernel/alloc/allocator.rs.
> 
> I did not propose to move this into the realloc() functions of the corresponding
> allocators intentionally, as there is a difference between calling realloc() and
> shrink_to().
> 
> I don't want that some user of e.g. Vmalloc::realloc() experiences page wise
> shrinking by copy. This is acceptable for Vec::shrink_to(), but not for
> realloc() in general.
I think this aligns with the reasoning behind the Shrinkable trait
in v3- keeping the shrink workaround separate from realloc() so
that other users of realloc() (like IntoIter) don't unexpectedly
get alloc+copy+free behavior.
Happy to implement whichever approach you both agree on.


^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH v3 0/4] rust: alloc: add Vec shrinking methods
  2026-02-10 15:05     ` Danilo Krummrich
  2026-02-10 17:42       ` Shivam Kalra
@ 2026-02-10 20:05       ` Alice Ryhl
  2026-02-10 20:43         ` Danilo Krummrich
  1 sibling, 1 reply; 24+ messages in thread
From: Alice Ryhl @ 2026-02-10 20:05 UTC (permalink / raw)
  To: Danilo Krummrich
  Cc: Shivam Kalra, Lorenzo Stoakes, Vlastimil Babka, Liam R. Howlett,
	Uladzislau Rezki, Miguel Ojeda, Boqun Feng, Gary Guo,
	Björn Roy Baron, Benno Lossin, Andreas Hindborg,
	Trevor Gross, Greg Kroah-Hartman, Arve Hjønnevåg,
	Todd Kjos, Christian Brauner, Carlos Llamas, rust-for-linux,
	linux-kernel

On Tue, Feb 10, 2026 at 4:05 PM Danilo Krummrich <dakr@kernel.org> wrote:
>
> On Tue Feb 10, 2026 at 2:57 PM CET, Alice Ryhl wrote:
> > On Tue, Feb 10, 2026 at 07:08:09PM +0530, Shivam Kalra wrote:
> >> This is a follow-up to my v3 series:
> >> https://lore.kernel.org/rust-for-linux/20260207-binder-shrink-vec-v3-v3-0-8ff388563427@cock.li/
> >>
> >> Hi all,
> >>
> >> Thanks for the feedback on v3. Before I respin, I want to confirm
> >> the direction for v4 to avoid unnecessary iterations.
> >>
> >> Proposed changes for v4:
> >>
> >> 1. Drop the Shrinkable trait entirely. Make shrink_to() a normal
> >>    method on Vec<T, A> that calls A::realloc(). (Danilo)
> >>
> >> 2. Add a temporary ShrinkQuirk trait to handle the vmalloc workaround
> >>    (page-boundary check + manual alloc+copy+free) until vrealloc
> >>    gains in-place shrinking support. (Danilo)
> >
> > I don't think you want any new traits at all. What types would even
> > implement the trait? The special code can go in the realloc() method of
> > Vmalloc struct in rust/kernel/alloc/allocator.rs.
>
> I did not propose to move this into the realloc() functions of the corresponding
> allocators intentionally, as there is a difference between calling realloc() and
> shrink_to().
>
> I don't want that some user of e.g. Vmalloc::realloc() experiences page wise
> shrinking by copy. This is acceptable for Vec::shrink_to(), but not for
> realloc() in general.

Ok. In that case we can add a method on KVVec directly for this
purpose, but I still don't think we need a trait?

Alice

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH v3 0/4] rust: alloc: add Vec shrinking methods
  2026-02-10 20:05       ` Alice Ryhl
@ 2026-02-10 20:43         ` Danilo Krummrich
  2026-02-10 20:53           ` Danilo Krummrich
  0 siblings, 1 reply; 24+ messages in thread
From: Danilo Krummrich @ 2026-02-10 20:43 UTC (permalink / raw)
  To: Alice Ryhl
  Cc: Shivam Kalra, Lorenzo Stoakes, Vlastimil Babka, Liam R. Howlett,
	Uladzislau Rezki, Miguel Ojeda, Boqun Feng, Gary Guo,
	Björn Roy Baron, Benno Lossin, Andreas Hindborg,
	Trevor Gross, Greg Kroah-Hartman, Arve Hjønnevåg,
	Todd Kjos, Christian Brauner, Carlos Llamas, rust-for-linux,
	linux-kernel

On Tue Feb 10, 2026 at 9:05 PM CET, Alice Ryhl wrote:
> On Tue, Feb 10, 2026 at 4:05 PM Danilo Krummrich <dakr@kernel.org> wrote:
>>
>> On Tue Feb 10, 2026 at 2:57 PM CET, Alice Ryhl wrote:
>> > On Tue, Feb 10, 2026 at 07:08:09PM +0530, Shivam Kalra wrote:
>> >> This is a follow-up to my v3 series:
>> >> https://lore.kernel.org/rust-for-linux/20260207-binder-shrink-vec-v3-v3-0-8ff388563427@cock.li/
>> >>
>> >> Hi all,
>> >>
>> >> Thanks for the feedback on v3. Before I respin, I want to confirm
>> >> the direction for v4 to avoid unnecessary iterations.
>> >>
>> >> Proposed changes for v4:
>> >>
>> >> 1. Drop the Shrinkable trait entirely. Make shrink_to() a normal
>> >>    method on Vec<T, A> that calls A::realloc(). (Danilo)
>> >>
>> >> 2. Add a temporary ShrinkQuirk trait to handle the vmalloc workaround
>> >>    (page-boundary check + manual alloc+copy+free) until vrealloc
>> >>    gains in-place shrinking support. (Danilo)
>> >
>> > I don't think you want any new traits at all. What types would even
>> > implement the trait? The special code can go in the realloc() method of
>> > Vmalloc struct in rust/kernel/alloc/allocator.rs.
>>
>> I did not propose to move this into the realloc() functions of the corresponding
>> allocators intentionally, as there is a difference between calling realloc() and
>> shrink_to().
>>
>> I don't want that some user of e.g. Vmalloc::realloc() experiences page wise
>> shrinking by copy. This is acceptable for Vec::shrink_to(), but not for
>> realloc() in general.
>
> Ok. In that case we can add a method on KVVec directly for this
> purpose, but I still don't think we need a trait?

KVVec::realloc() should not have this behavior either, we only want it for
VVec::shrink_to() and KVVec::shrink_to(), so I think we need a temporary quirk
trait.

Of course, we could also check for is_vmallloc_addr() in Vec::shrink_to()
directly, but that's too hacky. I want something that can survive a bit in case
the vrealloc() rework takes a while.

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH v3 0/4] rust: alloc: add Vec shrinking methods
  2026-02-10 20:43         ` Danilo Krummrich
@ 2026-02-10 20:53           ` Danilo Krummrich
  2026-02-10 20:56             ` Danilo Krummrich
  2026-02-10 20:58             ` Alice Ryhl
  0 siblings, 2 replies; 24+ messages in thread
From: Danilo Krummrich @ 2026-02-10 20:53 UTC (permalink / raw)
  To: Alice Ryhl
  Cc: Shivam Kalra, Lorenzo Stoakes, Vlastimil Babka, Liam R. Howlett,
	Uladzislau Rezki, Miguel Ojeda, Boqun Feng, Gary Guo,
	Björn Roy Baron, Benno Lossin, Andreas Hindborg,
	Trevor Gross, Greg Kroah-Hartman, Arve Hjønnevåg,
	Todd Kjos, Christian Brauner, Carlos Llamas, rust-for-linux,
	linux-kernel

On Tue Feb 10, 2026 at 9:43 PM CET, Danilo Krummrich wrote:
> On Tue Feb 10, 2026 at 9:05 PM CET, Alice Ryhl wrote:
>> On Tue, Feb 10, 2026 at 4:05 PM Danilo Krummrich <dakr@kernel.org> wrote:
>>>
>>> On Tue Feb 10, 2026 at 2:57 PM CET, Alice Ryhl wrote:
>>> > On Tue, Feb 10, 2026 at 07:08:09PM +0530, Shivam Kalra wrote:
>>> >> This is a follow-up to my v3 series:
>>> >> https://lore.kernel.org/rust-for-linux/20260207-binder-shrink-vec-v3-v3-0-8ff388563427@cock.li/
>>> >>
>>> >> Hi all,
>>> >>
>>> >> Thanks for the feedback on v3. Before I respin, I want to confirm
>>> >> the direction for v4 to avoid unnecessary iterations.
>>> >>
>>> >> Proposed changes for v4:
>>> >>
>>> >> 1. Drop the Shrinkable trait entirely. Make shrink_to() a normal
>>> >>    method on Vec<T, A> that calls A::realloc(). (Danilo)
>>> >>
>>> >> 2. Add a temporary ShrinkQuirk trait to handle the vmalloc workaround
>>> >>    (page-boundary check + manual alloc+copy+free) until vrealloc
>>> >>    gains in-place shrinking support. (Danilo)
>>> >
>>> > I don't think you want any new traits at all. What types would even
>>> > implement the trait? The special code can go in the realloc() method of
>>> > Vmalloc struct in rust/kernel/alloc/allocator.rs.
>>>
>>> I did not propose to move this into the realloc() functions of the corresponding
>>> allocators intentionally, as there is a difference between calling realloc() and
>>> shrink_to().
>>>
>>> I don't want that some user of e.g. Vmalloc::realloc() experiences page wise
>>> shrinking by copy. This is acceptable for Vec::shrink_to(), but not for
>>> realloc() in general.
>>
>> Ok. In that case we can add a method on KVVec directly for this
>> purpose, but I still don't think we need a trait?
>
> KVVec::realloc() should not have this behavior either, we only want it for

s/KVVec::realloc()/KVec::shrink_to()/

> VVec::shrink_to() and KVVec::shrink_to(), so I think we need a temporary quirk
> trait.

Unless you mean to implement shrink_to() for VVec and KVVec only, that would be
fine with me as well.

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH v3 0/4] rust: alloc: add Vec shrinking methods
  2026-02-10 20:53           ` Danilo Krummrich
@ 2026-02-10 20:56             ` Danilo Krummrich
  2026-02-10 20:58             ` Alice Ryhl
  1 sibling, 0 replies; 24+ messages in thread
From: Danilo Krummrich @ 2026-02-10 20:56 UTC (permalink / raw)
  To: Alice Ryhl
  Cc: Shivam Kalra, Lorenzo Stoakes, Vlastimil Babka, Liam R. Howlett,
	Uladzislau Rezki, Miguel Ojeda, Boqun Feng, Gary Guo,
	Björn Roy Baron, Benno Lossin, Andreas Hindborg,
	Trevor Gross, Greg Kroah-Hartman, Arve Hjønnevåg,
	Todd Kjos, Christian Brauner, Carlos Llamas, rust-for-linux,
	linux-kernel

On Tue Feb 10, 2026 at 9:53 PM CET, Danilo Krummrich wrote:
> On Tue Feb 10, 2026 at 9:43 PM CET, Danilo Krummrich wrote:
>> On Tue Feb 10, 2026 at 9:05 PM CET, Alice Ryhl wrote:
>>> On Tue, Feb 10, 2026 at 4:05 PM Danilo Krummrich <dakr@kernel.org> wrote:
>>>>
>>>> On Tue Feb 10, 2026 at 2:57 PM CET, Alice Ryhl wrote:
>>>> > On Tue, Feb 10, 2026 at 07:08:09PM +0530, Shivam Kalra wrote:
>>>> >> This is a follow-up to my v3 series:
>>>> >> https://lore.kernel.org/rust-for-linux/20260207-binder-shrink-vec-v3-v3-0-8ff388563427@cock.li/
>>>> >>
>>>> >> Hi all,
>>>> >>
>>>> >> Thanks for the feedback on v3. Before I respin, I want to confirm
>>>> >> the direction for v4 to avoid unnecessary iterations.
>>>> >>
>>>> >> Proposed changes for v4:
>>>> >>
>>>> >> 1. Drop the Shrinkable trait entirely. Make shrink_to() a normal
>>>> >>    method on Vec<T, A> that calls A::realloc(). (Danilo)
>>>> >>
>>>> >> 2. Add a temporary ShrinkQuirk trait to handle the vmalloc workaround
>>>> >>    (page-boundary check + manual alloc+copy+free) until vrealloc
>>>> >>    gains in-place shrinking support. (Danilo)
>>>> >
>>>> > I don't think you want any new traits at all. What types would even
>>>> > implement the trait? The special code can go in the realloc() method of
>>>> > Vmalloc struct in rust/kernel/alloc/allocator.rs.
>>>>
>>>> I did not propose to move this into the realloc() functions of the corresponding
>>>> allocators intentionally, as there is a difference between calling realloc() and
>>>> shrink_to().
>>>>
>>>> I don't want that some user of e.g. Vmalloc::realloc() experiences page wise
>>>> shrinking by copy. This is acceptable for Vec::shrink_to(), but not for
>>>> realloc() in general.
>>>
>>> Ok. In that case we can add a method on KVVec directly for this
>>> purpose, but I still don't think we need a trait?
>>
>> KVVec::realloc() should not have this behavior either, we only want it for
>
> s/KVVec::realloc()/KVec::shrink_to()/
>
>> VVec::shrink_to() and KVVec::shrink_to(), so I think we need a temporary quirk
>> trait.
>
> Unless you mean to implement shrink_to() for VVec and KVVec only, that would be

s/and/or/ (Sorry for another correction, slightly distracted currently. :)

> fine with me as well.

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH v3 0/4] rust: alloc: add Vec shrinking methods
  2026-02-10 20:53           ` Danilo Krummrich
  2026-02-10 20:56             ` Danilo Krummrich
@ 2026-02-10 20:58             ` Alice Ryhl
  2026-02-10 21:11               ` Danilo Krummrich
  1 sibling, 1 reply; 24+ messages in thread
From: Alice Ryhl @ 2026-02-10 20:58 UTC (permalink / raw)
  To: Danilo Krummrich
  Cc: Shivam Kalra, Lorenzo Stoakes, Vlastimil Babka, Liam R. Howlett,
	Uladzislau Rezki, Miguel Ojeda, Boqun Feng, Gary Guo,
	Björn Roy Baron, Benno Lossin, Andreas Hindborg,
	Trevor Gross, Greg Kroah-Hartman, Arve Hjønnevåg,
	Todd Kjos, Christian Brauner, Carlos Llamas, rust-for-linux,
	linux-kernel

On Tue, Feb 10, 2026 at 9:54 PM Danilo Krummrich <dakr@kernel.org> wrote:
>
> On Tue Feb 10, 2026 at 9:43 PM CET, Danilo Krummrich wrote:
> > On Tue Feb 10, 2026 at 9:05 PM CET, Alice Ryhl wrote:
> >> On Tue, Feb 10, 2026 at 4:05 PM Danilo Krummrich <dakr@kernel.org> wrote:
> >>>
> >>> On Tue Feb 10, 2026 at 2:57 PM CET, Alice Ryhl wrote:
> >>> > On Tue, Feb 10, 2026 at 07:08:09PM +0530, Shivam Kalra wrote:
> >>> >> This is a follow-up to my v3 series:
> >>> >> https://lore.kernel.org/rust-for-linux/20260207-binder-shrink-vec-v3-v3-0-8ff388563427@cock.li/
> >>> >>
> >>> >> Hi all,
> >>> >>
> >>> >> Thanks for the feedback on v3. Before I respin, I want to confirm
> >>> >> the direction for v4 to avoid unnecessary iterations.
> >>> >>
> >>> >> Proposed changes for v4:
> >>> >>
> >>> >> 1. Drop the Shrinkable trait entirely. Make shrink_to() a normal
> >>> >>    method on Vec<T, A> that calls A::realloc(). (Danilo)
> >>> >>
> >>> >> 2. Add a temporary ShrinkQuirk trait to handle the vmalloc workaround
> >>> >>    (page-boundary check + manual alloc+copy+free) until vrealloc
> >>> >>    gains in-place shrinking support. (Danilo)
> >>> >
> >>> > I don't think you want any new traits at all. What types would even
> >>> > implement the trait? The special code can go in the realloc() method of
> >>> > Vmalloc struct in rust/kernel/alloc/allocator.rs.
> >>>
> >>> I did not propose to move this into the realloc() functions of the corresponding
> >>> allocators intentionally, as there is a difference between calling realloc() and
> >>> shrink_to().
> >>>
> >>> I don't want that some user of e.g. Vmalloc::realloc() experiences page wise
> >>> shrinking by copy. This is acceptable for Vec::shrink_to(), but not for
> >>> realloc() in general.
> >>
> >> Ok. In that case we can add a method on KVVec directly for this
> >> purpose, but I still don't think we need a trait?
> >
> > KVVec::realloc() should not have this behavior either, we only want it for
>
> s/KVVec::realloc()/KVec::shrink_to()/
>
> > VVec::shrink_to() and KVVec::shrink_to(), so I think we need a temporary quirk
> > trait.
>
> Unless you mean to implement shrink_to() for VVec and KVVec only, that would be
> fine with me as well.

Yes that's what I meant. Only provide shrink_to() for those. After
all, if Kmalloc never actually shrinks when you call realloc, what's
the point of having KVec::shrink_to()?

Alice

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH v3 0/4] rust: alloc: add Vec shrinking methods
  2026-02-10 20:58             ` Alice Ryhl
@ 2026-02-10 21:11               ` Danilo Krummrich
  2026-02-11  1:08                 ` Shivam Kalra
  0 siblings, 1 reply; 24+ messages in thread
From: Danilo Krummrich @ 2026-02-10 21:11 UTC (permalink / raw)
  To: Alice Ryhl
  Cc: Shivam Kalra, Lorenzo Stoakes, Vlastimil Babka, Liam R. Howlett,
	Uladzislau Rezki, Miguel Ojeda, Boqun Feng, Gary Guo,
	Björn Roy Baron, Benno Lossin, Andreas Hindborg,
	Trevor Gross, Greg Kroah-Hartman, Arve Hjønnevåg,
	Todd Kjos, Christian Brauner, Carlos Llamas, rust-for-linux,
	linux-kernel

On Tue Feb 10, 2026 at 9:58 PM CET, Alice Ryhl wrote:
> On Tue, Feb 10, 2026 at 9:54 PM Danilo Krummrich <dakr@kernel.org> wrote:
>>
>> On Tue Feb 10, 2026 at 9:43 PM CET, Danilo Krummrich wrote:
>> > On Tue Feb 10, 2026 at 9:05 PM CET, Alice Ryhl wrote:
>> >> On Tue, Feb 10, 2026 at 4:05 PM Danilo Krummrich <dakr@kernel.org> wrote:
>> >>>
>> >>> On Tue Feb 10, 2026 at 2:57 PM CET, Alice Ryhl wrote:
>> >>> > On Tue, Feb 10, 2026 at 07:08:09PM +0530, Shivam Kalra wrote:
>> >>> >> This is a follow-up to my v3 series:
>> >>> >> https://lore.kernel.org/rust-for-linux/20260207-binder-shrink-vec-v3-v3-0-8ff388563427@cock.li/
>> >>> >>
>> >>> >> Hi all,
>> >>> >>
>> >>> >> Thanks for the feedback on v3. Before I respin, I want to confirm
>> >>> >> the direction for v4 to avoid unnecessary iterations.
>> >>> >>
>> >>> >> Proposed changes for v4:
>> >>> >>
>> >>> >> 1. Drop the Shrinkable trait entirely. Make shrink_to() a normal
>> >>> >>    method on Vec<T, A> that calls A::realloc(). (Danilo)
>> >>> >>
>> >>> >> 2. Add a temporary ShrinkQuirk trait to handle the vmalloc workaround
>> >>> >>    (page-boundary check + manual alloc+copy+free) until vrealloc
>> >>> >>    gains in-place shrinking support. (Danilo)
>> >>> >
>> >>> > I don't think you want any new traits at all. What types would even
>> >>> > implement the trait? The special code can go in the realloc() method of
>> >>> > Vmalloc struct in rust/kernel/alloc/allocator.rs.
>> >>>
>> >>> I did not propose to move this into the realloc() functions of the corresponding
>> >>> allocators intentionally, as there is a difference between calling realloc() and
>> >>> shrink_to().
>> >>>
>> >>> I don't want that some user of e.g. Vmalloc::realloc() experiences page wise
>> >>> shrinking by copy. This is acceptable for Vec::shrink_to(), but not for
>> >>> realloc() in general.
>> >>
>> >> Ok. In that case we can add a method on KVVec directly for this
>> >> purpose, but I still don't think we need a trait?
>> >
>> > KVVec::realloc() should not have this behavior either, we only want it for
>>
>> s/KVVec::realloc()/KVec::shrink_to()/
>>
>> > VVec::shrink_to() and KVVec::shrink_to(), so I think we need a temporary quirk
>> > trait.
>>
>> Unless you mean to implement shrink_to() for VVec and KVVec only, that would be
>> fine with me as well.
>
> Yes that's what I meant. Only provide shrink_to() for those. After
> all, if Kmalloc never actually shrinks when you call realloc, what's
> the point of having KVec::shrink_to()?

Nothing, but eventually we want a generic impl of shrink_to() with A::realloc().
But again, for now that's fine.

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH v3 0/4] rust: alloc: add Vec shrinking methods
  2026-02-10 21:11               ` Danilo Krummrich
@ 2026-02-11  1:08                 ` Shivam Kalra
  2026-02-11  6:51                   ` Alice Ryhl
  0 siblings, 1 reply; 24+ messages in thread
From: Shivam Kalra @ 2026-02-11  1:08 UTC (permalink / raw)
  To: Danilo Krummrich, Alice Ryhl, rust-for-linux, linux-kernel

On 11/02/26 02:41, Danilo Krummrich wrote:
> On Tue Feb 10, 2026 at 9:58 PM CET, Alice Ryhl wrote:
>> On Tue, Feb 10, 2026 at 9:54 PM Danilo Krummrich <dakr@kernel.org> wrote:
>> Yes that's what I meant. Only provide shrink_to() for those. After
>> all, if Kmalloc never actually shrinks when you call realloc, what's
>> the point of having KVec::shrink_to()?
> 
> Nothing, but eventually we want a generic impl of shrink_to() with A::realloc().
> But again, for now that's fine.
Thanks for the discussion. Just want to confirm my understanding
of the agreed approach:

Since VVec and KVVec are type aliases for Vec<T, Vmalloc> and
Vec<T, KVmalloc>, implementing shrink_to() on "only VVec and KVVec"
means writing separate impl blocks:

  impl<T> Vec<T, Vmalloc> { fn shrink_to() { ... } }
  impl<T> Vec<T, KVmalloc> { fn shrink_to() { ... } }

Is that what you had in mind, with the shrink logic duplicated
in both? Or would you prefer a shared impl with a trait bound to
avoid duplication?

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH v3 0/4] rust: alloc: add Vec shrinking methods
  2026-02-11  1:08                 ` Shivam Kalra
@ 2026-02-11  6:51                   ` Alice Ryhl
  2026-02-11  8:41                     ` Shivam Kalra
  0 siblings, 1 reply; 24+ messages in thread
From: Alice Ryhl @ 2026-02-11  6:51 UTC (permalink / raw)
  To: Shivam Kalra; +Cc: Danilo Krummrich, rust-for-linux, linux-kernel

On Wed, Feb 11, 2026 at 2:08 AM Shivam Kalra <shivamkalra98@gmail.com> wrote:
>
> On 11/02/26 02:41, Danilo Krummrich wrote:
> > On Tue Feb 10, 2026 at 9:58 PM CET, Alice Ryhl wrote:
> >> On Tue, Feb 10, 2026 at 9:54 PM Danilo Krummrich <dakr@kernel.org> wrote:
> >> Yes that's what I meant. Only provide shrink_to() for those. After
> >> all, if Kmalloc never actually shrinks when you call realloc, what's
> >> the point of having KVec::shrink_to()?
> >
> > Nothing, but eventually we want a generic impl of shrink_to() with A::realloc().
> > But again, for now that's fine.
> Thanks for the discussion. Just want to confirm my understanding
> of the agreed approach:
>
> Since VVec and KVVec are type aliases for Vec<T, Vmalloc> and
> Vec<T, KVmalloc>, implementing shrink_to() on "only VVec and KVVec"
> means writing separate impl blocks:
>
>   impl<T> Vec<T, Vmalloc> { fn shrink_to() { ... } }
>   impl<T> Vec<T, KVmalloc> { fn shrink_to() { ... } }
>
> Is that what you had in mind, with the shrink logic duplicated
> in both? Or would you prefer a shared impl with a trait bound to
> avoid duplication?

I would prefer either a single stand-alone function that both impls
blocks call, or implementing it for KVmalloc only. Trait is overkill
here.

Alice

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH v3 0/4] rust: alloc: add Vec shrinking methods
  2026-02-11  6:51                   ` Alice Ryhl
@ 2026-02-11  8:41                     ` Shivam Kalra
  2026-02-11  8:57                       ` Danilo Krummrich
  0 siblings, 1 reply; 24+ messages in thread
From: Shivam Kalra @ 2026-02-11  8:41 UTC (permalink / raw)
  To: Alice Ryhl; +Cc: Danilo Krummrich, rust-for-linux, linux-kernel

On 11/02/26 12:21, Alice Ryhl wrote:
> On Wed, Feb 11, 2026 at 2:08 AM Shivam Kalra <shivamkalra98@gmail.com> wrote:
>>
>> On 11/02/26 02:41, Danilo Krummrich wrote:
>>> On Tue Feb 10, 2026 at 9:58 PM CET, Alice Ryhl wrote:
>>>> On Tue, Feb 10, 2026 at 9:54 PM Danilo Krummrich <dakr@kernel.org> wrote:
>>>> Yes that's what I meant. Only provide shrink_to() for those. After
>>>> all, if Kmalloc never actually shrinks when you call realloc, what's
>>>> the point of having KVec::shrink_to()?
>>>
>>> Nothing, but eventually we want a generic impl of shrink_to() with A::realloc().
>>> But again, for now that's fine.
>> Thanks for the discussion. Just want to confirm my understanding
>> of the agreed approach:
>>
>> Since VVec and KVVec are type aliases for Vec<T, Vmalloc> and
>> Vec<T, KVmalloc>, implementing shrink_to() on "only VVec and KVVec"
>> means writing separate impl blocks:
>>
>>   impl<T> Vec<T, Vmalloc> { fn shrink_to() { ... } }
>>   impl<T> Vec<T, KVmalloc> { fn shrink_to() { ... } }
>>
>> Is that what you had in mind, with the shrink logic duplicated
>> in both? Or would you prefer a shared impl with a trait bound to
>> avoid duplication?
> 
> I would prefer either a single stand-alone function that both impls
> blocks call, or implementing it for KVmalloc only. Trait is overkill
> here.
> 
> Alice
Thanks Alice. I'll go with the standalone helper function approach
with separate impl blocks for Vec<T, Vmalloc> and Vec<T, KVmalloc>.

Will send v4 in a some time.

Shivam

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH v3 0/4] rust: alloc: add Vec shrinking methods
  2026-02-11  8:41                     ` Shivam Kalra
@ 2026-02-11  8:57                       ` Danilo Krummrich
  2026-02-11  9:35                         ` Shivam Kalra
  0 siblings, 1 reply; 24+ messages in thread
From: Danilo Krummrich @ 2026-02-11  8:57 UTC (permalink / raw)
  To: Shivam Kalra; +Cc: Alice Ryhl, rust-for-linux, linux-kernel

On Wed Feb 11, 2026 at 9:41 AM CET, Shivam Kalra wrote:
> Thanks Alice. I'll go with the standalone helper function approach
> with separate impl blocks for Vec<T, Vmalloc> and Vec<T, KVmalloc>.

If it's only needed for KVmalloc, which apparently is the case, let's just add
it for KVVec only.

Also, please make sure to add a TODO comment mentioning why this workaround
exists and what it should be replaced with, i.e. a generic shrink_to() that
calls into A::realloc().

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH v3 0/4] rust: alloc: add Vec shrinking methods
  2026-02-11  8:57                       ` Danilo Krummrich
@ 2026-02-11  9:35                         ` Shivam Kalra
  0 siblings, 0 replies; 24+ messages in thread
From: Shivam Kalra @ 2026-02-11  9:35 UTC (permalink / raw)
  To: Danilo Krummrich; +Cc: Alice Ryhl, rust-for-linux, linux-kernel

On 11/02/26 14:27, Danilo Krummrich wrote:
> On Wed Feb 11, 2026 at 9:41 AM CET, Shivam Kalra wrote:
>> Thanks Alice. I'll go with the standalone helper function approach
>> with separate impl blocks for Vec<T, Vmalloc> and Vec<T, KVmalloc>.
> 
> If it's only needed for KVmalloc, which apparently is the case, let's just add
> it for KVVec only.
> 
> Also, please make sure to add a TODO comment mentioning why this workaround
> exists and what it should be replaced with, i.e. a generic shrink_to() that
> calls into A::realloc().
Thanks for the discussion on v3. The direction for v4 is now clear.
Summary of changes for v4:
1. Drop the Shrinkable trait entirely. (Danilo)
2. Implement shrink_to() only for KVVec (impl<T> Vec<T, KVmalloc>),
   since that covers the actual use case (binder). No new traits
   needed. (Danilo,Alice)
3. Add a TODO comment explaining this is a temporary workaround
   (page-boundary check + manual alloc+copy+free) that should be
   replaced with a generic Vec<T, A>::shrink_to() calling
   A::realloc() once vrealloc gains in-place shrinking. (Danilo)
4. In the binder patch, use a less aggressive shrink strategy to
   avoid shrink-then-regrow oscillation: (Alice)
     if len < cap / 4 {
         shrink_to(cap / 2);
     }
5. Fix commit prefix to rust_binder: instead of rust: binder:. (Alice)

Also noting that starting from v4, I will be sending patches from
a new email address: shivamkalra98@zohomail.in
I previously sent patches as shivamklr@cock.li, then briefly from
shivamkalra98@gmail.com. Both accounts ran out of quota, so all
future patches (v4+) will come from this address.
Thanks,
Shivam

^ permalink raw reply	[flat|nested] 24+ messages in thread

end of thread, other threads:[~2026-02-11  9:36 UTC | newest]

Thread overview: 24+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-02-07 11:32 [PATCH v3 0/4] rust: alloc: add Vec shrinking methods Shivam Kalra via B4 Relay
2026-02-07 11:32 ` [PATCH v3 1/4] rust: alloc: introduce Shrinkable trait Shivam Kalra via B4 Relay
2026-02-07 11:32 ` [PATCH v3 2/4] rust: kvec: implement shrink_to and shrink_to_fit for Vec Shivam Kalra via B4 Relay
2026-02-07 17:23   ` Danilo Krummrich
2026-02-08 16:11     ` Shivam Kalra
2026-02-07 11:32 ` [PATCH v3 3/4] rust: alloc: add KUnit tests for Vec shrink operations Shivam Kalra via B4 Relay
2026-02-07 11:32 ` [PATCH v3 4/4] rust: binder: shrink all_procs when deregistering processes Shivam Kalra via B4 Relay
2026-02-09 13:54   ` Alice Ryhl
2026-02-10 11:47     ` Shivam Kalra
2026-02-10 13:38 ` [PATCH v3 0/4] rust: alloc: add Vec shrinking methods Shivam Kalra
2026-02-10 13:57   ` Alice Ryhl
2026-02-10 15:05     ` Danilo Krummrich
2026-02-10 17:42       ` Shivam Kalra
2026-02-10 20:05       ` Alice Ryhl
2026-02-10 20:43         ` Danilo Krummrich
2026-02-10 20:53           ` Danilo Krummrich
2026-02-10 20:56             ` Danilo Krummrich
2026-02-10 20:58             ` Alice Ryhl
2026-02-10 21:11               ` Danilo Krummrich
2026-02-11  1:08                 ` Shivam Kalra
2026-02-11  6:51                   ` Alice Ryhl
2026-02-11  8:41                     ` Shivam Kalra
2026-02-11  8:57                       ` Danilo Krummrich
2026-02-11  9:35                         ` Shivam Kalra

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox