Skip to content

Commit f1f996a

Browse files
committed
Handle pattern types wrapped in Option in FFI checks
1 parent 5bae8ca commit f1f996a

File tree

4 files changed

+35
-49
lines changed

4 files changed

+35
-49
lines changed

Diff for: compiler/rustc_lint/src/lib.rs

+1
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,7 @@
3333
#![feature(let_chains)]
3434
#![feature(rustc_attrs)]
3535
#![feature(rustdoc_internals)]
36+
#![feature(try_blocks)]
3637
#![warn(unreachable_pub)]
3738
// tidy-alphabetical-end
3839

Diff for: compiler/rustc_lint/src/types.rs

+31
Original file line numberDiff line numberDiff line change
@@ -877,6 +877,37 @@ fn ty_is_known_nonnull<'tcx>(
877877
.filter_map(|variant| transparent_newtype_field(tcx, variant))
878878
.any(|field| ty_is_known_nonnull(tcx, typing_env, field.ty(tcx, args), mode))
879879
}
880+
ty::Pat(base, pat) => {
881+
ty_is_known_nonnull(tcx, typing_env, *base, mode)
882+
|| Option::unwrap_or_default(
883+
try {
884+
match **pat {
885+
ty::PatternKind::Range { start, end, include_end } => {
886+
match (start, end) {
887+
(Some(start), None) => {
888+
start.try_to_value()?.try_to_bits(tcx, typing_env)? > 0
889+
}
890+
(Some(start), Some(end)) => {
891+
let start =
892+
start.try_to_value()?.try_to_bits(tcx, typing_env)?;
893+
let end =
894+
end.try_to_value()?.try_to_bits(tcx, typing_env)?;
895+
896+
if include_end {
897+
// This also works for negative numbers, as we just need
898+
// to ensure we aren't wrapping over zero.
899+
start > 0 && end >= start
900+
} else {
901+
start > 0 && end > start
902+
}
903+
}
904+
_ => false,
905+
}
906+
}
907+
}
908+
},
909+
)
910+
}
880911
_ => false,
881912
}
882913
}

Diff for: tests/ui/lint/clashing-extern-fn.rs

-4
Original file line numberDiff line numberDiff line change
@@ -499,13 +499,11 @@ mod pattern_types {
499499
extern "C" {
500500
fn pt_non_zero_usize() -> pattern_type!(usize is 1..);
501501
fn pt_non_zero_usize_opt() -> Option<pattern_type!(usize is 1..)>;
502-
//~^ WARN not FFI-safe
503502
fn pt_non_zero_usize_opt_full_range() -> Option<pattern_type!(usize is 0..)>;
504503
//~^ WARN not FFI-safe
505504
fn pt_non_null_ptr() -> pattern_type!(usize is 1..);
506505
fn pt_non_zero_usize_wrapper() -> NonZeroUsize;
507506
fn pt_non_zero_usize_wrapper_opt() -> Option<NonZeroUsize>;
508-
//~^ WARN not FFI-safe
509507
}
510508
}
511509
mod b {
@@ -515,12 +513,10 @@ mod pattern_types {
515513
// cases are warning for, from both a caller-convenience and optimisation perspective.
516514
fn pt_non_zero_usize() -> usize;
517515
fn pt_non_zero_usize_opt() -> usize;
518-
//~^ WARN `pt_non_zero_usize_opt` redeclared with a different signature
519516
fn pt_non_null_ptr() -> *const ();
520517
//~^ WARN `pt_non_null_ptr` redeclared with a different signature
521518
fn pt_non_zero_usize_wrapper() -> usize;
522519
fn pt_non_zero_usize_wrapper_opt() -> usize;
523-
//~^ WARN `pt_non_zero_usize_wrapper_opt` redeclared with a different signature
524520
}
525521
}
526522
}

Diff for: tests/ui/lint/clashing-extern-fn.stderr

+3-45
Original file line numberDiff line numberDiff line change
@@ -17,33 +17,15 @@ LL | fn hidden_niche_unsafe_cell() -> Option<UnsafeCell<NonZero<usiz
1717
= help: consider adding a `#[repr(C)]`, `#[repr(transparent)]`, or integer `#[repr(...)]` attribute to this enum
1818
= note: enum has no representation hint
1919

