Set Path for URL Protocol in c# - c#

So I created an URL protocol to run an application with the command arguments.
Here is my code:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.IO;
using Microsoft.Win32;
using System.Diagnostics;
namespace iw4Protocol
{
class Program
{
static void Main(string[] args)
{
RegistryKey key = Registry.ClassesRoot.OpenSubKey("gameProtocol");
if (key == null)
{
string iw4FullPath = Directory.GetCurrentDirectory();
gameProtocol protocol = new gameProtocol();
protocol.RegisterProtocol(gameFullPath);
}
else
{
RegistryKey gamepathkey = Registry.ClassesRoot.OpenSubKey("gameProtocol");
string gamepath = gamepathkey.GetValue("gamepath").ToString();
Environment.SetEnvironmentVariable("path",gamepath);
ProcessStartInfo startInfo = new ProcessStartInfo();
startInfo.FileName = #"test.exe";
startInfo.Arguments = Environment.CommandLine;
Process.Start(startInfo);
}
}
}
}
The problem is that the program need some files to get launched but it can't load them because the path isn't 'set'.
How I can set this path to launch all these needed files (like /cd command)?

If you want to set the PATH environment variable and use it in your process, add it to the Environment variables but you have to set UseShellExecute to false in that case:
ProcessStartInfo startInfo = new ProcessStartInfo();
// set environment
startInfo.UseShellExecute = false;
startInfo.EnvironmentVariables["PATH"] += ";" + gamepath;
// you might need more Environment vars, you're on your own here...
// start the exe
startInfo.FileName = #"test.exe";
startInfo.Arguments = Environment.CommandLine;
// added for debugging
startInfo.RedirectStandardOutput = true;
startInfo.RedirectStandardError = true;
var p = new Process();
p.StartInfo = startInfo;
using(var sw = new StreamWriter(File.Create("c:\\temp\\debug.txt"))) // make sure C:\temp exist
{
p.OutputDataReceived += (sender, pargs) => sw.WriteLine(pargs.Data);
p.ErrorDataReceived += (sender, pargs) => sw.WriteLine(pargs.Data);
p.Start();
p.BeginOutputReadLine();
p.BeginErrorReadLine();
p.WaitForExit();
}

Related

Redirecting process's output isn't working C#

I need to send an input from a C# program to another program and capture its process's output every time after the input is sent
Here I wrote a C program to be used as a process in C# program. The program will receive an input and print back the same string
#include <stdio.h>
#include <stdbool.h>
int main(){
while(true){
char buff[1000];
scanf(" %[^\n]s", buff);
printf("\nechoed : %s\n",buff);
}
}
This is my C# program that will send input and receive output to and from my C program
(I am starting the process in another thread so process.WaitForExit() will not block the main thread)
using System;
using System.Diagnostics;
using System.IO;
using System.Threading;
namespace MinExample
{
internal class Program
{
static StreamWriter processStreamWriter;
static string filePath = #"my_program.exe";
private static void MyProcOutputHandler(object sendingProcess,
DataReceivedEventArgs outLine)
{
if (!String.IsNullOrEmpty(outLine.Data))
{
Console.WriteLine("Data : " + outLine.Data);
}
}
//this doesn't works
static void StartProcessWithOutputRedirection()
{
ProcessStartInfo startInfo = new ProcessStartInfo();
startInfo.CreateNoWindow = false;
startInfo.UseShellExecute = false;
startInfo.FileName = filePath;
startInfo.WindowStyle = ProcessWindowStyle.Hidden;
//standard input out redirection
startInfo.RedirectStandardOutput = true;//redirect output
startInfo.RedirectStandardError = true;//redirect output
startInfo.RedirectStandardInput = true;
try
{
//Initialize process and register callback
Process process = new Process();
process.StartInfo = startInfo;
process.OutputDataReceived += new DataReceivedEventHandler(MyProcOutputHandler);
process.ErrorDataReceived += new DataReceivedEventHandler(MyProcOutputHandler);
//
process.Start();
//initialize stream writer so that the process can receive incoming input
processStreamWriter = process.StandardInput;
process.BeginOutputReadLine();
process.BeginErrorReadLine();
process.WaitForExit();
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
}
}
//this works
static void StartProcessNoOutputRedirection()
{
ProcessStartInfo startInfo = new ProcessStartInfo();
startInfo.CreateNoWindow = false;
startInfo.UseShellExecute = false;
startInfo.FileName = filePath;
startInfo.WindowStyle = ProcessWindowStyle.Hidden;
//standard input out redirection
startInfo.RedirectStandardOutput = false;
startInfo.RedirectStandardInput = true;
try
{
//Initialize process and set property
Process process = new Process();
process.StartInfo = startInfo;
//
process.Start();
//initialize stream writer so that the process can receive incoming input
processStreamWriter = process.StandardInput;
process.WaitForExit();
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
}
}
static void Main(string[] args)
{
/*
using StartProcessNoOutputRedirection works but using StartProcessWithOutputRedirection doesn't
*/
ThreadStart ths = new ThreadStart(StartProcessWithOutputRedirection);
Thread th = new Thread(ths);
th.Start();
while (true)
{
Console.Write("Input :");
string input = Console.ReadLine() ?? "";
processStreamWriter.WriteLine(input);
}
}
}
}
It will print the output each time the process receives an output when I don't redirect the output at all
However when I tried to redirect the output, the Process.OutputDataReceived event isn't being called back. I have searched another post and have tried to use process.BeginOutputReadLine(); after process.Start but it hasn't solved my issue
Any advice?

Process.StartInfo.FileName coming up blank

So, I am creating a C# program to run a command prompt command when a button is pressed, this is the code that executes when the button is pressed:
private void button1_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.Maximized;
string arg = textBox1.Text + "& exit";
process.StartInfo.Arguments = arg;
process.StartInfo.UseShellExecute = false;
process.StartInfo.RedirectStandardInput = true;
process.StartInfo.RedirectStandardOutput = true;
process.StartInfo.FileName = "cmd.exe";
process.StartInfo = startInfo;
process.Start();
string outp = process.StandardOutput.ReadToEnd();
string error = process.StandardError.ReadToEnd();
StreamWriter myStreamWriter = process.StandardInput;
myStreamWriter.WriteLine(textBox1.Text);
textBox2.Text = outp;
process.WaitForExit();
}
Maybe it's something obvious that I am missing, if it is, I am sorry(I am kind of a beginner at C#), but I can't, for the life of me, figure out why I get an exception thrown out of system.dll that reads as follows:
An unhandled exception of type 'System.InvalidOperationException' occurred in System.dll
Additional information: Cannot start process because a file name has not been provided.
However, I have provided a file name (line 5 of code snippet). Any help is GREATLY appreciated, thanks.
P.S.
This code uses:
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.IO;
using System.Diagnostics;
To run properly.
process.StartInfo = startInfo; //Here problem is there, you are
//refreshing "process.StartInfo" with "startInfo". As "startInfo" is empty in your code.
//So use below code
System.Diagnostics.Process process = new System.Diagnostics.Process();
System.Diagnostics.ProcessStartInfo startInfo = new System.Diagnostics.ProcessStartInfo();
startInfo.WindowStyle = System.Diagnostics.ProcessWindowStyle.Maximized;
string arg = textBox1.Text + "& exit";
startInfo.Arguments = arg;
startInfo.UseShellExecute = false;
startInfo.RedirectStandardInput = true;
startInfo.RedirectStandardOutput = true;
startInfo.FileName = "cmd.exe";
process.StartInfo = startInfo;
process.Start();

How to pipe output from C# application using cmd to text?

I'm running an app that uses a console app in the background
When I do this in cmd read-info.exe Myfile.file >fileinfo.txt it will create the file fileinfo.txt in the route folder.
But when I do it in code nothing happens, why?
private void button1_Click(object sender, EventArgs e)
{
FolderBrowserDialog theDialog = new FolderBrowserDialog();
theDialog.RootFolder = System.Environment.SpecialFolder.MyComputer;
if (theDialog.ShowDialog() == DialogResult.OK)
{
textBox1.Text = theDialog.SelectedPath.ToString();
string command = "read-info.exe " + textBox1.Text +"> File.txt";
string retur = CMD(command);
}
}
static string CMD(string args)
{
string cmdbat = "cd " + Application.StartupPath.Replace("\\", "/") + "\r\n";
cmdbat += args + " >> out.txt\r\n";
cmdbat += "exit\r\n";
File.WriteAllText("cmd.bat", cmdbat);
System.Diagnostics.Process process = new System.Diagnostics.Process();
System.Diagnostics.ProcessStartInfo startInfo = new System.Diagnostics.ProcessStartInfo();
startInfo.WindowStyle = System.Diagnostics.ProcessWindowStyle.Hidden;
startInfo.Arguments = "";
startInfo.UseShellExecute = true;
startInfo.WorkingDirectory = Application.StartupPath;
startInfo.CreateNoWindow = true;
startInfo.FileName = Application.StartupPath + "\\cmd.bat";
process.StartInfo = startInfo;
process.Start();
process.WaitForExit();
System.Threading.Thread.Sleep(5000);
string cmdOut = File.ReadAllText("out.txt");
File.Delete("cmd.bat");
File.Delete("out.txt");
return cmdOut;
}
See this - I tnink it is what necessary: http://www.dotnetperls.com/redirectstandardoutput
Copied from the link above:
using System;
using System.Diagnostics;
using System.IO;
class Program
{
static void Main()
{
//
// Setup the process with the ProcessStartInfo class.
//
ProcessStartInfo start = new ProcessStartInfo();
start.FileName = #"C:\7za.exe"; // Specify exe name.
start.UseShellExecute = false;
start.RedirectStandardOutput = true;
//
// Start the process.
//
using (Process process = Process.Start(start))
{
//
// Read in all the text from the process with the StreamReader.
//
using (StreamReader reader = process.StandardOutput)
{
string result = reader.ReadToEnd();
Console.Write(result);
}
}
}
}
use cmd /C for running console commands.
string command = "cmd /C read-info.exe " + textBox1.Text +"> File.txt";
Got It Working Thanks to #crashmstr
it outputs file as out.txt so just had to comment out File.Delete("out.txt");

