about summary refs log tree commit diff
diff options
context:
space:
mode:
authorbors <bors@rust-lang.org>2023-06-12 17:23:48 +0000
committerbors <bors@rust-lang.org>2023-06-12 17:23:48 +0000
commitdf77afbcaf3365a32066a8ca4a00ae6fc9a69647 (patch)
tree1d88c226fa8e26cb089a7f56d6b92e190aa27de3
parentb963a57205e548e8538a8182b1c273ea75007614 (diff)
parent9cb785b9d3cb07ba52691ab4f8e6cb0a91d7d9aa (diff)
downloadrust-df77afbcaf3365a32066a8ca4a00ae6fc9a69647.tar.gz
rust-df77afbcaf3365a32066a8ca4a00ae6fc9a69647.zip
Auto merge of #112563 - matthiaskrgr:rollup-ebetrzi, r=matthiaskrgr
Rollup of 4 pull requests

Successful merges:

 - #112302 (Suggest using `ptr::null_mut` when user provided `ptr::null` to a function expecting `ptr::null_mut`)
 - #112416 (Fix debug ICE for extern type with where clauses)
 - #112527 (Add windows_sys type definitions for ARM32 manually)
 - #112546 (new solver: extend assert to other aliases)

r? `@ghost`
`@rustbot` modify labels: rollup
-rw-r--r--compiler/rustc_ast_passes/src/ast_validation.rs20
-rw-r--r--compiler/rustc_hir_typeck/messages.ftl2
-rw-r--r--compiler/rustc_hir_typeck/src/errors.rs11
-rw-r--r--compiler/rustc_hir_typeck/src/fn_ctxt/checks.rs30
-rw-r--r--compiler/rustc_infer/src/infer/combine.rs6
-rw-r--r--compiler/rustc_trait_selection/src/solve/assembly/mod.rs2
-rw-r--r--library/std/src/sys/windows/c/windows_sys.rs20
-rw-r--r--src/tools/generate-windows-sys/src/arm_shim.rs20
-rw-r--r--src/tools/generate-windows-sys/src/main.rs4
-rw-r--r--tests/ui/extern/issue-112363-extern-item-where-clauses-debug-ice.rs10
-rw-r--r--tests/ui/extern/issue-112363-extern-item-where-clauses-debug-ice.stderr47
-rw-r--r--tests/ui/parser/foreign-ty-semantic-fail.rs1
-rw-r--r--tests/ui/parser/foreign-ty-semantic-fail.stderr13
-rw-r--r--tests/ui/typeck/ptr-null-mutability-suggestions.fixed11
-rw-r--r--tests/ui/typeck/ptr-null-mutability-suggestions.rs11
-rw-r--r--tests/ui/typeck/ptr-null-mutability-suggestions.stderr21
16 files changed, 219 insertions, 10 deletions
diff --git a/compiler/rustc_ast_passes/src/ast_validation.rs b/compiler/rustc_ast_passes/src/ast_validation.rs
index 04ed2767876..a0979bbda54 100644
--- a/compiler/rustc_ast_passes/src/ast_validation.rs
+++ b/compiler/rustc_ast_passes/src/ast_validation.rs
@@ -364,7 +364,12 @@ impl<'a> AstValidator<'a> {
         self.err_handler().emit_err(errors::BoundInContext { span, ctx });
     }
 
-    fn check_foreign_ty_genericless(&self, generics: &Generics, where_span: Span) {
+    fn check_foreign_ty_genericless(
+        &self,
+        generics: &Generics,
+        before_where_clause: &TyAliasWhereClause,
+        after_where_clause: &TyAliasWhereClause,
+    ) {
         let cannot_have = |span, descr, remove_descr| {
             self.err_handler().emit_err(errors::ExternTypesCannotHave {
                 span,
@@ -378,9 +383,14 @@ impl<'a> AstValidator<'a> {
             cannot_have(generics.span, "generic parameters", "generic parameters");
         }
 
-        if !generics.where_clause.predicates.is_empty() {
-            cannot_have(where_span, "`where` clauses", "`where` clause");
-        }
+        let check_where_clause = |where_clause: &TyAliasWhereClause| {
+            if let TyAliasWhereClause(true, where_clause_span) = where_clause {
+                cannot_have(*where_clause_span, "`where` clauses", "`where` clause");
+            }
+        };
+
+        check_where_clause(before_where_clause);
+        check_where_clause(after_where_clause);
     }
 
     fn check_foreign_kind_bodyless(&self, ident: Ident, kind: &str, body: Option<Span>) {
@@ -1039,7 +1049,7 @@ impl<'a> Visitor<'a> for AstValidator<'a> {
                 self.check_defaultness(fi.span, *defaultness);
                 self.check_foreign_kind_bodyless(fi.ident, "type", ty.as_ref().map(|b| b.span));
                 self.check_type_no_bounds(bounds, "`extern` blocks");
-                self.check_foreign_ty_genericless(generics, where_clauses.0.1);
+                self.check_foreign_ty_genericless(generics, &where_clauses.0, &where_clauses.1);
                 self.check_foreign_item_ascii_only(fi.ident);
             }
             ForeignItemKind::Static(_, _, body) => {
diff --git a/compiler/rustc_hir_typeck/messages.ftl b/compiler/rustc_hir_typeck/messages.ftl
index 4728edd837a..c1c58db5764 100644
--- a/compiler/rustc_hir_typeck/messages.ftl
+++ b/compiler/rustc_hir_typeck/messages.ftl
@@ -89,6 +89,8 @@ hir_typeck_suggest_boxing_note = for more on the distinction between the stack a
 
 hir_typeck_suggest_boxing_when_appropriate = store this in the heap by calling `Box::new`
 
+hir_typeck_suggest_ptr_null_mut = consider using `core::ptr::null_mut` instead
+
 hir_typeck_union_pat_dotdot = `..` cannot be used in union patterns
 
 hir_typeck_union_pat_multiple_fields = union patterns should have exactly one field
diff --git a/compiler/rustc_hir_typeck/src/errors.rs b/compiler/rustc_hir_typeck/src/errors.rs
index 5161a366ae7..6b4168d8944 100644
--- a/compiler/rustc_hir_typeck/src/errors.rs
+++ b/compiler/rustc_hir_typeck/src/errors.rs
@@ -298,6 +298,17 @@ pub enum SuggestBoxing {
     },
 }
 
+#[derive(Subdiagnostic)]
+#[suggestion(
+    hir_typeck_suggest_ptr_null_mut,
+    applicability = "maybe-incorrect",
+    code = "core::ptr::null_mut()"
+)]
+pub struct SuggestPtrNullMut {
+    #[primary_span]
+    pub span: Span,
+}
+
 #[derive(Diagnostic)]
 #[diag(hir_typeck_no_associated_item, code = "E0599")]
 pub struct NoAssociatedItem {
diff --git a/compiler/rustc_hir_typeck/src/fn_ctxt/checks.rs b/compiler/rustc_hir_typeck/src/fn_ctxt/checks.rs
index 48c3d6f08de..4a3e28ffce9 100644
--- a/compiler/rustc_hir_typeck/src/fn_ctxt/checks.rs
+++ b/compiler/rustc_hir_typeck/src/fn_ctxt/checks.rs
@@ -1,4 +1,5 @@
 use crate::coercion::CoerceMany;
+use crate::errors::SuggestPtrNullMut;
 use crate::fn_ctxt::arg_matrix::{ArgMatrix, Compatibility, Error, ExpectedIdx, ProvidedIdx};
 use crate::gather_locals::Declaration;
 use crate::method::MethodCallee;
@@ -814,6 +815,13 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
                 );
             }
 
+            self.suggest_ptr_null_mut(
+                expected_ty,
+                provided_ty,
+                provided_args[*provided_idx],
+                &mut err,
+            );
+
             // Call out where the function is defined
             self.label_fn_like(
                 &mut err,
@@ -1271,6 +1279,28 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
         err.emit();
     }
 
+    fn suggest_ptr_null_mut(
+        &self,
+        expected_ty: Ty<'tcx>,
+        provided_ty: Ty<'tcx>,
+        arg: &hir::Expr<'tcx>,
+        err: &mut rustc_errors::DiagnosticBuilder<'tcx, ErrorGuaranteed>,
+    ) {
+        if let ty::RawPtr(ty::TypeAndMut { mutbl: hir::Mutability::Mut, .. }) = expected_ty.kind()
+            && let ty::RawPtr(ty::TypeAndMut { mutbl: hir::Mutability::Not, .. }) = provided_ty.kind()
+            && let hir::ExprKind::Call(callee, _) = arg.kind
+            && let hir::ExprKind::Path(hir::QPath::Resolved(_, path)) = callee.kind
+            && let Res::Def(_, def_id) = path.res
+            && self.tcx.get_diagnostic_item(sym::ptr_null) == Some(def_id)
+        {
+            // The user provided `ptr::null()`, but the function expects
+            // `ptr::null_mut()`.
+            err.subdiagnostic(SuggestPtrNullMut {
+                span: arg.span
+            });
+        }
+    }
+
     // AST fragment checking
     pub(in super::super) fn check_lit(
         &self,
diff --git a/compiler/rustc_infer/src/infer/combine.rs b/compiler/rustc_infer/src/infer/combine.rs
index 7a80ee98cb3..bb2bd2faec2 100644
--- a/compiler/rustc_infer/src/infer/combine.rs
+++ b/compiler/rustc_infer/src/infer/combine.rs
@@ -34,7 +34,7 @@ use rustc_middle::infer::unify_key::{ConstVarValue, ConstVariableValue};
 use rustc_middle::infer::unify_key::{ConstVariableOrigin, ConstVariableOriginKind};
 use rustc_middle::ty::error::{ExpectedFound, TypeError};
 use rustc_middle::ty::relate::{RelateResult, TypeRelation};
-use rustc_middle::ty::{self, AliasKind, InferConst, ToPredicate, Ty, TyCtxt, TypeVisitableExt};
+use rustc_middle::ty::{self, InferConst, ToPredicate, Ty, TyCtxt, TypeVisitableExt};
 use rustc_middle::ty::{IntType, UintType};
 use rustc_span::DUMMY_SP;
 
@@ -103,12 +103,12 @@ impl<'tcx> InferCtxt<'tcx> {
 
             // We don't expect `TyVar` or `Fresh*` vars at this point with lazy norm.
             (
-                ty::Alias(AliasKind::Projection, _),
+                ty::Alias(..),
                 ty::Infer(ty::TyVar(_) | ty::FreshTy(_) | ty::FreshIntTy(_) | ty::FreshFloatTy(_)),
             )
             | (
                 ty::Infer(ty::TyVar(_) | ty::FreshTy(_) | ty::FreshIntTy(_) | ty::FreshFloatTy(_)),
-                ty::Alias(AliasKind::Projection, _),
+                ty::Alias(..),
             ) if self.next_trait_solver() => {
                 bug!()
             }
diff --git a/compiler/rustc_trait_selection/src/solve/assembly/mod.rs b/compiler/rustc_trait_selection/src/solve/assembly/mod.rs
index f32ff0442a4..1b749b9c854 100644
--- a/compiler/rustc_trait_selection/src/solve/assembly/mod.rs
+++ b/compiler/rustc_trait_selection/src/solve/assembly/mod.rs
@@ -320,7 +320,7 @@ impl<'tcx> EvalCtxt<'_, 'tcx> {
         candidates
     }
 
-    /// If the self type of a goal is a projection, computing the relevant candidates is difficult.
+    /// If the self type of a goal is an alias, computing the relevant candidates is difficult.
     ///
     /// To deal with this, we first try to normalize the self type and add the candidates for the normalized
     /// self type to the list of candidates in case that succeeds. We also have to consider candidates with the
diff --git a/library/std/src/sys/windows/c/windows_sys.rs b/library/std/src/sys/windows/c/windows_sys.rs
index 8c8b006a1d3..a4294f336fe 100644
--- a/library/std/src/sys/windows/c/windows_sys.rs
+++ b/library/std/src/sys/windows/c/windows_sys.rs
@@ -4275,3 +4275,23 @@ impl ::core::clone::Clone for XSAVE_FORMAT {
         *self
     }
 }
+// Begin of ARM32 shim
+// The raw content of this file should be processed by `generate-windows-sys`
+// to be merged with the generated binding. It is not supposed to be used as
+// a normal Rust module.
+cfg_if::cfg_if! {
+if #[cfg(target_arch = "arm")] {
+#[repr(C)]
+pub struct WSADATA {
+    pub wVersion: u16,
+    pub wHighVersion: u16,
+    pub szDescription: [u8; 257],
+    pub szSystemStatus: [u8; 129],
+    pub iMaxSockets: u16,
+    pub iMaxUdpDg: u16,
+    pub lpVendorInfo: PSTR,
+}
+pub enum CONTEXT {}
+}
+}
+// End of ARM32 shim
diff --git a/src/tools/generate-windows-sys/src/arm_shim.rs b/src/tools/generate-windows-sys/src/arm_shim.rs
new file mode 100644
index 00000000000..17c2ccb223c
--- /dev/null
+++ b/src/tools/generate-windows-sys/src/arm_shim.rs
@@ -0,0 +1,20 @@
+// Begin of ARM32 shim
+// The raw content of this file should be processed by `generate-windows-sys`
+// to be merged with the generated binding. It is not supposed to be used as
+// a normal Rust module.
+cfg_if::cfg_if! {
+if #[cfg(target_arch = "arm")] {
+#[repr(C)]
+pub struct WSADATA {
+    pub wVersion: u16,
+    pub wHighVersion: u16,
+    pub szDescription: [u8; 257],
+    pub szSystemStatus: [u8; 129],
+    pub iMaxSockets: u16,
+    pub iMaxUdpDg: u16,
+    pub lpVendorInfo: PSTR,
+}
+pub enum CONTEXT {}
+}
+}
+// End of ARM32 shim
diff --git a/src/tools/generate-windows-sys/src/main.rs b/src/tools/generate-windows-sys/src/main.rs
index 91d981462e8..65e480715ee 100644
--- a/src/tools/generate-windows-sys/src/main.rs
+++ b/src/tools/generate-windows-sys/src/main.rs
@@ -11,6 +11,9 @@ const PRELUDE: &str = r#"// This file is autogenerated.
 // ignore-tidy-filelength
 "#;
 
