I have a C# application that when run sets some environment variables. These environment variables need to be set system wide.
I use this code to actually do the set.
public static void SetEnvironmentVariable(string _keyName, string _value, RegistryValueKind _type) { using (RegistryKey reg = Registry.LocalMachine.OpenSubKey(@"SYSTEM\CurrentControlSet\Control\Session Manager\Environment", true)) { if (reg != null) { reg.SetValue(_keyName, _value, _type); } else { string x = string.Format( "Could find registry key that hosts Environment Variables: SYSTEM\\CurrentControlSet\\Control\\Session Manager\\Environment"); App.AppLogger.Error(x); throw new Exception(x); } } } This code works, but I notice some strange behavior. Immediately after running my app and this code, I run cmd as a regular user and take a look a the environment using the "set" command. It shows no changes.
I then run a cmd prompt as admin and run set. It shows the changes. Not only that, it shows fully expanded variables. Where ALLFOO=Foo, and PATH=C:\Windows\System32;%ALLFOO%;, the set command shows PATH=C:\Windows\System32;Foo;.
I then log off and back on. I then run cmd as a normal user. I type set and it shows the new environment variables, but not expanded. It shows PATH=C:\Windows\System32;%ALLFOO%; ( It seems to have no trouble expanding %SYSTEMROOT% for some reason.)
I get that the log-off and back on causes the new Explorer.exe that's launched to get the new env vars for the regular user's cmd.exe, but I don't understand why they are not expanded.
Why would running cmd and set as administrator show fully expanded environment variables and running cmd and set as a normal user would not?
When setting the env vars in the C# program i use the RegistryValueKind.ExpandString enumeration.
Edit: I am aware of the order of declaration time to expansion time issue with system variables and have edited the question example to reflect this.