Skip to content
This repository was archived by the owner on May 28, 2025. It is now read-only.

Commit 610eafe

Browse files
committed
Merge commit '76633199f4316b9c659d4ec0c102774d693cd940' into sync-from-rust
2 parents d45ff24 + 7663319 commit 610eafe

File tree

7 files changed

+147
-32
lines changed

7 files changed

+147
-32
lines changed

crates/hir-def/src/import_map.rs

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -111,7 +111,11 @@ fn collect_import_map(db: &dyn DefDatabase, krate: CrateId) -> FxIndexMap<ItemIn
111111

112112
let visible_items = mod_data.scope.entries().filter_map(|(name, per_ns)| {
113113
let per_ns = per_ns.filter_visibility(|vis| vis == Visibility::Public);
114-
if per_ns.is_none() { None } else { Some((name, per_ns)) }
114+
if per_ns.is_none() {
115+
None
116+
} else {
117+
Some((name, per_ns))
118+
}
115119
});
116120

117121
for (name, per_ns) in visible_items {

crates/hir-ty/src/chalk_ext.rs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@ pub trait TyExt {
2828
fn is_unknown(&self) -> bool;
2929
fn contains_unknown(&self) -> bool;
3030
fn is_ty_var(&self) -> bool;
31+
fn is_union(&self) -> bool;
3132

3233
fn as_adt(&self) -> Option<(hir_def::AdtId, &Substitution)>;
3334
fn as_builtin(&self) -> Option<BuiltinType>;
@@ -96,6 +97,10 @@ impl TyExt for Ty {
9697
matches!(self.kind(Interner), TyKind::InferenceVar(_, _))
9798
}
9899

100+
fn is_union(&self) -> bool {
101+
matches!(self.adt_id(Interner), Some(AdtId(hir_def::AdtId::UnionId(_))))
102+
}
103+
99104
fn as_adt(&self) -> Option<(hir_def::AdtId, &Substitution)> {
100105
match self.kind(Interner) {
101106
TyKind::Adt(AdtId(adt), parameters) => Some((*adt, parameters)),

crates/hir-ty/src/infer/closure.rs

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -735,6 +735,32 @@ impl InferenceContext<'_> {
735735
self.walk_expr(expr);
736736
}
737737

738+
fn restrict_precision_for_unsafe(&mut self) {
739+
for capture in &mut self.current_captures {
740+
let mut ty = self.table.resolve_completely(self.result[capture.place.local].clone());
741+
if ty.as_raw_ptr().is_some() || ty.is_union() {
742+
capture.kind = CaptureKind::ByRef(BorrowKind::Shared);
743+
capture.place.projections.truncate(0);
744+
continue;
745+
}
746+
for (i, p) in capture.place.projections.iter().enumerate() {
747+
ty = p.projected_ty(
748+
ty,
749+
self.db,
750+
|_, _, _| {
751+
unreachable!("Closure field only happens in MIR");
752+
},
753+
self.owner.module(self.db.upcast()).krate(),
754+
);
755+
if ty.as_raw_ptr().is_some() || ty.is_union() {
756+
capture.kind = CaptureKind::ByRef(BorrowKind::Shared);
757+
capture.place.projections.truncate(i + 1);
758+
break;
759+
}
760+
}
761+
}
762+
}
763+
738764
fn adjust_for_move_closure(&mut self) {
739765
for capture in &mut self.current_captures {
740766
if let Some(first_deref) =
@@ -924,6 +950,7 @@ impl InferenceContext<'_> {
924950
self.result.mutated_bindings_in_closure.insert(item.place.local);
925951
}
926952
}
953+
self.restrict_precision_for_unsafe();
927954
// closure_kind should be done before adjust_for_move_closure
928955
let closure_kind = self.closure_kind();
929956
match capture_by {

crates/hir/src/display.rs

Lines changed: 58 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
//! HirDisplay implementations for various hir types.
22
use hir_def::{
3-
data::adt::VariantData,
3+
data::adt::{StructKind, VariantData},
44
generics::{
55
TypeOrConstParamData, TypeParamProvenance, WherePredicate, WherePredicateTypeTarget,
66
},
@@ -163,7 +163,40 @@ impl HirDisplay for Struct {
163163
write!(f, "{}", self.name(f.db).display(f.db.upcast()))?;
164164
let def_id = GenericDefId::AdtId(AdtId::StructId(self.id));
165165
write_generic_params(def_id, f)?;
166+
167+
let variant_data = self.variant_data(f.db);
168+
if let StructKind::Tuple = variant_data.kind() {
169+
f.write_char('(')?;
170+
let mut it = variant_data.fields().iter().peekable();
171+
172+
while let Some((id, _)) = it.next() {
173+
let field = Field { parent: (*self).into(), id };
174+
field.ty(f.db).hir_fmt(f)?;
175+
if it.peek().is_some() {
176+
f.write_str(", ")?;
177+
}
178+
}
179+
180+
f.write_str(");")?;
181+
}
182+
166183
write_where_clause(def_id, f)?;
184+
185+
if let StructKind::Record = variant_data.kind() {
186+
let fields = self.fields(f.db);
187+
if fields.is_empty() {
188+
f.write_str(" {}")?;
189+
} else {
190+
f.write_str(" {\n")?;
191+
for field in self.fields(f.db) {
192+
f.write_str(" ")?;
193+
field.hir_fmt(f)?;
194+
f.write_str(",\n")?;
195+
}
196+
f.write_str("}")?;
197+
}
198+
}
199+
167200
Ok(())
168201
}
169202
}
@@ -176,6 +209,18 @@ impl HirDisplay for Enum {
176209
let def_id = GenericDefId::AdtId(AdtId::EnumId(self.id));
177210
write_generic_params(def_id, f)?;
178211
write_where_clause(def_id, f)?;
212+
213+
let variants = self.variants(f.db);
214+
if !variants.is_empty() {
215+
f.write_str(" {\n")?;
216+
for variant in variants {
217+
f.write_str(" ")?;
218+
variant.hir_fmt(f)?;
219+
f.write_str(",\n")?;
220+
}
221+
f.write_str("}")?;
222+
}
223+
179224
Ok(())
180225
}
181226
}
@@ -188,6 +233,18 @@ impl HirDisplay for Union {
188233
let def_id = GenericDefId::AdtId(AdtId::UnionId(self.id));
189234
write_generic_params(def_id, f)?;
190235
write_where_clause(def_id, f)?;
236+
237+
let fields = self.fields(f.db);
238+
if !fields.is_empty() {
239+
f.write_str(" {\n")?;
240+
for field in self.fields(f.db) {
241+
f.write_str(" ")?;
242+
field.hir_fmt(f)?;
243+
f.write_str(",\n")?;
244+
}
245+
f.write_str("}")?;
246+
}
247+
191248
Ok(())
192249
}
193250
}

crates/ide-diagnostics/src/handlers/mutability_errors.rs

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1225,6 +1225,22 @@ fn foo(mut foo: Foo) {
12251225
};
12261226
call_me();
12271227
}
1228+
"#,
1229+
);
1230+
}
1231+
1232+
#[test]
1233+
fn regression_15670() {
1234+
check_diagnostics(
1235+
r#"
1236+
//- minicore: fn
1237+
1238+
pub struct A {}
1239+
pub unsafe fn foo(a: *mut A) {
1240+
let mut b = || -> *mut A { &mut *a };
1241+
//^^^^^ 💡 warn: variable does not need to be mutable
1242+
let _ = b();
1243+
}
12281244
"#,
12291245
);
12301246
}

0 commit comments

Comments
 (0)