C # Leggere il registro: ProductID restituisce null nell’app x86 di destinazione. “Qualsiasi CPU” funziona bene

Recentemente mi sono spostato su una macchina W7 a 64 bit con VS 2010. Il mio progetto è impostato per funzionare su Any CPU . Quando cambio questo per essere indirizzato a x86 ho notato che alcune delle mie chiamate al registro non funzionano più.

Sto cercando di leggere il campo ProductID modo:

 RegistryKey windowsNTKey = Registry.LocalMachine.OpenSubKey(@"Software\Microsoft\Windows NT\CurrentVersion"); object productID = windowsNTKey.GetValue("ProductId"); 

productID è sempre null quando si esegue in modalità x86, quando è in esecuzione in “Qualsiasi CPU” funziona correttamente. Che cosa sta succedendo qui?

Alcune chiavi di registro vengono reindirizzate da WOW64. Ulteriori informazioni su questo argomento sono disponibili su MSDN http://msdn.microsoft.com/en-us/library/aa384232(v=vs.85).aspx

Se vuoi davvero accedere sempre al nodo x64 (.Net4):

  RegistryKey localMachine = RegistryKey.OpenBaseKey(Microsoft.Win32.RegistryHive.LocalMachine, RegistryView.Registry64); RegistryKey windowsNTKey = localMachine.OpenSubKey(@"Software\Microsoft\Windows NT\CurrentVersion"); object productID = windowsNTKey.GetValue("ProductId"); 

Questo codice otterrà l’id per tutti i tipi di architetture os e architetture di programma. Potrebbe essere scritto più breve ma mi piace la leggibilità

  static string GetProductId() { RegistryKey localMachine = null; if (Environment.Is64BitOperatingSystem) { localMachine = RegistryKey.OpenBaseKey(Microsoft.Win32.RegistryHive.LocalMachine, RegistryView.Registry64); } else { localMachine = RegistryKey.OpenBaseKey(Microsoft.Win32.RegistryHive.LocalMachine, RegistryView.Registry32); } RegistryKey windowsNTKey = localMachine.OpenSubKey(@"Software\Microsoft\Windows NT\CurrentVersion"); return windowsNTKey.GetValue("ProductId").ToString(); } 

Su win64 alcune chiavi di registro dell’applicazione a 32 bit sono archiviate nella sottochiave Software\Wow6432Node .

Se si desidera passare alla chiave a 64 bit, è ansible utilizzare l’enum RegistryView come parametro di RegistryKey.OpenBaseKey

Personalmente per fare in modo che il codice funzioni sempre nella chiave di registro principale (non in WoW6432) usando tale costruzione:

RegistryKey.OpenBaseKey(RegistryHive.CurrentUser, Environment.Is64BitOperatingSystem ? RegistryView.Registry64 : RegistryView.Registry32)