Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Fix memory leak for
Option<SwiftType>
This commit fixes a memory leak when passing `Option<SwiftType>` to `extern "Rust"` functions. For example, the following bridge module would lead to memory leaks: ```rust #[swift_bridge::bridge] mod ffi { extern "Swift" { type SomeSwiftType; } extern "Rust" { fn rust_fn_takes_swift_type(arg: Option<SomeSwiftType>); } } ``` When the above `rust_fn_takes_swift_type` function was called the `SomeSwiftType` would be retained twice. When the Rust side later freed `SomeSwiftType` the retain count would drop from 2 to 1. Since there was still 1 retain, `SomeSwiftType` would never get freed. ## Impact Support for passing `Option<SomeSwiftType>` from Swift to Rust was introduced earlier today. This functionality was released in `swift-bridge = "0.1.54"`. W will be deploying `swift-bridge = "0.1.55" today. "0.1.55" will contain a fix for the leak. Because support for `Option<SomeSwiftType>` was released today, and the fix will be released today, it should be unlikely that anyone has experienced this leak. We will yank "0.1.54" from "crates.io". All users (probably zero) that are bridging `Option<SomeSwiftType>` should upgrade from "0.1.54" to "0.1.55" to. ## Solution This commit does the following: - When passing ownership of a Swift type from Swift to Rust we now increment the retain count by one. Before this commit we were incrementing it by two. - When passing ownership of a Swift type from Rust to Swift we avoid calling the the Rust handle's `Drop` implementation. We avoid this by using `std::mem::forget`. This ensures that the retain count does not get decremented. - When passing ownership of a Swift type from Rust to Swift the Swift side does not increment the retain count. With all of the above we should now be able to: - Create an `Option<SwiftType>` Swift type on the Swift side - Pass ownership of the `Option<SwiftType> to Rust. The retain count is now 1. - Pass ownership back to Swift. The retain count is still 1. Before this commit, when passing an `Option<SwiftType>` it was: - Create a Swift type on the Swift side - Pass `Option<SwiftType>` to Rust. Retain count is now 2 - Rust passes ownership back to Swift. Retain count is now 1 - Retain count never hits 0. Memory has been leaked.
- Loading branch information