+/// This is a shim for the ARM (32-bit) architecture, which is no longer supported by windows-rs.
+const ARM_SHIM: &str = include_str!("arm_shim.rs");
+
 fn main() -> io::Result<()> {
     let mut path: PathBuf =
         std::env::args_os().nth(1).expect("a path to the rust repository is required").into();
@@ -32,6 +35,7 @@ fn main() -> io::Result<()> {
     let mut f = std::fs::File::create(&path)?;
     f.write_all(PRELUDE.as_bytes())?;
     f.write_all(bindings.as_bytes())?;
+    f.write_all(ARM_SHIM.as_bytes())?;
 
     Ok(())
 }
diff --git a/tests/ui/extern/issue-112363-extern-item-where-clauses-debug-ice.rs b/tests/ui/extern/issue-112363-extern-item-where-clauses-debug-ice.rs
new file mode 100644
index 00000000000..17e08f511d7
--- /dev/null
+++ b/tests/ui/extern/issue-112363-extern-item-where-clauses-debug-ice.rs
@@ -0,0 +1,10 @@
+extern "C" {
+    type Item = [T] where [T]: Sized;
+    //~^ incorrect `type` inside `extern` block
+    //~| `type`s inside `extern` blocks cannot have `where` clauses
+    //~| cannot find type `T` in this scope
+    //~| cannot find type `T` in this scope
+    //~| extern types are experimental
+}
+
+fn main() {}
diff --git a/tests/ui/extern/issue-112363-extern-item-where-clauses-debug-ice.stderr b/tests/ui/extern/issue-112363-extern-item-where-clauses-debug-ice.stderr
new file mode 100644
index 00000000000..bdc6755038a
--- /dev/null
+++ b/tests/ui/extern/issue-112363-extern-item-where-clauses-debug-ice.stderr
@@ -0,0 +1,47 @@
+error: incorrect `type` inside `extern` block
+  --> $DIR/issue-112363-extern-item-where-clauses-debug-ice.rs:2:10
+   |
+LL | extern "C" {
+   | ---------- `extern` blocks define existing foreign types and types inside of them cannot have a body
+LL |     type Item = [T] where [T]: Sized;
+   |          ^^^^   --- the invalid body
+   |          |
+   |          cannot have a body
+   |
+   = note: for more information, visit https://doc.rust-lang.org/std/keyword.extern.html
+
+error: `type`s inside `extern` blocks cannot have `where` clauses
+  --> $DIR/issue-112363-extern-item-where-clauses-debug-ice.rs:2:21
+   |
+LL | extern "C" {
+   | ---------- `extern` block begins here
+LL |     type Item = [T] where [T]: Sized;
+   |                     ^^^^^^^^^^^^^^^^ help: remove the `where` clause
+   |
+   = note: for more information, visit https://doc.rust-lang.org/std/keyword.extern.html
+
+error[E0412]: cannot find type `T` in this scope
+  --> $DIR/issue-112363-extern-item-where-clauses-debug-ice.rs:2:28
+   |
+LL |     type Item = [T] where [T]: Sized;
+   |                            ^ not found in this scope
+
+error[E0412]: cannot find type `T` in this scope
+  --> $DIR/issue-112363-extern-item-where-clauses-debug-ice.rs:2:18
+   |
+LL |     type Item = [T] where [T]: Sized;
+   |                  ^ not found in this scope
+
+error[E0658]: extern types are experimental
+  --> $DIR/issue-112363-extern-item-where-clauses-debug-ice.rs:2:5
+   |
+LL |     type Item = [T] where [T]: Sized;
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |
+   = note: see issue #43467 <https://github.com/rust-lang/rust/issues/43467> for more information
+   = help: add `#![feature(extern_types)]` to the crate attributes to enable
+
+error: aborting due to 5 previous errors
+
+Some errors have detailed explanations: E0412, E0658.
+For more information about an error, try `rustc --explain E0412`.
diff --git a/tests/ui/parser/foreign-ty-semantic-fail.rs b/tests/ui/parser/foreign-ty-semantic-fail.rs
index 96b15232b10..4d30086e765 100644
--- a/tests/ui/parser/foreign-ty-semantic-fail.rs
+++ b/tests/ui/parser/foreign-ty-semantic-fail.rs
@@ -15,4 +15,5 @@ extern "C" {
     //~^ ERROR incorrect `type` inside `extern` block
 
     type E: where;
+    //~^ ERROR `type`s inside `extern` blocks cannot have `where` clauses
 }
diff --git a/tests/ui/parser/foreign-ty-semantic-fail.stderr b/tests/ui/parser/foreign-ty-semantic-fail.stderr
index 588e4966aae..2b400dfea3b 100644
--- a/tests/ui/parser/foreign-ty-semantic-fail.stderr
+++ b/tests/ui/parser/foreign-ty-semantic-fail.stderr
@@ -61,5 +61,16 @@ LL |     type D = u8;
    |
    = note: for more information, visit https://doc.rust-lang.org/std/keyword.extern.html
 
-error: aborting due to 6 previous errors
+error: `type`s inside `extern` blocks cannot have `where` clauses
+  --> $DIR/foreign-ty-semantic-fail.rs:17:13
+   |
+LL | extern "C" {
+   | ---------- `extern` block begins here
+...
+LL |     type E: where;
+   |             ^^^^^ help: remove the `where` clause
+   |
+   = note: for more information, visit https://doc.rust-lang.org/std/keyword.extern.html
+
+error: aborting due to 7 previous errors
 
diff --git a/tests/ui/typeck/ptr-null-mutability-suggestions.fixed b/tests/ui/typeck/ptr-null-mutability-suggestions.fixed
new file mode 100644
index 00000000000..d00536b29cf
--- /dev/null
+++ b/tests/ui/typeck/ptr-null-mutability-suggestions.fixed
@@ -0,0 +1,11 @@
+// run-rustfix
+
+#[allow(unused_imports)]
+use std::ptr;
+
+fn expecting_null_mut(_: *mut u8) {}
+
+fn main() {
+    expecting_null_mut(core::ptr::null_mut());
+    //~^ ERROR mismatched types
+}
diff --git a/tests/ui/typeck/ptr-null-mutability-suggestions.rs b/tests/ui/typeck/ptr-null-mutability-suggestions.rs
new file mode 100644
index 00000000000..ea3066d2289
--- /dev/null
+++ b/tests/ui/typeck/ptr-null-mutability-suggestions.rs
@@ -0,0 +1,11 @@
+// run-rustfix
+
+#[allow(unused_imports)]
+use std::ptr;
+
+fn expecting_null_mut(_: *mut u8) {}
+
+fn main() {
+    expecting_null_mut(ptr::null());
+    //~^ ERROR mismatched types
+}
diff --git a/tests/ui/typeck/ptr-null-mutability-suggestions.stderr b/tests/ui/typeck/ptr-null-mutability-suggestions.stderr
new file mode 100644
index 00000000000..705b029bdea
--- /dev/null
+++ b/tests/ui/typeck/ptr-null-mutability-suggestions.stderr
@@ -0,0 +1,21 @@
+error[E0308]: mismatched types
+  --> $DIR/ptr-null-mutability-suggestions.rs:9:24
+   |
+LL |     expecting_null_mut(ptr::null());
+   |     ------------------ ^^^^^^^^^^^
+   |     |                  |
+   |     |                  types differ in mutability
+   |     |                  help: consider using `core::ptr::null_mut` instead: `core::ptr::null_mut()`
+   |     arguments to this function are incorrect
+   |
+   = note: expected raw pointer `*mut u8`
+              found raw pointer `*const _`
+note: function defined here
+  --> $DIR/ptr-null-mutability-suggestions.rs:6:4
+   |
+LL | fn expecting_null_mut(_: *mut u8) {}
+   |    ^^^^^^^^^^^^^^^^^^ ----------
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0308`.