Trying to enumerate servers on the network

I have an interesting problem.  This problem primarily shows up on Windows 2008 machines, we tested on a 2003 machine and it works fine.

Here is the scenario:  using the NetServerEnum call, enumerate all machines on one domain.  Get 400+ nodes.  Wait a couple of minutes, and run the call again get 32 nodes.  First enumeration takes 7 minutes to verify findings (ping nodes returned in the call).  Second enumeration takes 7 SECONDS to verify findings.

How and why would this happen.
Some machine details:  Windows 2008 Server SP1 Enterprise on a domain (trusted to the domain being enumerated).
SQL Server 2008 to store results returned.
Logged on as local administrator (doesn't matter if I'm logged on as domain admin or local admin, same problem).
This is a 2003 domain and we are a remote office.

I do have access to a 2008 development machine on which I can get some more details if needed.

Thanks in advance!
ericlockshineDirector of ITAsked:
Who is Participating?
I wear a lot of hats...

"The solutions and answers provided on Experts Exchange have been extremely helpful to me over the last few years. I wear a lot of hats - Developer, Database Administrator, Help Desk, etc., so I know a lot of things but not a lot about one thing. Experts Exchange gives me answers from people who do know a lot about one thing, in a easy to use platform." -Todd S.

jkrCommented:
Do you get similar results when using 'WNetEnumResource()' instead? You'll find some ready made code at http://win32.mvps.org/network/wnoe_wner.c - I'll post that below.
#include <stdio.h>
#include <windows.h>
#pragma hdrstop
 
 
 
// compile and link with
 
//	cl wnoe_wner.c mpr.lib
 
 
int main( void );
int doEnum( int level, NETRESOURCE *pnr );
void exterr( void );
 
 
 
void exterr( void )
{
	char errbuf[2048], namebuf[2048];
	DWORD err;
 
	errbuf[0] = namebuf[0] = '\0';
	if ( WNetGetLastError( &err, errbuf, sizeof errbuf, namebuf, sizeof namebuf ) == NO_ERROR )
		printf( "Error %lu (\"%s\") reported by \"%s\".\n",
			err, errbuf, namebuf );
	return;
}
 
 
 
int doEnum( int level, NETRESOURCE *pnr )
{
	DWORD rc, rc2;
	HANDLE hEnum;
	DWORD count, bufsize, ui;
	NETRESOURCE buf[200];
	const char *type, *cont;
 
	rc = WNetOpenEnum( RESOURCE_GLOBALNET, RESOURCETYPE_ANY, 0, pnr, &hEnum );
	if ( rc == ERROR_ACCESS_DENIED )
	{
		printf( "%-6.6s %-4.4s%*s  Error 5 -- access denied\n", "", "", level * 2, "" );
		return 1;
	}
 
	if ( rc )
	{
		printf( "WNOE(): rc = %lu, gle = %lu\n", rc, rc2 = GetLastError() );
		if ( rc2 == ERROR_EXTENDED_ERROR )
			exterr();
		return 0;
	}
 
	while ( 1 )
	{
		count = (DWORD) -1L;
		bufsize = sizeof buf;
		rc = WNetEnumResource( hEnum, &count, buf, &bufsize );
		if ( rc != NO_ERROR )
			break;
		for ( ui = 0; ui < count; ++ ui )
		{
			switch ( buf[ui].dwDisplayType )
			{
				case RESOURCEDISPLAYTYPE_DOMAIN:
					type = "domain"; break;
				case RESOURCEDISPLAYTYPE_GENERIC:
					type = "generic"; break;
				case RESOURCEDISPLAYTYPE_SERVER:
					type = "server"; break;
				case RESOURCEDISPLAYTYPE_SHARE:
					type = "share"; break;
				default:
					type = "unknown"; break;
			}
			cont = ( buf[ui].dwUsage & RESOURCEUSAGE_CONTAINER )? "container": "";
			printf( "%-6.6s %-4.4s%*s  %s (%s)\n", type, cont, level * 2, "",
				buf[ui].lpRemoteName, buf[ui].lpProvider );
			// now we recurse if it's a container
			if ( buf[ui].dwUsage & RESOURCEUSAGE_CONTAINER )
				doEnum( level + 1, &buf[ui] );
		}
	}
 
	if ( rc != ERROR_NO_MORE_ITEMS ) // bad things
	{
		printf( "WNER(): rc = %lu, gle = %lu\n", rc, rc2 = GetLastError() );
		if ( rc2 == ERROR_EXTENDED_ERROR )
			exterr();
	}
 
	WNetCloseEnum( hEnum );
	return 1;
}
 
 
 
int main( void )
{
	doEnum( 0, NULL );
 
	return 0;
}

Open in new window

0

Experts Exchange Solution brought to you by

Your issues matter to us.

Facing a tech roadblock? Get the help and guidance you need from experienced professionals who care. Ask your question anytime, anywhere, with no hassle.

Start your 7-day free trial
ericlockshineDirector of ITAuthor Commented:
jkr, sorry it took so long to get back.  I was pulled off and just got back.  I'll test your code sample above shortly, probably today or tomorrow and submit my findings.

Thanks for the assistance.
0
ericlockshineDirector of ITAuthor Commented:
jkr,
I was always able to enumerate the machines using your sample code.  I also saw the other items you had at the website, so I tried some of them.  Since they always work, it must be something in our program.
0
Has Powershell sent you back into the Stone Age?

If managing Active Directory using Windows Powershell® is making you feel like you stepped back in time, you are not alone.  For nearly 20 years, AD admins around the world have used one tool for day-to-day AD management: Hyena. Discover why.

jkrCommented:
Well, 'NetServerEnum()' is superseded by the API in teh above example, that's why I suggested tring that. Any chance you can replace your enumeration code with the above?
0
ericlockshineDirector of ITAuthor Commented:
I wish I could replace the code.  This is a part of the code that I am not allowed to modify (it is part of the core of the product).  About the only thing I can do is start to log information about the calls and when/if they fail.  If I can show that the code has been superseded, then I may be able to change it, but I'm not sure.

I'm wondering why the call would enumerate all nodes one time and then only a portion the next.  If I could figure out the pattern of what was being enumerated, I may be able to figure that out, and show them why the new code would be better.

I know this one has been open a while, but I'm still working on it.  Thanks for the assist so far jkr.
0
ericlockshineDirector of ITAuthor Commented:
Thanks for the assist jkr.  The code cannot be replaced at this time, but when I wote a little app for it, it worked every time, where the other code worked all but 2 out of 10 runs.  I think that part of the issue was dns/wins/ad related, since we are a remote site and during the time of the 2 that failed, the network was flaky.
0
It's more than this solution.Get answers and train to solve all your tech problems - anytime, anywhere.Try it for free Edge Out The Competitionfor your dream job with proven skills and certifications.Get started today Stand Outas the employee with proven skills.Start learning today for free Move Your Career Forwardwith certification training in the latest technologies.Start your trial today
Microsoft Development

From novice to tech pro — start learning today.