@@ -150,26 +150,36 @@ If you really want global mutable state, try using `static mut` or a global
150150"## ,
151151
152152E0018 : r##"
153- The value of static and const variables must be known at compile time. You
154- can't cast a pointer as an integer because we can't know what value the
155- address will take.
156153
157- However, pointers to other constants' addresses are allowed in constants,
158- example:
154+ The value of static and constant integers must be known at compile time. You
155+ can't cast a pointer to an integer because the address of a pointer can
156+ vary.
159157
158+ For example, if you write:
160159```
161- const X: u32 = 50;
162- const Y: *const u32 = &X;
160+ static MY_STATIC: u32 = 42;
161+ static MY_STATIC_ADDR: usize = &MY_STATIC as *const _ as usize;
162+ static WHAT: usize = (MY_STATIC_ADDR^17) + MY_STATIC_ADDR;
163163```
164164
165- Therefore, casting one of these non-constant pointers to an integer results
166- in a non-constant integer which lead to this error. Example:
165+ Then `MY_STATIC_ADDR` would contain the address of `MY_STATIC`. However,
166+ the address can change when the program is linked, as well as change
167+ between different executions due to ASLR, and many linkers would
168+ not be able to calculate the value of `WHAT`.
169+
170+ On the other hand, static and constant pointers can point either to
171+ a known numeric address or to the address of a symbol.
167172
168173```
169- const X: u32 = 1;
170- const Y: usize = &X as *const u32 as usize;
171- println!("{}", Y);
174+ static MY_STATIC_ADDR: &'static u32 = &MY_STATIC;
175+ // ... and also
176+ static MY_STATIC_ADDR2: *const u32 = &MY_STATIC;
177+
178+ const CONST_ADDR: *const u8 = 0x5f3759df as *const u8;
172179```
180+
181+ This does not pose a problem by itself because they can't be
182+ accessed directly.
173183"## ,
174184
175185E0019 : r##"
@@ -347,55 +357,59 @@ From [RFC 246]:
347357[RFC 246]: https://github.com/rust-lang/rfcs/pull/246
348358"## ,
349359
360+
350361E0395 : r##"
351- The value assigned to a constant expression must be known at compile time,
352- which is not the case when comparing raw pointers. Erroneous code example:
362+ The value assigned to a constant scalar must be known at compile time,
363+ which is not the case when comparing raw pointers.
353364
365+
366+ Erroneous code example:
354367```
355- static foo : i32 = 42;
356- static bar : i32 = 43 ;
368+ static FOO : i32 = 42;
369+ static BAR : i32 = 42 ;
357370
358- static baz : bool = { (&foo as *const i32) == (&bar as *const i32) };
371+ static BAZ : bool = { (&FOO as *const i32) == (&BAR as *const i32) };
359372// error: raw pointers cannot be compared in statics!
360373```
361374
362- Please check that the result of the comparison can be determined at compile time
363- or isn't assigned to a constant expression. Example:
375+ The address assigned by the linker to `FOO` and `BAR` may or may not
376+ be identical, so the value of `BAZ` can't be determined.
377+
378+ If you want to do the comparison, please do it at run-time.
379+
380+ For example:
364381
365382```
366- static foo : i32 = 42;
367- static bar : i32 = 43 ;
383+ static FOO : i32 = 42;
384+ static BAR : i32 = 42 ;
368385
369- let baz: bool = { (&foo as *const i32) == (&bar as *const i32) };
386+ let baz: bool = { (&FOO as *const i32) == (&BAR as *const i32) };
370387// baz isn't a constant expression so it's ok
371388```
372389"## ,
373390
374391E0396 : r##"
375- The value assigned to a constant expression must be known at compile time,
376- which is not the case when dereferencing raw pointers. Erroneous code
377- example:
392+ The value behind a raw pointer can't be determined at compile- time
393+ (or even link-time), which means it can't be used in a constant
394+ expression.
378395
396+ For example:
379397```
380- const foo: i32 = 42;
381- const baz: *const i32 = (&foo as *const i32);
398+ const REG_ADDR: *const u8 = 0x5f3759df as *const u8;
382399
383- const deref: i32 = *baz ;
400+ const VALUE: u8 = unsafe { *REG_ADDR } ;
384401// error: raw pointers cannot be dereferenced in constants
385402```
386403
387- To fix this error, please do not assign this value to a constant expression.
388- Example:
404+ A possible fix is to dereference your pointer at some point in run-time.
389405
390- ```
391- const foo: i32 = 42;
392- const baz: *const i32 = (&foo as *const i32);
406+ For example:
393407
394- unsafe { let deref: i32 = *baz; }
395- // baz isn't a constant expression so it's ok
396408```
409+ const REG_ADDR: *const u8 = 0x5f3759df as *const u8;
397410
398- You'll also note that this assignment must be done in an unsafe block!
411+ let reg_value = unsafe { *REG_ADDR };
412+ ```
399413"## ,
400414
401415E0397 : r##"
0 commit comments