I have been banging my head against the wall for a while now, and can't
seem to id the problem. I've been through a ton of posts and the code
doesn't seem any different. Can anybody see it?
When I call to GetTokenInforma tion I receive a buffer size (see
//HERE... comment in code), but when I let the code continue, asp.net
just sits there returning nothing, apparently on the
Marshal.AllocHG lobal call.
Here's the library function:
// ~~~~~~~~~~~~~~~ ~~~~~~~~~~~~~~~ ~~~~~~~~~~~~~~~ ~~~~~~~~~~
using System;
using System.Collecti ons.Specialized ;
using System.Director yServices;
using System.Runtime. InteropServices ;
using System.Security .Principal;
using System.Text.Reg ularExpressions ;
namespace foobar.Library
{
public class AdFunctions
{
enum TOKEN_INFORMATI ON_CLASS
{
TokenUser = 1,
TokenGroups,
TokenPrivileges ,
TokenOwner,
TokenPrimaryGro up,
TokenDefaultDac l,
TokenSource,
TokenType,
TokenImpersonat ionLevel,
TokenStatistics ,
TokenRestricted Sids,
TokenSessionId,
TokenGroupsAndP rivileges,
TokenSessionRef erence,
TokenSandBoxIne rt,
TokenAuditPolic y,
TokenOrigin
}
public struct TOKEN_USER
{
public SID_AND_ATTRIBU TES User; // a single SID_AND_ATTRIBU TES
struct
}
public struct TOKEN_GROUPS
{
public int GroupCount; // DWORD number of groups
public SID_AND_ATTRIBU TES[] Groups; // array of SID_AND_ATTRIBU TES
structs
}
public struct SID_AND_ATTRIBU TES
{
public IntPtr Sid; // pointer to a sid
public int Attributes; // DWORD attributes
}
//[DllImport("adva pi32.dll", CharSet=CharSet .Auto)]
//static extern bool ConvertSidToStr ingSid( IntPtr pSID,
[In,Out,MarshalA s(UnmanagedType .LPTStr)] ref string pStringSid);
// Using IntPtr for pSID insted of Byte[]
[DllImport("adva pi32.dll", CharSet=CharSet .Auto, SetLastError=tr ue)]
static extern bool ConvertSidToStr ingSid(IntPtr pSID, out IntPtr
pSid);
[DllImport("adva pi32.dll", CharSet=CharSet .Auto, SetLastError=tr ue)]
static extern bool ConvertStringSi dToSid( string sStringSid, out
IntPtr pSID );
[DllImport("adva pi32.dll", SetLastError=tr ue)]
static extern bool GetTokenInforma tion(
IntPtr TokenHandle,
TOKEN_INFORMATI ON_CLASS TokenInformatio nClass,
IntPtr TokenInformatio n,
int TokenInformatio nLength,
out int ReturnLength);
[DllImport("kern el32.dll")]
static extern IntPtr LocalFree(IntPt r hMem);
public int GetGroupSidsFro mToken(IntPtr pToken, ref string[] aSids)
{
int iTokenInfoLengt h = 0;
bool bResult = true;
// first call gets length of TokenInformatio n
bResult = GetTokenInforma tion( pToken,
TOKEN_INFORMATI ON_CLASS.TokenG roups, IntPtr.Zero, 0, out
iTokenInfoLengt h );
//HERE if I uncomment this, the call returns an integer rapidly
//return iTokenInfoLengt h;
// if we got a return, continue
if ( iTokenInfoLengt h > 0 )
{
// allocate a memory buffer for the TokenInformatio n
IntPtr pTokenInfo = Marshal.AllocHG lobal( iTokenInfoLengt h );
// get the TokenInformatio n
bResult = GetTokenInforma tion( pToken,
TOKEN_INFORMATI ON_CLASS.TokenG roups , pTokenInfo, iTokenInfoLengt h, out
iTokenInfoLengt h ) ;
if ( bResult == false ) { return 2; }
// convert the TokenInformatio n to a TOKEN_GROUPS struct
TOKEN_GROUPS TokenGroups = ( TOKEN_GROUPS )Marshal.PtrToS tructure(
pTokenInfo , typeof( TOKEN_GROUPS ) ) ;
// loop through the groups
for ( int i=0; i < TokenGroups.Gro upCount; i++ )
{
IntPtr pSid = IntPtr.Zero;
// get the string representation of the sid
bResult = ConvertSidToStr ingSid( TokenGroups.Gro ups[i].Sid, out
pSid );
if ( bResult == false ) { return 3; }
// put it into a c# string and free the memory
string sSid = Marshal.PtrToSt ringAuto( pSid );
LocalFree(pSid) ;
// add it to the array reference
aSids[i] = sSid;
}
}
else
{
// GetTokenInforma tion returned a 0 length
return 1;
}
// all set
return 0;
}
}
}
// ~~~~~~~~~~~~~~~ ~~~~~~~~~~~~~~~ ~~~~~~~~~~~~~~~ ~~~~~~~~~~
Here's the code behind file that calls it:
// ~~~~~~~~~~~~~~~ ~~~~~~~~~~~~~~~ ~~~~~~~~~~~~~~~ ~~~~~~~~~~
using System;
using System.Collecti ons;
using System.Componen tModel;
using System.Data;
using System.Drawing;
using System.Security .Principal;
using System.Web;
using System.Web.Sess ionState;
using System.Web.UI;
using System.Web.UI.W ebControls;
using System.Web.UI.H tmlControls;
using foobar.Library;
namespace Users
{
/// <summary>
/// Summary description for WebForm1.
/// </summary>
public class Default : System.Web.UI.P age
{
protected System.Web.UI.W ebControls.Labe l lblStatusLine;
private void Page_Load(objec t sender, System.EventArg s e)
{
Trace.Write("de bug", "Page_Load: entered function");
Trace.Write("de bug", "Page_Load: user id is " +
System.Web.Http Context.Current .User.Identity. Name.ToString() );
Trace.Write("de bug", "Page_Load: process id is " +
WindowsIdentity .GetCurrent().N ame.ToString() );
string[] aSids = new string[200];
Trace.Write("de bug", "Page_Load: created array" );
AdFunctions oAdFunctions = new AdFunctions();
Trace.Write("de bug", "Page_Load: created AdFunctions object" );
int iReturn =
oAdFunctions.Ge tGroupSidsFromT oken(WindowsIde ntity.GetCurren t().Token,
ref aSids);
Trace.Write("de bug", "Page_Load: AdFunctions.Get GroupSidsFromTo ken
returned " + iReturn.ToStrin g() );
if ( iReturn == 0 )
{
// TODO color the output
lblStatusLine.T ext = "ok...";
}
else
{
lblStatusLine.T ext = Application["ProductNam e"] + " could not
retrive your logon groups. Please contact your administrator
(GetGroupSidsFr omToken:" + iReturn.ToStrin g() + ").";
}
}
#region Web Form Designer generated code
override protected void OnInit(EventArg s e)
{
//
// CODEGEN: This call is required by the ASP.NET Web Form Designer.
//
InitializeCompo nent();
base.OnInit(e);
}
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeCompo nent()
{
this.Load += new System.EventHan dler(this.Page_ Load);
}
#endregion
}
}
// ~~~~~~~~~~~~~~~ ~~~~~~~~~~~~~~~ ~~~~~~~~~~~~~~~ ~~~~~~~~~~
and finally the aspx page:
// ~~~~~~~~~~~~~~~ ~~~~~~~~~~~~~~~ ~~~~~~~~~~~~~~~ ~~~~~~~~~~
<%@ Page language="c#" Codebehind="Def ault.aspx.cs"
AutoEventWireup ="false" Inherits="Users .Default" Trace="True"%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN" >
<HTML>
<HEAD>
<title>WebForm1 </title>
<meta name="GENERATOR " Content="Micros oft Visual Studio .NET 7.1">
<meta name="CODE_LANG UAGE" Content="C#">
<meta name="vs_defaul tClientScript" content="JavaSc ript">
<meta name="vs_target Schema"
content="http://schemas.microso ft.com/intellisense/ie5">
</HEAD>
<body MS_POSITIONING= "GridLayout ">
<form id="Form1" method="post" runat="server">
<asp:Label id="lblStatusLi ne" style="Z-INDEX: 101; LEFT: 160px;
POSITION: absolute; TOP: 760px"
runat="server" Width="872px"></asp:Label>
</form>
</body>
</HTML>