Fix some typos in StructFlags

This commit is contained in:
hkalbasi 2023-04-23 21:55:47 +03:30
parent 2feabc4dc4
commit 232f293c19
5 changed files with 84 additions and 5 deletions

View file

@ -60,7 +60,7 @@ bitflags! {
/// Indicates whether this struct is `ManuallyDrop`.
const IS_MANUALLY_DROP = 1 << 6;
/// Indicates whether this struct is `UnsafeCell`.
const IS_UNSAFE_CELL = 1 << 6;
const IS_UNSAFE_CELL = 1 << 7;
}
}

View file

@ -7,7 +7,7 @@ use crate::db::HirDatabase;
pub fn is_box(db: &dyn HirDatabase, adt: AdtId) -> bool {
let AdtId::StructId(id) = adt else { return false };
db.struct_data(id).flags.contains(StructFlags::IS_UNSAFE_CELL)
db.struct_data(id).flags.contains(StructFlags::IS_BOX)
}
pub fn is_unsafe_cell(db: &dyn HirDatabase, adt: AdtId) -> bool {

View file

@ -3,8 +3,8 @@
use std::{fmt::Display, iter};
use crate::{
db::HirDatabase, infer::PointerCast, ClosureId, Const, ConstScalar, InferenceResult, Interner,
MemoryMap, Substitution, Ty, TyKind,
db::HirDatabase, display::HirDisplay, infer::PointerCast, lang_items::is_box, ClosureId, Const,
ConstScalar, InferenceResult, Interner, MemoryMap, Substitution, Ty, TyKind,
};
use chalk_ir::Mutability;
use hir_def::{
@ -115,8 +115,11 @@ impl<V, T> ProjectionElem<V, T> {
match self {
ProjectionElem::Deref => match &base.data(Interner).kind {
TyKind::Raw(_, inner) | TyKind::Ref(_, _, inner) => inner.clone(),
TyKind::Adt(adt, subst) if is_box(db, adt.0) => {
subst.at(Interner, 0).assert_ty_ref(Interner).clone()
}
_ => {
never!("Overloaded deref is not a projection");
never!("Overloaded deref on type {} is not a projection", base.display(db));
return TyKind::Error.intern(Interner);
}
},

View file

@ -1939,3 +1939,54 @@ fn foo() {
"#,
);
}
#[test]
fn box_deref_is_builtin() {
check(
r#"
//- minicore: deref
use core::ops::Deref;
#[lang = "owned_box"]
struct Box<T>(*mut T);
impl<T> Box<T> {
fn new(t: T) -> Self {
loop {}
}
}
impl<T> Deref for Box<T> {
type Target = T;
fn deref(&self) -> &Self::Target;
}
struct Foo;
impl Foo {
fn foo(&self) {}
}
fn test() {
Box::new(Foo).foo();
//^^^^^^^^^^^^^ adjustments: Deref(None), Borrow(Ref(Not))
}
"#,
);
}
#[test]
fn manually_drop_deref_is_not_builtin() {
check(
r#"
//- minicore: manually_drop, deref
struct Foo;
impl Foo {
fn foo(&self) {}
}
use core::mem::ManuallyDrop;
fn test() {
ManuallyDrop::new(Foo).foo();
//^^^^^^^^^^^^^^^^^^^^^^ adjustments: Deref(Some(OverloadedDeref(Some(Not)))), Borrow(Ref(Not))
}
"#,
);
}

View file

@ -31,6 +31,7 @@
//! infallible:
//! iterator: option
//! iterators: iterator, fn
//! manually_drop: drop
//! non_zero:
//! option: panic
//! ord: eq, option
@ -194,6 +195,30 @@ pub mod convert {
// region:drop
pub mod mem {
// region:manually_drop
#[lang = "manually_drop"]
#[repr(transparent)]
pub struct ManuallyDrop<T: ?Sized> {
value: T,
}
impl<T> ManuallyDrop<T> {
pub const fn new(value: T) -> ManuallyDrop<T> {
ManuallyDrop { value }
}
}
// region:deref
impl<T: ?Sized> crate::ops::Deref for ManuallyDrop<T> {
type Target = T;
fn deref(&self) -> &T {
&self.value
}
}
// endregion:deref
// endregion:manually_drop
pub fn drop<T>(_x: T) {}
}
// endregion:drop