When users click on a button, I want it to run the logon script(launching from server), but each computer in different servers, so I get the server name. But the netlogon.StartInfo.Arguments = slnres + #"/c \netlogon\logon.cmd"; line is not working as it should be. It should run the logon.cmd on the PC(mapping network drivers, printers, etc), and then the CMD should close.
private void MapNetwork_Click(object sender, EventArgs e)
{
Process sln = new Process();
sln.StartInfo.UseShellExecute = false;
sln.StartInfo.WindowStyle = ProcessWindowStyle.Hidden;
sln.StartInfo.FileName = "cmd.exe";
sln.StartInfo.Arguments = "/c echo %logonserver%";
sln.StartInfo.RedirectStandardOutput = true;
sln.Start();
string slnres = sln.StandardOutput.ReadToEnd();
label1.Text = slnres;
Process netlogon = new Process();
netlogon.StartInfo.UseShellExecute = false;
netlogon.StartInfo.FileName = "cmd.exe";
netlogon.StartInfo.Arguments = slnres + #"/c \netlogon\logon.cmd";
netlogon.Start();
}
A couple things:
You don't need to run a command prompt to get an environment variable. You can use Environment.GetEnvironmentVariable.
Your Arguments property for your call to logon.cmd is being constructed into this:
\\myserver/c \netlogon\logon.cmd
When I think you want this:
/c \\myserver\netlogon\logon.cmd
So make sure you put slnres at the right place in your string. Your code should look like this:
private void MapNetwork_Click(object sender, EventArgs e)
{
string slnres = Environment.GetEnvironmentVariable("logonserver");
label1.Text = slnres;
Process netlogon = new Process();
netlogon.StartInfo.UseShellExecute = false;
netlogon.StartInfo.FileName = "cmd.exe";
netlogon.StartInfo.Arguments = "/c " + slnres + #"\netlogon\logon.cmd";
netlogon.Start();
}
i am a little confused about your question and i am not rly sure if i understand you correctly. some time ago i made a program where i had to run few powershell commands, so i made a class for it. redirected to your button it would look like that:
(and remember you need the fqdn to your file location => Reading File From Network Location)
using System.Diagnostics;
//class lvl scope vars
string output;
string ErrorOutput;
private void MapNetwork_Click(object sender, EventArgs e)
{
//define process arguments
ProcessStartInfo startInfo = new ProcessStartInfo();
startInfo.FileName = #"cmd.exe";
startInfo.Arguments = #"FQDN path to your file on the server; exit";
startInfo.UseShellExecute = false;
startInfo.CreateNoWindow = true;
startInfo.RedirectStandardOutput = true;
startInfo.RedirectStandardError = true;
//start process
Process process = new Process();
process.StartInfo = startInfo;
process.Start();
process.WaitForExit();
//outpunt handling
if (string.IsNullOrEmpty(ErrorOutput))
{
return output;
}
else
{
return ErrorOutput;
}
}
first of all i would check if your application is able to open the file one the shared network location. (server available? access rights to server? serer mapped?)
after that you can check if he is able to start the file locally. (does it need admin rights to run the *.cmd, *.bat file)
now you can check if your application runs it correctly.
Related
i am trying to call and collect the data returned by the CMD command query user.
Calling this via cmd from the Windows-startbar gives me a normal result.
Calling this via this c# function give 0 output.
public void callQueryUser()
{
ProcessStartInfo psi = new ProcessStartInfo("cmd.exe");
Process p = Process.Start(psi);
string cmd = string.Format(#"/c query user");
psi.Arguments = cmd;
psi.RedirectStandardOutput = true;
psi.UseShellExecute = false;
psi.CreateNoWindow = true;
psi.WaitForExit();
string result = p.StandardOutput.ReadToEnd();
MessageBox.Show(result);
}
I checked and the Window says command cant befound... I also check if they are both the same cmd.exe and thats also true. It seems like calling the cmd.exe via C# makes somewhat of a differences.
Anyone any idea what i could check next ?
It's not necessary to use cmd to retrieve the information you want using Process. However, if your OS is 64-bit, your program is running as 32-bit, and you're trying to access %windir%\System32\query.exe, you need to use %windir%\Sysnative\query.exe instead.
Try the following:
Option 1:
public void callQueryUser()
{
string queryPath = string.Empty;
//use 'Sysnative' to access 64-bit files (in System32) if program is running as 32-bit process
//use 'SysWow64' to access 32-bit files on 64-bit OS
if (Environment.Is64BitOperatingSystem && !Environment.Is64BitProcess)
queryPath = System.IO.Path.Combine(Environment.GetEnvironmentVariable("windir"), "Sysnative", "query.exe");
else
queryPath = System.IO.Path.Combine(Environment.GetEnvironmentVariable("windir"), "System32", "query.exe");
Debug.WriteLine("queryPath: " + queryPath);
// create new instance
ProcessStartInfo startInfo = new ProcessStartInfo(queryPath);
startInfo.Arguments = "user"; //arguments
startInfo.CreateNoWindow = true; //don't create a window
startInfo.RedirectStandardError = true; //redirect standard error
startInfo.RedirectStandardOutput = true; //redirect standard output
startInfo.UseShellExecute = false; //if true, uses 'ShellExecute'; if false, uses 'CreateProcess'
startInfo.WindowStyle = ProcessWindowStyle.Hidden;
//create new instance
using (Process p = new Process { StartInfo = startInfo, EnableRaisingEvents = true })
{
//subscribe to event and add event handler code
p.ErrorDataReceived += (sender, e) =>
{
if (!String.IsNullOrEmpty(e.Data))
{
//ToDo: add desired code
Debug.WriteLine("Error: " + e.Data);
}
};
//subscribe to event and add event handler code
p.OutputDataReceived += (sender, e) =>
{
if (!String.IsNullOrEmpty(e.Data))
{
//ToDo: add desired code
Debug.WriteLine("Output: " + e.Data);
string result = e.Data;
MessageBox.Show(result);
}
};
p.Start(); //start
p.BeginErrorReadLine(); //begin async reading for standard error
p.BeginOutputReadLine(); //begin async reading for standard output
//waits until the process is finished before continuing
p.WaitForExit();
}
}
Option 2:
public void callQueryUser()
{
string queryPath = string.Empty;
//environment variable windir has the same value as SystemRoot
//use 'Sysnative' to access 64-bit files (in System32) if program is running as 32-bit process
//use 'SysWow64' to access 32-bit files on 64-bit OS
if (Environment.Is64BitOperatingSystem && !Environment.Is64BitProcess)
queryPath = System.IO.Path.Combine(Environment.GetEnvironmentVariable("windir"), "Sysnative", "query.exe");
else
queryPath = System.IO.Path.Combine(Environment.GetEnvironmentVariable("windir"), "System32", "query.exe");
Debug.WriteLine("queryPath: " + queryPath);
// create new instance
ProcessStartInfo startInfo = new ProcessStartInfo(queryPath);
startInfo.Arguments = "user"; //arguments
startInfo.CreateNoWindow = true; //don't create a window
startInfo.RedirectStandardError = true; //redirect standard error
startInfo.RedirectStandardOutput = true; //redirect standard output
startInfo.UseShellExecute = false; //if true, uses 'ShellExecute'; if false, uses 'CreateProcess'
startInfo.WindowStyle = ProcessWindowStyle.Hidden;
//create new instance
using (Process p = new Process { StartInfo = startInfo, EnableRaisingEvents = true })
{
p.Start(); //start
//waits until the process is finished before continuing
p.WaitForExit();
string result = p.StandardOutput.ReadToEnd();
MessageBox.Show(result);
}
}
Resources:
Accessing files from System32 directory using 32 bit application on 64 bit machine
Process Class
ProcessStartInfo Class
Environment.GetEnvironmentVariable Method
So I am trying to use a Button to open a CMD.exe window to execute a command which allows me to automatically open a Remote Desktop with an IP from my network. I already built a piece of code, but it doesn't work. This is the code:
private void cmdRemote_Click(object sender, EventArgs e)
{
System.Diagnostics.Process process = new System.Diagnostics.Process();
System.Diagnostics.ProcessStartInfo startInfo = new System.Diagnostics.ProcessStartInfo();
startInfo.WindowStyle = System.Diagnostics.ProcessWindowStyle.Hidden;
startInfo.FileName = "cmd.exe";
startInfo.Arguments = "mstsc /v:" + txtIP.Text;
process.StartInfo = startInfo;
process.Start();
}
I would like to know why it doesn't execute the command.
Add "/c" in front of your arguments list, else cmd won't execute it:
cmd /c mstsc /v:...
Or, why don't you call mstsc directly?
private void cmdRemote_Click(object sender, EventArgs e)
{
var process = new System.Diagnostics.Process();
process.StartInfo = new ProcessStartInfo
{
FileName = "mstsc"
Arguments = "/v:" + txtIP.Text
}
process.Start();
}
or shorter:
Process.Start("mstsc", "/v:" + this.txtIP.Text);
Don't forget to validate the value of Text!
Instead of calling the cmd.exe, you can call the mstsc
startInfo.FileName = "mstsc"
startInfo.Arguments= " /v " + txtIP.Text
I'm trying to connect to a linux machine via pLink and PuTTY to transfer some .txt file. Right now I'm just trying to make the connection work. I have a small window with 2 textboxes (username,linux1) and a password box (pwbox1), and a button that when you click, it should connect you to the linux machine!
Here's my code:
private void button1_Click(object sender, RoutedEventArgs e)
{
string user = username.Text;
string passw = pwbox1.Password;
string linuxHst = linux1.Text;
ProcessStartInfo psi = new ProcessStartInfo(#"C:\Program Files (x86)\PuTTY\plink.exe", user + "#" + linuxHst + " -pw " + passw);
psi.RedirectStandardInput = true;
psi.RedirectStandardOutput = true;
psi.WindowStyle = ProcessWindowStyle.Normal;
psi.UseShellExecute = false;
psi.CreateNoWindow = false;
Process process = Process.Start(psi);
process.WaitForExit(5000);
}
The problem is that when I try this with the console application it works, without the textboxes! but I need it to work with WPF.
Can anyone please tell me what I'm doing wrong? am I missing something?
I'm trying to build a .net application that will run some console commands (like running phantomJs) and return me the outcome of the operations. But by default I'm getting everything from the starting of cmd.exe to closing it. Any ideas for a quick fix or do I need to play with regexes ?
Here's my code as for now :
System.Diagnostics.ProcessStartInfo psi = new System.Diagnostics.ProcessStartInfo("cmd.exe");
psi.UseShellExecute = false;
psi.RedirectStandardOutput = true;
psi.RedirectStandardInput = true;
psi.RedirectStandardError = true;
System.Diagnostics.Process proc = System.Diagnostics.Process.Start(psi);
System.IO.StreamReader sOut = proc.StandardOutput;
System.IO.StreamWriter sIn = proc.StandardInput;
sIn.WriteLine("phantomjs -v");
sIn.WriteLine("EXIT");
proc.Close();
string results = sOut.ReadToEnd().Trim();
sIn.Close();
sOut.Close();
PhantomJS is an executable (according to their docs) - why not execute that directly rather than running cmd.exe? That will avoid the cmd.exe noise.
Or redirect the output of phantomjs to a log file and load the log file.
Or if you absolutely have to use cmd.exe and can't redirect ... I'd maybe throw some echo sentinels around the phantomjs to serve as parse start/stop points.
e.g.,
echo PARSE START
runcommand.exe
echo PARSE STOP
But don't do that.
Instead of using the different streams. Why not use cmd as filename and pass it the -c "phantomjs -v" as argument. Then use proc.StandardOutput.ReadToEnd() to grab everything that is outputted in the console. This should leave out unneeded info as it only reads what the output of the executed command is.
Following code might not work, but should give you the general idea.
ProcessStartInfo psi = new ProcessStartInfo();
psi.FileName = "cmd";
psi.Arguments = "/c \"phantomjs -v\"";
psi.UseShellExecute = false;
psi.RedirectStandardOutput = true;
// Optional other options
Process proc = Process.Start(psi);
string output = proc.StandardOutput.ReadToEnd();
proc.WaitForExit();
If you are on an unix machine:
sIn.WriteLine("phantomjs -v > /dev/null");
Windows:
sIn.WriteLine("phantomjs -v > NUL");
I hope that the following would be helpful!
{
Process xyProcess = new Process();
xyProcess.StartInfo.FileName = "FilenameYouWant";
xyProcess.StartInfo.UseShellExecute = false;
xyProcess.StartInfo.CreateNoWindow = true;
xyProcess.StartInfo.WindowStyle = ProcessWindowStyle.Hidden;
xyProcess.StartInfo.RedirectStandardInput = true;
xyProcess.StartInfo.RedirectStandardOutput = true;
xyProcess.StartInfo.RedirectStandardError = true;
xyProcess.StartInfo.Arguments += "any arg1 you want ";
xyProcess.StartInfo.Arguments += "any arg2 you want ";
xyProcess.EnableRaisingEvents = true;
xyProcess.OutputDataReceived += process_DataReceived;
// Start the process
xyProcess.Start();
xyProcess.BeginErrorReadLine();
xyProcess.BeginOutputReadLine();
xyProcess.WaitForExit();
}
static private void process_DataReceived(object sender, DataReceivedEventArgs e)
{
//Catch the process response here
}
I have this code that I'm trying to run a Python script. It works correctly when I do it manually via the command prompt but if I try to do it via a button click in a C# Windows form it doesn't work.
private void btnGenerateAndrowarn_Click(object sender, EventArgs e) {
string[] filePaths = Directory.GetFiles(#"C:\Users\User1\Desktop\Android Tools\androwarn\Samples", "*.apk");
foreach (string fileName in filePaths) {
ProcessStartInfo startInfo;
Process process;
string directory = #"C:\Users\User1\Desktop\Android Tools\androwarn\";
string script = "androwarn.py";
startInfo = new ProcessStartInfo("python");
startInfo.WorkingDirectory = directory;
startInfo.Arguments = directory + script + " -i " + fileName + " -r html -v 3";
startInfo.UseShellExecute = false;
startInfo.CreateNoWindow = true;
startInfo.RedirectStandardOutput = true;
startInfo.RedirectStandardError = true;
process = new Process();
process.StartInfo = startInfo;
process.Start();
}
}
Most likely is that python is not in your %PATH%.