Skip to content
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

Bug: PCWSTR is potentially unsound in safe code if used wrong #2258

Closed
MolotovCherry opened this issue Dec 23, 2022 · 2 comments
Closed

Bug: PCWSTR is potentially unsound in safe code if used wrong #2258

MolotovCherry opened this issue Dec 23, 2022 · 2 comments
Labels
bug Something isn't working

Comments

@MolotovCherry
Copy link

MolotovCherry commented Dec 23, 2022

Which crate is this about?

windows

Crate version

0.43.0

Summary

It is possible to cause corruption issues by using PCWSTR and not taking careful note about lifetimes and when things get dropped.

It might also be said that since we have to use the produced PCWSTR in unsafe code anyways, it's not strictly technically "unsafe" in safe code. But regardless, whatever course is decided from this report, I think this is important to take note of for people since it is a very easy gotcha to fall into.

Edit: Got here from #973 , and found that one of the posted solution comments had exactly this bug, demonstrating just how easy it is to accidentally get wrong. I really do feel that a convenience function to make a PCWSTR would help mitigate such a gotcha like this one

Toolchain version/configuration

Default host: x86_64-pc-windows-msvc
rustup home: C:\Users\MyUser\.rustup

installed toolchains

stable-x86_64-pc-windows-msvc
nightly-x86_64-pc-windows-msvc (default)
1.63-x86_64-pc-windows-msvc
1.65.0-x86_64-pc-windows-msvc

active toolchain

nightly-x86_64-pc-windows-msvc (default)
rustc 1.67.0-nightly (e75aab045 2022-11-09)

Reproducible example

For example, in the following, using PCWSTR at all is unsound, because the HSTRING it a temporary that gets immediately dropped, rendering the contents of the PCWSTR invalid from the get-go
PCWSTR(HSTRING::from(s).as_ptr())

To fix it, the values must be explicitly assigned so that they will drop after the usage of PCWSTR.

let h_title = HSTRING::from(title);
let h_message = HSTRING::from(message);

let title = PCWSTR::from_raw(h_title.as_ptr());
let message = PCWSTR::from_raw(h_message.as_ptr());

unsafe {
    MessageBoxW(None, message, title, icon.into());
}

Of course, it is possible to create this issue in other use-cases as well. The main point being, if the lifetime of the string isn't at least as long as PCWSTR, we're in trouble

Crate manifest

[dependencies.windows]
version = "0.43.0"
features = [
    "Win32_UI_WindowsAndMessaging",
    "Win32_Foundation"
]

Expected behavior

No corruption.

Actual behavior

Pointer in PCWSTR is invalid

Additional comments

Not sure the best way to fix this, but it is definitely a gotcha that many people may not be aware of.

@MolotovCherry MolotovCherry added the bug Something isn't working label Dec 23, 2022
@MolotovCherry MolotovCherry changed the title Bug: PCWSTR is unsafe in safe code Bug: PCWSTR is potentially unsafe in safe code if used wrong Dec 23, 2022
@riverar
Copy link
Collaborator

riverar commented Dec 23, 2022

Related to #2082, #2136, and others.

@MolotovCherry MolotovCherry changed the title Bug: PCWSTR is potentially unsafe in safe code if used wrong Bug: PCWSTR is potentially unsound in safe code if used wrong Dec 23, 2022
@kennykerr
Copy link
Collaborator

As @riverar pointed out, this has already been improved to some extent. While PCWSTR makes it relatively easy to write incorrect code, it is not in itself unsafe from a Rust perspective and care should be taken to use such APIs correctly.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working
Projects
None yet
Development

No branches or pull requests

3 participants