gpt4 book ai didi

c# - 确定应用程序从哪个位置启动

转载 作者:行者123 更新时间:2023-11-30 15:56:48 25 4
gpt4 key购买 nike

是否有可能确定 c# 应用程序是如何启动的?

在我的例子中,我想检查这个应用程序 (wpf) 是否由位于特定文件夹中的快捷方式启动。

所以,有两种方法可以打开我的应用程序

  • 使用直接快捷方式
  • 启动另一个类似于更新管理器的应用程序来使我的应用程序保持最新。检查后,它使用 Process.Start() 启动我的应用程序

而且我想确保应用程序只能通过更新管理器启动。

最佳答案

您可以使用的技巧是检查父进程的 PID,然后获取父进程的一些信息。

如果父进程名称类似于“explorer.exe”,则应用程序是从快捷方式启动的,或者直接通过在资源管理器中双击启动。

否则,它是从另一个应用程序启动的:它可能是您的更新应用程序,也可能是另一个与您的更新应用程序同名的应用程序...

这意味着您必须重新考虑您想要深入了解这样的解决方案,以及您想要安全控制的深度。您可以将参数从您的更新程序传递到您的主应用程序,或者通过 token 交换实现一些进程间通信……不可能建立 100% 安全的系统。

正如上面有人评论的那样,这似乎是一个 XY 问题……也可能不是。也许这只是一个安全问题。建议修改您对该软件的具体目标。

如果您需要在 .NET 中检索进程信息的示例代码(通过使用 System.Management),那么只需尝试下面列出的代码。您所要做的就是将它放在一个名为“Updater”的控制台应用程序项目中,并在代码中正确设置您的主应用程序的路径。

如果您通过在不同情况下启动和关闭 YourApplication.exe 来尝试一下这个示例,那么您应该能够看到如下输出:

Parent process 'Updater.exe' [PID=5472]
Parent process 'explorer.exe' [PID=12052]

以下代码在 VS2017 .Net 4.6.1 上测试

using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Management;

class Program
{
static void Main(string[] args)
{
Process.Start(new ProcessStartInfo()
{
FileName = "YourApplication.exe" // path to your application
});

while (Console.ReadKey(true).Key != ConsoleKey.Escape)
{
Process process = Process.GetProcessesByName("YourApplication").FirstOrDefault(); // your application's process name
if (process == null)
{
Console.WriteLine($"Process is not running...");
continue;
}
ProcessManager pm = ProcessManager.FromLocalMachine();
var processProperties = pm.GetProcessProperties(process.Id);
int parentProcessId = Convert.ToInt32(processProperties[EProcessProperty.ParentProcessId]);

try
{
var parentProcessProperties = pm.GetProcessProperties(parentProcessId);
string parentProcessName = parentProcessProperties[EProcessProperty.Name].ToString();
Console.WriteLine($"Parent process '{parentProcessName ?? "Unknown"}' [PID={parentProcessId}]");
Console.WriteLine("---------------------------------");
}
catch { Console.WriteLine("Parent process information not found."); }
}
}
}

public class ProcessConnection
{
internal ManagementScope ManagementScope { get; }

internal ProcessConnection(string machineName, string user = null, string password = null, string domain = null)
{
ManagementScope = new ManagementScope
{
Path = new ManagementPath(@"\\" + machineName + @"\root\CIMV2"),
Options = new ConnectionOptions
{
Impersonation = ImpersonationLevel.Impersonate,
Authentication = AuthenticationLevel.Default,
EnablePrivileges = true,
Username = user == null ? null : (string.IsNullOrWhiteSpace(domain) ? user : $"{domain}\\{user}"),
Password = user == null ? null : password,
},
};
ManagementScope.Connect();
}
}

