Impersonation code in C#

While investigating a customer issue, I needed code to impersonate a different user on the current thread.  A quick search of the msdn blogs turned up this post, which got me most of the way there.  I decided to wrap the code into a class that inherits from IDisposable just to make it easily usable in a using statement.  Here is what I came up with:

using System;

using System.ComponentModel;

using System.Runtime.InteropServices;

using System.Security.Principal;


public class ImpersonatedUser : IDisposable


    IntPtr userHandle;

    WindowsImpersonationContext impersonationContext;


    public ImpersonatedUser(string user, string domain, string password)


        userHandle = IntPtr.Zero;

        bool loggedOn = LogonUser(






            out userHandle);


        if (!loggedOn)

            throw new Win32Exception(Marshal.GetLastWin32Error());


        // Begin impersonating the user

        impersonationContext = WindowsIdentity.Impersonate(userHandle);



    public void Dispose()


        if (userHandle != IntPtr.Zero)



            userHandle = IntPtr.Zero;





    [DllImport("advapi32.dll", SetLastError = true)]

    static extern bool LogonUser(

        string lpszUsername,

        string lpszDomain,

        string lpszPassword,

        LogonType dwLogonType,

        LogonProvider dwLogonProvider,

        out IntPtr phToken



    [DllImport("kernel32.dll", SetLastError = true)]

    static extern bool CloseHandle(IntPtr hHandle);


    enum LogonType : int


        Interactive = 2,

        Network = 3,

        Batch = 4,

        Service = 5,

        NetworkCleartext = 8,

        NewCredentials = 9,



    enum LogonProvider : int


        Default = 0,



Comments (2)

  1. Gareth says:

    Would I be right in saying that as the ImpersonatedUser class does not have a finalizer there is no pint in calling “GC.SuppressFinalize(this);”? And there would be no point in adding a finalizer as it would run on a different thread?

  2. JonCole says:


    I believe you are right about the SuppressFinalize call.  I pounded this code out pretty quickly and didn’t consider that fact.  I have removed the unnecssary code.  Thanks for the comment.

Skip to main content