3

We are trying to add a key value pair into the Windows registry using C#.

The key to write is an Environment variable for another user. The user will be a Service User, and never log on.

We have been able to get the user SID, and add it to the Registry, by P/Invoking LoadUserProfile.

However, when trying to write to the Environment Sub Key there is a problem:

 using (var key = Registry.Users.OpenSubKey(userSid + "\\Environment")) { if (key == null) { Debug.WriteLine("Key was null (typical)"); return; } key.SetValue("A", "B"); } 

This throws an UnauthorizedAccessException with the really helpful message

Cannot write to the registry key

The application is running as an administrator.

For obvious reasons I am guessing it is something to do with the security access control. I can get the access control, using var security = key.GetAccessControl(); However, I don't know what values to change to be able to write to the Environment.

Just for the record, I can write values to some other keys such as HKEY_USERS itself, or HKEY_LOCAL_MACHINE itself, but I cannot write to HKEY_LOCAL_MACHINE\Public for example.

Here is the stack trace if it helps:

************** Exception Text ************** System.UnauthorizedAccessException: Cannot write to the registry key. at System.ThrowHelper.ThrowUnauthorizedAccessException(ExceptionResource resource) at Microsoft.Win32.RegistryKey.EnsureWriteable() at Microsoft.Win32.RegistryKey.SetValue(String name, Object value, RegistryValueKind valueKind) at Microsoft.Win32.RegistryKey.SetValue(String name, Object value) at TestingEnvVariables.Form1.GetVariablesButtonClick(Object sender, EventArgs e) at System.Windows.Forms.Control.OnClick(EventArgs e) at System.Windows.Forms.Button.OnClick(EventArgs e) at System.Windows.Forms.Button.OnMouseUp(MouseEventArgs mevent) at System.Windows.Forms.Control.WmMouseUp(Message& m, MouseButtons button, Int32 clicks) at System.Windows.Forms.Control.WndProc(Message& m) at System.Windows.Forms.ButtonBase.WndProc(Message& m) at System.Windows.Forms.Button.WndProc(Message& m) at System.Windows.Forms.Control.ControlNativeWindow.OnMessage(Message& m) at System.Windows.Forms.Control.ControlNativeWindow.WndProc(Message& m) at System.Windows.Forms.NativeWindow.Callback(IntPtr hWnd, Int32 msg, IntPtr wparam, IntPtr lparam) 
7
  • 1
    Does the application is running "Run As Admin". If not, please try that. It looks like, you don't have permissions to write. Commented Mar 17, 2017 at 8:02
  • 1
    @MuralidharanDeenathayalan - yes, it is running in "Run as Admin" Commented Mar 17, 2017 at 8:03
  • 1
    Try impersonating the user, using the same user token you obtained in order to call LoadUserProfile. Commented Mar 17, 2017 at 8:21
  • 1
    @HarryJohnston - I tried that. That did not allow me to write to the registry, and when I tried using Environment.SetEnvrionmentVariable it set the variable in my ordinary user profile Commented Mar 17, 2017 at 8:24
  • When you try to do it manually with regedit: does it fail too, or succeed? Commented Mar 17, 2017 at 10:41

1 Answer 1

4

Bingo!

From the MSDN article on RegistryKey.OpenSubKey(String):

Retrieves a subkey as read-only.

You need RegistryKey.OpenSubKey(String, Boolean) (MSDN article):

Retrieves a specified subkey, and specifies whether write access is to be applied to the key.

Sign up to request clarification or add additional context in comments.

1 Comment

That's it! What an idiot I am! Elementary mistake! Thanks Harry Johnston.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.