@@ -64,6 +64,31 @@ enum ZeroIsValid {
64
64
One ( NonNull < ( ) > ) = 1 ,
65
65
}
66
66
67
+ #[ rustfmt:: skip]
68
+ #[ allow( dead_code) ]
69
+ enum SoManyVariants {
70
+ A1 , A2 , A3 , A4 , A5 , A6 , A7 , A8 , A9 , A10 , A11 , A12 , A13 , A14 , A15 , A16 , A17 ,
71
+ A18 , A19 , A20 , A21 , A22 , A23 , A24 , A25 , A26 , A27 , A28 , A29 , A30 , A31 , A32 ,
72
+ A33 , A34 , A35 , A36 , A37 , A38 , A39 , A40 , A41 , A42 , A43 , A44 , A45 , A46 , A47 ,
73
+ A48 , A49 , A50 , A51 , A52 , A53 , A54 , A55 , A56 , A57 , A58 , A59 , A60 , A61 , A62 ,
74
+ A63 , A64 , A65 , A66 , A67 , A68 , A69 , A70 , A71 , A72 , A73 , A74 , A75 , A76 , A77 ,
75
+ A78 , A79 , A80 , A81 , A82 , A83 , A84 , A85 , A86 , A87 , A88 , A89 , A90 , A91 , A92 ,
76
+ A93 , A94 , A95 , A96 , A97 , A98 , A99 , A100 , A101 , A102 , A103 , A104 , A105 , A106 ,
77
+ A107 , A108 , A109 , A110 , A111 , A112 , A113 , A114 , A115 , A116 , A117 , A118 , A119 ,
78
+ A120 , A121 , A122 , A123 , A124 , A125 , A126 , A127 , A128 , A129 , A130 , A131 , A132 ,
79
+ A133 , A134 , A135 , A136 , A137 , A138 , A139 , A140 , A141 , A142 , A143 , A144 , A145 ,
80
+ A146 , A147 , A148 , A149 , A150 , A151 , A152 , A153 , A154 , A155 , A156 , A157 , A158 ,
81
+ A159 , A160 , A161 , A162 , A163 , A164 , A165 , A166 , A167 , A168 , A169 , A170 , A171 ,
82
+ A172 , A173 , A174 , A175 , A176 , A177 , A178 , A179 , A180 , A181 , A182 , A183 , A184 ,
83
+ A185 , A186 , A187 , A188 , A189 , A190 , A191 , A192 , A193 , A194 , A195 , A196 , A197 ,
84
+ A198 , A199 , A200 , A201 , A202 , A203 , A204 , A205 , A206 , A207 , A208 , A209 , A210 ,
85
+ A211 , A212 , A213 , A214 , A215 , A216 , A217 , A218 , A219 , A220 , A221 , A222 , A223 ,
86
+ A224 , A225 , A226 , A227 , A228 , A229 , A230 , A231 , A232 , A233 , A234 , A235 , A236 ,
87
+ A237 , A238 , A239 , A240 , A241 , A242 , A243 , A244 , A245 , A246 , A247 , A248 , A249 ,
88
+ A250 , A251 , A252 , A253 , A254 , A255 , A256 ,
89
+ }
90
+
91
+ #[ track_caller]
67
92
fn test_panic_msg < T > ( op : impl ( FnOnce ( ) -> T ) + panic:: UnwindSafe , msg : & str ) {
68
93
let err = panic:: catch_unwind ( op) . err ( ) ;
69
94
assert_eq ! (
@@ -72,6 +97,19 @@ fn test_panic_msg<T>(op: impl (FnOnce() -> T) + panic::UnwindSafe, msg: &str) {
72
97
) ;
73
98
}
74
99
100
+ #[ track_caller]
101
+ // If strict mode is enabled, expect the msg. Otherwise, expect there to be no error.
102
+ fn test_strict_panic_msg < T > ( op : impl ( FnOnce ( ) -> T ) + panic:: UnwindSafe , msg : & str ) {
103
+ let err = panic:: catch_unwind ( op) . err ( ) ;
104
+
105
+ let expectation = if cfg ! ( strict) { Some ( & msg) } else { None } ;
106
+
107
+ assert_eq ! (
108
+ err. as_ref( ) . and_then( |a| a. downcast_ref:: <& str >( ) ) ,
109
+ expectation
110
+ ) ;
111
+ }
112
+
75
113
fn main ( ) {
76
114
unsafe {
77
115
// Uninhabited types
@@ -221,6 +259,67 @@ fn main() {
221
259
"attempted to leave type `core::mem::manually_drop::ManuallyDrop<LR>` uninitialized, which is invalid"
222
260
) ;
223
261
262
+ test_panic_msg (
263
+ || mem:: uninitialized :: < & ' static [ u8 ] > ( ) ,
264
+ "attempted to leave type `&[u8]` uninitialized, which is invalid"
265
+ ) ;
266
+
267
+ test_panic_msg (
268
+ || mem:: uninitialized :: < & ' static [ u16 ] > ( ) ,
269
+ "attempted to leave type `&[u16]` uninitialized, which is invalid"
270
+ ) ;
271
+
272
+ test_panic_msg (
273
+ || mem:: uninitialized :: < SoManyVariants > ( ) ,
274
+ "attempted to leave type `SoManyVariants` uninitialized, which is invalid"
275
+ ) ;
276
+
277
+ test_panic_msg (
278
+ || mem:: zeroed :: < [ ( & ' static [ u8 ] , & ' static str ) ; 1 ] > ( ) ,
279
+ "attempted to zero-initialize type `[(&[u8], &str); 1]`, which is invalid"
280
+ ) ;
281
+
282
+ test_panic_msg (
283
+ || mem:: uninitialized :: < [ & ' static [ u16 ] ; 1 ] > ( ) ,
284
+ "attempted to leave type `[&[u16]; 1]` uninitialized, which is invalid"
285
+ ) ;
286
+
287
+ test_panic_msg (
288
+ || mem:: zeroed :: < [ NonNull < ( ) > ; 1 ] > ( ) ,
289
+ "attempted to zero-initialize type `[core::ptr::non_null::NonNull<()>; 1]`, which is invalid"
290
+ ) ;
291
+
292
+ test_panic_msg (
293
+ || mem:: uninitialized :: < [ NonNull < ( ) > ; 1 ] > ( ) ,
294
+ "attempted to leave type `[core::ptr::non_null::NonNull<()>; 1]` uninitialized, which is invalid"
295
+ ) ;
296
+
297
+ test_panic_msg (
298
+ || mem:: zeroed :: < LR_NonZero > ( ) ,
299
+ "attempted to zero-initialize type `LR_NonZero`, which is invalid"
300
+ ) ;
301
+
302
+ test_panic_msg (
303
+ || mem:: zeroed :: < [ LR_NonZero ; 1 ] > ( ) ,
304
+ "attempted to zero-initialize type `[LR_NonZero; 1]`, which is invalid"
305
+ ) ;
306
+
307
+ test_panic_msg (
308
+ || mem:: zeroed :: < [ LR_NonZero ; 1 ] > ( ) ,
309
+ "attempted to zero-initialize type `[LR_NonZero; 1]`, which is invalid"
310
+ ) ;
311
+
312
+ test_panic_msg (
313
+ || mem:: zeroed :: < ManuallyDrop < LR_NonZero > > ( ) ,
314
+ "attempted to zero-initialize type `core::mem::manually_drop::ManuallyDrop<LR_NonZero>`, \
315
+ which is invalid"
316
+ ) ;
317
+
318
+ test_panic_msg (
319
+ || mem:: uninitialized :: < ( & ' static [ u8 ] , & ' static str ) > ( ) ,
320
+ "attempted to leave type `(&[u8], &str)` uninitialized, which is invalid"
321
+ ) ;
322
+
224
323
// Some things that should work.
225
324
let _val = mem:: zeroed :: < bool > ( ) ;
226
325
let _val = mem:: zeroed :: < LR > ( ) ;
@@ -230,63 +329,34 @@ fn main() {
230
329
let _val = mem:: zeroed :: < MaybeUninit < NonNull < u32 > > > ( ) ;
231
330
let _val = mem:: zeroed :: < [ !; 0 ] > ( ) ;
232
331
let _val = mem:: zeroed :: < ZeroIsValid > ( ) ;
332
+ let _val = mem:: zeroed :: < SoManyVariants > ( ) ;
333
+ let _val = mem:: uninitialized :: < [ SoManyVariants ; 0 ] > ( ) ;
233
334
let _val = mem:: uninitialized :: < MaybeUninit < bool > > ( ) ;
234
335
let _val = mem:: uninitialized :: < [ !; 0 ] > ( ) ;
235
336
let _val = mem:: uninitialized :: < ( ) > ( ) ;
236
337
let _val = mem:: uninitialized :: < ZeroSized > ( ) ;
237
338
238
- if cfg ! ( strict) {
239
- test_panic_msg (
240
- || mem:: uninitialized :: < i32 > ( ) ,
241
- "attempted to leave type `i32` uninitialized, which is invalid"
242
- ) ;
243
-
244
- test_panic_msg (
245
- || mem:: uninitialized :: < * const ( ) > ( ) ,
246
- "attempted to leave type `*const ()` uninitialized, which is invalid"
247
- ) ;
248
-
249
- test_panic_msg (
250
- || mem:: uninitialized :: < [ i32 ; 1 ] > ( ) ,
251
- "attempted to leave type `[i32; 1]` uninitialized, which is invalid"
252
- ) ;
253
-
254
- test_panic_msg (
255
- || mem:: zeroed :: < NonNull < ( ) > > ( ) ,
256
- "attempted to zero-initialize type `core::ptr::non_null::NonNull<()>`, which is invalid"
257
- ) ;
258
-
259
- test_panic_msg (
260
- || mem:: zeroed :: < [ NonNull < ( ) > ; 1 ] > ( ) ,
261
- "attempted to zero-initialize type `[core::ptr::non_null::NonNull<()>; 1]`, which is invalid"
262
- ) ;
263
-
264
- // FIXME(#66151) we conservatively do not error here yet (by default).
265
- test_panic_msg (
266
- || mem:: zeroed :: < LR_NonZero > ( ) ,
267
- "attempted to zero-initialize type `LR_NonZero`, which is invalid"
268
- ) ;
269
-
270
- test_panic_msg (
271
- || mem:: zeroed :: < ManuallyDrop < LR_NonZero > > ( ) ,
272
- "attempted to zero-initialize type `core::mem::manually_drop::ManuallyDrop<LR_NonZero>`, \
273
- which is invalid"
274
- ) ;
275
- } else {
276
- // These are UB because they have not been officially blessed, but we await the resolution
277
- // of <https://github.com/rust-lang/unsafe-code-guidelines/issues/71> before doing
278
- // anything about that.
279
- let _val = mem:: uninitialized :: < i32 > ( ) ;
280
- let _val = mem:: uninitialized :: < * const ( ) > ( ) ;
281
-
282
- // These are UB, but best to test them to ensure we don't become unintentionally
283
- // stricter.
284
-
285
- // It's currently unchecked to create invalid enums and values inside arrays.
286
- let _val = mem:: zeroed :: < LR_NonZero > ( ) ;
287
- let _val = mem:: zeroed :: < [ LR_NonZero ; 1 ] > ( ) ;
288
- let _val = mem:: zeroed :: < [ NonNull < ( ) > ; 1 ] > ( ) ;
289
- let _val = mem:: uninitialized :: < [ NonNull < ( ) > ; 1 ] > ( ) ;
290
- }
339
+ // These are UB because they have not been officially blessed, but we await the resolution
340
+ // of <https://github.com/rust-lang/unsafe-code-guidelines/issues/71> before doing
341
+ // anything about that.
342
+ test_strict_panic_msg (
343
+ || mem:: uninitialized :: < i32 > ( ) ,
344
+ "attempted to leave type `i32` uninitialized, which is invalid"
345
+ ) ;
346
+
347
+ test_strict_panic_msg (
348
+ || mem:: uninitialized :: < * const ( ) > ( ) ,
349
+ "attempted to leave type `*const ()` uninitialized, which is invalid"
350
+ ) ;
351
+
352
+ test_strict_panic_msg (
353
+ || mem:: uninitialized :: < [ i32 ; 1 ] > ( ) ,
354
+ "attempted to leave type `[i32; 1]` uninitialized, which is invalid"
355
+ ) ;
356
+
357
+ test_strict_panic_msg (
358
+ || mem:: uninitialized :: < [ ( & ' static [ u8 ] , & ' static str ) ; 1 ] > ( ) ,
359
+ "attempted to leave type `[(&[u8], &str); 1]` uninitialized, which is invalid"
360
+ ) ;
291
361
}
292
362
}
0 commit comments