Skip to content
Closed
Show file tree
Hide file tree
Changes from 8 commits
Commits
Show all changes
19 commits
Select commit Hold shift + click to select a range
878a796
Add missing safety descriptions to Arc's 'from_raw','increment_strong…
DiuDiu777 Dec 19, 2024
c89f0dc
Adjust syntax
c410-f3r Dec 22, 2024
be23697
Detect overflow when the literal is larger than i128::MAX
s-cerevisiae Jan 8, 2025
330be17
Detect overflow when the literal is negative
s-cerevisiae Jan 8, 2025
1517a41
Add test cases and test for `HELP`
s-cerevisiae Jan 8, 2025
c04e65d
Extract integer conversion into a function
s-cerevisiae Jan 8, 2025
c994637
Only treat plain literal patterns as short
oli-obk Jan 8, 2025
4a85755
Minor simplification
s-cerevisiae Jan 11, 2025
f52724c
Add comment on case to mark the original issue
s-cerevisiae Jan 12, 2025
74e2e8b
Suggest the smallest fitting type instead
s-cerevisiae Jan 12, 2025
c4a5e12
Clarify note in `std::sync::LazyLock` example
Jan 15, 2025
bbeb5e3
Update `compiler-builtins` to 0.1.144
tgross35 Jan 16, 2025
48e671e
fix typo in library/alloc/src/sync.rs
DiuDiu777 Jan 16, 2025
79a1658
Rollup merge of #133720 - c410-f3r:cfg-match-foo-bar-baz, r=joshtriplett
matthiaskrgr Jan 16, 2025
663b35b
Rollup merge of #134496 - DiuDiu777:fix-doc, r=ibraheemdev
matthiaskrgr Jan 16, 2025
13c3759
Rollup merge of #135249 - s-cerevisiae:fix-overflowing-literals-help,…
matthiaskrgr Jan 16, 2025
2760486
Rollup merge of #135251 - oli-obk:push-lmpyvvyrtplk, r=ytmimi
matthiaskrgr Jan 16, 2025
b898de4
Rollup merge of #135556 - AeonSolstice:patch-1, r=tgross35
matthiaskrgr Jan 16, 2025
4dcc3f3
Rollup merge of #135560 - tgross35:update-builtins, r=tgross35
matthiaskrgr Jan 16, 2025
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
31 changes: 23 additions & 8 deletions compiler/rustc_lint/src/types/literal.rs
Original file line number Diff line number Diff line change
Expand Up @@ -204,20 +204,35 @@ fn get_type_suggestion(t: Ty<'_>, val: u128, negative: bool) -> Option<&'static
match t.kind() {
ty::Uint(ty::UintTy::Usize) | ty::Int(ty::IntTy::Isize) => None,
ty::Uint(_) => Some(Integer::fit_unsigned(val).uint_ty_str()),
ty::Int(_) if negative => Some(Integer::fit_signed(-(val as i128)).int_ty_str()),
ty::Int(int) => {
let signed = Integer::fit_signed(val as i128);
let unsigned = Integer::fit_unsigned(val);
Some(if Some(unsigned.size().bits()) == int.bit_width() {
unsigned.uint_ty_str()
ty::Int(_) => {
let signed = literal_to_i128(val, negative).map(Integer::fit_signed);
if negative {
signed.map(Integer::int_ty_str)
} else {
signed.int_ty_str()
})
let unsigned = Integer::fit_unsigned(val);
Some(if let Some(signed) = signed {
if unsigned.size() < signed.size() {
unsigned.uint_ty_str()
} else {
signed.int_ty_str()
}
} else {
unsigned.uint_ty_str()
})
}
}
_ => None,
}
}

fn literal_to_i128(val: u128, negative: bool) -> Option<i128> {
if negative {
(val <= i128::MAX as u128 + 1).then(|| val.wrapping_neg() as i128)
} else {
val.try_into().ok()
}
}

fn lint_int_literal<'tcx>(
cx: &LateContext<'tcx>,
type_limits: &TypeLimits,
Expand Down
26 changes: 26 additions & 0 deletions tests/ui/lint/type-overflow.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,20 +3,46 @@

fn main() {
let error = 255i8; //~WARNING literal out of range for `i8`
//~^ HELP consider using the type `u8` instead

let ok = 0b1000_0001; // should be ok -> i32
let ok = 0b0111_1111i8; // should be ok -> 127i8

let fail = 0b1000_0001i8; //~WARNING literal out of range for `i8`
//~^ HELP consider using the type `u8` instead
//~| HELP consider using the type `u8` for the literal and cast it to `i8`

let fail = 0x8000_0000_0000_0000i64; //~WARNING literal out of range for `i64`
//~^ HELP consider using the type `u64` instead
//~| HELP consider using the type `u64` for the literal and cast it to `i64`

let fail = 0x1_FFFF_FFFFu32; //~WARNING literal out of range for `u32`
//~^ HELP consider using the type `u64` instead

let fail: i128 = 0x8000_0000_0000_0000_0000_0000_0000_0000;
//~^ WARNING literal out of range for `i128`
//~| HELP consider using the type `u128` instead
//~| HELP consider using the type `u128` for the literal and cast it to `i128`

let fail = 0x8000_0000_0000_0000_0000_0000_0000_0000;
//~^ WARNING literal out of range for `i32`
//~| HELP consider using the type `u128` instead

let fail = -0x8000_0000_0000_0000_0000_0000_0000_0000; // issue #131849
//~^ WARNING literal out of range for `i32`
//~| HELP consider using the type `i128` instead

let fail = -0x8000_0000_0000_0000_0000_0000_0000_0001i128;
//~^ WARNING literal out of range for `i128`

let fail = 340282366920938463463374607431768211455i8;
//~^ WARNING literal out of range for `i8`
//~| HELP consider using the type `u128` instead

let fail = 0x8FFF_FFFF_FFFF_FFFE; //~WARNING literal out of range for `i32`
//~| HELP consider using the type `u64` instead
//~| HELP

let fail = -0b1111_1111i8; //~WARNING literal out of range for `i8`
//~| HELP consider using the type `i16` instead
}
53 changes: 45 additions & 8 deletions tests/ui/lint/type-overflow.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ LL | #![warn(overflowing_literals)]
| ^^^^^^^^^^^^^^^^^^^^

warning: literal out of range for `i8`
--> $DIR/type-overflow.rs:10:16
--> $DIR/type-overflow.rs:11:16
|
LL | let fail = 0b1000_0001i8;
| ^^^^^^^^^^^^^
Expand All @@ -29,7 +29,7 @@ LL | let fail = 0b1000_0001u8 as i8;
| ~~~~~~~~~~~~~~~~~~~

warning: literal out of range for `i64`
--> $DIR/type-overflow.rs:12:16
--> $DIR/type-overflow.rs:15:16
|
LL | let fail = 0x8000_0000_0000_0000i64;
| ^^^^^^^^^^^^^^^^^^^^^^^^
Expand All @@ -45,15 +45,15 @@ LL | let fail = 0x8000_0000_0000_0000u64 as i64;
| ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

warning: literal out of range for `u32`
--> $DIR/type-overflow.rs:14:16
--> $DIR/type-overflow.rs:19:16
|
LL | let fail = 0x1_FFFF_FFFFu32;
| ^^^^^^^^^^^^^^^^ help: consider using the type `u64` instead: `0x1_FFFF_FFFFu64`
|
= note: the literal `0x1_FFFF_FFFFu32` (decimal `8589934591`) does not fit into the type `u32` and will become `4294967295u32`

warning: literal out of range for `i128`
--> $DIR/type-overflow.rs:16:22
--> $DIR/type-overflow.rs:22:22
|
LL | let fail: i128 = 0x8000_0000_0000_0000_0000_0000_0000_0000;
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
Expand All @@ -66,26 +66,63 @@ LL | let fail: i128 = 0x8000_0000_0000_0000_0000_0000_0000_0000u128 as i128;
| ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

warning: literal out of range for `i32`
--> $DIR/type-overflow.rs:19:16
--> $DIR/type-overflow.rs:27:16
|
LL | let fail = 0x8000_0000_0000_0000_0000_0000_0000_0000;
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
= note: the literal `0x8000_0000_0000_0000_0000_0000_0000_0000` (decimal `170141183460469231731687303715884105728`) does not fit into the type `i32` and will become `0i32`
= help: consider using the type `u128` instead

warning: literal out of range for `i32`
--> $DIR/type-overflow.rs:31:17
|
LL | let fail = -0x8000_0000_0000_0000_0000_0000_0000_0000; // issue #131849
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
= note: the literal `0x8000_0000_0000_0000_0000_0000_0000_0000` (decimal `170141183460469231731687303715884105728`) does not fit into the type `i32`
= note: and the value `-0x8000_0000_0000_0000_0000_0000_0000_0000` will become `0i32`
= help: consider using the type `i128` instead

warning: literal out of range for `i128`
--> $DIR/type-overflow.rs:35:17
|
LL | let fail = -0x8000_0000_0000_0000_0000_0000_0000_0001i128;
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
= note: the literal `0x8000_0000_0000_0000_0000_0000_0000_0001i128` (decimal `170141183460469231731687303715884105729`) does not fit into the type `i128`
= note: and the value `-0x8000_0000_0000_0000_0000_0000_0000_0001i128` will become `170141183460469231731687303715884105727i128`

warning: literal out of range for `i8`
--> $DIR/type-overflow.rs:38:16
|
LL | let fail = 340282366920938463463374607431768211455i8;
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
= note: the literal `340282366920938463463374607431768211455i8` does not fit into the type `i8` whose range is `-128..=127`
= help: consider using the type `u128` instead

warning: literal out of range for `i32`
--> $DIR/type-overflow.rs:42:16
|
LL | let fail = 0x8FFF_FFFF_FFFF_FFFE;
| ^^^^^^^^^^^^^^^^^^^^^
|
= note: the literal `0x8FFF_FFFF_FFFF_FFFE` (decimal `10376293541461622782`) does not fit into the type `i32` and will become `-2i32`
= help: consider using the type `i128` instead
= help: consider using the type `u64` instead
help: to use as a negative number (decimal `-2`), consider using the type `u32` for the literal and cast it to `i32`
|
LL | let fail = 0x8FFF_FFFF_FFFF_FFFEu32 as i32;
| ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

warning: literal out of range for `i8`
--> $DIR/type-overflow.rs:21:17
--> $DIR/type-overflow.rs:46:17
|
LL | let fail = -0b1111_1111i8;
| ^^^^^^^^^^^^^ help: consider using the type `i16` instead: `0b1111_1111i16`
|
= note: the literal `0b1111_1111i8` (decimal `255`) does not fit into the type `i8`
= note: and the value `-0b1111_1111i8` will become `1i8`

warning: 7 warnings emitted
warning: 11 warnings emitted