Skip to content

Commit b807286

Browse files
authored
Streamline GetOwnership/FromArg/IntoReturn (#20126)
# Objective Three impls are generated for each of these traits when the `reflect_functions` feature is enabled. Helps with #19873. ## Solution Two of the three (the `&T` and `&mut T` ones) can be avoided by instead providing blanket impls. The impl for `T` remains. ## Testing I checked the output via `cargo expand`. According to `-Zmacro-stats`, the size of the `Reflect` code generate for `bevy_ui` drops by 10.4%.
1 parent 2a5e9c1 commit b807286

File tree

10 files changed

+113
-223
lines changed

10 files changed

+113
-223
lines changed

crates/bevy_reflect/derive/src/impls/func/from_arg.rs

Lines changed: 3 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -13,23 +13,11 @@ pub(crate) fn impl_from_arg(where_clause_options: &WhereClauseOptions) -> proc_m
1313
quote! {
1414
impl #impl_generics #bevy_reflect::func::args::FromArg for #type_path #ty_generics #where_reflect_clause {
1515
type This<'from_arg> = #type_path #ty_generics;
16-
fn from_arg(arg: #bevy_reflect::func::args::Arg) -> #FQResult<Self::This<'_>, #bevy_reflect::func::args::ArgError> {
16+
fn from_arg(arg: #bevy_reflect::func::args::Arg) ->
17+
#FQResult<Self::This<'_>, #bevy_reflect::func::args::ArgError>
18+
{
1719
arg.take_owned()
1820
}
1921
}
20-
21-
impl #impl_generics #bevy_reflect::func::args::FromArg for &'static #type_path #ty_generics #where_reflect_clause {
22-
type This<'from_arg> = &'from_arg #type_path #ty_generics;
23-
fn from_arg(arg: #bevy_reflect::func::args::Arg) -> #FQResult<Self::This<'_>, #bevy_reflect::func::args::ArgError> {
24-
arg.take_ref()
25-
}
26-
}
27-
28-
impl #impl_generics #bevy_reflect::func::args::FromArg for &'static mut #type_path #ty_generics #where_reflect_clause {
29-
type This<'from_arg> = &'from_arg mut #type_path #ty_generics;
30-
fn from_arg(arg: #bevy_reflect::func::args::Arg) -> #FQResult<Self::This<'_>, #bevy_reflect::func::args::ArgError> {
31-
arg.take_mut()
32-
}
33-
}
3422
}
3523
}

crates/bevy_reflect/derive/src/impls/func/get_ownership.rs

Lines changed: 0 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -17,17 +17,5 @@ pub(crate) fn impl_get_ownership(
1717
#bevy_reflect::func::args::Ownership::Owned
1818
}
1919
}
20-
21-
impl #impl_generics #bevy_reflect::func::args::GetOwnership for &'_ #type_path #ty_generics #where_reflect_clause {
22-
fn ownership() -> #bevy_reflect::func::args::Ownership {
23-
#bevy_reflect::func::args::Ownership::Ref
24-
}
25-
}
26-
27-
impl #impl_generics #bevy_reflect::func::args::GetOwnership for &'_ mut #type_path #ty_generics #where_reflect_clause {
28-
fn ownership() -> #bevy_reflect::func::args::Ownership {
29-
#bevy_reflect::func::args::Ownership::Mut
30-
}
31-
}
3220
}
3321
}

crates/bevy_reflect/derive/src/impls/func/into_return.rs

Lines changed: 3 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -13,21 +13,11 @@ pub(crate) fn impl_into_return(
1313

1414
quote! {
1515
impl #impl_generics #bevy_reflect::func::IntoReturn for #type_path #ty_generics #where_reflect_clause {
16-
fn into_return<'into_return>(self) -> #bevy_reflect::func::Return<'into_return> where Self: 'into_return {
16+
fn into_return<'into_return>(self) -> #bevy_reflect::func::Return<'into_return>
17+
where Self: 'into_return
18+
{
1719
#bevy_reflect::func::Return::Owned(#bevy_reflect::__macro_exports::alloc_utils::Box::new(self))
1820
}
1921
}
20-
21-
impl #impl_generics #bevy_reflect::func::IntoReturn for &#type_path #ty_generics #where_reflect_clause {
22-
fn into_return<'into_return>(self) -> #bevy_reflect::func::Return<'into_return> where Self: 'into_return {
23-
#bevy_reflect::func::Return::Ref(self)
24-
}
25-
}
26-
27-
impl #impl_generics #bevy_reflect::func::IntoReturn for &mut #type_path #ty_generics #where_reflect_clause {
28-
fn into_return<'into_return>(self) -> #bevy_reflect::func::Return<'into_return> where Self: 'into_return {
29-
#bevy_reflect::func::Return::Mut(self)
30-
}
31-
}
3222
}
3323
}

