SYSK 106: The Cost of Using WindowsPrincipal
Did you know that using WindowsPrincipal.IsInRole is ~40+% slower than doing the same work yourself? Run the code below and you’ll see … Don’t take me wrong – I do not suggest you avoid using IsInRole call; after all a single call is so fast on most computers that it is not even measurable using a timer… It’s just nice to know the cost of doing business J
public bool IsInRoleCustom(System.Security.Principal.WindowsIdentity wi, string role)
{
bool result = false;
System.Security.Principal.IdentityReference id = new System.Security.Principal.NTAccount(role).Translate(typeof(System.Security.Principal.SecurityIdentifier));
foreach (System.Security.Principal.IdentityReference group in wi.Groups)
{
if (group.Value == id.Value)
{
result = true;
break;
}
}
return result;
}
public bool IsInRoleSystem(System.Security.Principal.WindowsIdentity wi, string role)
{
return new System.Security.Principal.WindowsPrincipal(wi).IsInRole(role);
}
private void Form1_Load(object sender, EventArgs e)
{
System.Security.Principal.WindowsIdentity wi = System.Security.Principal.WindowsIdentity.GetCurrent();
string role = "Guests";
int cnt = 20000;
long t11, t12, t21, t22;
t11 = DateTime.Now.Ticks;
for (int i = 1; i < cnt; i++)
{
bool result = IsInRoleCustom(wi, role);
}
t12 = DateTime.Now.Ticks;
t21 = DateTime.Now.Ticks;
for (int i = 1; i < cnt; i++)
{
bool result = IsInRoleSystem(wi, role);
}
t22 = DateTime.Now.Ticks;
System.Diagnostics.Debug.WriteLine((t12-t11).ToString());
System.Diagnostics.Debug.WriteLine((t22-t21).ToString());
System.Diagnostics.Debug.WriteLine(((t22 - t21)/TimeSpan.TicksPerMillisecond).ToString());
System.Diagnostics.Debug.WriteLine(((float) (t22 - t21) / (t12 - t11)).ToString());
}
Comments
Anonymous
April 17, 2006
The question, then, is Why? What else is the system call doing that's taking up that extra time?Anonymous
April 17, 2006
The comment has been removedAnonymous
April 17, 2006
I've been in optimization mode for the past couple weeks, so my viewpoint is definitely skewed. When I see 40% possible improvement in time, it makes me giddy. Now that improvement may only end up a couple cycles in the long run, and as we all know, we shouldn't prematurely optimize, but if funcX() returns the same boolean value as funcY() with the same parameters and there are no other side effects that differentiate the two functions, I'd take those extra cycles and apply them elsewhere.
Is there something else going on in the system code that is overlooked in the custom code? Some edge case that won't get handled correctly by simple SID comparison?
Anyway, I just thought it was interesting about the performance difference between system and custom code. For any very specific task like this, you'd expect the system implementer to have selected the ideal implementation. When the ideal implementation isn't the fastest, it's interesting to hear the reasons why.Anonymous
October 12, 2006
Hi, I could not find Group in WindowsIdentity (as in your code - wi.Groups). Also I could not find "System.Security.Principal.IdentityReference". In what vesion of .NET is this available? Thanks a lot.Anonymous
October 12, 2006
.NET 2.0Anonymous
January 07, 2008
You've been kicked (a good thing) - Trackback from DotNetKicks.com