133d722a9Sopenharmony_ci// Mangled symbol arrangements:
233d722a9Sopenharmony_ci//
333d722a9Sopenharmony_ci//   (a) One-off internal symbol.
433d722a9Sopenharmony_ci//          pattern:  {CXXBRIDGE} $ {NAME}
533d722a9Sopenharmony_ci//          examples:
633d722a9Sopenharmony_ci//             - cxxbridge1$exception
733d722a9Sopenharmony_ci//          defining characteristics:
833d722a9Sopenharmony_ci//             - 2 segments
933d722a9Sopenharmony_ci//             - starts with cxxbridge
1033d722a9Sopenharmony_ci//
1133d722a9Sopenharmony_ci//   (b) Behavior on a builtin binding without generic parameter.
1233d722a9Sopenharmony_ci//          pattern:  {CXXBRIDGE} $ {TYPE} $ {NAME}
1333d722a9Sopenharmony_ci//          examples:
1433d722a9Sopenharmony_ci//             - cxxbridge1$string$len
1533d722a9Sopenharmony_ci//          defining characteristics:
1633d722a9Sopenharmony_ci//             - 3 segments
1733d722a9Sopenharmony_ci//             - starts with cxxbridge
1833d722a9Sopenharmony_ci//
1933d722a9Sopenharmony_ci//   (c) Behavior on a builtin binding with generic parameter.
2033d722a9Sopenharmony_ci//          pattern:  {CXXBRIDGE} $ {TYPE} $ {PARAM...} $ {NAME}
2133d722a9Sopenharmony_ci//          examples:
2233d722a9Sopenharmony_ci//             - cxxbridge1$box$org$rust$Struct$alloc
2333d722a9Sopenharmony_ci//             - cxxbridge1$unique_ptr$std$vector$u8$drop
2433d722a9Sopenharmony_ci//          defining characteristics:
2533d722a9Sopenharmony_ci//             - 4+ segments
2633d722a9Sopenharmony_ci//             - starts with cxxbridge
2733d722a9Sopenharmony_ci//
2833d722a9Sopenharmony_ci//   (d) User-defined extern function.
2933d722a9Sopenharmony_ci//          pattern:  {NAMESPACE...} $ {CXXBRIDGE} $ {NAME}
3033d722a9Sopenharmony_ci//          examples:
3133d722a9Sopenharmony_ci//             - cxxbridge1$new_client
3233d722a9Sopenharmony_ci//             - org$rust$cxxbridge1$new_client
3333d722a9Sopenharmony_ci//          defining characteristics:
3433d722a9Sopenharmony_ci//             - cxxbridge is second from end
3533d722a9Sopenharmony_ci//          FIXME: conflict with (a) if they collide with one of our one-off symbol names in the global namespace
3633d722a9Sopenharmony_ci//
3733d722a9Sopenharmony_ci//   (e) User-defined extern member function.
3833d722a9Sopenharmony_ci//          pattern:  {NAMESPACE...} $ {CXXBRIDGE} $ {TYPE} $ {NAME}
3933d722a9Sopenharmony_ci//          examples:
4033d722a9Sopenharmony_ci//             - org$cxxbridge1$Struct$get
4133d722a9Sopenharmony_ci//          defining characteristics:
4233d722a9Sopenharmony_ci//             - cxxbridge is third from end
4333d722a9Sopenharmony_ci//          FIXME: conflict with (b) if e.g. user binds a type in global namespace that collides with our builtin type names
4433d722a9Sopenharmony_ci//
4533d722a9Sopenharmony_ci//   (f) Operator overload.
4633d722a9Sopenharmony_ci//          pattern:  {NAMESPACE...} $ {CXXBRIDGE} $ {TYPE} $ operator $ {NAME}
4733d722a9Sopenharmony_ci//          examples:
4833d722a9Sopenharmony_ci//             - org$rust$cxxbridge1$Struct$operator$eq
4933d722a9Sopenharmony_ci//          defining characteristics:
5033d722a9Sopenharmony_ci//             - second segment from end is `operator` (not possible in type or namespace names)
5133d722a9Sopenharmony_ci//
5233d722a9Sopenharmony_ci//   (g) Closure trampoline.
5333d722a9Sopenharmony_ci//          pattern:  {NAMESPACE...} $ {CXXBRIDGE} $ {TYPE?} $ {NAME} $ {ARGUMENT} $ {DIRECTION}
5433d722a9Sopenharmony_ci//          examples:
5533d722a9Sopenharmony_ci//             - org$rust$cxxbridge1$Struct$invoke$f$0
5633d722a9Sopenharmony_ci//          defining characteristics:
5733d722a9Sopenharmony_ci//             - last symbol is `0` (C half) or `1` (Rust half) which are not legal identifiers on their own
5833d722a9Sopenharmony_ci//
5933d722a9Sopenharmony_ci//
6033d722a9Sopenharmony_ci// Mangled preprocessor variable arrangements:
6133d722a9Sopenharmony_ci//
6233d722a9Sopenharmony_ci//   (A) One-off internal variable.
6333d722a9Sopenharmony_ci//          pattern:  {CXXBRIDGE} _ {NAME}
6433d722a9Sopenharmony_ci//          examples:
6533d722a9Sopenharmony_ci//             - CXXBRIDGE1_PANIC
6633d722a9Sopenharmony_ci//             - CXXBRIDGE1_RUST_STRING
6733d722a9Sopenharmony_ci//          defining characteristics:
6833d722a9Sopenharmony_ci//             - NAME does not begin with STRUCT or ENUM
6933d722a9Sopenharmony_ci//
7033d722a9Sopenharmony_ci//   (B) Guard around user-defined type.
7133d722a9Sopenharmony_ci//          pattern:  {CXXBRIDGE} _ {STRUCT or ENUM} _ {NAMESPACE...} $ {TYPE}
7233d722a9Sopenharmony_ci//          examples:
7333d722a9Sopenharmony_ci//             - CXXBRIDGE1_STRUCT_org$rust$Struct
7433d722a9Sopenharmony_ci//             - CXXBRIDGE1_ENUM_Enabled
7533d722a9Sopenharmony_ci
7633d722a9Sopenharmony_ciuse crate::syntax::symbol::{self, Symbol};
7733d722a9Sopenharmony_ciuse crate::syntax::{ExternFn, Pair, Types};
7833d722a9Sopenharmony_ci
7933d722a9Sopenharmony_ciconst CXXBRIDGE: &str = "cxxbridge1";
8033d722a9Sopenharmony_ci
8133d722a9Sopenharmony_cimacro_rules! join {
8233d722a9Sopenharmony_ci    ($($segment:expr),+ $(,)?) => {
8333d722a9Sopenharmony_ci        symbol::join(&[$(&$segment),+])
8433d722a9Sopenharmony_ci    };
8533d722a9Sopenharmony_ci}
8633d722a9Sopenharmony_ci
8733d722a9Sopenharmony_cipub fn extern_fn(efn: &ExternFn, types: &Types) -> Symbol {
8833d722a9Sopenharmony_ci    match &efn.receiver {
8933d722a9Sopenharmony_ci        Some(receiver) => {
9033d722a9Sopenharmony_ci            let receiver_ident = types.resolve(&receiver.ty);
9133d722a9Sopenharmony_ci            join!(
9233d722a9Sopenharmony_ci                efn.name.namespace,
9333d722a9Sopenharmony_ci                CXXBRIDGE,
9433d722a9Sopenharmony_ci                receiver_ident.name.cxx,
9533d722a9Sopenharmony_ci                efn.name.rust,
9633d722a9Sopenharmony_ci            )
9733d722a9Sopenharmony_ci        }
9833d722a9Sopenharmony_ci        None => join!(efn.name.namespace, CXXBRIDGE, efn.name.rust),
9933d722a9Sopenharmony_ci    }
10033d722a9Sopenharmony_ci}
10133d722a9Sopenharmony_ci
10233d722a9Sopenharmony_cipub fn operator(receiver: &Pair, operator: &'static str) -> Symbol {
10333d722a9Sopenharmony_ci    join!(
10433d722a9Sopenharmony_ci        receiver.namespace,
10533d722a9Sopenharmony_ci        CXXBRIDGE,
10633d722a9Sopenharmony_ci        receiver.cxx,
10733d722a9Sopenharmony_ci        "operator",
10833d722a9Sopenharmony_ci        operator,
10933d722a9Sopenharmony_ci    )
11033d722a9Sopenharmony_ci}
11133d722a9Sopenharmony_ci
11233d722a9Sopenharmony_ci// The C half of a function pointer trampoline.
11333d722a9Sopenharmony_cipub fn c_trampoline(efn: &ExternFn, var: &Pair, types: &Types) -> Symbol {
11433d722a9Sopenharmony_ci    join!(extern_fn(efn, types), var.rust, 0)
11533d722a9Sopenharmony_ci}
11633d722a9Sopenharmony_ci
11733d722a9Sopenharmony_ci// The Rust half of a function pointer trampoline.
11833d722a9Sopenharmony_cipub fn r_trampoline(efn: &ExternFn, var: &Pair, types: &Types) -> Symbol {
11933d722a9Sopenharmony_ci    join!(extern_fn(efn, types), var.rust, 1)
12033d722a9Sopenharmony_ci}
121