crates/bevy_reflect/src/func/args/from_arg.rs

Lines changed: 28 additions & 43 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,17 @@
11
use crate::func::args::{Arg, ArgError};
2+
use crate::{Reflect, TypePath};
23

34
/// A trait for types that can be created from an [`Arg`].
45
///
56
/// This trait exists so that types can be automatically converted into an [`Arg`]
6-
/// so they can be put into an [`ArgList`] and passed to a [`DynamicFunction`] or [`DynamicFunctionMut`].
7+
/// so they can be put into an [`ArgList`] and passed to a [`DynamicFunction`] or
8+
/// [`DynamicFunctionMut`].
79
///
810
/// This trait is used instead of a blanket [`From`] implementation due to coherence issues:
911
/// we can't implement `From<T>` for both `T` and `&T`/`&mut T`.
1012
///
11-
/// This trait is automatically implemented when using the `Reflect` [derive macro].
13+
/// This trait is automatically implemented for non-reference types when using the `Reflect`
14+
/// [derive macro]. Blanket impls cover `&T` and `&mut T`.
1215
///
1316
/// [`ArgList`]: crate::func::args::ArgList
1417
/// [`DynamicFunction`]: crate::func::DynamicFunction
@@ -29,6 +32,22 @@ pub trait FromArg {
2932
fn from_arg(arg: Arg) -> Result<Self::This<'_>, ArgError>;
3033
}
3134

35+
// Blanket impl.
36+
impl<T: Reflect + TypePath> FromArg for &'static T {
37+
type This<'a> = &'a T;
38+
fn from_arg(arg: Arg) -> Result<Self::This<'_>, ArgError> {
39+
arg.take_ref()
40+
}
41+
}
42+
43+
// Blanket impl.
44+
impl<T: Reflect + TypePath> FromArg for &'static mut T {
45+
type This<'a> = &'a mut T;
46+
fn from_arg(arg: Arg) -> Result<Self::This<'_>, ArgError> {
47+
arg.take_mut()
48+
}
49+
}
50+
3251
/// Implements the [`FromArg`] trait for the given type.
3352
///
3453
/// This will implement it for `$ty`, `&$ty`, and `&mut $ty`.
@@ -40,64 +59,30 @@ macro_rules! impl_from_arg {
4059
(
4160
$ty: ty
4261
$(;
43-
<
44-
$($T: ident $(: $T1: tt $(+ $T2: tt)*)?),*
45-
>
62+
< $($T: ident $(: $T1: tt $(+ $T2: tt)*)?),* >
4663
)?
4764
$(
48-
[
49-
$(const $N: ident : $size: ident),*
50-
]
65+
[ $(const $N: ident : $size: ident),* ]
5166
)?
5267
$(
53-
where
54-
$($U: ty $(: $U1: tt $(+ $U2: tt)*)?),*
68+
where $($U: ty $(: $U1: tt $(+ $U2: tt)*)?),*
5569
)?
5670
) => {
5771
impl <
5872
$($($T $(: $T1 $(+ $T2)*)?),*)?
5973
$(, $(const $N : $size),*)?
6074
> $crate::func::args::FromArg for $ty
6175
$(
62-
where
63-
$($U $(: $U1 $(+ $U2)*)?),*
76+
where $($U $(: $U1 $(+ $U2)*)?),*
6477
)?
6578
{
6679
type This<'from_arg> = $ty;
67-
fn from_arg(arg: $crate::func::args::Arg) -> Result<Self::This<'_>, $crate::func::args::ArgError> {
80+
fn from_arg(arg: $crate::func::args::Arg) ->
81+
Result<Self::This<'_>, $crate::func::args::ArgError>
82+
{
6883
arg.take_owned()
6984
}
7085
}
71-
72-
impl <
73-
$($($T $(: $T1 $(+ $T2)*)?),*)?
74-
$(, $(const $N : $size),*)?
75-
> $crate::func::args::FromArg for &'static $ty
76-
$(
77-
where
78-
$($U $(: $U1 $(+ $U2)*)?),*
79-
)?
80-
{
81-
type This<'from_arg> = &'from_arg $ty;
82-
fn from_arg(arg: $crate::func::args::Arg) -> Result<Self::This<'_>, $crate::func::args::ArgError> {
83-
arg.take_ref()
84-
}
85-
}
86-
87-
impl <
88-
$($($T $(: $T1 $(+ $T2)*)?),*)?
89-
$(, $(const $N : $size),*)?
90-
> $crate::func::args::FromArg for &'static mut $ty
91-
$(
92-
where
93-
$($U $(: $U1 $(+ $U2)*)?),*
94-
)?
95-
{
96-
type This<'from_arg> = &'from_arg mut $ty;
97-
fn from_arg(arg: $crate::func::args::Arg) -> Result<Self::This<'_>, $crate::func::args::ArgError> {
98-
arg.take_mut()
99-
}
100-
}
10186
};
10287
}
10388

