Skip to content

Commit ce734ba

Browse files
committed
Remove i128 and u128 from improper_ctypes_definitions
Rust's 128-bit integers have historically been incompatible with C [1]. However, there have been a number of changes in Rust and LLVM that mean this is no longer the case: * Incorrect alignment of `i128` on x86 [1]: adjusting Rust's alignment proposed at rust-lang/compiler-team#683, implemented at rust-lang#116672. * LLVM version of the above: resolved in LLVM, including ABI fix. Present in LLVM18 (our minimum supported version). * Incorrect alignment of `i128` on 64-bit PowerPC, SPARC, and MIPS [2]: Rust's data layouts adjusted at rust-lang#132422, rust-lang#132741, rust-lang#134115. * LLVM version of the above: done in LLVM 20 llvm/llvm-project#102783. * Incorrect return convention of `i128` on Windows: adjusted to match GCC and Clang at rust-lang#134290. At [3], the lang team considered it acceptable to remove `i128` from `improper_ctypes_definitions` if the LLVM version is known to be compatible. Time has elapsed since then and we have dropped support for LLVM versions that do not have the x86 fixes, meaning a per-llvm-version lint should no longer be necessary. The PowerPC, SPARC, and MIPS changes only came in LLVM 20 but since Rust's datalayouts have also been updated to match, we will be using the correct alignment regardless of LLVM version. Closes: rust-lang#134288 Closes: rust-lang#128950 [1]: rust-lang#54341 [2]: rust-lang#128950 [3]: rust-lang/lang-team#255 (comment)
1 parent 4e1356b commit ce734ba

10 files changed

+58
-196
lines changed

compiler/rustc_lint/messages.ftl

-2
Original file line numberDiff line numberDiff line change
@@ -359,8 +359,6 @@ lint_improper_ctypes = `extern` {$desc} uses type `{$ty}`, which is not FFI-safe
359359
.label = not FFI-safe
360360
.note = the type is defined here
361361
362-
lint_improper_ctypes_128bit = 128-bit integers don't currently have a known stable ABI
363-
364362
lint_improper_ctypes_array_help = consider passing a pointer to the array
365363
366364
lint_improper_ctypes_array_reason = passing raw arrays by value is not FFI-safe

compiler/rustc_lint/src/types.rs

