正如标题所说:C#中是否存在常用方式,尤其是非托管本机C ++以确定已安装的CLR版本?这意味着不仅要检查是否根据this KB article安装了Framework。我想通过使用CLR接口来完成它,对于CLR1,CLR1.1和CLR2已完成here。通过这种方式,我可以确保它们真正安装。但这不适用于CLR4。任何想法?
我的目标是创建一个可用的CLR版本的枚举,如Clrver(无论进程列表功能是否正确)。
答案 0 :(得分:5)
“通用方式”与否,但dotNetInstaller at Codeplex在本机非托管C ++代码中执行此操作 它是开源的,看看它们是如何做到的。
此外,您可以使用ICLRMetaHost::EnumerateInstalledRuntimes Method检测.NET v4 +和GetRequestedRuntimeInfoInfo(与clrver.cpp的方式大致相同)来检测.NET v1-v2。 所以你必须打两个电话,但这应该涵盖它。
答案 1 :(得分:-1)
在阅读Jeffrey Richters的书Applied Microsoft® .NET Framework Programming时,我发现了一些有趣的提示。面向主题加载公共语言运行时(p.41),他提到检查注册表路径(和子项)HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\.NETFramework\policy
以检查已安装的运行时。因此,我发现了一个有趣KB article的主题。此外,在运行时如何解析类型引用(p.132)一节中,他提到 mscorlib.dll 与CLR版本绑定。所以我认为应该可以检查找到的注册表项与该文件及其版本,以确保找到的密钥安装CLR版本。
在下文中,您将在代码中找到我的结论。 :)我认为Clrver做了类似的事情。我认为这个解决方案也应该适用于本机C ++应用程序,因为我的下面的代码是C#,并且只使用非常基本的框架函数。
List<string> installedRuntimes = new List<string>();
Regex rxVersion = new Regex(@"^[v](\d{1,5})([\.](\d{1,5})){0,3}$");
Regex rxVersionPart = new Regex(@"^\d{1,5}$");
try
{
string installPath = Convert.ToString(Registry.GetKey("HKEY_LOCAL_MACHINE/SOFTWARE/Microsoft/.NETFramework").GetValue("InstallRoot"));
string[] shortVersions = Registry.GetKey("HKEY_LOCAL_MACHINE/SOFTWARE/Microsoft/.NETFramework/Policy", false).GetSubKeyNames();
foreach (string shortVersion in shortVersions)
if (rxVersion.IsMatch(shortVersion))
{
string[] versionExtensions = Registry.GetKey("HKEY_LOCAL_MACHINE/SOFTWARE/Microsoft/.NETFramework/Policy/" + shortVersion, false).GetValueNames();
foreach (string versionExtension in versionExtensions)
if (rxVersionPart.IsMatch(versionExtension))
{
string fullVersion = shortVersion + "." + versionExtension;
if (rxVersion.IsMatch(fullVersion))
{
string clrPath = installPath + fullVersion + "\\mscorlib.dll";
if (File.Exists(clrPath) && FileVersionInfo.GetVersionInfo(clrPath).FileVersion.StartsWith(fullVersion.Substring(1))) installedRuntimes.Add(fullVersion);
}
}
}
}
catch { } // May fails while getting a specific registry key, if Microsoft changes the naming rules.
(不要搞砸Registry.GetKey(...)
- 它只是.NET注册表功能的包装器,以便按照我习惯使用注册表的方式进行简化。)最后你应该拥有CLR当Clrver列出它时,列表installedRuntimes
内的版本字符串。