Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Merged by Bors] - Make Reflect safe to implement #5010

Closed
wants to merge 26 commits into from
Closed
Show file tree
Hide file tree
Changes from 5 commits
Commits
Show all changes
26 commits
Select commit Hold shift + click to select a range
9356871
Initial commit
PROMETHIA-27 Jun 14, 2022
c764de1
Made core changes to `Reflect`
PROMETHIA-27 Jun 14, 2022
9a71ebf
Updated impls until it compiles again
PROMETHIA-27 Jun 14, 2022
47e6802
Got tests compiling and passing
PROMETHIA-27 Jun 14, 2022
479e63d
Added downcast test
PROMETHIA-27 Jun 14, 2022
ff804f7
Remove missed safety comment
PROMETHIA-27 Jun 14, 2022
4611cc9
Updated example to use `Reflect::type_id()`
PROMETHIA-27 Jun 14, 2022
1916a2f
Type ID -> `TypeId`
PROMETHIA-27 Jun 14, 2022
4bcfc1f
Made type_id() impl default
PROMETHIA-27 Jun 14, 2022
2a7d0f0
Removed unused imports
PROMETHIA-27 Jun 14, 2022
6a04778
Type Name -> type name
PROMETHIA-27 Jun 17, 2022
cad5074
Merge branch 'bevyengine:main' into make-reflect-safe
PROMETHIA-27 Jun 21, 2022
05d01f9
change to better naming scheme
PROMETHIA-27 Jun 21, 2022
1073a84
Merge branch 'make-reflect-safe' of https://github.com/PROMETHIA-27/b…
PROMETHIA-27 Jun 21, 2022
48803b3
fixing ambiguities
PROMETHIA-27 Jun 21, 2022
e79a8c3
Remove unnecessary TypeId imports
PROMETHIA-27 Jun 21, 2022
bde44f2
Add `represents` method to `dyn Reflect`
PROMETHIA-27 Jun 26, 2022
ced94c7
underlying_type_id -> type_id
PROMETHIA-27 Jun 26, 2022
4df85c4
Merge branch 'bevyengine:main' into make-reflect-safe
PROMETHIA-27 Jun 26, 2022
03c97b4
Merge branch 'make-reflect-safe' of https://github.com/PROMETHIA-27/b…
PROMETHIA-27 Jun 26, 2022
cec23c0
Fix slightly broken test
PROMETHIA-27 Jun 26, 2022
2ae01fb
Un-fixing broken test
PROMETHIA-27 Jun 26, 2022
481823f
underlying_type_id -> type_id
PROMETHIA-27 Jun 26, 2022
29a9379
Doc links
PROMETHIA-27 Jun 27, 2022
7b66ee8
as_mut_any -> as_any_mut
PROMETHIA-27 Jun 27, 2022
2f557c1
Removed invalid doc links
PROMETHIA-27 Jun 27, 2022
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -213,7 +213,7 @@ impl ReflectTraits {
match &self.partial_eq {
TraitImpl::Implemented => Some(quote! {
fn reflect_partial_eq(&self, value: &dyn #bevy_reflect_path::Reflect) -> Option<bool> {
let value = value.any();
let value = value.any_ref();
if let Some(value) = value.downcast_ref::<Self>() {
Some(std::cmp::PartialEq::eq(self, value))
} else {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ pub(crate) fn impl_value(
TokenStream::from(quote! {
impl #impl_generics #bevy_reflect_path::FromReflect for #type_name #ty_generics #where_clause {
fn from_reflect(reflect: &dyn #bevy_reflect_path::Reflect) -> Option<Self> {
Some(reflect.any().downcast_ref::<#type_name #ty_generics>()?.clone())
Some(reflect.any_ref().downcast_ref::<#type_name #ty_generics>()?.clone())
}
}
})
Expand Down
49 changes: 39 additions & 10 deletions crates/bevy_reflect/bevy_reflect_derive/src/impls.rs
Original file line number Diff line number Diff line change
Expand Up @@ -126,22 +126,32 @@ pub(crate) fn impl_struct(derive_data: &ReflectDeriveData) -> TokenStream {
}
}

// SAFE: any and any_mut both return self
unsafe impl #impl_generics #bevy_reflect_path::Reflect for #struct_name #ty_generics #where_clause {
impl #impl_generics #bevy_reflect_path::Reflect for #struct_name #ty_generics #where_clause {
#[inline]
fn type_name(&self) -> &str {
std::any::type_name::<Self>()
}

#[inline]
fn type_id(&self) -> std::any::TypeId {
std::any::TypeId::of::<Self>()
}

#[inline]
fn get_type_info(&self) -> &'static #bevy_reflect_path::TypeInfo {
<Self as #bevy_reflect_path::Typed>::type_info()
}

#[inline]
fn any(&self) -> &dyn std::any::Any {
fn any(self: Box<Self>) -> Box<dyn std::any::Any> {
self
}

#[inline]
fn any_ref(&self) -> &dyn std::any::Any {
self
}

#[inline]
fn any_mut(&mut self) -> &mut dyn std::any::Any {
self
Expand Down Expand Up @@ -279,22 +289,32 @@ pub(crate) fn impl_tuple_struct(derive_data: &ReflectDeriveData) -> TokenStream
}
}

// SAFE: any and any_mut both return self
unsafe impl #impl_generics #bevy_reflect_path::Reflect for #struct_name #ty_generics #where_clause {
impl #impl_generics #bevy_reflect_path::Reflect for #struct_name #ty_generics #where_clause {
#[inline]
fn type_name(&self) -> &str {
std::any::type_name::<Self>()
}

#[inline]
fn type_id(&self) -> std::any::TypeId {
std::any::TypeId::of::<Self>()
}

#[inline]
fn get_type_info(&self) -> &'static #bevy_reflect_path::TypeInfo {
<Self as #bevy_reflect_path::Typed>::type_info()
}

#[inline]
fn any(&self) -> &dyn std::any::Any {
fn any(self: Box<Self>) -> Box<dyn std::any::Any> {
self
}

#[inline]
fn any_ref(&self) -> &dyn std::any::Any {
self
}

#[inline]
fn any_mut(&mut self) -> &mut dyn std::any::Any {
self
Expand Down Expand Up @@ -379,20 +399,29 @@ pub(crate) fn impl_value(

#typed_impl

// SAFE: any and any_mut both return self
unsafe impl #impl_generics #bevy_reflect_path::Reflect for #type_name #ty_generics #where_clause {
impl #impl_generics #bevy_reflect_path::Reflect for #type_name #ty_generics #where_clause {
#[inline]
fn type_name(&self) -> &str {
std::any::type_name::<Self>()
}

#[inline]
fn type_id(&self) -> std::any::TypeId {
std::any::TypeId::of::<Self>()
}

#[inline]
fn get_type_info(&self) -> &'static #bevy_reflect_path::TypeInfo {
<Self as #bevy_reflect_path::Typed>::type_info()
}

#[inline]
fn any(&self) -> &dyn std::any::Any {
fn any(self: Box<Self>) -> Box<dyn std::any::Any> {
self
}

#[inline]
fn any_ref(&self) -> &dyn std::any::Any {
self
}

Expand All @@ -418,7 +447,7 @@ pub(crate) fn impl_value(

#[inline]
fn apply(&mut self, value: &dyn #bevy_reflect_path::Reflect) {
let value = value.any();
let value = value.any_ref();
if let Some(value) = value.downcast_ref::<Self>() {
*self = value.clone();
} else {
Expand Down
15 changes: 12 additions & 3 deletions crates/bevy_reflect/src/array.rs
Original file line number Diff line number Diff line change
Expand Up @@ -152,20 +152,29 @@ impl DynamicArray {
}
}

// SAFE: any and any_mut both return self
unsafe impl Reflect for DynamicArray {
impl Reflect for DynamicArray {
#[inline]
fn type_name(&self) -> &str {
self.name.as_str()
}

#[inline]
fn type_id(&self) -> TypeId {
TypeId::of::<Self>()
}

#[inline]
fn get_type_info(&self) -> &'static TypeInfo {
<Self as Typed>::type_info()
}

#[inline]
fn any(&self) -> &dyn Any {
fn any(self: Box<Self>) -> Box<dyn Any> {
self
}

#[inline]
fn any_ref(&self) -> &dyn Any {
self
}

Expand Down
15 changes: 11 additions & 4 deletions crates/bevy_reflect/src/impls/smallvec.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
use smallvec::SmallVec;
use std::any::Any;
use std::any::{Any, TypeId};

use crate::utility::GenericTypeInfoCell;
use crate::{
Expand Down Expand Up @@ -55,20 +55,27 @@ where
}
}

// SAFE: any and any_mut both return self
unsafe impl<T: smallvec::Array + Send + Sync + 'static> Reflect for SmallVec<T>
impl<T: smallvec::Array + Send + Sync + 'static> Reflect for SmallVec<T>
where
T::Item: FromReflect + Clone,
{
fn type_name(&self) -> &str {
std::any::type_name::<Self>()
}

fn type_id(&self) -> TypeId {
TypeId::of::<Self>()
}

fn get_type_info(&self) -> &'static TypeInfo {
<Self as Typed>::type_info()
}

fn any(&self) -> &dyn Any {
fn any(self: Box<Self>) -> Box<dyn Any> {
self
}

fn any_ref(&self) -> &dyn Any {
self
}

Expand Down
66 changes: 51 additions & 15 deletions crates/bevy_reflect/src/impls/std.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ use bevy_reflect_derive::{impl_from_reflect_value, impl_reflect_value};
use bevy_utils::{Duration, HashMap, HashSet};
use serde::{Deserialize, Serialize};
use std::{
any::Any,
any::{Any, TypeId},
borrow::Cow,
hash::{Hash, Hasher},
ops::Range,
Expand Down Expand Up @@ -106,16 +106,24 @@ impl<T: FromReflect> List for Vec<T> {
}

// SAFE: any and any_mut both return self
PROMETHIA-27 marked this conversation as resolved.
Show resolved Hide resolved
unsafe impl<T: FromReflect> Reflect for Vec<T> {
impl<T: FromReflect> Reflect for Vec<T> {
fn type_name(&self) -> &str {
std::any::type_name::<Self>()
}

fn type_id(&self) -> TypeId {
TypeId::of::<Self>()
}

fn get_type_info(&self) -> &'static TypeInfo {
<Self as Typed>::type_info()
}

fn any(&self) -> &dyn Any {
fn any(self: Box<Self>) -> Box<dyn Any> {
self
}

fn any_ref(&self) -> &dyn Any {
self
}

Expand Down Expand Up @@ -234,17 +242,24 @@ impl<K: Reflect + Eq + Hash, V: Reflect> Map for HashMap<K, V> {
}
}

// SAFE: any and any_mut both return self
unsafe impl<K: Reflect + Eq + Hash, V: Reflect> Reflect for HashMap<K, V> {
impl<K: Reflect + Eq + Hash, V: Reflect> Reflect for HashMap<K, V> {
fn type_name(&self) -> &str {
std::any::type_name::<Self>()
}

fn type_id(&self) -> TypeId {
TypeId::of::<Self>()
}

fn get_type_info(&self) -> &'static TypeInfo {
<Self as Typed>::type_info()
}

fn any(&self) -> &dyn Any {
fn any(self: Box<Self>) -> Box<dyn Any> {
self
}

fn any_ref(&self) -> &dyn Any {
self
}

Expand Down Expand Up @@ -354,19 +369,28 @@ impl<T: Reflect, const N: usize> Array for [T; N] {
}
}

// SAFE: any and any_mut both return self
unsafe impl<T: Reflect, const N: usize> Reflect for [T; N] {
impl<T: Reflect, const N: usize> Reflect for [T; N] {
#[inline]
fn type_name(&self) -> &str {
std::any::type_name::<Self>()
}

#[inline]
fn type_id(&self) -> TypeId {
TypeId::of::<Self>()
}

fn get_type_info(&self) -> &'static TypeInfo {
<Self as Typed>::type_info()
}

#[inline]
fn any(&self) -> &dyn Any {
fn any(self: Box<Self>) -> Box<dyn Any> {
self
}

#[inline]
fn any_ref(&self) -> &dyn Any {
self
}

Expand Down Expand Up @@ -474,17 +498,24 @@ impl_array_get_type_registration! {
30 31 32
}

// SAFE: any and any_mut both return self
unsafe impl Reflect for Cow<'static, str> {
impl Reflect for Cow<'static, str> {
fn type_name(&self) -> &str {
std::any::type_name::<Self>()
}

fn type_id(&self) -> TypeId {
TypeId::of::<Self>()
}

fn get_type_info(&self) -> &'static TypeInfo {
<Self as Typed>::type_info()
}

fn any(&self) -> &dyn Any {
fn any(self: Box<Self>) -> Box<dyn Any> {
self
}

fn any_ref(&self) -> &dyn Any {
self
}

Expand All @@ -501,7 +532,7 @@ unsafe impl Reflect for Cow<'static, str> {
}

fn apply(&mut self, value: &dyn Reflect) {
let value = value.any();
let value = value.any_ref();
if let Some(value) = value.downcast_ref::<Self>() {
*self = value.clone();
} else {
Expand Down Expand Up @@ -534,7 +565,7 @@ unsafe impl Reflect for Cow<'static, str> {
}

fn reflect_partial_eq(&self, value: &dyn Reflect) -> Option<bool> {
let value = value.any();
let value = value.any_ref();
if let Some(value) = value.downcast_ref::<Self>() {
Some(std::cmp::PartialEq::eq(self, value))
} else {
Expand Down Expand Up @@ -564,7 +595,12 @@ impl GetTypeRegistration for Cow<'static, str> {

impl FromReflect for Cow<'static, str> {
fn from_reflect(reflect: &dyn crate::Reflect) -> Option<Self> {
Some(reflect.any().downcast_ref::<Cow<'static, str>>()?.clone())
Some(
reflect
.any_ref()
.downcast_ref::<Cow<'static, str>>()?
.clone(),
)
}
}

Expand Down
Loading