20-
warning: `extern` block uses type `Option<(usize) is 1..=>`, which is not FFI-safe
21-
--> $DIR/clashing-extern-fn.rs:501:43
22-
|
23-
LL | fn pt_non_zero_usize_opt() -> Option<pattern_type!(usize is 1..)>;
24-
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
25-
|
26-
= help: consider adding a `#[repr(C)]`, `#[repr(transparent)]`, or integer `#[repr(...)]` attribute to this enum
27-
= note: enum has no representation hint
28-
2920
warning: `extern` block uses type `Option<(usize) is 0..=>`, which is not FFI-safe
30-
--> $DIR/clashing-extern-fn.rs:503:54
21+
--> $DIR/clashing-extern-fn.rs:502:54
3122
|
3223
LL | fn pt_non_zero_usize_opt_full_range() -> Option<pattern_type!(usize is 0..)>;
3324
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
3425
|
3526
= help: consider adding a `#[repr(C)]`, `#[repr(transparent)]`, or integer `#[repr(...)]` attribute to this enum
3627
= note: enum has no representation hint
3728

38-
warning: `extern` block uses type `Option<NonZeroUsize>`, which is not FFI-safe
39-
--> $DIR/clashing-extern-fn.rs:507:51
40-
|
41-
LL | fn pt_non_zero_usize_wrapper_opt() -> Option<NonZeroUsize>;
42-
| ^^^^^^^^^^^^^^^^^^^^ not FFI-safe
43-
|
44-
= help: consider adding a `#[repr(C)]`, `#[repr(transparent)]`, or integer `#[repr(...)]` attribute to this enum
45-
= note: enum has no representation hint
46-
4729
warning: `clash` redeclared with a different signature
4830
--> $DIR/clashing-extern-fn.rs:13:13
4931
|
@@ -285,20 +267,8 @@ LL | fn hidden_niche_unsafe_cell() -> Option<UnsafeCell<NonZero<usiz
285267
= note: expected `unsafe extern "C" fn() -> usize`
286268
found `unsafe extern "C" fn() -> Option<UnsafeCell<NonZero<usize>>>`
287269

288-
warning: `pt_non_zero_usize_opt` redeclared with a different signature
289-
--> $DIR/clashing-extern-fn.rs:517:13
290-
|
291-
LL | fn pt_non_zero_usize_opt() -> Option<pattern_type!(usize is 1..)>;
292-
| ------------------------------------------------------------------ `pt_non_zero_usize_opt` previously declared here
293-
...
294-
LL | fn pt_non_zero_usize_opt() -> usize;
295-
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ this signature doesn't match the previous declaration
296-
|
297-
= note: expected `unsafe extern "C" fn() -> Option<(usize) is 1..=>`
298-
found `unsafe extern "C" fn() -> usize`
299-
300270
warning: `pt_non_null_ptr` redeclared with a different signature
301-
--> $DIR/clashing-extern-fn.rs:519:13
271+
--> $DIR/clashing-extern-fn.rs:516:13
302272
|
303273
LL | fn pt_non_null_ptr() -> pattern_type!(usize is 1..);
304274
| ---------------------------------------------------- `pt_non_null_ptr` previously declared here
@@ -309,17 +279,5 @@ LL | fn pt_non_null_ptr() -> *const ();
309279
= note: expected `unsafe extern "C" fn() -> (usize) is 1..=`
310280
found `unsafe extern "C" fn() -> *const ()`
311281

312-
warning: `pt_non_zero_usize_wrapper_opt` redeclared with a different signature
313-
--> $DIR/clashing-extern-fn.rs:522:13
314-
|
315-
LL | fn pt_non_zero_usize_wrapper_opt() -> Option<NonZeroUsize>;
316-
| ----------------------------------------------------------- `pt_non_zero_usize_wrapper_opt` previously declared here
317-
...
318-
LL | fn pt_non_zero_usize_wrapper_opt() -> usize;
319-
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ this signature doesn't match the previous declaration
320-
|
321-
= note: expected `unsafe extern "C" fn() -> Option<NonZeroUsize>`
322-
found `unsafe extern "C" fn() -> usize`
323-
324-
warning: 28 warnings emitted
282+
warning: 24 warnings emitted
325283

0 commit comments

Comments
 (0)