I need to provide access to a remote folder on a shared hosting from a few Windows computers. This hosting service offers me SSH and just only one user account. It's not possible to create more SSH users or local accounts on server. I don't want these computers' users to know the SSH password to avoid them having full access to an SSH console. I don't even want to provide them with different SSH rsa keys for the same reason.
So, this is my approach to solve this issue: to develop a .Net application that maps this remote folder to a windows drive using WinFsp + SSHFS-Win, executing the command "net use" to automatically mount the drive, so users don't have to know the password. The password is encrypted inside the code, the encryption algorithm is complex and obfuscated, so it will be difficult for these users to decompile the code and decrypt the password. I know this solution is not 100% secure, but is enough for me in this case.
When I execute the command bellow using C# Process everything works like a charm (WinFsp and SSHFS-Win must be installed).
net use S: \\sshfs\ssh_user@host\shared_folder [decrypted_password] /user:ssh_user
But the password is visible on Task Manager (Detail tab > Command line) during the Process execution, and I consider this unacceptable.
To avoid this, I tried the following:
net use S: \\sshfs\ssh_user@host\shared_folder * /user:ssh_user
Now the Process waits for user to input the password. In this case I could auto type the password from code using SendKeys.Send, but then the password could be easily extracted with any keylogger. The solution should be to redirect standard input so I can send the password to the process from code, but that isn't working at all. When I use the following code the command responds with an "Access denied" error.
This isn't working:
Process proc = new() {
StartInfo = new("net") {
CreateNoWindow = true,
UseShellExecute = false,
RedirectStandardInput = true,
Arguments = @"use S: \\sshfs\ssh_user@host\shared_folder * /user:ssh_user"
}
};
proc.Start();
proc.StandardInput.WriteLine(decryptedPassword);
proc.StandardInput.Close();
proc.WaitForExit();
I have tested this code with other commands instead of "net use" and it works perfectly. For example, if I test it with sort command, which also waits for user's input, the password is passed as input to the command without problem:
Process proc = new() {
StartInfo = new("sort") {
CreateNoWindow = true,
UseShellExecute = false,
RedirectStandardInput = true,
RedirectStandardOutput = true
}
};
proc.Start();
proc.StandardInput.WriteLine(decryptedPassword);
proc.StandardInput.Close();
Debug.WriteLine(proc.StandardOutput.ReadToEnd());
proc.WaitForExit();
Now I can see the password printed on Visual Studio debug console, so I know the code is correct.
I suspect that "net use" command (or maybe SSHFS-Win) somehow doesn't allow input redirection and password need to be actually typed on keyboard. To confirm this, I have tested the following commands directly on windows Command Prompt (cmd.exe), and I always get "Access denied":
echo password | net use S: \\sshfs\ssh_user@host\shared_folder * /user:ssh_user
echo(password|net use S: \\sshfs\ssh_user@host\shared_folder * /user:ssh_user
echo|set /p=password|net use S: \\sshfs\ssh_user@host\shared_folder * /user:ssh_user
Can anyone confirm if input redirection is not possible with net use command? Or am I doing something wrong? Does anyone have another solution?
Finally, I have solved this issue by executing sshfs-win.exe instead of "net use". With sshfs-win.exe the standard input redirection works fine, as expected.
Also, this is working when executing directly on windows command prompt: