{"id":16389410,"url":"https://github.com/qqwy/rust-backdrop_arc","last_synced_at":"2025-03-23T04:31:36.251Z","repository":{"id":91781610,"uuid":"607339074","full_name":"Qqwy/rust-backdrop_arc","owner":"Qqwy","description":"An Arc (atomically reference counted smart pointer) that supports customized dropping strategies using Backdrop.","archived":false,"fork":false,"pushed_at":"2023-08-16T17:29:34.000Z","size":203,"stargazers_count":5,"open_issues_count":0,"forks_count":0,"subscribers_count":2,"default_branch":"main","last_synced_at":"2025-03-18T17:46:26.834Z","etag":null,"topics":["memory-management","no-std-alloc","reference-counting","rust","rust-lang","smart-pointer","threading","tokio-rs"],"latest_commit_sha":null,"homepage":"https://crates.io/crates/backdrop_arc","language":"Rust","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/Qqwy.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE-APACHE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2023-02-27T19:41:25.000Z","updated_at":"2023-07-07T23:34:17.000Z","dependencies_parsed_at":"2024-10-28T15:25:02.565Z","dependency_job_id":"9fb5e359-666b-4ba2-a566-21f99d1accac","html_url":"https://github.com/Qqwy/rust-backdrop_arc","commit_stats":{"total_commits":130,"total_committers":16,"mean_commits":8.125,"dds":0.6615384615384615,"last_synced_commit":"606a8073caa9435d2cb9566264e19a32768278cb"},"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Qqwy%2Frust-backdrop_arc","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Qqwy%2Frust-backdrop_arc/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Qqwy%2Frust-backdrop_arc/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Qqwy%2Frust-backdrop_arc/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/Qqwy","download_url":"https://codeload.github.com/Qqwy/rust-backdrop_arc/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":245056889,"owners_count":20553855,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["memory-management","no-std-alloc","reference-counting","rust","rust-lang","smart-pointer","threading","tokio-rs"],"created_at":"2024-10-11T04:32:52.862Z","updated_at":"2025-03-23T04:31:36.230Z","avatar_url":"https://github.com/Qqwy.png","language":"Rust","funding_links":[],"categories":[],"sub_categories":[],"readme":"# BackdropArc \u0026emsp; [![Latest Version]][crates.io] [![License]][license path] [![requires: rustc 1.56+]][Rust 1.56.1]\n\n[Latest Version]: https://img.shields.io/crates/v/backdrop_arc.svg\n[crates.io]: https://crates.io/crates/backdrop_arc\n[License]: https://img.shields.io/badge/license-MIT-blue.svg\n[license path]: https://github.com/qqwy/rust-backdrop_arc/blob/main/LICENSE\n[requires: rustc 1.56+]: https://img.shields.io/badge/rustc-1.56+-lightgray.svg\n[Rust 1.56.1]: https://rust-lang.org/\n\nAn Arc (atomically reference counted smart pointer) that supports customized dropping strategies using [backdrop](https://crates.io/crates/backdrop).\n\n`backdrop_arc::Arc\u003cT, BackdropStrategy\u003e` works very much like a `std::sync::Arc\u003cT\u003e`, except for two differences:\n\n### 1. Drop strategies\n\nWhen the last clone of a particular Arc goes out of scope, rather than dropping normally, the particular [BackdropStrategy](https://docs.rs/backdrop/latest/backdrop/trait.BackdropStrategy.html) is invoked. This way, dropping large or complex structures can be done in a background thread, background tokio task, delayed until later, etc.\n\nThis allows better reasoning about how long code using an Arc will take, since this is no longer dependent on 'do I own the last Arc or not?'.\n\nAn `backdrop_arc::Arc\u003cT, S\u003e` behaves much like a [`Arc\u003cbackdrop::Backdrop\u003cBox\u003cT\u003e, S\u003e\u003e`](https://docs.rs/backdrop/latest/backdrop/struct.Backdrop.html#the-problem-with-arc),\nin that the backdrop strategy is executed _when the last Arc clone goes out of scope_.\nThe difference with `Arc\u003cbackdrop::Backdrop\u003cBox\u003cT\u003e, S\u003e\u003e` is that there is no double pointer-indirection (arc -\u003e box -\u003e T), managing the allocated `T` is done directly in the Arc.\n\n[`backdrop_arc::Arc`]: \u003chttps://docs.rs/backdrop_arc/latest/backdrop_arc/struct.Arc.html\u003e\n\n### 2. No weak pointers =\u003e smaller arcs, predictable drop behaviour\n\n[`std::sync::Arc\u003cT\u003e`] allows the usage of weak pointers. This is very helpful internally in self-referential structures (trees, graphs) but frequently not needed.\nOn the other hand, weak pointers are not 'free':\n- They make every Arc instance bigger (3 words instead of 2), since instead of storing `(ptr, reference_count)` they need to store `(ptr, reference_count, weak_reference_count)`.\n- They make dropping an `Arc\u003cT\u003e` more complex. The 'drop glue' of `T` will run once the last strong reference goes out of scope. But to not make Weak pointers dangle, the _deallocation_ of `T` only happens when the last `Weak` pointer goes out of scope ([see here](https://doc.rust-lang.org/std/sync/struct.Arc.html#breaking-cycles-with-weak)). As you can imagine, this 'two part drop' interacts badly with `BackdropStrategy` where we want to e.g. move objects to a background thread on drop, because we need to make sure that the allocation of `T` lives long enough.\n\nTherefore, `backdrop_arc` is modeled on the excellent [`triomphe`](https://crates.io/crates/triomphe) library.\nConverting a [`backdrop_arc::Arc`] to and from a [`triomphe::Arc`] is a zero-cost operation, as the two types are guaranteed to have the same representation in memory.\n(The same holds true for [`backdrop_arc::UniqueArc`] \u003c-\u003e [`triomphe::UniqueArc`])\n\nNot supporting weak pointers enables a bunch of other features:\n- [`backdrop_arc::Arc`] does not need any read-modify-update operations to handle the possibility of weak references.\n- [`backdrop_arc::UniqueArc`] allows one to construct a temporarily-mutable Arc which can be converted to a regular [`backdrop_arc::Arc`] later.\n- [`backdrop_arc::OffsetArc`] can be used transparently from C++ code and is compatible with (and can be converted to/from) [`backdrop_arc::Arc`].\n- [`backdrop_arc::ArcBorrow`] is functionally similar to `\u0026backdrop_arc::Arc\u003cT\u003e`, however in memory it's simply `\u0026T`. This makes it more flexible for FFI; the source of the borrow need not be an Arc pinned on the stack (and can instead be a pointer from C++, or an `OffsetArc`). Additionally, this helps avoid pointer-chasing.\n- [`backdrop_arc::Arc`] has can be constructed for dynamically-sized types via `from_header_and_iter`\n- [`backdrop_arc::ArcUnion`] is union of two [`backdrop_arc:Arc`]s which fits inside one word of memory\n\n[`std::sync::Arc`]: \u003chttps://doc.rust-lang.org/std/sync/struct.Arc.html\u003e\n[`backdrop_arc::Arc`]: \u003chttps://docs.rs/backdrop_arc/latest/backdrop_arc/struct.Arc.html\u003e\n[`backdrop_arc::UniqueArc`]: \u003chttps://docs.rs/backdrop_arc/latest/backdrop_arc/struct.UniqueArc.html\u003e\n[`backdrop_arc::ArcBorrow`]: \u003chttps://docs.rs/backdrop_arc/latest/backdrop_arc/struct.ArcBorrow.html\u003e\n[`backdrop_arc::ArcUnion`]: \u003chttps://docs.rs/backdrop_arc/latest/backdrop_arc/struct.ArcUnion.html\u003e\n[`backdrop_arc::OffsetArc`]: \u003chttps://docs.rs/backdrop_arc/latest/backdrop_arc/struct.OffsetArc.html\u003e\n[`triomphe::Arc`]: \u003chttps://docs.rs/triomphe/latest/triomphe/struct.Arc.html\u003e\n[`triomphe::UniqueArc`]: \u003chttps://docs.rs/triomphe/latest/triomphe/struct.UniqueArc.html\u003e\n\n# Features\n\n- `backdrop_arc` supports no_std environments, as long as `alloc` is available, by disabling the (enabled by default) `std` feature.\n- `serde`: Enables serialization/deserialization with the [`serde`](https://crates.io/crates/serde) crate.\n- `stable_deref_trait`: Implements the `StableDeref` trait from the [`stable_deref_trait`](https://crates.io/crates/stable_deref_trait) crate for [`backdrop_arc::Arc`].\n- `arc-swap`: Use [`backdrop_arc::Arc`] together with the [`arc-swap`](https://crates.io/crates/arc-swap) crate.\n- `triomphe`: Convert (zero-cost) between [`triomphe::Arc`] \u003c-\u003e [`backdrop_arc::Arc`] (and [`backdrop_arc::UniqueArc`] \u003c-\u003e [`triomphe::UniqueArc`]).\n- `unsize` use [`backdrop_arc::Arc`] together with the [`unsize`](https://crates.io/crates/unsize) crate.\n- `yoke`: Implements the [`CloneableCart`](https://docs.rs/yoke/0.6.2/yoke/trait.CloneableCart.html) trait from the the [`yoke`](https://crates.io/crates/yoke) crate for [`backdrop_arc::Arc`], making it easier to use in zero-copy serialization scenarios.\n\n[`triomphe::Arc`]: \u003chttps://docs.rs/triomphe/latest/triomphe/struct.Arc.html\u003e\n[`triomphe::UniqueArc`]: \u003chttps://docs.rs/triomphe/latest/triomphe/struct.UniqueArc.html\u003e\n\n\n## Attribution\n\nThe source code of `backdrop_arc` is very heavily based on (and originally a fork of) [`triomphe`](https://crates.io/crates/triomphe),\nwhich itself originates from [`servo_arc`](https://crates.io/crates/servo_arc).\n\n## MSRV\n\nThe Minimum Supported Rust Version of backdrop_arc is Rust 1.56.1, because `backdrop` uses the edition 2021 Rust syntax.\nThere are no (required) Rust features or (required) dependencies besides `backdrop`, making this a very lightweight and portable crate.\n\n## Changelog\n\n- 0.3.0:\n  - Replace `Arc::clone_many` with a much more friendly implementation + signature, returning a new iterator type.\n- 0.2.0:\n  - Adds optional support for `yoke` (to use a `backdrop_arc::Arc` as a [`yoke::CloneableCart`](https://docs.rs/yoke/0.6.2/yoke/trait.CloneableCart.html)). Enable with the `yoke` feature.\n  - Adds `Arc::clone_many` and `Arc::clone_many_into_slice`, allowing you to clone an Arc many times at once with only a single atomic barrier.\n- 0.1.x: Initial version\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fqqwy%2Frust-backdrop_arc","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fqqwy%2Frust-backdrop_arc","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fqqwy%2Frust-backdrop_arc/lists"}