crates/bevy_reflect/src/func/args/ownership.rs

Lines changed: 38 additions & 59 deletions
Original file line numberDiff line numberDiff line change
@@ -1,21 +1,5 @@
11
use core::fmt::{Display, Formatter};
22

3-
/// A trait for getting the ownership of a type.
4-
///
5-
/// This trait exists so that [`TypedFunction`] can automatically generate
6-
/// [`FunctionInfo`] containing the proper [`Ownership`] for its [argument] types.
7-
///
8-
/// This trait is automatically implemented when using the `Reflect` [derive macro].
9-
///
10-
/// [`TypedFunction`]: crate::func::TypedFunction
11-
/// [`FunctionInfo`]: crate::func::FunctionInfo
12-
/// [argument]: crate::func::args::Arg
13-
/// [derive macro]: derive@crate::Reflect
14-
pub trait GetOwnership {
15-
/// Returns the ownership of [`Self`].
16-
fn ownership() -> Ownership;
17-
}
18-
193
/// The ownership of a type.
204
#[derive(Debug, Copy, Clone, PartialEq, Eq)]
215
pub enum Ownership {
@@ -37,6 +21,39 @@ impl Display for Ownership {
3721
}
3822
}
3923

24+
/// A trait for getting the ownership of a type.
25+
///
26+
/// This trait exists so that [`TypedFunction`] can automatically generate
27+
/// [`FunctionInfo`] containing the proper [`Ownership`] for its [argument] types.
28+
///
29+
/// This trait is automatically implemented for non-reference types when using the `Reflect`
30+
/// [derive macro]. Blanket impls cover `&T` and `&mut T`.
31+
///
32+
/// [`TypedFunction`]: crate::func::TypedFunction
33+
/// [`FunctionInfo`]: crate::func::FunctionInfo
34+
/// [argument]: crate::func::args::Arg
35+
/// [derive macro]: derive@crate::Reflect
36+
pub trait GetOwnership {
37+
/// Returns the ownership of [`Self`].
38+
fn ownership() -> Ownership {
39+
Ownership::Owned
40+
}
41+
}
42+
43+
// Blanket impl.
44+
impl<T> GetOwnership for &'_ T {
45+
fn ownership() -> Ownership {
46+
Ownership::Ref
47+
}
48+
}
49+
50+
// Blanket impl.
51+
impl<T> GetOwnership for &'_ mut T {
52+
fn ownership() -> Ownership {
53+
Ownership::Mut
54+
}
55+
}
56+
4057
/// Implements the [`GetOwnership`] trait for the given type.
4158
///
4259
/// This will implement it for `$ty`, `&$ty`, and `&mut $ty`.
@@ -48,61 +65,23 @@ macro_rules! impl_get_ownership {
4865
(
4966
$ty: ty
5067
$(;
51-
<
52-
$($T: ident $(: $T1: tt $(+ $T2: tt)*)?),*
53-
>
68+
< $($T: ident $(: $T1: tt $(+ $T2: tt)*)?),* >
5469
)?
5570
$(
56-
[
57-
$(const $N: ident : $size: ident),*
58-
]
71+
[ $(const $N: ident : $size: ident),* ]
5972
)?
6073
$(
61-
where
62-
$($U: ty $(: $U1: tt $(+ $U2: tt)*)?),*
74+
where $($U: ty $(: $U1: tt $(+ $U2: tt)*)?),*
6375
)?
6476
) => {
6577
impl <
6678
$($($T $(: $T1 $(+ $T2)*)?),*)?
6779
$(, $(const $N : $size),*)?
6880
> $crate::func::args::GetOwnership for $ty
6981
$(
70-
where
71-
$($U $(: $U1 $(+ $U2)*)?),*
82+
where $($U $(: $U1 $(+ $U2)*)?),*
7283
)?
73-
{
74-
fn ownership() -> $crate::func::args::Ownership {
75-
$crate::func::args::Ownership::Owned
76-
}
77-
}
78-
79-
impl <
80-
$($($T $(: $T1 $(+ $T2)*)?),*)?
81-
$(, $(const $N : $size),*)?
82-
> $crate::func::args::GetOwnership for &'_ $ty
83-
$(
84-
where
85-
$($U $(: $U1 $(+ $U2)*)?),*
86-
)?
87-
{
88-
fn ownership() -> $crate::func::args::Ownership {
89-
$crate::func::args::Ownership::Ref
90-
}
91-
}
92-
93-
impl <
94-
$($($T $(: $T1 $(+ $T2)*)?),*)?
95-
$(, $(const $N : $size),*)?
96-
> $crate::func::args::GetOwnership for &'_ mut $ty
97-
$(
98-
where
99-
$($U $(: $U1 $(+ $U2)*)?),*
100-
)?
101-
{
102-
fn ownership() -> $crate::func::args::Ownership {
103-
$crate::func::args::Ownership::Mut
104-
}
105-
}
84+
{}
10685
};
10786
}
10887

crates/bevy_reflect/src/func/macros.rs

Lines changed: 12 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -28,69 +28,49 @@ macro_rules! impl_function_traits {
2828
(
2929
$ty: ty
3030
$(;
31-
<
32-
$($T: ident $(: $T1: tt $(+ $T2: tt)*)?),*
33-
>
31+
< $($T: ident $(: $T1: tt $(+ $T2: tt)*)?),* >
3432
)?
3533
$(
36-
[
37-
$(const $N: ident : $size: ident),*
38-
]
34+
[ $(const $N: ident : $size: ident),* ]
3935
)?
4036
$(
41-
where
42-
$($U: ty $(: $U1: tt $(+ $U2: tt)*)?),*
37+
where $($U: ty $(: $U1: tt $(+ $U2: tt)*)?),*
4338
)?
4439
) => {
4540
$crate::func::args::impl_get_ownership!(
4641
$ty
4742
$(;
48-
<
49-
$($T $(: $T1 $(+ $T2)*)?),*
50-
>
43+
< $($T $(: $T1 $(+ $T2)*)?),* >
5144
)?
5245
$(
53-
[
54-
$(const $N : $size),*
55-
]
46+
[ $(const $N : $size),* ]
5647
)?
5748
$(
58-
where
59-
$($U $(: $U1 $(+ $U2)*)?),*
49+
where $($U $(: $U1 $(+ $U2)*)?),*
6050
)?
6151
);
6252
$crate::func::args::impl_from_arg!(
6353
$ty
6454
$(;
65-
<
66-
$($T $(: $T1 $(+ $T2)*)?),*
67-
>
55+
< $($T $(: $T1 $(+ $T2)*)?),* >
6856
)?
6957
$(
70-
[
71-
$(const $N : $size),*
72-
]
58+
[ $(const $N : $size),* ]
7359
)?
7460
$(
75-
where
76-
$($U $(: $U1 $(+ $U2)*)?),*
61+
where $($U $(: $U1 $(+ $U2)*)?),*
7762
)?
7863
);
7964
$crate::func::impl_into_return!(
8065
$ty
8166
$(;
82-
<
83-
$($T $(: $T1 $(+ $T2)*)?),*
84-
>
67+
< $($T $(: $T1 $(+ $T2)*)?),* >
8568
)?
8669
$(
87-
[
88-
$(const $N : $size),*
89-
]
70+
[ $(const $N : $size),* ]
9071
)?
9172
$(
92-
where
93-
$($U $(: $U1 $(+ $U2)*)?),*
73+
where $($U $(: $U1 $(+ $U2)*)?),*
9474
)?
9575
);
9676
};

0 commit comments

Comments
 (0)