Using Process to connect via mstsc.exe failes - c#

I have created a small tool where I want to connect to remote desktop via mstsc.exe.
I found a lot of samples and obviously they all work. But for some reaons my doesnt! :(
Actually its a small code
private void RunRDP(object sender, EventArgs e)
{
Process rdcProcess = new Process();
//Add/Change Credentials
/**
rdcProcess.StartInfo.FileName = Environment.ExpandEnvironmentVariables(#"%SystemRoot%\system32\cmdkey.exe");
rdcProcess.StartInfo.Arguments = String.Format(#"/generic:TERMSRV/{0} /user:{1} /pass:{2}", tbServer.Text, tbUsername.Text, tbPassword.Text);
rdcProcess.Start();
*/
//Perform mstsc
rdcProcess.StartInfo.FileName = Environment.ExpandEnvironmentVariables(#"%SystemRoot%\system32\mstsc.exe");
rdcProcess.StartInfo.Arguments = string.Format(#"/v {0}", tbServer.Text);
rdcProcess.Start();
}
I took out the adding credentials just to test the connection... still fails.
When I comment the line
rdcProcess.StartInfo.Arguments = string.Format(#"/v {0}", tbServer.Text);
It at least opens mstsc.exe
In any other case I receive the error
Invalid connection File
The error must be some like this. Translating this from german to english doesnt bring any similar error descriptions :D
Why does my programm fails ?

running 'mstsc /?' gives me:
/v:<server[:port]> -- Specifies the remote computer to which you want to connect.
So I guess you should change it to:
rdcProcess.StartInfo.Arguments = string.Format(#"/v:{0}", tbServer.Text);

Related

Running ngrok console application as a process from C# does not work

Dear Stack Overflow Community,
I'm trying to communicate with the Ngrok console using C #. Unfortunately "StartInfo.Arguments" does not work. For example, if I write "StartInfo.Arguments =" ngrok in the c# code", the ngrok help text does not appear, but" ERROR: Unrecognized command: ngrok "in the log. But if I open the console myself and write in" ngrok "it works.
private void startServer()
Process compiler = new Process();
compiler.StartInfo.FileName = "ngrok.exe";
compiler.StartInfo.Arguments = "\"ngrok\"";
compiler.StartInfo.UseShellExecute = false;
compiler.StartInfo.RedirectStandardOutput = true;
compiler.Start();
Console.WriteLine(compiler.StandardOutput.ReadToEnd());
compiler.WaitForExit();
}
you are using "ngrok" as argument. That is the same as you would write ngrok.exe ngrok in the console. The command is not recognized by ngrok. Try to use proper arguments for example compiler.StartInfo.Arguments = "http 80"; or just leave it blank. If you want to use ngrok with the port 80 over http your code has to look like that:
private void startServer()
Process compiler = new Process();
compiler.StartInfo.FileName = "ngrok.exe";
compiler.StartInfo.Arguments = "http 80";
compiler.StartInfo.UseShellExecute = false;
compiler.StartInfo.RedirectStandardOutput = true;
compiler.Start();
Console.WriteLine(compiler.StandardOutput.ReadToEnd());
compiler.WaitForExit();
}

How do I call a python script from a network drive using c#

I'm calling a python script from a C# tool. I based my code on this post. I use ProcessStartInfo to start python and pass a .py file and some argument to it. The code runs fine when the .py, CreateAssessorMap.py, file is on the c drive but not when it is on a mapped network drive. No error is thrown but no python code is executed as far as I can see. If I manually do the same operation from the command line it runs fine.
The code below the first procStartInfo.Arguments will fail as CreateAssessorMap.py is on a network drive. The commented out line below it would work as the script is on the C drive.
private void btnPrint_Click(object sender, EventArgs e)
{
try
{
ProcessStartInfo procStartInfo = new ProcessStartInfo();
procStartInfo.FileName = "python";
procStartInfo.Arguments = string.Format("{0} {1} {2}", #"D:\Map_Generate_Scripts\CreateAssessorMap.py", this.txtSheet.Text, txtDestinationFolder.Text);
//procStartInfo.Arguments = string.Format("{0} {1} {2} ", #"C:\Projects\Map_Generate_Scripts\CreateAssessorMap.py", this.txtSheet.Text, txtDestinationFolder.Text);
procStartInfo.UserName = null;
procStartInfo.UseShellExecute = false;
procStartInfo.RedirectStandardOutput = true;
// Do not create the black window.
procStartInfo.CreateNoWindow = true;
// Now you create a process, assign its ProcessStartInfo, and start it.
using (Process process = Process.Start(procStartInfo))
{
using (System.IO.StreamReader reader = process.StandardOutput)
{
string result = reader.ReadToEnd();
Console.Write(result);
}
}
}
catch (Exception ecpt)
{
Console.WriteLine(ecpt.Message);
}
this.Parent.Hide();
}
Edit
I added some error handling and the python code is failing with the message that the .py file cannot be found.
python: can't open file 'D:\Map_Generate_Scripts\CreateAssessorMapCreateAssessorMap.py': [Errno 2] No such file or directory
I know it exists since I can run the file from the command line with the same arguments. So it seems that when I run from C# the python process can't find the d drive.
I assume that when it runs from a network drive it takes longer and your program does not wait for Python script's completion. I suggest adding proces.Wait() before reading the output stream.
As stated in the comments, the solution for Dowlers was to use the full path instead of the mapped network drive.
Change
#"D:\Map_Generate_Scripts\CreateAssessorMap.py"
To
#"\\[network path]\Map_Generate_Scripts\CreateAssessorMap.py"

Unable to push to GitLab endpoint LibGit2Sharp

I am attempting to initialize and push an initial commit to GitLab repository using LibGit2Sharp.
if (!Directory.Exists("D:\\GitRepos\\" + repositoryName))
{
Directory.CreateDirectory("D:\\GitRepos\\" + repositoryName);
File.Create("D:\\GitRepos\\" + repositoryName + "\\README.md").Close();
}
Repository.Init("D:\\GitRepos\\" + repositoryName);
using (var repo = new Repository("D:\\GitRepos\\" + repositoryName))
{
repo.Index.Add("README.md");
Signature author = new Signature("user", "user#user.com", DateTime.Now);
Signature committer = author;
repo.Commit("Initial Commit", author, committer);
repo.Network.Remotes.Add("origin", validRepoHttpsUrl);
Remote remote = repo.Network.Remotes["origin"];
var options = new PushOptions
{
CredentialsProvider = (_url, _user, _cred) =>
new UsernamePasswordCredentials {Username = "validuser", Password = "validpassword"}
};
string pushRefSpec = #"refs/heads/master";
repo.Network.Push(remote, pushRefSpec, options);
}
}
The repository is created and initialized locally without issue. The README file is created and added to the repo index and commit succeeds. When I try to push the commit to the remote endpoint I receive an error stating :
"Request failed with status code: 411"
If I put a breakpoint right before the push and set the http.postBuffer for the repo with the following command:
git config http.postBuffer 524288000
I receive a new error when the push executes:
Failed to write chunk footer: The connection with the server was terminated abnormally
I was able to quickly stand up a bitbucket git repo and push to it without any issues, seems that this may be a problem with gitlab.
It looks like this is a known issue for libgit2sharp based on RobertN's comment. https://github.com/libgit2/libgit2sharp/issues/905
I was able to work around this temporarily by handling the push with a git CLI call.
Process p = new Process();
// Redirect the output stream of the child process.
p.StartInfo.UseShellExecute = false;
p.StartInfo.RedirectStandardOutput = true;
p.StartInfo.WorkingDirectory = "D:\\GitRepos\\" + repositoryName;
p.StartInfo.FileName = "git.exe";
p.StartInfo.Arguments = "push -u origin master";
p.Start();
string output = p.StandardOutput.ReadToEnd();
p.WaitForExit();
Something to note is that when this is being run as a windows service as local system the call takes 2-3 minutes for a small commit to push. When i switched the service to run as a domain user it is immediate. Also, this only works because I have ssh and proper keys setup on my host, otherwise git would prompt for a username and password. I had to use the SSH URL instead of HTTP as stated in the original question.

Trying to run psexec to remote to server and recycle app pool

If I run this from my command prompt it works fine.
psexec \ServerName cscript.exe iisapp.vbs /a AppName /r
I'm trying to do the same thing with C# console app. I'm using the below code but most of the time the application hangs and doesn't complete, and the few times it does it throws an error code. Am I doing this wrong? Does anyone know where I can look up the error or error code?
static void RecycleAppPool(string sServer)
{
Console.Clear();
ProcessStartInfo p = new ProcessStartInfo("psexec.exe", "\\\\" + sServer + " cscript.exe iisapp.vbs /a <AppName> /r");
p.RedirectStandardInput = true;
p.UseShellExecute = false;
Process.Start(p);
}
When it completes with an error, looks like this
"cscript.exe exited with error code -2147024664"
EDIT
Below code working well
static void RecycleAppPool(string sServer)
{
Console.Clear();
ProcessStartInfo p = new ProcessStartInfo("psexec.exe");
p.Arguments = #"\\" + sServer + #" cscript.exe iisapp.vbs /a AppName /r";
p.UseShellExecute = false;
Process.Start(p);
}
VS2003/8/10: Tools->Error Lookup. Paste in the error code in hex. 800700E8. It's "The pipe is being closed." Not very helpful - some issue with redirection i guess.
Do you really have in the ProcessStartInfo parameter, or is that being used to replace what your actual app name is?
Have you tried recycling using appcmd instead of iisapp.vbs?
And, in this thread they recycled a remote application pool using WMI.
If it's IIS7 then you can you the web admin namespace from C#:
using System;
using System.Xml.Serialization;
using Microsoft.Web.Administration;
using System.Linq;
using System.Runtime.InteropServices;
///...
var serverManager = ServerManager.OpenRemote(#"\\myiisserver");
var appPool = serverManager.ApplicationPools["my app pool name"];
appPool.Recycle();
You can learn more about the Web Admin Namespace here. So far it has worked very well for us. BUT must be installed on the client and remote machines.
I struggled with this a lot for the last 2 days trying every solution I found online. I'm trying to recycle an application pool on remote machines on a different domain. The first method I tried with PsExec returned error 3. I tried DirectoryEntry and failed on permissions as well and then tried using ServerManager but the same issue.
Finally, I moved to WMI and it worked:
public static void RecycleIis4(string user, string password, string serverName = "LOCALHOST", string appPoolName = "DefaultAppPool")
{
var processToRun = new[] { #"c:\Windows\system32\inetsrv\appcmd recycle APPPOOL " + appPoolName };
var connection = new ConnectionOptions { Username = user, Password = password };
var wmiScope = new ManagementScope(string.Format(#"\\{0}\root\cimv2", serverName), connection);
var wmiProcess = new ManagementClass(wmiScope, new ManagementPath("Win32_Process"), new ObjectGetOptions());
wmiProcess.InvokeMethod("Create", processToRun);
}
Hope this helps.

WMI + Bitlocker + C# Get encrypted Volumes produces timeout

i want to create a wrapper class for specific WMI functions that affect Bitlocker functionality. The first step is to get all the Bitlocker volumes of a machine so I created a Console Application and did this:
private static ManagementClass management;
private static ManagementObjectCollection Volumes = null;
static void Main(string[] args)
{
ManagementPath path = new ManagementPath();
path.Server = "";
path.NamespacePath = "\\ROOT\\CIMV2\\Security\\MicrosoftVolumeEncryption";
path.ClassName = "Win32_EncryptableVolume";
ConnectionOptions options = new ConnectionOptions();
options.Authentication = AuthenticationLevel.PacketPrivacy;
options.Impersonation = ImpersonationLevel.Impersonate;
ManagementScope scope = new ManagementScope(path, options);
ObjectGetOptions getOptions = new ObjectGetOptions();
management = new ManagementClass(scope, path, getOptions);
management.Get();
Volumes = management.GetInstances();
}
When I run this on a non-Bitlocker machine the Volumes Collection gets initialized OK, only that it has a Count of 0 of course. Now I copied the code over to a WinForms App and when I click a button to run this code it steps through OK but when I try to expand the collection during debugging the App hangs and I get a "Function evaluation timed out". It's the same code just in another Application. What could be the reason for this?
Hm. I got a null reference exception if I didn't run it as administrator, but when I ran it as administrator (Win 7 x64, btw), I got four Volumes back.
I just had a similar issue, I will post my code for you hopefully it helps.
ManagementObjectSearcher Encryption = new ManagementObjectSearcher(#"root\cimv2\Security\MicrosoftVolumeEncryption", "SELECT * FROM Win32_EncryptableVolume");
foreach (ManagementObject QueryObj in Encryption.Get())
{
string EncryptionStatus = QueryObj.GetPropertyValue("ProtectionStatus").ToString();
if (EncryptionStatus == "0")
{
EncryptionDialog.Text = "Unencrypted";
}
else if (EncryptionStatus == "1")
{
EncryptionDialog.Text = "Encrypted - SysPrep will not complete";
}
else if (EncryptionStatus == "2")
{
EncryptionDialog.Text = "Cannot Determine Encryption";
}
}
I'm using this to display the status for a sysprep tool i'm creating so the "EncryptionDialog.Text = ..." can be replaced with any other calls you may need. you also need to remember "which caused me issues at least" if you are using visual studio you will need to add a file to your project labeled "Application Manifest File" in the "Add New File" Dialog. The reason for this is that the application will need to be opened in Administrator mode(Just an FYI in case you haven't made it that far)

Categories

Resources