473,245 Members | 1,406 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 473,245 software developers and data experts.

Marshal.AllocHGlobal failure after calling GetTokenInformation

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 GetTokenInformation 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.AllocHGlobal call.

Here's the library function:

// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ ~~~~~
using System;
using System.Collections.Specialized;
using System.DirectoryServices;
using System.Runtime.InteropServices;
using System.Security.Principal;
using System.Text.RegularExpressions;
namespace foobar.Library
{
public class AdFunctions
{
enum TOKEN_INFORMATION_CLASS
{
TokenUser = 1,
TokenGroups,
TokenPrivileges,
TokenOwner,
TokenPrimaryGroup,
TokenDefaultDacl,
TokenSource,
TokenType,
TokenImpersonationLevel,
TokenStatistics,
TokenRestrictedSids,
TokenSessionId,
TokenGroupsAndPrivileges,
TokenSessionReference,
TokenSandBoxInert,
TokenAuditPolicy,
TokenOrigin
}

public struct TOKEN_USER
{
public SID_AND_ATTRIBUTES User; // a single SID_AND_ATTRIBUTES
struct
}

public struct TOKEN_GROUPS
{
public int GroupCount; // DWORD number of groups
public SID_AND_ATTRIBUTES[] Groups; // array of SID_AND_ATTRIBUTES
structs
}

public struct SID_AND_ATTRIBUTES
{
public IntPtr Sid; // pointer to a sid
public int Attributes; // DWORD attributes
}
//[DllImport("advapi32.dll", CharSet=CharSet.Auto)]
//static extern bool ConvertSidToStringSid( IntPtr pSID,
[In,Out,MarshalAs(UnmanagedType.LPTStr)] ref string pStringSid);

// Using IntPtr for pSID insted of Byte[]
[DllImport("advapi32.dll", CharSet=CharSet.Auto, SetLastError=true)]
static extern bool ConvertSidToStringSid(IntPtr pSID, out IntPtr
pSid);

[DllImport("advapi32.dll", CharSet=CharSet.Auto, SetLastError=true)]
static extern bool ConvertStringSidToSid( string sStringSid, out
IntPtr pSID );

[DllImport("advapi32.dll", SetLastError=true)]
static extern bool GetTokenInformation(
IntPtr TokenHandle,
TOKEN_INFORMATION_CLASS TokenInformationClass,
IntPtr TokenInformation,
int TokenInformationLength,
out int ReturnLength);

[DllImport("kernel32.dll")]
static extern IntPtr LocalFree(IntPtr hMem);

public int GetGroupSidsFromToken(IntPtr pToken, ref string[] aSids)
{
int iTokenInfoLength = 0;
bool bResult = true;

// first call gets length of TokenInformation
bResult = GetTokenInformation( pToken,
TOKEN_INFORMATION_CLASS.TokenGroups, IntPtr.Zero, 0, out
iTokenInfoLength );

//HERE if I uncomment this, the call returns an integer rapidly
//return iTokenInfoLength;

// if we got a return, continue
if ( iTokenInfoLength > 0 )
{
// allocate a memory buffer for the TokenInformation
IntPtr pTokenInfo = Marshal.AllocHGlobal( iTokenInfoLength );

// get the TokenInformation
bResult = GetTokenInformation( pToken,
TOKEN_INFORMATION_CLASS.TokenGroups , pTokenInfo, iTokenInfoLength, out
iTokenInfoLength ) ;
if ( bResult == false ) { return 2; }

// convert the TokenInformation to a TOKEN_GROUPS struct
TOKEN_GROUPS TokenGroups = ( TOKEN_GROUPS )Marshal.PtrToStructure(
pTokenInfo , typeof( TOKEN_GROUPS ) ) ;

// loop through the groups
for ( int i=0; i < TokenGroups.GroupCount; i++ )
{
IntPtr pSid = IntPtr.Zero;

// get the string representation of the sid
bResult = ConvertSidToStringSid( TokenGroups.Groups[i].Sid, out
pSid );
if ( bResult == false ) { return 3; }

// put it into a c# string and free the memory
string sSid = Marshal.PtrToStringAuto( pSid );
LocalFree(pSid);

// add it to the array reference
aSids[i] = sSid;
}
}
else
{
// GetTokenInformation returned a 0 length
return 1;
}

// all set
return 0;
}


}
}

// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ ~~~~~

Here's the code behind file that calls it:

// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ ~~~~~

using System;
using System.Collections;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Security.Principal;
using System.Web;
using System.Web.SessionState;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Web.UI.HtmlControls;

using foobar.Library;

namespace Users
{
/// <summary>
/// Summary description for WebForm1.
/// </summary>
public class Default : System.Web.UI.Page
{
protected System.Web.UI.WebControls.Label lblStatusLine;

private void Page_Load(object sender, System.EventArgs e)
{
Trace.Write("debug", "Page_Load: entered function");
Trace.Write("debug", "Page_Load: user id is " +
System.Web.HttpContext.Current.User.Identity.Name. ToString() );
Trace.Write("debug", "Page_Load: process id is " +
WindowsIdentity.GetCurrent().Name.ToString() );

string[] aSids = new string[200];
Trace.Write("debug", "Page_Load: created array" );

AdFunctions oAdFunctions = new AdFunctions();
Trace.Write("debug", "Page_Load: created AdFunctions object" );

int iReturn =
oAdFunctions.GetGroupSidsFromToken(WindowsIdentity .GetCurrent().Token,
ref aSids);
Trace.Write("debug", "Page_Load: AdFunctions.GetGroupSidsFromToken
returned " + iReturn.ToString() );

if ( iReturn == 0 )
{
// TODO color the output
lblStatusLine.Text = "ok...";
}
else
{
lblStatusLine.Text = Application["ProductName"] + " could not
retrive your logon groups. Please contact your administrator
(GetGroupSidsFromToken:" + iReturn.ToString() + ").";
}
}

#region Web Form Designer generated code
override protected void OnInit(EventArgs e)
{
//
// CODEGEN: This call is required by the ASP.NET Web Form Designer.
//
InitializeComponent();
base.OnInit(e);
}

/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
this.Load += new System.EventHandler(this.Page_Load);

}
#endregion
}
}

// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ ~~~~~

and finally the aspx page:

// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ ~~~~~

<%@ Page language="c#" Codebehind="Default.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="Microsoft Visual Studio .NET 7.1">
<meta name="CODE_LANGUAGE" Content="C#">
<meta name="vs_defaultClientScript" content="JavaScript">
<meta name="vs_targetSchema"
content="http://schemas.microsoft.com/intellisense/ie5">
</HEAD>
<body MS_POSITIONING="GridLayout">
<form id="Form1" method="post" runat="server">
<asp:Label id="lblStatusLine" style="Z-INDEX: 101; LEFT: 160px;
POSITION: absolute; TOP: 760px"
runat="server" Width="872px"></asp:Label>
</form>
</body>
</HTML>

Nov 17 '05 #1
1 4138
I managed to fix this, the fixed code is below:

thanks to Mattias from the post "How to call Win32 Native API
GetTokenInformation() using C#?"

public class Misc
{

public Array redim(Array arrToResize, int length)
{
// from http://www.code101.com/Code101/Displ...le.aspx?cid=54
Type t= arrToResize.GetType().GetElementType();
Array newArray=Array.CreateInstance(t,length);
Array.Copy(arrToResize,0,newArray,0,Math.Min(arrTo Resize.Length,length));
return newArray;
}
}