public class ProcessManager
{
public static ProcessManager FromLocalMachine() => new ProcessManager()
{
Machine = Environment.MachineName,
};

public static ProcessManager FromRemoteMachine(string machine, string user = null, string password = null, string domain = null) => new ProcessManager()
{
Machine = machine,
User = user,
Password = password,
Domain = domain,
};

private ProcessManager() { }

public string Machine { get; private set; }
public string User { get; private set; }
public string Password { get; private set; }
public string Domain { get; private set; }

private ProcessConnection Connection { get; set; }
private ManagementScope ManagementScope => Connection == null ? (Connection = new ProcessConnection(Machine, User, Password, Domain)).ManagementScope : Connection.ManagementScope;

public EProcessStartStatus StartProcess(string processPath)
{
ManagementClass mc = new ManagementClass($"\\\\{Machine}\\root\\CIMV2", "Win32_Process", null);
ManagementBaseObject process = mc.GetMethodParameters("Create");
process["CommandLine"] = processPath;
ManagementBaseObject createCode = mc.InvokeMethod("Create", process, null);
string createCodeStr = createCode["ReturnValue"].ToString();
return (EProcessStartStatus)Convert.ToInt32(createCodeStr);
}

public bool KillProcess(string processName)
{
try
{
SelectQuery query = new SelectQuery($"SELECT * FROM Win32_Process WHERE Name = '{processName}'");
ManagementObjectSearcher searcher = new ManagementObjectSearcher(ManagementScope, query);
foreach (ManagementObject mo in searcher.Get()) mo.InvokeMethod("Terminate", null);
return true;
}
catch { return false; }
}

public bool KillProcess(int processId)
{
try
{
SelectQuery query = new SelectQuery($"SELECT * FROM Win32_Process WHERE ProcessId = '{processId}'");
ManagementObjectSearcher searcher = new ManagementObjectSearcher(ManagementScope, query);
foreach (ManagementObject mo in searcher.Get()) mo.InvokeMethod("Terminate", null);
return true;
}
catch { return false; }
}

public void SetProcessPriority(string processName, EProcessPriority priority)
{
SelectQuery query = new SelectQuery($"SELECT * FROM Win32_Process WHERE Name = '{processName}'");
ManagementObjectSearcher managementObjectSearcher = new ManagementObjectSearcher(ManagementScope, query);
foreach (ManagementObject managementObject in managementObjectSearcher.Get())
{
ManagementBaseObject methodParams = managementObject.GetMethodParameters("SetPriority");
methodParams["Priority"] = priority;
managementObject.InvokeMethod("SetPriority", methodParams, null);
}
}

public string GetProcessOwner(string processName)
{
SelectQuery query = new SelectQuery($"SELECT * FROM Win32_Process WHERE Name = '{processName}'");
ManagementObjectSearcher searcher = new ManagementObjectSearcher(ManagementScope, query);
foreach (ManagementObject mo in searcher.Get())
{
ManagementBaseObject methodParams = mo.GetMethodParameters("GetOwner");
ManagementBaseObject owner = mo.InvokeMethod("GetOwner", null, null);
return owner["User"].ToString();
}
return null;
}

public string GetProcessOwnerSID(string processName)
{
SelectQuery query = new SelectQuery($"SELECT * FROM Win32_Process WHERE Name = '{processName}'");
ManagementObjectSearcher searcher = new ManagementObjectSearcher(ManagementScope, query);
foreach (ManagementObject mo in searcher.Get())
{
ManagementBaseObject methodParams = mo.GetMethodParameters("GetOwnerSid");
ManagementBaseObject OwnerSid = mo.InvokeMethod("GetOwnerSid", null, null);
return OwnerSid["Sid"].ToString();
}
return null;
}

public IList<int> GetRunningProcesses()
{
IList<int> processes = new List<int>();
SelectQuery query = new SelectQuery("SELECT * FROM Win32_Process");
ManagementObjectSearcher searcher = new ManagementObjectSearcher(ManagementScope, query);
foreach (ManagementObject mo in searcher.Get()) processes.Add(int.Parse(mo["ProcessId"].ToString()));
return processes;
}

public IDictionary<EProcessProperty, object> GetProcessProperties(int processId)
{
SelectQuery query = new SelectQuery($"SELECT * FROM Win32_Process WHERE ProcessId = '{processId}'");
ManagementObjectSearcher searcher = new ManagementObjectSearcher(ManagementScope, query);

Dictionary<EProcessProperty, object> properties = new Dictionary<EProcessProperty, object>();
foreach (ManagementObject mo in searcher.Get())
{
foreach (PropertyData pd in mo.Properties)
{
if (Enum.TryParse(pd.Name, out EProcessProperty e)) properties[e] = pd.Value;
else Console.WriteLine(pd.Name + " is not mapped in the properties enumeration.");
}
}
return properties;
}

public IDictionary<EProcessProperty, object> GetProcessProperties(string processName)
{
SelectQuery query = new SelectQuery($"SELECT * FROM Win32_Process WHERE Name = '{processName}'");
ManagementObjectSearcher searcher = new ManagementObjectSearcher(ManagementScope, query);

Dictionary<EProcessProperty, object> properties = new Dictionary<EProcessProperty, object>();
foreach (ManagementObject mo in searcher.Get())
{
foreach (PropertyData pd in mo.Properties)
{
if (Enum.TryParse(pd.Name, out EProcessProperty e)) properties[e] = pd.Value;
else Console.WriteLine(pd.Name + " is not mapped in the properties enumeration.");
}
}
return properties;
}

public IList<int> GetProcessessFromExecutablePath(string executablePath)
{
SelectQuery query = new SelectQuery($"SELECT * FROM Win32_Process WHERE ExecutablePath = '{executablePath.Replace("\\", "\\\\")}'");
ManagementObjectSearcher searcher = new ManagementObjectSearcher(ManagementScope, query);
return searcher.Get().Cast<ManagementObject>().Select(mo => Convert.ToInt32(mo["ProcessId"])).ToList();
}

}

public enum EProcessPriority : uint
{
IDLE = 0x40,
BELOW_NORMAL = 0x4000,
NORMAL = 0x20,
ABOVE_NORMAL = 0x8000,
HIGH_PRIORITY = 0x80,
REALTIME = 0x100
}

public enum EProcessStartStatus
{
Success = 0,
AccessDenied = 2,
NoPermissions = 3,
Unknown = 8,
FileNotFound = 9,
Invalid = 21,
}

public enum EProcessProperty
{
Caption,
CommandLine,
CreationClassName,
CreationDate,
CSCreationClassName,
CSName,
Description,
ExecutablePath,
ExecutionState,
Handle,
HandleCount,
InstallDate,
KernelModeTime,
MaximumWorkingSetSize,
MinimumWorkingSetSize,
Name,
OSCreationClassName,
OSName,
OtherOperationCount,
OtherTransferCount,
PageFaults,
PageFileUsage,
ParentProcessId,
PeakPageFileUsage,
PeakVirtualSize,
PeakWorkingSetSize,
Priority,
PrivatePageCount,
ProcessId,
QuotaNonPagedPoolUsage,
QuotaPagedPoolUsage,
QuotaPeakNonPagedPoolUsage,
QuotaPeakPagedPoolUsage,
ReadOperationCount,
ReadTransferCount,
SessionId,
Status,
TerminationDate,
ThreadCount,
UserModeTime,
VirtualSize,
WindowsVersion,
WorkingSetSize,
WriteOperationCount,
WriteTransferCount,
}

关于c# - 确定应用程序从哪个位置启动,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/46090371/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com