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

libnative uses CreateProcessA on windows #13815

Closed
alexcrichton opened this issue Apr 28, 2014 · 9 comments · Fixed by #14075
Closed

libnative uses CreateProcessA on windows #13815

alexcrichton opened this issue Apr 28, 2014 · 9 comments · Fixed by #14075
Labels
A-runtime Area: std's runtime and "pre-main" init for handling backtraces, unwinds, stack overflows E-easy Call for participation: Easy difficulty. Experience needed to fix: Not much. Good first issue. E-mentor Call for participation: This issue has a mentor. Use #t-compiler/help on Zulip for discussion. O-windows Operating system: Windows

Comments

@alexcrichton
Copy link
Member

It should use CreateProcessW to properly encode running binaries with utf8 names.

Needs tests to be accompanied with the change.

cc #9822, I can mentor this

@Rufflewind
Copy link
Contributor

Made an attempt at it (no tests yet). I did some manual testing on Windows and it looks like the current working directory and environment variables are being encoded correctly. However, the arguments are still showing garbage (encoded as UTF8 but with zeroes after every byte).

Edit 1: Found the source of the problem: make_command_line doesn't handle Unicode properly.

Edit 2: Changed to GetEnvironmentStrings (os::env_as_bytes) as well. Do you want this as a separate patch or combine with the above?

@alexcrichton
Copy link
Member Author

Nice work! Feel free to lump it all together as 1 PR, but separate commits for separate changes would be nice.

@Rufflewind
Copy link
Contributor

Thanks! Do you have any suggestions on how I should write the tests? Testing spawn and env_as_bytes requires coordinating at least two processes so I'm not sure how that would work in the testing framework.

@alexcrichton
Copy link
Member Author

I'd recommend writing a run-pass test or two with some interesting file names. The test can exec itself to test other argument passing behavior.

@Rufflewind
Copy link
Contributor

Here's a preliminary test that copies itself into a subdirectory with a non-ASCII name and then runs it as a child process. The parent process also adds an environment variable and an argument, both containing non-ASCII characters. The child process makes sure all the strings are intact.

It works fine when compiled and executed manually (on both Debian and Windows), but not with the test runner. On both Debian and Windows the test fails due to missing symbols. I'm looking into this but don't have an explanation/solution yet.

@alexcrichton
Copy link
Member Author

Nice job, that looks great!

You're likely seeing problems due to being unable to find the dynamic library dependencies. You're overriding the dynamic loader path environment variable to nothing, so all the libraries cannot be found.

You can probably get around it by compiling statically, using // no-prefer-dynamic near the top of the file (like other test directives).

@alexcrichton
Copy link
Member Author

It would also probably be best to use std::io::Process instead of native::io::Process directly. That way you can test both libgreen and libnative.

@Rufflewind
Copy link
Contributor

You're likely seeing problems due to being unable to find the dynamic library dependencies. You're overriding the dynamic loader path environment variable to nothing, so all the libraries cannot be found.

That's what I originally thought too, so I made sure to append to the existing environment variables. However, the error still occurs. I'll use // no-prefer-dynamic and see if that helps.

@Rufflewind
Copy link
Contributor

I think the reason why the library can't be found is because the test runner adds a relative path to the environment variables. But, in any case, using static linking works.

(Sorry for the spam; didn't realize "Issue" is a special word on GitHub.)

bors added a commit that referenced this issue May 13, 2014
- Use Unicode-aware versions of `CreateProcess` (Fixes #13815) and `Get/FreeEnvironmentStrings`.
    - Includes a helper function `os::win32::as_mut_utf16_p`, which does the same thing as `os::win32::as_utf16_p` except the pointer is mutable.
    - Fixed `make_command_line` to handle Unicode correctly.
- Tests for the above.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-runtime Area: std's runtime and "pre-main" init for handling backtraces, unwinds, stack overflows E-easy Call for participation: Easy difficulty. Experience needed to fix: Not much. Good first issue. E-mentor Call for participation: This issue has a mentor. Use #t-compiler/help on Zulip for discussion. O-windows Operating system: Windows
Projects
None yet
Development

Successfully merging a pull request may close this issue.

2 participants