Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
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
2 changes: 2 additions & 0 deletions compiler/rustc_hir_typeck/messages.ftl
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,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
Expand Down
11 changes: 11 additions & 0 deletions compiler/rustc_hir_typeck/src/errors.rs
Original file line number Diff line number Diff line change
Expand Up @@ -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 {
Expand Down
30 changes: 30 additions & 0 deletions compiler/rustc_hir_typeck/src/fn_ctxt/checks.rs
Original file line number Diff line number Diff line change
@@ -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;
Expand Down Expand Up @@ -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,
Expand Down Expand Up @@ -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,
Expand Down
11 changes: 11 additions & 0 deletions tests/ui/typeck/ptr-null-mutability-suggestions.fixed
Original file line number Diff line number Diff line change
@@ -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
}
11 changes: 11 additions & 0 deletions tests/ui/typeck/ptr-null-mutability-suggestions.rs
Original file line number Diff line number Diff line change
@@ -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
}
21 changes: 21 additions & 0 deletions tests/ui/typeck/ptr-null-mutability-suggestions.stderr
Original file line number Diff line number Diff line change
@@ -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`.