lending-cell icon indicating copy to clipboard operation
lending-cell copied to clipboard

Insufficient synchronization in `LendingCell::try_get`

Open tremwil opened this issue 4 months ago • 0 comments

LendingCell::try_get and try_to_borrowed check Arc::strong_count() to verify that there are no borrowed instances. This function uses Relaxed memory ordering to load the strong count, as as such it will not synchronize with dropping the BorrowedCell.

This does not introduce safety problems, because a mutable reference is required to create a BorrowedCell. However, it does mean that LendingCell::try_get and try_to_borrowed could incorrectly panic due to reading a stale strong count of 2 when the BorrowedCell has in fact been dropped.

To fix, use the following to check for uniqueness instead:

fn is_unique(&self) -> bool {
    // Synchronize with BorrowedCell's Drop that decrements the strong count
    // Note: This would not be sufficient in the presence of weak refs!
    std::sync::atomic::fence(Ordering::Acquire);
    Arc::strong_count(&self.inner) == 1
}

tremwil avatar Nov 27 '25 20:11 tremwil