批处理文件编译器






3.82/5 (47投票s)
一篇文章,描述如何将批处理文件转换为可执行文件。
目录
引言
本文档展示了如何将批处理文件编译成可执行文件。编译后的可执行文件可以在不显示窗口的情况下运行,并且您可以像传递给批处理文件一样向其传递命令行参数。
程序工作原理
这个程序编译批处理文件的方式相当巧妙且奇怪,所以我称这个程序为“模拟编译器”。批处理文件甚至没有被解析。这个程序创建另一个程序,并将指定的批处理文件作为嵌入文件添加到该程序中。当生成的程序执行时,它会将嵌入的批处理文件提取到临时文件夹中,并使用 Process
类运行它。很简单,不是吗?
使用代码
为了从您的应用程序创建另一个程序,您需要创建 CSharpCodeProvider
类的一个实例。下面的代码片段展示了如何操作。
using (CSharpCodeProvider code=new CSharpCodeProvider())
{
CompilerParameters compar = new CompilerParameters();
string option = "/target:winexe";
// Set the icon for executable
if (Properties.Settings.Default.Customicon &&
File.Exists(Properties.Settings.Default.iconpath))
{
option += " " + "/win32icon:" + "\"" +
Properties.Settings.Default.iconpath + "\"";
}
compar.CompilerOptions = option;
compar.GenerateExecutable = true;
compar.IncludeDebugInformation = false;
//Add the bat file as an embedded resource
if (File.Exists(filepath))
{
compar.EmbeddedResources.Add(filepath);
}
compar.OutputAssembly = path;
compar.GenerateInMemory = false;
//Add references
compar.ReferencedAssemblies.Add("System.dll");
compar.ReferencedAssemblies.Add("System.Data.dll");
compar.ReferencedAssemblies.Add("System.Deployment.dll");
compar.ReferencedAssemblies.Add("System.Drawing.dll");
compar.ReferencedAssemblies.Add("System.Windows.Forms.dll");
compar.ReferencedAssemblies.Add("System.Xml.dll");
compar.TreatWarningsAsErrors = false;
//Compile it
//The code is included in the executable as a resource
CompilerResults res =
code.CompileAssemblyFromSource(compar, Properties.Resources.Program);
if (res.Errors.Count > 0)
{
result = false;
}
else
result = true;
}
当您运行生成的可执行文件时,它将提取批处理文件,处理命令行参数(如果有的话),并运行它。如果指定,批处理文件将在不创建任何窗口的情况下运行。以下是展示如何实现此功能的代码。
//This code requires System.Reflection namespace
//Extracts the bat file
private void extract()
{
string name = Assembly.GetExecutingAssembly().GetManifestResourceNames()[0];
hide = name.EndsWith("hideit.bat");
Stream theResource = Assembly.GetExecutingAssembly().GetManifestResourceStream(name);
BinaryReader br = new BinaryReader(theResource);
FileStream fs = new FileStream(Environment.GetEnvironmentVariable("TEMP") +
"\\it.bat", FileMode.Create);
byte[] bt = new byte[theResource.Length];
theResource.Read(bt, 0, bt.Length);
fs.Write(bt, 0, bt.Length);
br.Close();
fs.Close();
}
//Process command line arguments
private string buildargument(string[] args)
{
StringBuilder arg = new StringBuilder();
for (int i = 0; i < args.Length; i++)
{
arg.Append(args[i] + " ");
}
return arg.ToString();
}
//Start the process
private void start(string[] args)
{
ProcessStartInfo info = new ProcessStartInfo();
info.FileName = Environment.GetEnvironmentVariable("TEMP") + "\\it.bat";
//Specify argument
info.Arguments = buildargument(args);
//Hide the window if specified
info.CreateNoWindow = hide;
if (hide)
{
info.WindowStyle = ProcessWindowStyle.Hidden;
}
//Set the working directory for the bat file. This is important as the
//bat file might use relative path
info.WorkingDirectory = Application.StartupPath;
//At last start the process
Process proc = new Process();
proc.StartInfo = info;
proc.Start();
}
关注点
这个程序编译批处理文件的方式相当巧妙且有点奇怪。
历史
- 2007年6月17日 - 初始发布。