1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
// Quercus Video Editor - Non-Linear Video Editor
// Copyright (C) 2026 Quercus Team
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
//! The shared ABI value-handle type (single-lib unification).
//!
//! Every module crate used to define its own `CHandle` with an identical
//! `{ctx, addref, release, abi_version}` layout but a distinct Rust type,
//! so cross-module calls had to cross an `extern "C"`/dlsym boundary.
//! With the module-to-module calls going back to direct Rust calls (see
//! `docs/zh/plans/riir/single-lib.md`), one canonical handle type lives
//! here in `quercuscore-rs` (the crate every module already depends on) and
//! every crate re-exports it. The C layout is unchanged, so the frozen
//! module C ABIs (`Quercus<Mod><Type>*` handles in `include/<mod>/*.h`) are
//! unaffected.
use c_void;
/// ABI value handle mirroring the C handle struct
/// (`{ctx, addref, release, abi_version}`) from `include/common/handle.h`.
///
/// `ctx` points to an opaque refcounted box; `addref`/`release` are the
/// box's atomic increment/decrement (release destroys at zero);
/// `abi_version` is a tag stamped by each crate's `make_owned` (0 for
/// empty handles). Structurally identical to every `Quercus<Mod><Type>` value
/// handle, so a handle can cross any module boundary by value.
/// The empty handle is the natural default (some crates derive `Default`
/// on structs holding a handle).
// Handles follow the shared_ptr-like convention of
// `include/common/handle.h`: they are opaque, refcounted and safe to
// share across threads (the module crates use them behind mutexes).
unsafe
unsafe