Discussion:
How exactly should one go about calling AcquireCredentialsHandle using Kerberos?
(too old to reply)
Eugen
2010-06-24 22:10:58 UTC
Permalink
Hello everyone,

I'm trying hard but do not make any progress on this issue. I'm
working on a WPF Windows application that has its own user
authentication and allows different Active Directory users to log in
which are different from the user who is logged in to the Windows
session; those users are not currently logged into Windows in their
own sessions. We want to use Kerberos brokered authentication for
authenticating with servers and I'm afraid that I'm doing something
terribly stupid because I cannot get the AcquireCredentialsHandle to
fail, no matter how silly are the user name + domain + password
combinations that I use. The code I use is below, please let me know
how should I go about doing this the right way.

Thanks much, eugen


NativeMethods.SEC_WINNT_AUTH_IDENTITY credentials =
new
NativeMethods.SEC_WINNT_AUTH_IDENTITY(userName.ToString(),

domainName.ToString(),

password.ToString());
int size = Marshal.SizeOf(credentials);
IntPtr pCredentials = Marshal.AllocHGlobal(size);
Marshal.StructureToPtr(credentials, pCredentials, false);

NativeMethods.SecHandle outHandle = new
NativeMethods.SecHandle();
NativeMethods.SECURITY_INTEGER expiration = new
NativeMethods.SECURITY_INTEGER();

string principal;
if ((domainName.Length > 0) && (userName.Length > 0))
principal = userName.ToString() + "@" +
domainName.ToString();
else
principal = userName.ToString();

try
{
result =
NativeMethods.AcquireCredentialsHandle(principal,

"Kerberos",

(int)NativeMethods.SECPKG_CRED_OUTBOUND,

IntPtr.Zero,

pCredentials,

IntPtr.Zero,

IntPtr.Zero,
ref
outHandle,
ref
expiration);
}
finally
{
Marshal.FreeHGlobal(pCredentials);
}

Where the pinvoke declarations are:

[StructLayout(LayoutKind.Sequential)]
public struct SECURITY_INTEGER
{
public uint LowPart;
public uint HighPart;
};

[StructLayout(LayoutKind.Sequential)]
public struct SecHandle
{
public IntPtr LowPart;
public IntPtr HighPart;
};

internal static uint SEC_WINNT_AUTH_IDENTITY_UNICODE = 0x2;

[StructLayout(LayoutKind.Sequential, CharSet =
CharSet.Unicode)]
public struct SEC_WINNT_AUTH_IDENTITY
{
internal string User;
internal uint UserLength;
internal string Domain;
internal uint DomainLength;
internal string Password;
internal uint PasswordLength;
internal uint Flags;

internal SEC_WINNT_AUTH_IDENTITY(string user,
string domain,
string password)
{
InitializeFields(out this.User, out this.UserLength,
user);
InitializeFields(out this.Domain, out
this.DomainLength, domain);
InitializeFields(out this.Password, out
this.PasswordLength, password);
this.Flags = SEC_WINNT_AUTH_IDENTITY_UNICODE;
}

private static void InitializeFields(out string field,
out uint fieldLength,
string param)
{
field = param;
fieldLength = (uint)GetStringLength(field);
}

private static int GetStringLength(string field)
{
return String.IsNullOrEmpty(field) ? 0 : field.Length;
}
};

//
// Credential Use Flags
//
internal static uint SECPKG_CRED_INBOUND = 0x00000001;
internal static uint SECPKG_CRED_OUTBOUND = 0x00000002;
internal static uint SECPKG_CRED_BOTH = 0x00000003;
internal static uint SECPKG_CRED_DEFAULT = 0x00000004;
internal static uint SECPKG_CRED_RESERVED = 0xF0000000;

[DllImport("secur32.dll", CharSet=CharSet.Unicode,
SetLastError = true)]
internal static extern int AcquireCredentialsHandle(
string pszPrincipal, //SEC_CHAR*
string pszPackage, //
SEC_CHAR* //"Kerberos","NTLM","Negotiative"
int fCredentialUse,
IntPtr PAuthenticationID,//_LUID AuthenticationID,//
pvLogonID, //PLUID
IntPtr pAuthData,//PVOID
IntPtr pGetKeyFn, //SEC_GET_KEY_FN
IntPtr pvGetKeyArgument, //PVOID
ref SecHandle phCredential, //SecHandle //
PCtxtHandle ref
ref SECURITY_INTEGER ptsExpiry); //PTimeStamp //
TimeStamp ref
dB.
2010-06-30 16:30:30 UTC
Permalink
Check out http://waffle.codeplex.com, it's has NET code that does all
of this.

Loading...