-4
Original file line numberDiff line numberDiff line change
@@ -1296,10 +1296,6 @@ impl<'a, 'tcx> ImproperCTypesVisitor<'a, 'tcx> {
12961296
// but only the base type is relevant for being representable in FFI.
12971297
ty::Pat(base, ..) => self.check_type_for_ffi(acc, base),
12981298

1299-
ty::Int(ty::IntTy::I128) | ty::Uint(ty::UintTy::U128) => {
1300-
FfiUnsafe { ty, reason: fluent::lint_improper_ctypes_128bit, help: None }
1301-
}
1302-
13031299
// Primitive types with a stable representation.
13041300
ty::Bool | ty::Int(..) | ty::Uint(..) | ty::Float(..) | ty::Never => FfiSafe,
13051301

tests/ui/asm/naked-functions-ffi.rs

-1
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,6 @@ use std::arch::naked_asm;
88
#[naked]
99
pub extern "C" fn naked(p: char) -> u128 {
1010
//~^ WARN uses type `char`
11-
//~| WARN uses type `u128`
1211
unsafe {
1312
naked_asm!("");
1413
}

tests/ui/asm/naked-functions-ffi.stderr

+1-9
Original file line numberDiff line numberDiff line change
@@ -8,13 +8,5 @@ LL | pub extern "C" fn naked(p: char) -> u128 {
88
= note: the `char` type has no C equivalent
99
= note: `#[warn(improper_ctypes_definitions)]` on by default
1010

11-
warning: `extern` fn uses type `u128`, which is not FFI-safe
12-
--> $DIR/naked-functions-ffi.rs:9:37
13-
|
14-
LL | pub extern "C" fn naked(p: char) -> u128 {
15-
| ^^^^ not FFI-safe
16-
|
17-
= note: 128-bit integers don't currently have a known stable ABI
18-
19-
warning: 2 warnings emitted
11+
warning: 1 warning emitted
2012

tests/ui/lint/lint-ctypes-enum.rs

-6
Original file line numberDiff line numberDiff line change
@@ -80,14 +80,12 @@ extern "C" {
8080
fn option_nonzero_u32(x: Option<num::NonZero<u32>>);
8181
fn option_nonzero_u64(x: Option<num::NonZero<u64>>);
8282
fn option_nonzero_u128(x: Option<num::NonZero<u128>>);
83-
//~^ ERROR `extern` block uses type `u128`
8483
fn option_nonzero_usize(x: Option<num::NonZero<usize>>);
8584
fn option_nonzero_i8(x: Option<num::NonZero<i8>>);
8685
fn option_nonzero_i16(x: Option<num::NonZero<i16>>);
8786
fn option_nonzero_i32(x: Option<num::NonZero<i32>>);
8887
fn option_nonzero_i64(x: Option<num::NonZero<i64>>);
8988
fn option_nonzero_i128(x: Option<num::NonZero<i128>>);
90-
//~^ ERROR `extern` block uses type `i128`
9189
fn option_nonzero_isize(x: Option<num::NonZero<isize>>);
9290
fn option_transparent_struct(x: Option<TransparentStruct<num::NonZero<u8>>>);
9391
fn option_transparent_enum(x: Option<TransparentEnum<num::NonZero<u8>>>);
@@ -105,14 +103,12 @@ extern "C" {
105103
fn result_nonzero_u32_t(x: Result<num::NonZero<u32>, ()>);
106104
fn result_nonzero_u64_t(x: Result<num::NonZero<u64>, ()>);
107105
fn result_nonzero_u128_t(x: Result<num::NonZero<u128>, ()>);
108-
//~^ ERROR `extern` block uses type `u128`
109106
fn result_nonzero_usize_t(x: Result<num::NonZero<usize>, ()>);
110107
fn result_nonzero_i8_t(x: Result<num::NonZero<i8>, ()>);
111108
fn result_nonzero_i16_t(x: Result<num::NonZero<i16>, ()>);
112109
fn result_nonzero_i32_t(x: Result<num::NonZero<i32>, ()>);
113110
fn result_nonzero_i64_t(x: Result<num::NonZero<i64>, ()>);
114111
fn result_nonzero_i128_t(x: Result<num::NonZero<i128>, ()>);
115-
//~^ ERROR `extern` block uses type `i128`
116112
fn result_nonzero_isize_t(x: Result<num::NonZero<isize>, ()>);
117113
fn result_transparent_struct_t(x: Result<TransparentStruct<num::NonZero<u8>>, ()>);
118114
fn result_transparent_enum_t(x: Result<TransparentEnum<num::NonZero<u8>>, ()>);
@@ -143,14 +139,12 @@ extern "C" {
143139
fn result_nonzero_u32_e(x: Result<(), num::NonZero<u32>>);
144140
fn result_nonzero_u64_e(x: Result<(), num::NonZero<u64>>);
145141
fn result_nonzero_u128_e(x: Result<(), num::NonZero<u128>>);
146-
//~^ ERROR `extern` block uses type `u128`
147142
fn result_nonzero_usize_e(x: Result<(), num::NonZero<usize>>);
148143
fn result_nonzero_i8_e(x: Result<(), num::NonZero<i8>>);
149144
fn result_nonzero_i16_e(x: Result<(), num::NonZero<i16>>);
150145
fn result_nonzero_i32_e(x: Result<(), num::NonZero<i32>>);
151146
fn result_nonzero_i64_e(x: Result<(), num::NonZero<i64>>);
152147
fn result_nonzero_i128_e(x: Result<(), num::NonZero<i128>>);
153-
//~^ ERROR `extern` block uses type `i128`
154148
fn result_nonzero_isize_e(x: Result<(), num::NonZero<isize>>);
155149
fn result_transparent_struct_e(x: Result<(), TransparentStruct<num::NonZero<u8>>>);
156150
fn result_transparent_enum_e(x: Result<(), TransparentEnum<num::NonZero<u8>>>);

tests/ui/lint/lint-ctypes-enum.stderr

+19-67
Original file line numberDiff line numberDiff line change
@@ -45,24 +45,8 @@ note: the type is defined here
4545
LL | enum T {
4646
| ^^^^^^
4747

48-
error: `extern` block uses type `u128`, which is not FFI-safe
49-
--> $DIR/lint-ctypes-enum.rs:82:31
50-
|
51-
LL | fn option_nonzero_u128(x: Option<num::NonZero<u128>>);
52-
| ^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
53-
|
54-
= note: 128-bit integers don't currently have a known stable ABI
55-
56-
error: `extern` block uses type `i128`, which is not FFI-safe
57-
--> $DIR/lint-ctypes-enum.rs:89:31
58-
|
59-
LL | fn option_nonzero_i128(x: Option<num::NonZero<i128>>);
60-
| ^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
61-
|
62-
= note: 128-bit integers don't currently have a known stable ABI
63-
6448
error: `extern` block uses type `Option<TransparentUnion<NonZero<u8>>>`, which is not FFI-safe
65-
--> $DIR/lint-ctypes-enum.rs:94:36
49+
--> $DIR/lint-ctypes-enum.rs:92:36
6650
|
6751
LL | fn option_transparent_union(x: Option<TransparentUnion<num::NonZero<u8>>>);
6852
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
@@ -71,7 +55,7 @@ LL | fn option_transparent_union(x: Option<TransparentUnion<num::NonZero<u8>
7155
= note: enum has no representation hint
7256

7357
error: `extern` block uses type `Option<Rust<NonZero<u8>>>`, which is not FFI-safe
74-
--> $DIR/lint-ctypes-enum.rs:96:28
58+
--> $DIR/lint-ctypes-enum.rs:94:28
7559
|
7660
LL | fn option_repr_rust(x: Option<Rust<num::NonZero<u8>>>);
7761
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
@@ -80,32 +64,16 @@ LL | fn option_repr_rust(x: Option<Rust<num::NonZero<u8>>>);
8064
= note: enum has no representation hint
8165

8266
error: `extern` block uses type `Option<u8>`, which is not FFI-safe
83-
--> $DIR/lint-ctypes-enum.rs:97:21
67+
--> $DIR/lint-ctypes-enum.rs:95:21
8468
|
8569
LL | fn option_u8(x: Option<u8>);
8670
| ^^^^^^^^^^ not FFI-safe
8771
|
8872
= help: consider adding a `#[repr(C)]`, `#[repr(transparent)]`, or integer `#[repr(...)]` attribute to this enum
8973
= note: enum has no representation hint
9074

91-
error: `extern` block uses type `u128`, which is not FFI-safe
92-
--> $DIR/lint-ctypes-enum.rs:107:33
93-
|
94-
LL | fn result_nonzero_u128_t(x: Result<num::NonZero<u128>, ()>);
95-
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
96-
|
97-
= note: 128-bit integers don't currently have a known stable ABI
98-
99-
error: `extern` block uses type `i128`, which is not FFI-safe
100-
--> $DIR/lint-ctypes-enum.rs:114:33
101-
|
102-
LL | fn result_nonzero_i128_t(x: Result<num::NonZero<i128>, ()>);
103-
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
104-
|
105-
= note: 128-bit integers don't currently have a known stable ABI
106-
10775
error: `extern` block uses type `Result<TransparentUnion<NonZero<u8>>, ()>`, which is not FFI-safe
108-
--> $DIR/lint-ctypes-enum.rs:119:38
76+
--> $DIR/lint-ctypes-enum.rs:115:38
10977
|
11078
LL | fn result_transparent_union_t(x: Result<TransparentUnion<num::NonZero<u8>>, ()>);
11179
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
@@ -114,7 +82,7 @@ LL | fn result_transparent_union_t(x: Result<TransparentUnion<num::NonZero<u
11482
= note: enum has no representation hint
11583

11684
error: `extern` block uses type `Result<Rust<NonZero<u8>>, ()>`, which is not FFI-safe
117-
--> $DIR/lint-ctypes-enum.rs:121:30
85+
--> $DIR/lint-ctypes-enum.rs:117:30
11886
|
11987
LL | fn result_repr_rust_t(x: Result<Rust<num::NonZero<u8>>, ()>);
12088
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
@@ -123,7 +91,7 @@ LL | fn result_repr_rust_t(x: Result<Rust<num::NonZero<u8>>, ()>);
12391
= note: enum has no representation hint
12492

12593
error: `extern` block uses type `Result<NonZero<u8>, U>`, which is not FFI-safe
126-
--> $DIR/lint-ctypes-enum.rs:125:51
94+
--> $DIR/lint-ctypes-enum.rs:121:51
12795
|
12896
LL | fn result_1zst_exhaustive_single_variant_t(x: Result<num::NonZero<u8>, U>);
12997
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
@@ -132,7 +100,7 @@ LL | fn result_1zst_exhaustive_single_variant_t(x: Result<num::NonZero<u8>,
132100
= note: enum has no representation hint
133101

134102
error: `extern` block uses type `Result<NonZero<u8>, B>`, which is not FFI-safe
135-
--> $DIR/lint-ctypes-enum.rs:127:53
103+
--> $DIR/lint-ctypes-enum.rs:123:53
136104
|
137105
LL | fn result_1zst_exhaustive_multiple_variant_t(x: Result<num::NonZero<u8>, B>);
138106
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
@@ -141,7 +109,7 @@ LL | fn result_1zst_exhaustive_multiple_variant_t(x: Result<num::NonZero<u8>
141109
= note: enum has no representation hint
142110

143111
error: `extern` block uses type `Result<NonZero<u8>, NonExhaustive>`, which is not FFI-safe
144-
--> $DIR/lint-ctypes-enum.rs:129:51
112+
--> $DIR/lint-ctypes-enum.rs:125:51
145113
|
146114
LL | fn result_1zst_non_exhaustive_no_variant_t(x: Result<num::NonZero<u8>, NonExhaustive>);
147115
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
@@ -150,7 +118,7 @@ LL | fn result_1zst_non_exhaustive_no_variant_t(x: Result<num::NonZero<u8>,
150118
= note: enum has no representation hint
151119

152120
error: `extern` block uses type `Result<NonZero<u8>, Field>`, which is not FFI-safe
153-
--> $DIR/lint-ctypes-enum.rs:132:49
121+
--> $DIR/lint-ctypes-enum.rs:128:49
154122
|
155123
LL | fn result_1zst_exhaustive_single_field_t(x: Result<num::NonZero<u8>, Field>);
156124
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
@@ -159,32 +127,16 @@ LL | fn result_1zst_exhaustive_single_field_t(x: Result<num::NonZero<u8>, Fi
159127
= note: enum has no representation hint
160128

161129
error: `extern` block uses type `Result<Result<(), NonZero<u8>>, ()>`, which is not FFI-safe
162-
--> $DIR/lint-ctypes-enum.rs:134:30
130+
--> $DIR/lint-ctypes-enum.rs:130:30
163131
|
164132
LL | fn result_cascading_t(x: Result<Result<(), num::NonZero<u8>>, ()>);
165133
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
166134
|
167135
= help: consider adding a `#[repr(C)]`, `#[repr(transparent)]`, or integer `#[repr(...)]` attribute to this enum
168136
= note: enum has no representation hint
169137

170-
error: `extern` block uses type `u128`, which is not FFI-safe
171-
--> $DIR/lint-ctypes-enum.rs:145:33
172-
|
173-
LL | fn result_nonzero_u128_e(x: Result<(), num::NonZero<u128>>);
174-
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
175-
|
176-
= note: 128-bit integers don't currently have a known stable ABI
177-
178-
error: `extern` block uses type `i128`, which is not FFI-safe
179-
--> $DIR/lint-ctypes-enum.rs:152:33
180-
|
181-
LL | fn result_nonzero_i128_e(x: Result<(), num::NonZero<i128>>);
182-
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
183-
|
184-
= note: 128-bit integers don't currently have a known stable ABI
185-
186138
error: `extern` block uses type `Result<(), TransparentUnion<NonZero<u8>>>`, which is not FFI-safe
187-
--> $DIR/lint-ctypes-enum.rs:157:38
139+
--> $DIR/lint-ctypes-enum.rs:151:38
188140
|
189141
LL | fn result_transparent_union_e(x: Result<(), TransparentUnion<num::NonZero<u8>>>);
190142
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
@@ -193,7 +145,7 @@ LL | fn result_transparent_union_e(x: Result<(), TransparentUnion<num::NonZe
193145
= note: enum has no representation hint
194146

195147
error: `extern` block uses type `Result<(), Rust<NonZero<u8>>>`, which is not FFI-safe
196-
--> $DIR/lint-ctypes-enum.rs:159:30
148+
--> $DIR/lint-ctypes-enum.rs:153:30
197149
|
198150
LL | fn result_repr_rust_e(x: Result<(), Rust<num::NonZero<u8>>>);
199151
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
@@ -202,7 +154,7 @@ LL | fn result_repr_rust_e(x: Result<(), Rust<num::NonZero<u8>>>);
202154
= note: enum has no representation hint
203155

204156
error: `extern` block uses type `Result<U, NonZero<u8>>`, which is not FFI-safe
205-
--> $DIR/lint-ctypes-enum.rs:163:51
157+
--> $DIR/lint-ctypes-enum.rs:157:51
206158
|
207159
LL | fn result_1zst_exhaustive_single_variant_e(x: Result<U, num::NonZero<u8>>);
208160
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
@@ -211,7 +163,7 @@ LL | fn result_1zst_exhaustive_single_variant_e(x: Result<U, num::NonZero<u8
211163
= note: enum has no representation hint
212164

213165
error: `extern` block uses type `Result<B, NonZero<u8>>`, which is not FFI-safe
214-
--> $DIR/lint-ctypes-enum.rs:165:53
166+
--> $DIR/lint-ctypes-enum.rs:159:53
215167
|
216168
LL | fn result_1zst_exhaustive_multiple_variant_e(x: Result<B, num::NonZero<u8>>);
217169
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
@@ -220,7 +172,7 @@ LL | fn result_1zst_exhaustive_multiple_variant_e(x: Result<B, num::NonZero<
220172
= note: enum has no representation hint
221173

222174
error: `extern` block uses type `Result<NonExhaustive, NonZero<u8>>`, which is not FFI-safe
223-
--> $DIR/lint-ctypes-enum.rs:167:51
175+
--> $DIR/lint-ctypes-enum.rs:161:51
224176
|
225177
LL | fn result_1zst_non_exhaustive_no_variant_e(x: Result<NonExhaustive, num::NonZero<u8>>);
226178
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
@@ -229,7 +181,7 @@ LL | fn result_1zst_non_exhaustive_no_variant_e(x: Result<NonExhaustive, num
229181
= note: enum has no representation hint
230182

231183
error: `extern` block uses type `Result<Field, NonZero<u8>>`, which is not FFI-safe
232-
--> $DIR/lint-ctypes-enum.rs:170:49
184+
--> $DIR/lint-ctypes-enum.rs:164:49
233185
|
234186
LL | fn result_1zst_exhaustive_single_field_e(x: Result<Field, num::NonZero<u8>>);
235187
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
@@ -238,7 +190,7 @@ LL | fn result_1zst_exhaustive_single_field_e(x: Result<Field, num::NonZero<
238190
= note: enum has no representation hint
239191

240192
error: `extern` block uses type `Result<(), Result<(), NonZero<u8>>>`, which is not FFI-safe
241-
--> $DIR/lint-ctypes-enum.rs:172:30
193+
--> $DIR/lint-ctypes-enum.rs:166:30
242194
|
243195
LL | fn result_cascading_e(x: Result<(), Result<(), num::NonZero<u8>>>);
244196
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe
@@ -247,13 +199,13 @@ LL | fn result_cascading_e(x: Result<(), Result<(), num::NonZero<u8>>>);
247199
= note: enum has no representation hint
248200

249201
error: `extern` block uses type `Result<(), ()>`, which is not FFI-safe
250-
--> $DIR/lint-ctypes-enum.rs:174:27
202+
--> $DIR/lint-ctypes-enum.rs:168:27
251203
|
252204
LL | fn result_unit_t_e(x: Result<(), ()>);
253205
| ^^^^^^^^^^^^^^ not FFI-safe
254206
|
255207
= help: consider adding a `#[repr(C)]`, `#[repr(transparent)]`, or integer `#[repr(...)]` attribute to this enum
256208
= note: enum has no representation hint
257209

258-
error: aborting due to 27 previous errors
210+
error: aborting due to 21 previous errors
259211

tests/ui/lint/lint-ctypes-fn.rs

+6-9
Original file line numberDiff line numberDiff line change
@@ -89,12 +89,6 @@ pub extern "C" fn boxed_trait(p: Box<dyn Trait>) { }
8989
pub extern "C" fn char_type(p: char) { }
9090
//~^ ERROR uses type `char`
9191

92-
pub extern "C" fn i128_type(p: i128) { }
93-
//~^ ERROR uses type `i128`
94-
95-
pub extern "C" fn u128_type(p: u128) { }
96-
//~^ ERROR uses type `u128`
97-
9892
pub extern "C" fn tuple_type(p: (i32, i32)) { }
9993
//~^ ERROR uses type `(i32, i32)`
10094

@@ -120,9 +114,6 @@ pub extern "C" fn fn_type2(p: fn()) { }
120114

121115
pub extern "C" fn fn_contained(p: RustBadRet) { }
122116

123-
pub extern "C" fn transparent_i128(p: TransparentI128) { }
124-
//~^ ERROR: uses type `i128`
125-
126117
pub extern "C" fn transparent_str(p: TransparentStr) { }
127118
//~^ ERROR: uses type `str`
128119

@@ -161,6 +152,12 @@ pub extern "C" fn good17(p: TransparentCustomZst) { }
161152
#[allow(improper_ctypes_definitions)]
162153
pub extern "C" fn good18(_: &String) { }
163154

155+
pub extern "C" fn good_i128_type(p: i128) { }
156+
157+
pub extern "C" fn good_u128_type(p: u128) { }
158+
159+
pub extern "C" fn good_transparent_i128(p: TransparentI128) { }
160+
164161
#[cfg(not(target_arch = "wasm32"))]
165162
pub extern "C" fn good1(size: *const c_int) { }
166163

0 commit comments

Comments
 (0)