Closed lion328 closed 2 years ago
Hi @lion328 !
Yeah, it makes sense. This is related to https://github.com/net-lisias-ksp/KSPe/issues/25 by the way.
The KSPe.Light
thingy behaves, it uses the host system's path separator as defined on the C# runtime. Since you are running Proton, the C# runtime believes it's a Windows machine and so KSPe.Light uses "\" as path separator.
IMHO this is a bug on Proton itself - it should be aware of that and somehow tell the Mono's runtime in use to use the "/" as path separator instead - or perhaps applying to the paths it receives from Mono the same handling done when receiving a path from a Windows native code.
There's a reason you are using Proton instead of the native Linux release of KSP?
Moving this to KSPe, as this is related to KSPe.Light
.
@lion328
Anyway, I don't think
Reparse_readlink
should be called inside Proton. I guess the sandbox Proton uses mapped/usr/bin
toZ:\usr\bin
and the mod foundreadlink
in there (I wonder if this can happen in Windows if I putreadlink
inC:\usr\bin
).
In time, it's not. Under Windows, native Windows32 calls are made to do the job (see this link for details).
Your problem is (almost surely) related to #25 (the "\" versus "/" thingy).
I done more tests today and found out that Proton can run Linux executables inside Windows apps, so part of it is probably a bug when Windows version of Mono run inside Proton. However, I don't see it is the same bug in #25. The last stack trace is similar but it came from a Linux version of Mono, while I use a Windows version of it (inside Proton).
The real problem, in my opinion, is the way the mod detects readlink
/realpath
here. When run inside *nix systems (and not inside Proton),Directory.GetFiles
is working properly. On the other hand, if this run inside WIndows, paths with /
in the front are interpreted as the root of the drive, so /usr/bin
will become C:\usr\bin
if I run KSP from C: drive. This means that I can rename an executable (or anything really) to readlink
, put it in C:\usr\bin
, and the mod will run it, even in Windows. This is definitely not a Proton bug, but Proton mapped the Linux filesystem to Z: drive, which is why Z:\usr\bin\readlink
was detected in the first place. It would be better if the mod check if it's running in Windows first before choosing which method to use.
There's a reason you are using Proton instead of the native Linux release of KSP?
For KSP it just a matter of preference really. I mean it ran pretty well so why not? Some games have an inferior Linux version or worse mod support, so I stopped deciding on this and just run the Windows version whenever I can.
The real problem, in my opinion, is the way the mod detects
readlink
/realpath
here. When run inside *nix systems (and not inside Proton),Directory.GetFiles
is working properly. On the other hand, if this run inside WIndows, paths with/
in the front are interpreted as the root of the drive, so/usr/bin
will becomeC:\usr\bin
if I run KSP from C: drive. This means that I can rename an executable (or anything really) toreadlink
, put it inC:\usr\bin
, and the mod will run it, even in Windows. This is definitely not a Proton bug, but Proton mapped the Linux filesystem to Z: drive, which is whyZ:\usr\bin\readlink
was detected in the first place. It would be better if the mod check if it's running in Windows first before choosing which method to use.Linux version or worse mod support, so I stopped deciding on this and just run the Windows version whenever I can.
Nope. Absolutely most of the users are running on Windows, if you were right about that code running under Windows, then I would have a lot of complains.
There's a check at runtime to see if the code is being running under a *nix or Windows, and the code you pinpointed is not used when running on Windows.
If it is being used when running on a Windows environment under Proton, it's because somehow Proton failed to fool the Mono runtime to believe it's under Windows.
So, unless you can reproduce the problem under Windows (and then it would be a failure on the code that detects the environment), we have a missing use case on Proton itself.
Suggested reading:
https://github.com/mono/mono/blob/main/mcs/class/System.Core/System/Util.cs
Nope. Absolutely most of the users are running on Windows, if you were right about that code running under Windows, then I would have a lot of complains.
Let me be the first one to complain, then. I understand that this is a niche problem, which is why you don't have any complaint about this, and it's just a warning in Windows.
I did what I described before in Windows (basically saved an empty file to G:\usr\bin\readlink
) and here's the result:
[KSPe] WARNING: Reparse_readlink got a ApplicationName='/usr/bin\readlink', CommandLine='-n "G:\ksptest\GameData\__LOCAL"', CurrentDirectory='', Native error= %1 is not a valid Win32 application.
Full log if you're interested: KSP.log
So yes, KSPe tried to use readlink in Windows. It's because readlink detection is run regardless of OS. It didn't failed catastrophically but it's an unintended behavior (IMO) regardless. Fortunately, the fix is the same for both Proton and Windows. If you didn't want to support Proton, that's fine, but this clearly happens in Windows too.
Now, you might think that this is not a normal thing normal users will do, but I can think of a valid situation for this too. If I have a dual boot setup between Windows and Linux, and for some reason I run games from a Linux partition (from a single partition setup), then I would have this exact problem.
There's a check at runtime to see if the code is being running under a *nix or Windows, and the code you pinpointed is not used when running on Windows.
I don't see why it will not run in Windows (and the fact that it was running from my testing). Since the code is inside the static constructor, it's always run when the class is loaded. That's why I said that it tried to find readlink in Windows too.
If it is being used when running on a Windows environment under Proton, it's because somehow Proton failed to fool the Mono runtime to believe it's under Windows.
I'm pretty sure Proton will pass this check, but it never had a chance to run it in the first place since KSPe detected a file named "readlink" and run this line first:
All I ask at this point really is just for you to swap these two lines, and the problem (both in WIndows and Proton) will be gone. It would be better if you just put a check inside the static constructor instead, but it's your call.
Also, I tested your claim about Proton failed to fool to be Windows by using this code (which copied from here):
using System;
public class WindowsCheck
{
public static bool IsThisWindows => ((int)System.Environment.OSVersion.Platform < 4);
public static void Main(string[] args)
{
Console.WriteLine(IsThisWindows);
}
}
Linux:
$ mono windowschk.exe
False
Proton:
$ STEAM_COMPAT_CLIENT_INSTALL_PATH=/run/media/lion328/Games/Steam STEAM_COMPAT_DATA_PATH="/run/media/lion328/Games/Steam/steamapps/compatdata/220200" WINEPREFIX=$PWD /run/media/lion328/Games/Steam/steamapps/common/Proton\ 7.0/proton run windowschk.exe
fsync: up and running.
wine: RLIMIT_NICE is <= 20, unable to use setpriority safely
True
So it works correctly and LowLevelTools.Windows.IsThisWindows
will be true inside Proton.
So it works correctly and
LowLevelTools.Windows.IsThisWindows
will be true inside Proton.
Now I'm worried. Because if LowLevelTools.Windows.IsThisWindows
is True, and yet readlink is being called, I have a serious flaw somewhere on the code.
I'm checking it.
JESUS CHRIST - I was completely biased on the problem and failed to read the code with the proper critical mindset.
30 seconds of proper reading the code was all what I had needed to detect and solve the issue.
Fixed on https://github.com/net-lisias-ksp/KSPe/commit/c7fe090eaf89b2873f493e75ad7a123a59df5f08
KSPe 2.4.1.16 was released with the fix.
Hotfixes for the following Add'Ons are available for download on the respective releases:
@lion328 , thank you very much for your patience!
Cheers!
(I will keep this open waiting for the confirmation of the fix)
Tried on Proton and it works now. Thanks!
Tried on Proton and it works now. Thanks!
Things usually works better when you don't use them by accident on the wrong environment as I did!
Cheers!
Note to my future self:
When I initially coded that stunt, I assumed that the code would run on Windows or on *NIX, and took no measure to prevent heterogeneous environments as CYGWIN or something, where the TWO filesystems could be valid at the same time.
On Windows, there's absolutely no "/usr" subdirectory on the root file system. Point. So the code that would search for realpath
would always fail, and so the pointer to it would always be null
. And so I didn't cared about checking if I was running on Windows or similar because that would never happen (users of CYGWIN would have problems, but who would compile KSP on CYGWIN???)
But then Proton came. On Proton, the code thinks it's running on Windows but the UNIX filesystem is also there, and so the realpath
code would find it!!! And then I got a situation in which a NIX only tool was being fed with a Windows pathname and things just blew up.
(and I was thinking it was Proton, because it was the only other possible situation where this crapness could happen….)
So I:
realpath
to be run only on *NIXAny one of the actions above would solve this issue by itself, but I choose to implement both because Murphy is a prophet and sooner or later I will refactor this thing and doing this way I will prevent shooting my own feet on the process.
Note to my future self:
Keep an eye on this post from forum: https://forum.kerbalspaceprogram.com/index.php?/topic/179030-ksp-130-tweakscale-under-lisias-management-24615-2022-0523/&do=findComment&comment=4114908
You see that '/home/sean/.local/share/Steam/steamapps/common/Proton 5.13/dist/share/default_pfx/dosdevices/z:/boot/efi' stunt? By some reason someone at Steam though it could be a good idea to map a SYSTEM PROTECTED folder, inaccessible by the user, inside his home folder.
Hi, i'm having the same issue, even after trying the fix from #25. Here's the log:
`[LOG 08:09:51.368] [AddonLoader]: Instantiating addon 'Startup' from assembly 'DistantObject'
[EXC 08:09:52.101] IOException: Invalid handle to path ""
Microsoft.Win32.NativeMethods.DuplicateHandle (System.Runtime.InteropServices.HandleRef hSourceProcessHandle, System.Runtime.InteropServices.SafeHandle hSourceHandle, System.Runtime.InteropServices.HandleRef hTargetProcess, Microsoft.Win32.SafeHandles.SafeWaitHandle& targetHandle, System.Int32 dwDesiredAccess, System.Boolean bInheritHandle, System.Int32 dwOptions) (at
Hi, @cparadis777
Hi, i'm having the same issue, even after trying the fix from #25. Here's the log: I'm running Proton Experimental, with TweakScale 2.4.6.15B and KSP version 1.12.3. The issue arises only when using TweakScale.
Yeah, I had borked something on the KSPe.Light
thingy.
Download this file from https://github.com/net-lisias-ksp/TweakScale/releases and replace the KSPe.Light.TweakScale.dll
on your GameData with this new one.
In time… why using Proton when there's a Linux release available? Proton does a good job on the translation, but using the real deal on the metal is always faster - a lot faster, sometimes...
I've read a lot of accounts saying that proton was preferable for kidding, as the native Linux version slows down significantly when modded. Thanks for the rapid answer, I'll try the fix!
Hi! I played KSP in Proton and just updated TweakScale to v2.4.6.13, and it doesn't work anymore. Here's the full log: KSP_tweakscale.log. An excerpt:
As far as I understand, there are no error other than this one in the log. TweakScale v2.4.6.12 also have the same issue. Latest version that works for me is v2.4.6.11. For the test, I only installed TweakScale, Module Manager, and KSP-Recall, so I don't think this is a conflict from other mods.
The same issue also appeared in Distant Object Enhancement: KSP_distantobject.log. From the log:
I did a little digging and I suspect that this KSPe commit caused the issue, but I didn't have a setup in order to bisect it. Anyway, I don't think
Reparse_readlink
should be called inside Proton. I guess the sandbox Proton uses mapped/usr/bin
toZ:\usr\bin
and the mod foundreadlink
in there (I wonder if this can happen in Windows if I putreadlink
inC:\usr\bin
).OS: Arch Linux x86_64 Proton 7.0-2 (experimental also didn't work)