public class AdFunctions
{
enum TOKEN_INFORMATION_CLASS
{
TokenUser = 1,
TokenGroups,
TokenPrivileges,
TokenOwner,
TokenPrimaryGroup,
TokenDefaultDacl,
TokenSource,
TokenType,
TokenImpersonationLevel,
TokenStatistics,
TokenRestrictedSids,
TokenSessionId,
TokenGroupsAndPrivileges,
TokenSessionReference,
TokenSandBoxInert,
TokenAuditPolicy,
TokenOrigin
}

public struct TOKEN_USER
{
public SID_AND_ATTRIBUTES User; // a single SID_AND_ATTRIBUTES
struct
}

[StructLayout(LayoutKind.Sequential)]
public struct TOKEN_GROUPS
{
public int GroupCount; // DWORD number of groups
public SID_AND_ATTRIBUTES[] Groups; // array of SID_AND_ATTRIBUTES
structs
}

[StructLayout(LayoutKind.Sequential)]
public struct SID_AND_ATTRIBUTES
{
public IntPtr Sid; // pointer to a sid
public int Attributes; // DWORD attributes
}
//[DllImport("advapi32.dll", CharSet=CharSet.Auto)]
//static extern bool ConvertSidToStringSid( IntPtr pSID,
[In,Out,MarshalAs(UnmanagedType.LPTStr)] ref string pStringSid);

// Using IntPtr for pSID insted of Byte[]
[DllImport("advapi32.dll", CharSet=CharSet.Auto, SetLastError=true)]
static extern bool ConvertSidToStringSid(IntPtr pSID, out IntPtr
pSid);

[DllImport("advapi32.dll", CharSet=CharSet.Auto, SetLastError=true)]
static extern bool ConvertStringSidToSid( string sStringSid, out
IntPtr pSID );

[DllImport("advapi32.dll", SetLastError=true)]
static extern bool GetTokenInformation(
IntPtr TokenHandle,
TOKEN_INFORMATION_CLASS TokenInformationClass,
IntPtr TokenInformation,
int TokenInformationLength,
out int ReturnLength);

[DllImport("kernel32.dll")]
static extern IntPtr LocalFree(IntPtr hMem);

public int GetGroupSidsFromToken(IntPtr pToken, ref string[] aSids)
{
int iTokenInfoLength = 0;
bool bResult = true;

// first call gets length of TokenInformation
bResult = GetTokenInformation( pToken,
TOKEN_INFORMATION_CLASS.TokenGroups, IntPtr.Zero, 0, out
iTokenInfoLength );
// if I uncomment this, the call returns an integer rapidly
//return iTokenInfoLength;

// if we got a return, continue
if ( iTokenInfoLength > 0 )
{
// allocate a memory buffer for the TokenInformation
IntPtr pTokenInfo = Marshal.AllocHGlobal( iTokenInfoLength );

// get the TokenInformation
bResult = GetTokenInformation( pToken,
TOKEN_INFORMATION_CLASS.TokenGroups , pTokenInfo, iTokenInfoLength, out
iTokenInfoLength ) ;
if ( bResult == false ) { return 2; }

// why would this be here and not after Marshal.PtrToStructure?
like TokenGroups.GroupCount?
int groupCount = Marshal.ReadInt32( pTokenInfo );

// convert the TokenInformation to a TOKEN_GROUPS struct
// BREAKING HERE
//TOKEN_GROUPS TokenGroups = ( TOKEN_GROUPS
)Marshal.PtrToStructure( pTokenInfo , typeof( TOKEN_GROUPS ) ) ;

// get a pointer to the first group
int pSidAndAttibutes = (int)pTokenInfo + 4;

// loop through the groups
for ( int i=0; i < groupCount; i++ )
{
// marshall the struct out of the pointer
SID_AND_ATTRIBUTES SidAndAttibutes =
(SID_AND_ATTRIBUTES)Marshal.PtrToStructure( (IntPtr)pSidAndAttibutes ,
typeof(SID_AND_ATTRIBUTES) ) ;

// initialize a pointer and get the sid converted
IntPtr pSid = IntPtr.Zero;
bResult = ConvertSidToStringSid( SidAndAttibutes.Sid, out pSid );
if ( bResult == false ) { return 3; }

// place it into a c# string and free up the memory
string sSid = Marshal.PtrToStringAuto( pSid );
LocalFree(pSid);

// add it to the array reference
aSids[i] = sSid;

// move to the next pointer
pSidAndAttibutes += Marshal.SizeOf( typeof(SID_AND_ATTRIBUTES) );
}
// redim the array
Misc oMisc = new Misc();
aSids = (string[])oMisc.redim(aSids, groupCount);
}
else
{
// GetTokenInformation returned a 0 length
return 1;
}

// all set
return 0;
}

Nov 17 '05 #2

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

2
by: Stefan | last post by:
I have the following question The Marshal class contains a function to allocate a block of memory 1. Marshal.AllocHGlobal ( int cb 2. Marshal.AllocHGlobal ( IntPtr cb The first version I can...
2
by: Hypnotron | last post by:
Hello, Regarding Marshal.AllocHGlobal versus Marshal.AllocCoTaskMem Does anyone know the circumstances in which one should use one over the other? ...
0
by: Hypnotron | last post by:
>Hello, >Regarding Marshal.AllocHGlobal versus Marshal.AllocCoTaskMem Does anyone >know the circumstances in which one should use one over the other? >...
13
by: Just Me | last post by:
The following almost works. The problem is Marshal.PtrToStringAuto seems to terminate at the first null so I don't get the full string. Any suggestions on how to fix this? Or how to improve the...
2
by: scottt | last post by:
I need to call into a C++ DLL from my C# code. The function is expecting a void pointer to an unsigned short. Which would be more correct? UInt16 wRegData; IntPtr p =...
2
by: runner | last post by:
I'm trying to call some functions from OpenSSL library but I'm a bit confused when I have to use pinvoke. first function should create key from some input data, it's declared : void...
2
by: O.B. | last post by:
When using Marshal to copy data from a byte array to the structure below, only the first byte of the "other" array is getting copied from the original byte array. What do I need to specify to get...
0
by: Charming12 | last post by:
Hi All, I have a strange problem and due to my inefficiency with IntPtr i am unable to figure it out. I have an structure something like: public struct Detail { public int age; public...
2
by: O.B. | last post by:
I have operation within a class that marshals the data into a byte array. Below are three different ways that work. Are there any downsides to using one over the the other? public virtual byte...
0
by: fareedcanada | last post by:
Hello I am trying to split number on their count. suppose i have 121314151617 (12cnt) then number should be split like 12,13,14,15,16,17 and if 11314151617 (11cnt) then should be split like...
0
by: stefan129 | last post by:
Hey forum members, I'm exploring options for SSL certificates for multiple domains. Has anyone had experience with multi-domain SSL certificates? Any recommendations on reliable providers or specific...
0
Git
by: egorbl4 | last post by:
Скачал я git, хотел начать настройку, а там вылезло вот это Что это? Что мне с этим делать? ...
1
by: davi5007 | last post by:
Hi, Basically, I am trying to automate a field named TraceabilityNo into a web page from an access form. I've got the serial held in the variable strSearchString. How can I get this into the...
0
by: MeoLessi9 | last post by:
I have VirtualBox installed on Windows 11 and now I would like to install Kali on a virtual machine. However, on the official website, I see two options: "Installer images" and "Virtual machines"....
0
by: DolphinDB | last post by:
The formulas of 101 quantitative trading alphas used by WorldQuant were presented in the paper 101 Formulaic Alphas. However, some formulas are complex, leading to challenges in calculation. Take...
0
by: DolphinDB | last post by:
Tired of spending countless mintues downsampling your data? Look no further! In this article, you’ll learn how to efficiently downsample 6.48 billion high-frequency records to 61 million...
0
by: Aftab Ahmad | last post by:
So, I have written a code for a cmd called "Send WhatsApp Message" to open and send WhatsApp messaage. The code is given below. Dim IE As Object Set IE =...
0
isladogs
by: isladogs | last post by:
The next Access Europe meeting will be on Wednesday 6 Mar 2024 starting at 18:00 UK time (6PM UTC) and finishing at about 19:15 (7.15PM). In this month's session, we are pleased to welcome back...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.