Save The Cmd output into txt file in C#

How Can i save the CMD Commands into txt file in C#
or how can i display command prompt in C#
here is my code
private void button1_Click(object sender, EventArgs e)
{
var p = new Process();
string path = #"C:\Users\Microsoft";
string argu = "-na>somefile.bat";
ProcessStartInfo process = new ProcessStartInfo("netstat", argu);
process.RedirectStandardOutput = false;
process.UseShellExecute = false;
process.CreateNoWindow = false;
Process.Start(process);
p.StartInfo.WorkingDirectory = path;
p.StartInfo.FileName = "sr.txt";
p.Start();
p.WaitForExit();
}
You can redirect the standard output:
using System;
using System.Diagnostics;
using System.IO;
class Program
{
static void Main()
{
//
// Setup the process with the ProcessStartInfo class.
//
ProcessStartInfo start = new ProcessStartInfo();
start.FileName = #"C:\7za.exe"; // Specify exe name.
start.UseShellExecute = false;
start.RedirectStandardOutput = true;
//
// Start the process.
//
using (Process process = Process.Start(start))
{
//
// Read in all the text from the process with the StreamReader.
//
using (StreamReader reader = process.StandardOutput)
{
string result = reader.ReadToEnd();
Console.Write(result);
}
}
}
}
Code is from here
Also look to this answer: redirecting output to the text file c#

Input & Output from cmd.exe shell

I am trying to create a Windows Forms C# project that interacts with the command prompt shell (cmd.exe).
I want to open a command prompt, send a command (like ipconfig) and then read the results back into the windows form into a string, textbox, or whatever.
Here is what I have so far, but I am stuck. I cannot write or read to the command prompt.
using System;
using System.Collections.Generic;
using System.Linq;
using System.Windows.Forms;
using System.Diagnostics;
using System.IO;
namespace WindowsFormsApplication1
{
static class Program
{
/// <summary>
/// The main entry point for the application.
/// </summary>
[STAThread]
static void Main()
{
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Application.Run(new Form1());
System.Diagnostics.Process p = new System.Diagnostics.Process();
p.StartInfo.UseShellExecute = false;
p.StartInfo.FileName = "cmd.exe";
p.StartInfo.Arguments = "/k dir *.*";
p.StartInfo.RedirectStandardError = true;
p.StartInfo.RedirectStandardInput = true;
p.StartInfo.RedirectStandardOutput = true;
p.Start();
StreamWriter inputWriter = p.StandardInput;
StreamReader outputWriter = p.StandardOutput;
StreamReader errorReader = p.StandardError;
p.WaitForExit();
}
}
}
Any help would be greatly appreciated.
Thanks.
Here is a SO question that will give you the information you need:
How To: Execute command line in C#, get STD OUT results
Basically, you ReadToEnd on your System.IO.StreamReader.
So, for example, in your code you would modify the line StreamReader errorReader = p.StandardError; to read
using(StreamReader errorReader = p.StandardError)
{
error = myError.ReadToEnd();
}
var yourcommand = "<put your command here>";
var procStart = new System.Diagnostics.ProcessStartInfo("cmd", "/c " + yourcommand);
procStart.CreateNoWindow = true;
procStart.RedirectStandardOutput = true;
procStart.UseShellExecute = false;
var proc = new System.Diagnostics.Process();
proc.StartInfo = procStart;
proc.Start();
var result = proc.StandardOutput.ReadToEnd();
Console.WriteLine(result);

Categories