mirror of
https://github.com/rust-lang/rust.git
synced 2025-04-28 11:07:42 +00:00
Rollup merge of #99581 - nnethercote:improve-derive-packed-errors, r=estebank
Improve error messages involving `derive` and `packed`. There are two errors involving `derive` and `packed`. ``` `#[derive]` can't be derived on a `#[repr(packed)]` struct with type or const parameters `#[derive]` can't be derived on a `#[repr(packed)]` struct that does not derive Copy ``` The second one overstates things. It is possible to use derive on a repr(packed) struct that doesn't derive Copy in two cases. - If all the fields within the struct meet the required alignment: 1 for `repr(packed)`, or `N` for `repr(packed(N))`. - If `Default` is the only trait derived. This commit improves things in a few ways. - Changes the errors to say `this trait can't be derived on this ...`. This is more accurate, because it's just *this* trait and *this* packed struct that are a problem, not *all* derived traits on *all* packed structs. - Adds more details to the "ERROR" lines in the test case, enough to distinguish between the two error messages. - Adds more cases to the test case that don't cause errors, e.g. `Default` derives. - Uses a wider variety of builtin traits in the test case, for better coverage. r? `@estebank`
This commit is contained in:
commit
921cfbe56f
@ -36,13 +36,16 @@ fn unsafe_derive_on_repr_packed(tcx: TyCtxt<'_>, def_id: LocalDefId) {
|
||||
tcx.struct_span_lint_hir(UNALIGNED_REFERENCES, lint_hir_id, tcx.def_span(def_id), |lint| {
|
||||
// FIXME: when we make this a hard error, this should have its
|
||||
// own error code.
|
||||
let message = if tcx.generics_of(def_id).own_requires_monomorphization() {
|
||||
"`#[derive]` can't be used on a `#[repr(packed)]` struct with \
|
||||
type or const parameters (error E0133)"
|
||||
let extra = if tcx.generics_of(def_id).own_requires_monomorphization() {
|
||||
"with type or const parameters"
|
||||
} else {
|
||||
"`#[derive]` can't be used on a `#[repr(packed)]` struct that \
|
||||
does not derive Copy (error E0133)"
|
||||
"that does not derive `Copy`"
|
||||
};
|
||||
let message = format!(
|
||||
"`{}` can't be derived on this `#[repr(packed)]` struct {} (error E0133)",
|
||||
tcx.item_name(tcx.trait_id_of_impl(def_id.to_def_id()).expect("derived trait name")),
|
||||
extra
|
||||
);
|
||||
lint.build(message).emit();
|
||||
});
|
||||
}
|
||||
|
@ -1,29 +1,43 @@
|
||||
#![deny(unaligned_references)]
|
||||
|
||||
// check that derive on a packed struct with non-Copy fields
|
||||
// correctly. This can't be made to work perfectly because
|
||||
// we can't just use the field from the struct as it might
|
||||
// not be aligned.
|
||||
// Check that deriving certain builtin traits on certain packed structs cause
|
||||
// errors. This happens when the derived trait would need to use a potentially
|
||||
// misaligned reference. But there are two cases that are allowed:
|
||||
// - If all the fields within the struct meet the required alignment: 1 for
|
||||
// `repr(packed)`, or `N` for `repr(packed(N))`.
|
||||
// - If `Default` is the only trait derived, because it doesn't involve any
|
||||
// references.
|
||||
|
||||
#[derive(Copy, Clone, PartialEq, Eq)]
|
||||
//~^ ERROR `#[derive]` can't be used
|
||||
#[derive(Copy, Clone, Default, PartialEq, Eq)]
|
||||
//~^ ERROR `Clone` can't be derived on this `#[repr(packed)]` struct with type or const parameters
|
||||
//~| hard error
|
||||
//~^^^ ERROR `#[derive]` can't be used
|
||||
//~^^^ ERROR `PartialEq` can't be derived on this `#[repr(packed)]` struct with type or const parameters
|
||||
//~| hard error
|
||||
#[repr(packed)]
|
||||
pub struct Foo<T>(T, T, T);
|
||||
|
||||
#[derive(PartialEq, Eq)]
|
||||
//~^ ERROR `#[derive]` can't be used
|
||||
#[derive(Default, Hash)]
|
||||
//~^ ERROR `Hash` can't be derived on this `#[repr(packed)]` struct that does not derive `Copy`
|
||||
//~| hard error
|
||||
#[repr(packed)]
|
||||
pub struct Bar(u32, u32, u32);
|
||||
|
||||
#[derive(PartialEq)]
|
||||
// This one is fine because the field alignment is 1.
|
||||
#[derive(Default, Hash)]
|
||||
#[repr(packed)]
|
||||
pub struct Bar2(u8, i8, bool);
|
||||
|
||||
// This one is fine because the field alignment is 2, matching `packed(2)`.
|
||||
#[derive(Default, Hash)]
|
||||
#[repr(packed(2))]
|
||||
pub struct Bar3(u16, i16, bool);
|
||||
|
||||
// This one is fine because it's not packed.
|
||||
#[derive(Debug, Default)]
|
||||
struct Y(usize);
|
||||
|
||||
#[derive(PartialEq)]
|
||||
//~^ ERROR `#[derive]` can't be used
|
||||
#[derive(Debug, Default)]
|
||||
//~^ ERROR `Debug` can't be derived on this `#[repr(packed)]` struct that does not derive `Copy`
|
||||
//~| hard error
|
||||
#[repr(packed)]
|
||||
struct X(Y);
|
||||
|
@ -1,7 +1,7 @@
|
||||
error: `#[derive]` can't be used on a `#[repr(packed)]` struct with type or const parameters (error E0133)
|
||||
--> $DIR/deriving-with-repr-packed.rs:8:16
|
||||
error: `Clone` can't be derived on this `#[repr(packed)]` struct with type or const parameters (error E0133)
|
||||
--> $DIR/deriving-with-repr-packed.rs:11:16
|
||||
|
|
||||
LL | #[derive(Copy, Clone, PartialEq, Eq)]
|
||||
LL | #[derive(Copy, Clone, Default, PartialEq, Eq)]
|
||||
| ^^^^^
|
||||
|
|
||||
note: the lint level is defined here
|
||||
@ -13,43 +13,43 @@ LL | #![deny(unaligned_references)]
|
||||
= note: for more information, see issue #82523 <https://github.com/rust-lang/rust/issues/82523>
|
||||
= note: this error originates in the derive macro `Clone` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||
|
||||
error: `#[derive]` can't be used on a `#[repr(packed)]` struct with type or const parameters (error E0133)
|
||||
--> $DIR/deriving-with-repr-packed.rs:8:23
|
||||
error: `PartialEq` can't be derived on this `#[repr(packed)]` struct with type or const parameters (error E0133)
|
||||
--> $DIR/deriving-with-repr-packed.rs:11:32
|
||||
|
|
||||
LL | #[derive(Copy, Clone, PartialEq, Eq)]
|
||||
LL | #[derive(Copy, Clone, Default, PartialEq, Eq)]
|
||||
| ^^^^^^^^^
|
||||
|
|
||||
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
||||
= note: for more information, see issue #82523 <https://github.com/rust-lang/rust/issues/82523>
|
||||
= note: this error originates in the derive macro `PartialEq` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||
|
||||
error: `#[derive]` can't be used on a `#[repr(packed)]` struct that does not derive Copy (error E0133)
|
||||
--> $DIR/deriving-with-repr-packed.rs:16:10
|
||||
error: `Hash` can't be derived on this `#[repr(packed)]` struct that does not derive `Copy` (error E0133)
|
||||
--> $DIR/deriving-with-repr-packed.rs:19:19
|
||||
|
|
||||
LL | #[derive(PartialEq, Eq)]
|
||||
| ^^^^^^^^^
|
||||
LL | #[derive(Default, Hash)]
|
||||
| ^^^^
|
||||
|
|
||||
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
||||
= note: for more information, see issue #82523 <https://github.com/rust-lang/rust/issues/82523>
|
||||
= note: this error originates in the derive macro `PartialEq` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||
= note: this error originates in the derive macro `Hash` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||
|
||||
error: `#[derive]` can't be used on a `#[repr(packed)]` struct that does not derive Copy (error E0133)
|
||||
--> $DIR/deriving-with-repr-packed.rs:25:10
|
||||
error: `Debug` can't be derived on this `#[repr(packed)]` struct that does not derive `Copy` (error E0133)
|
||||
--> $DIR/deriving-with-repr-packed.rs:39:10
|
||||
|
|
||||
LL | #[derive(PartialEq)]
|
||||
| ^^^^^^^^^
|
||||
LL | #[derive(Debug, Default)]
|
||||
| ^^^^^
|
||||
|
|
||||
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
||||
= note: for more information, see issue #82523 <https://github.com/rust-lang/rust/issues/82523>
|
||||
= note: this error originates in the derive macro `PartialEq` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||
= note: this error originates in the derive macro `Debug` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||
|
||||
error: aborting due to 4 previous errors
|
||||
|
||||
Future incompatibility report: Future breakage diagnostic:
|
||||
error: `#[derive]` can't be used on a `#[repr(packed)]` struct with type or const parameters (error E0133)
|
||||
--> $DIR/deriving-with-repr-packed.rs:8:16
|
||||
error: `Clone` can't be derived on this `#[repr(packed)]` struct with type or const parameters (error E0133)
|
||||
--> $DIR/deriving-with-repr-packed.rs:11:16
|
||||
|
|
||||
LL | #[derive(Copy, Clone, PartialEq, Eq)]
|
||||
LL | #[derive(Copy, Clone, Default, PartialEq, Eq)]
|
||||
| ^^^^^
|
||||
|
|
||||
note: the lint level is defined here
|
||||
@ -62,10 +62,10 @@ LL | #![deny(unaligned_references)]
|
||||
= note: this error originates in the derive macro `Clone` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||
|
||||
Future breakage diagnostic:
|
||||
error: `#[derive]` can't be used on a `#[repr(packed)]` struct with type or const parameters (error E0133)
|
||||
--> $DIR/deriving-with-repr-packed.rs:8:23
|
||||
error: `PartialEq` can't be derived on this `#[repr(packed)]` struct with type or const parameters (error E0133)
|
||||
--> $DIR/deriving-with-repr-packed.rs:11:32
|
||||
|
|
||||
LL | #[derive(Copy, Clone, PartialEq, Eq)]
|
||||
LL | #[derive(Copy, Clone, Default, PartialEq, Eq)]
|
||||
| ^^^^^^^^^
|
||||
|
|
||||
note: the lint level is defined here
|
||||
@ -78,11 +78,11 @@ LL | #![deny(unaligned_references)]
|
||||
= note: this error originates in the derive macro `PartialEq` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||
|
||||
Future breakage diagnostic:
|
||||
error: `#[derive]` can't be used on a `#[repr(packed)]` struct that does not derive Copy (error E0133)
|
||||
--> $DIR/deriving-with-repr-packed.rs:16:10
|
||||
error: `Hash` can't be derived on this `#[repr(packed)]` struct that does not derive `Copy` (error E0133)
|
||||
--> $DIR/deriving-with-repr-packed.rs:19:19
|
||||
|
|
||||
LL | #[derive(PartialEq, Eq)]
|
||||
| ^^^^^^^^^
|
||||
LL | #[derive(Default, Hash)]
|
||||
| ^^^^
|
||||
|
|
||||
note: the lint level is defined here
|
||||
--> $DIR/deriving-with-repr-packed.rs:1:9
|
||||
@ -91,14 +91,14 @@ LL | #![deny(unaligned_references)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^
|
||||
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
||||
= note: for more information, see issue #82523 <https://github.com/rust-lang/rust/issues/82523>
|
||||
= note: this error originates in the derive macro `PartialEq` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||
= note: this error originates in the derive macro `Hash` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||
|
||||
Future breakage diagnostic:
|
||||
error: `#[derive]` can't be used on a `#[repr(packed)]` struct that does not derive Copy (error E0133)
|
||||
--> $DIR/deriving-with-repr-packed.rs:25:10
|
||||
error: `Debug` can't be derived on this `#[repr(packed)]` struct that does not derive `Copy` (error E0133)
|
||||
--> $DIR/deriving-with-repr-packed.rs:39:10
|
||||
|
|
||||
LL | #[derive(PartialEq)]
|
||||
| ^^^^^^^^^
|
||||
LL | #[derive(Debug, Default)]
|
||||
| ^^^^^
|
||||
|
|
||||
note: the lint level is defined here
|
||||
--> $DIR/deriving-with-repr-packed.rs:1:9
|
||||
@ -107,5 +107,5 @@ LL | #![deny(unaligned_references)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^
|
||||
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
||||
= note: for more information, see issue #82523 <https://github.com/rust-lang/rust/issues/82523>
|
||||
= note: this error originates in the derive macro `PartialEq` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||
= note: this error originates in the derive macro `Debug` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user