-
Notifications
You must be signed in to change notification settings - Fork 13.3k
"raw pointers cannot be cast to integers in statics" justification is incorrect #30705
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Comments
If this were true then statics could not take references to each other. Hence casting pointers to integers should be allowed in statics. |
First, the extended diagnostic errors are not written by the core Rust team, so inaccuracies are to be expected (we would still like to fix them to some degree). Of course, the real reason is that we want the values of statics to be known at compile-time, either as an integer or as a known offset from a symbol, and that if you could cast pointers to integers, you could do arithmetic on these integers and end up with values that are neither. It certainly would have been possible to prohibit the arithmetic instead of the round-tripping, but at the time it seemed to me that it would be just an insufficiently useful overcomplication. If you have a sensible use-case for a more lenient model, we would like to know about it. Maybe I should rather attach this post to the error message? |
Of course this cannot work.
I have a single use case namely pub static SELF_PTR: usize = &SELF_PTR as *const _ as usize;
let real_to_virt = SELF_PTR - (&SELF_PTR as *const _ as usize); to calculate the difference between the current program counter and the position the linker assumed the program counter to be. In OS dev this can then be used to create the page tables with the correct virtual to physical address mapping. The advantage of usize is that the static doesn't have to be mut because usize is Sync. It's not that big of an issue. |
Making it work would require some significant modification to the Can't you wrap your pointer with an |
lrs has deprecated Unique in favor of
And none of these implement Sync. In any case, since this pointer is only used once to calculate real_to_virt, I don't think using a wrapper is worth it. This is not a big issue and it's certainly not necessary to do any modifications to fix this use case. |
If you're speaking of E0018, my bad, I'm the one who wrote it. How would you improve the error explanation? |
Personally, I'd find it very useful for things like descriptor handling in OS dev. What I would like to be able to do is something like this: type InterruptHandler = fn();
#[repr(C, packed)]
struct Descriptor {
base_low: u16,
selector: u16,
flags: u16,
base_high:u16,
impl Descriptor
const fn new(handler: &InterruptHandler, selector: u16, flags: u16) -> Descriptor {
Descriptor {
base_low: (handler as *const _ as usize & 0xFFFF) as u16,
selector: selector,
flags: flags,
base_high: ((handler as *const _ as usize >> 16) & 0xFFFF) as u16,
}
}
} The architecture defines the format of a |
This is incorrect as the following code shows:
The value of
X
is only known at link time.The text was updated successfully, but these errors were encountered: