UnauthorizedAccessException writing to HKLM

Q. I’m trying to write to HKLM on a Vista computer using the following code:

Dim k As Microsoft.Win32.RegistryKey
k = Microsoft.Win32.Registry.LocalMachine.OpenSubKey("software", True)
k = k.CreateSubKey("subkey1\testprogram")
k.SetValue("foo", "bar")

But, when I get to the last line, the UnauthorizedAccessException is thrown.  How do I fix this?

A. It is throwing an exception because Microsoft considers writing to HKLM a security risk which requires elevated privileges.  When you are programming in .NET, you should not store application specific data in the registry.  Instead you should store this information in a file on the hard drive.  I’ll give you some tips on how to do that at the end of this article.  But, first I want to try to convince you that using the Registry is evil.

Using the registry to store your data, decreases the performance of your computer.
That’s right.  The registry is a sequential database.  Looking for data in it is similar to opening a file and sequentially reading through the file until you find what it is you are looking for.  The larger the registry, the longer it will take to find the item at the end.  Therefore, any application that uses the registry to store information will take longer to find the information.  Over time, this means your computer will take longer to boot and application will suffer.

Registry data can not be backed up easily.
Most people who do backup their computers expect the data that needs to be backed up in the Documents folder.  At a minimum, they expect to be able to xcopy the drive to another drive and still have all the data they need.  I recently suffered from a computer malfunction that required me to xcopy my drive to an external drive, re-install Windows (and all my programs) and restore my data from the external drive.

It was then that I found out that one of the programs I was using was storing data I needed to restore in the registry!  Arrgh.  I’ve since found a different program for that job.

Contrast this to Eudora that I can move from one computer to another by doing nothing but copying from one computer to another!

.NET is suppose to be XCopy deployable
Since .NET released, the intention from Microsoft is that an installation program is not needed to either place the program on a computer or to move from one computer to another.  If you are storing data in the registry, you obviously won’t be able to use XCopy deploy to move your application.

Registry security gets in the way.
And of course, there is the question at hand, which reminds me of a story.

A patient comes into the doctor’s office and says, “Doc, it hurts when I do this.”  To which the doctor responds, “Well, then… Don’t do that.”

So, what to do instead?
There are two types of data you might need to store.  Data that every user who logs into the computer will need to be able to access in common and data that is user specific.  Microsoft has provided an API for storing app settings for the current version of the software.  But, I personally find that unusable because every version has to start over.  If you can use it, it is probably the easiest method.  But, it isn’t a cure all.

Store to a file.
The last time I really needed to store configuration data for an application was when I created VSS.NET  What I did for this application is that I created a serializable class that held all of the configuration information.  By making it serializable, I could store the configuration data either as binary or xml into a file stream anywhere I needed.  Since this information was user specific, I stored the information in a file locally.

I’m assuming you already know how to create a serializable class and save it to a file.  What you may not be aware of is how to find the various system locations on the computer.  Especially since they are in different physical locations depending on what operating system you are running.  So, here they are:

System.Environment.GetFolderPath(param), returns the path of one of the system folders and the enum System.Environment.SpecialFolder holds the constants that get passed in as the parameter.

Using this, you can store your data into the Document directory, AppData, or several other folders.  I prefer to store into the Document directory whenever I can so that the information will get backed up.  Preferably in a clearly marked directory so that it does not get deleted, or as a hidden file.  If that doesn’t work.  AppData is my second choice.

So, how do you fix the UnauthorizedSecurityException when writing to HKLM?  You stop writing to the registry and write to a file instead.


Related Post

7 Responses to “UnauthorizedAccessException writing to HKLM”

  • gmagana:

    This is equivalent to saying “how do you fix this rendering problem in IE? Use firefox.”

    A serialized class… What happens to your data when, on a version upgrade, you change the structure of the class? What happens when the .NET version changes? In both cases, you cannot read the serialized class anymore. Your settings/data are lost. The worst possible thing to do. Serialization is not intended for long-term storage of data.

    At least dig into the past and suggest INI files (which are quite appropriate for storing small amounts of configuration options or data sets). Even using wordy-old XML is a better option that serialized-class binary files.

    In C\C++, binary files saved to disk straight from structs were a pain in the ass to deal with in case of needing to change the underlying struct as part of a version upgrade for the exact same reason your suggestion here is a bad idea.

  • Jibbers42:

    Good post, right up until, “I prefer to store into the Document…”

    I can’t stand how much crap is stuffed into *My* Documents. It’s My Documents dammit, mine! It isn’t Your Documents or Thier Documents. I guess in Vista it’s just Documents, so maybe the ownership is up for debate, lol (actually all the folder name changes in Vista are great).


  • Jibbers42:

    Jesus gmagana, kinda rough, but valid.

    I thought the same when I read about the serialized class suggestion, but forgot about it by the time he advocated cluttering my documents folder, lol.

  • Dave:

    Yes, gmagana, you are both “kind of rough” AND not at all accurate.

    If you implement serialization correctly my method works very well. In fact, I used it on an active application. You have to serialize the version of the object and account for it when you read, but that does not make the solution unworkable, nor does it make the post dumb or technically worthless.

    Pull out your history book and look at the Archive method in MFC/C++ and you will find that this is EXACTLY how they dealt with this situation. OK.. not everyone got the memo on this because I’ve seen some pretty serious inaccurate implementations. But using a version identifier is the correct way to do this in both situations.

    Of course, if all you do is apply the Serializable attribute, you are GOING to have BIG trouble. But, that’s not what I’m suggesting. I’m suggesting IMPLEMENTING the Serializable interface which gives you a lot more control, and was specifically made for long term storage.

    BTW, what do you think is happening when you save a Word, Excel, PowerPoint, etc document? That’s versioned object serialization happening there. If serialization were such a huge problem, then I guess we’d have to store everything in a database.

    Implementation using EITHER binary OR XML is completely valid depending on how accessible you want that data to be outside your application. That is an implementation detail and you’ll get yourself in trouble saying that it should ALWAYS be one or the other.

  • Dave:


    You’ll note I gave options on where to store the data. Documents is just one possible location which may or may not be valid for your application.

  • [...] .NET AnswersASP.NET, HTML, CSS, Visual Studio, CSharp, VB.NET and other programming items of interest. UnauthorizedAccessException writing to HKLM [...]

  • OJ:

    I also hate apps that clutter up My Documents, especially when the stuff they store in there are not in any way a document! Application settings don’t belong in My Documents.

    Surely an application settings file that is stored somewhere in Isolated Storage would be the preferred option when using .NET? You don’t have to worry about security, you can get per-user settings, and you don’t have to worry about dealing with the registry at all.

Leave a Reply

Comment Policy:

  • You must verify your comment by responding to the automated email that is sent to your email address. Unverified comments will never show.Leave a good comment that adds to the conversation and I'll leave your link in.
  • Leave me pure spam and I'll delete it.
  • Leave a general comment and I'll remove the link but keep the comment.

Notify me of followup comments via e-mail