-
Notifications
You must be signed in to change notification settings - Fork 841
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
How to tell in Linux under WSL if using WSL1 vs WSL2 ? #4555
Comments
Here is a helpful doc - https://docs.microsoft.com/en-us/windows/wsl/wsl2-install while setting a distro to be backed by WSL 2, I would run the following command in Powershell: wsl -s 2 You can find your Distro by running: wsl -l |
Yes, but there is no particularly good way right now to know your own distribution name once you are inside. There was another ask for that recently #4479. Probably (possibly?) one way is to run a regex on
While WSL2:
If it were me I wouldn't make a hard bet on the WSL2 string being set in concrete, but conversely, I can't imagine the WSL1 format changing gratuitously (not without grumbling, anyway). Matching that " |
Here is a sample C program on how #include <stdio.h>
#include <string.h>
#include <sys/utsname.h>
int main(void)
{
struct utsname buf;
memset(&buf, 0, sizeof buf);
int ret = uname(&buf);
if (ret == 0)
{
if (strstr(buf.release, "Microsoft"))
printf("WSL1\n");
else
printf("WSL2\n");
}
else
printf("uname error\n");
} |
+1 for code always. But implied in my post was maybe better not to rely on |
There may be hundreds of ad-hoc way to do it. For example, only WSL2 has |
Money ➡️ mouth:
|
detect wsl1:) |
|
Update (Windows 10 version 2004): I'm brand new to WSL2, however...
|
WSL2 has the directory |
I think that perhaps a belt & braces approach is needed. We have don't have any control over WSL1 getting a similar folder added. Likewise, whether 'Microsoft' has upper or lower case. Using Try We can write something like Or alternatively, we can look in '/proc'. We can't guarantee 'lshw' to be present in every Linux distro, although it usually is: In WSL1 eg. |
What about the environment variable |
No. |
@Biswa96 I asked if it's suitable for WSL1 OR WSL 2, not WSL 2 vs WSL 1 so it sounds like the answer to my question is actually yes? |
Yes but not retroactively. |
@therealkenc is the way you described (distinguish between WSL 1 and WSL 2 using the GCC version) going to be guaranteed stable, even in future versions of WSL 1? Which is the guaranteed way to distinguish between these two and nōn-WSL Linux then? The presence of the string Someone suggested checking the root filesystem type, which for WSL 1 is Anything that needs superuser privilegues (lshw…) is also out, for hopefully obvious reasons. |
No guarantees in life. Although given that the unspoken textual API has now irretrievably leaked into userspace, yes, I would treat regex That said, users can (and do) compile their own kernels in WSL2 and then misname the their kernel, or compile with Possible approach:
|
This might do. I was thinking of simplifying this a bit:
Doing this without The WSL 2 detection is even more fragile. Addition of an API from the start would have helped :/ For version detection, uname(2) exists, so this can also be done without procfs. The WSL 2 caveats apply :/ |
Use |
therealkenc dixit:
In `uname(2)` if you can't depend on `/proc`. The `gcc` test was
belt+suspenders overkill, and given existence possibility `clang`
probably does more harm than good. `strstr(buf.release, "Microsoft")`
means WSL1. Else Linux/Android/WSL2. For [your
OK, great, that will work.
purposes](https://github.com/tarent/ECN-Bits/blob/18320ef9e0b0a674e09668392224770d7ba6a7be/c/lib/tc.c#L53)
WSL2 is Linux anyway.
Oh, kudos for finding this one. For that purpose, WSL 2 probably
is “don’t use” anyway, considering the networking issues. But I
guess there are other people around who might wish to figure out
WSL 2, too. Perhaps an identifier can be added in a next version?
Thanks, I’ll adapt the code to use uname(2) and check for WSL 1
only and document that.
|
WSL2 should be perfectly fine. WSL1 looks like it might be "don't use anyway". Either that's a hard fail in your use-case, or it isn't a hard fail. If it isn't a hard fail, there is no reason for it to be a hard fail on Linux or Android either. Just let that function always succeed, and lie about success when it doesn't. If it is a hard fail, you don't need to test for WSL1. Let it fail. The better approach than querying the OS is to test capabilities. Here, the runtime capability test is whether
That's existence environment |
therealkenc dixit:
> WSL 2 probably is “don’t use” anyway
WSL2 should be perfectly fine.
Except it doesn’t share the host network and doesn’t even
support IPv6, AIUI (I haven’t tested this yet, this was
information I gleaned from learning about WSL 2 ahead of
tests) which is a pretty big problem. Disqualifyingly so.
_WSL1_ looks like it might be "don't use anyway". Either that's a hard
Nah, the _setting_ the traffic class is an add-on, the
project is about _getting_ it really, and IPV6_RECVTCLASS
(and IP_RECVTOS) work fine, both on WSL 1 and on Winsock2.
fail in your use-case, or it isn't a hard fail. If it **isn't** a hard
fail, there is no reason for it to be a hard fail on Linux or Android
Mh, probably. I’ve documented this, but I’d expect Windows-
oriented users to use the ws2/ variant anyway, which omits
this functionality completely.
The better approach than querying the OS is to test capabilities. Here,
the runtime capability test is whether `setsockopt(...IPV6_TCLASS...)`
works, not whether you are "on WSL1" or "on Linux". Maybe one day in
some mythical future `IPV6_TCLASS` starts working on win32 (and by
extension WSL1). I bring it up not for your specific use-case, but
because near all of the "`if(WSL)`" scattered on the Interwebs are
testing the wrong thing.
Yes, completely!
Unfortunately, some of the things fail silently, or need an actual
network socket to test. This is also not quite my area of expertise,
but if I figure out feature tests I’ll use them. I’ve got multiple
places to work on first, though…
> Perhaps an identifier can be added in a next version?
That's existence environment `WSL_DISTRO_NAME ` for WSL plus `&&
WSL_INTEROP` to differentiate WSL1 v. WSL2. But you can't use it
Except when someone unset them… it’s like procfs… it’s normally
there but not always. Still helpful but fragile.
But thank you anyway. I’ll treat WSL 2 as regular Linux and
proceed with the tests, and WSL is not the project main concern
right now anyway.
|
Based on microsoft/WSL#4555 via https://github .com//issues/374 which has a ton more possibilities to detect WSL.
Based on microsoft/WSL#4555 via https://github .com//issues/374 which has a ton more possibilities to detect WSL.
Based on microsoft/WSL#4555 via #374 which has a ton more possibilities to detect WSL.
Based on microsoft/WSL#4555 via #374 which has a ton more possibilities to detect WSL.
Detecting WSL (bash code). Tested with
The detection should be future safe. Code is from a new (currently not released) native systemd initialization for WSL |
t-ru dixit:
Detecting WSL (bash code). Tested with
From a shell developer PoV this is horridly inefficient.
You call mount twice, you can use grep -q instead of -c,
a temporary file is also not necessary, etc.
(I needed a C solution in the project that caused me to ask anyway.)
bye,
//mirabilos
--
„Cool, /usr/share/doc/mksh/examples/uhr.gz ist ja ein Grund,
mksh auf jedem System zu installieren.“
-- XTaran auf der OpenRheinRuhr, ganz begeistert
(EN: “[…]uhr.gz is a reason to install mksh on every system.”)
|
Maybe. But it's working. Is your C-Code working under all conditions? Is your C-Code posted above inefficient?
many roads lead to rome
The temporary file is required. The reason is that commands (grep, awk, head, ...) are not work on wsl.exe.
Feel free and write your one holy grail solution. |
t-ru dixit:
> From a shell developer PoV this is horridly inefficient.
Maybe. But it's working.
I’m almost tempted to make a more efficient shell implementation
of the same algorithm, but your attitude is… off-putting, at least.
>a temporary file is also not necessary,
The temporary file is required. The reason is that grep on the wsl.exe does not work.
Why even use grep? Shows how little you understand the Unix toolkit
and shell. (But then, you mentioned systemd, so this is to be expected.)
bye,
//mirabilos
--
22:59⎜<Vutral> glaub ich termkit is kompliziert | glabe nicht das man
damit schneller arbeitet | reizüberflutung │ wie windows │ alles evil
zuviel bilder │ wie ein spiel | 23:00⎜<Vutral> die meisten raffen auch
nicht mehr von windows | 23:01⎜<Vutral> bilderbücher sind ja auch nich
wirklich verbreitet als erwachsenen literatur ‣ who needs GUIs thus?
|
I know the tools very well. But I write the code on a system that has only a minimal set of packages installed. Writing tiny code on systems that have all the tools installed is easy. Another aspect is that WSL is from Microsoft. There, the clocks tick differently than usual. By the way, the code was written in less than 30 minutes. Systemd is the devil and because it is so bad, all major Linux distributions have switched to Systemd. The problem with Systemd is not Systemd, but the users who don't understand it. It is the same as with Wayland.
The most important thing in an implementation is that it works. Optimization is phase 2. I published the code because there was no solution for the problem "detection of WSL" that works reliably so far. Feel free to adapt the code and write your own implementation. |
t-ru dixit:
if [ -n "$( cat /proc/self/mounts | grep rootfs | grep -E 'lxfs | wslfs' )" ] ; then
cat | grep | grep… AAAAAAAAAAAAH!
>I know the tools very well. But I write the code on a system that has
>only a minimal set of packages installed. Writing tiny code on systems
>that have all the tools installed is easy.
It’s not about the amount of tools, it’s how one uses them.
|
Bring butter to the fishes. Post better code. I will gladly take it over. I found code from you
Top code... What is with WSL and custom kernels? Many, many "if" statements. Is this good code? Write better code and post it. I'm waiting!!! |
This commit filters the following warning: > UserWarning: Signature b'\x00\xd0\xcc\xcc\xcc\xcc\xcc\xcc\xfb\xbf\x00\x00\x00\x00\x00\x00' for > <class 'numpy.longdouble'> does not match any known type: falling back to type probe function. > This warnings [sic] indicates broken support for the dtype! > machar = _get_machar(dtype) To ensure that this warning is only filtered on WSL1, we try to detect WSL by checking for a WSL-specific string from the uname, which appears to be endorsed by WSL devs. (microsoft/WSL#4555 (comment)) I also tried checking the `WSL_INTEROP` and `WSL_DISTRO_NAME` environment variables as suggested in the above linked issues, but I liked that `platform` was already imported inside `casting.py`. There is perhaps a more thorough approach where we collect all raised warnings, test the collected warnings, etc. but I didn't want to overcomplicate things.
This commit filters the following warning: > UserWarning: Signature b'\x00\xd0\xcc\xcc\xcc\xcc\xcc\xcc\xfb\xbf\x00\x00\x00\x00\x00\x00' for > <class 'numpy.longdouble'> does not match any known type: falling back to type probe function. > This warnings [sic] indicates broken support for the dtype! > machar = _get_machar(dtype) To ensure that this warning is only filtered on WSL1, we try to detect WSL by checking for a WSL-specific string from the uname, which appears to be endorsed by WSL devs. (microsoft/WSL#4555 (comment)) I also tried checking the `WSL_INTEROP` and `WSL_DISTRO_NAME` environment variables as suggested in the above linked issues, but I preferred reusing the `platform` module that was already imported inside `casting.py`. There is perhaps a more thorough approach where we collect all raised warnings, test the collected warnings, etc. but I didn't want to overcomplicate things.
This commit filters the following warning: > UserWarning: Signature b'\x00\xd0\xcc\xcc\xcc\xcc\xcc\xcc\xfb\xbf\x00\x00\x00\x00\x00\x00' for > <class 'numpy.longdouble'> does not match any known type: falling back to type probe function. > This warnings [sic] indicates broken support for the dtype! > machar = _get_machar(dtype) To ensure that this warning is only filtered on WSL1, we try to detect WSL by checking for a WSL-specific string from the uname, which appears to be endorsed by WSL devs. (microsoft/WSL#4555 (comment)) I also tried checking the `WSL_INTEROP` and `WSL_DISTRO_NAME` environment variables as suggested in the above linked issues, but I preferred reusing the `platform` module that was already imported inside `casting.py`. There is perhaps a more thorough approach where we collect all raised warnings, test the collected warnings, etc. but I didn't want to overcomplicate things.
This commit filters the following warning: > UserWarning: Signature b'\x00\xd0\xcc\xcc\xcc\xcc\xcc\xcc\xfb\xbf\x00\x00\x00\x00\x00\x00' for > <class 'numpy.longdouble'> does not match any known type: falling back to type probe function. > This warnings [sic] indicates broken support for the dtype! > machar = _get_machar(dtype) To ensure that this warning is only filtered on WSL1, we try to detect WSL by checking for a WSL-specific string from the uname, which appears to be endorsed by WSL devs. (microsoft/WSL#4555 (comment)) I also tried checking the `WSL_INTEROP` and `WSL_DISTRO_NAME` environment variables as suggested in the above linked issues, but I preferred reusing the `platform` module that was already imported inside `casting.py`. There is perhaps a more thorough approach where we collect all raised warnings, test the collected warnings, etc. but I didn't want to overcomplicate things.
Documentation missing instructions in how to tell within Linux under WSL whether using WSL1 or WSL2.
The text was updated successfully, but these errors were encountered: