Link to home
Start Free TrialLog in
Avatar of jhance
jhance

asked on

RasEnumEntries problem

Reference the following code:

     LPRASENTRYNAME lpRasEntryName;
     lpRasEntryName = (LPRASENTRYNAME)HeapAlloc(GetProcessHeap(), 0, sizeof(RASENTRYNAME));

     memset(lpRasEntryName, 0, sizeof(RASENTRYNAME));
     lpRasEntryName->dwSize = sizeof(RASENTRYNAME);

     DWORD dwRet;
     DWORD cb = sizeof(RASENTRYNAME);
     DWORD cbEntries = 0;

     dwRet = RasEnumEntries(NULL, NULL, lpRasEntryName, &cb, &cbEntries);

At run time, RasEnumEntries() returns 610 - ERROR_BUFFER_INVALID.  I'm at a loss as to what is wrong here.  Probably something trivial that I'm missing after staring at this for too long...
Avatar of DanRollins
DanRollins
Flag of United States of America image

This code works on my Win2K machine.  

#include <windows.h>
#include <ras.h>
#include <rasError.h>

#pragma comment(lib, "Rasapi32.lib" )
void main ( void )
{
    LPRASENTRYNAME lpRasEntryName;
    DWORD nRecSize= sizeof(RASENTRYNAME);

    lpRasEntryName = (LPRASENTRYNAME)HeapAlloc(GetProcessHeap(), 0, nRecSize );
    memset( lpRasEntryName, 0, nRecSize );
    lpRasEntryName->dwSize= nRecSize;

    DWORD nBufSize= nRecSize;
    DWORD nEntries= 0;
    DWORD dwRet= RasEnumEntries(NULL, NULL, lpRasEntryName, &nBufSize, &nEntries);
     if ( dwRet == ERROR_BUFFER_TOO_SMALL ) {
          lpRasEntryName= (LPRASENTRYNAME)HeapReAlloc( GetProcessHeap(), 0, lpRasEntryName, nBufSize );
         dwRet= RasEnumEntries(NULL, NULL, lpRasEntryName, &nBufSize, &nEntries);
     }
}

I can get
   632 -- ERROR_INVALID_SIZE
and
   603 -- ERROR_BUFFER_TOO_SMALL

by making various intentional errors, but I can't duplicate the problem you describe.  However, be advised that there are four distinct variations of the RASENTRYNAME sructure:

WINVER < 0x0500 (small), Non-UNICODE     (254)
WINVER < 0x0500 (small), UNICODE            (520)

WINVER >= 0x0500 (large), Non-UNICODE   (532)
WINVER >= 0x0500 (large), UNICODE        (1048)

And that there are two different versions of RAS.H  In the VS 6 version, we see:

#define RASENTRYNAMEW struct tagRASENTRYNAMEW
RASENTRYNAMEW{
    DWORD dwSize;
    WCHAR szEntryName[ RAS_MaxEntryName + 1 ];
};

#define RASENTRYNAMEA struct tagRASENTRYNAMEA
RASENTRYNAMEA {
    DWORD dwSize;
    CHAR  szEntryName[ RAS_MaxEntryName + 1 ];
};

while in the VS 7 (and presumably the most up-to-date SDK), we see:

#define RASENTRYNAMEW struct tagRASENTRYNAMEW
RASENTRYNAMEW {
    DWORD dwSize;
    WCHAR szEntryName[ RAS_MaxEntryName + 1 ];
#if (WINVER >= 0x500)
    DWORD dwFlags;
    WCHAR szPhonebookPath[MAX_PATH + 1];
#endif
};

#define RASENTRYNAMEA struct tagRASENTRYNAMEA
RASENTRYNAMEA {
    DWORD dwSize;
    CHAR  szEntryName[ RAS_MaxEntryName + 1 ];
#if (WINVER >= 0x500)
    DWORD dwFlags;
    CHAR  szPhonebookPath[MAX_PATH + 1];
#endif
};

I suppose that you could get a 610 error if you foreably mismatched the structure and the function... the Is that any help?

Is there any reason to use
    HeapAlloc(GetProcessHeap(),...
rather than malloc or other other more standard allocator?

-- Dan
Avatar of northernchill
northernchill

Is there a value returned in cb and/or cbEntries?
If so what are they?

Your code looks right. What version of Windows?
Avatar of jhance

ASKER

>>Is there a value returned in cb and/or cbEntries?

Nope.  The contents of both cb and cbEntries are unchanged through the call to RasEnumEntries.

>>Your code looks right. What version of Windows?

Win98SE
Do you have some dial up networking connections defined?

I can't see any problems, but you might want to try this to attempt to isolate the problem - Change the lpRasEntryName variable from a pointer to a local instance.

RASENTRYNAME RasEntryName;
RasEntryName.dwSize = sizeof(RASENTRYNAME);
RasEnumEntries(NULL,NULL,&RasEntryName,&cb,&cbEntries);

and see what happens.

This is not a solution, just one path to help solve a problem.
Avatar of jhance

ASKER

Yes, I have 4 DUN connections defined.

I changed it to use a local instance of RASENTRYNAME and still get error 610.
That suggests that is not a problem in the chunk of code you posted, but rather is rooted deeper in your project.

Does the function containing this code do anything before this block is executed? Could you post that if it does.
Avatar of jhance

ASKER

At this point, the code I posted above is about all there is...  I've removed all other code.
jhance,
I provided a complete program.  Did you run it?  Does it generate a 610 error?  

If so, then all that is left is that the DLL itself is returning that error unexpectedly.  Win98SE is rather old.  Perhaps there is a better version of Rasapi32.Dll that you could try using.  I tested against version 5.0.2195.5438

Is there any reason to use
   HeapAlloc(GetProcessHeap(),...
rather than malloc or other other more standard allocator?

-- Dan
Avatar of jhance

ASKER

>>provided a complete program.  Did you run it?  Does it generate a 610 error?  

Your code is virtually the same as mine and it does generate a 610 error

>>If so, then all that is left is that the DLL itself is returning that error unexpectedly.  Win98SE is rather old.  Perhaps there is a better version of Rasapi32.Dll that you could try using.  I tested against version 5.0.2195.5438

Well yes, I know Win98 is old.  But the SDK says even Win95 supports this API.

>>Is there any reason to use
  HeapAlloc(GetProcessHeap(),...

Not really.  I had been trying with new/delete but was getting this error.  The sample code in the SDK uses HeapAlloc and while I didn't think it should matter, it does appear that HeapAlloc gets blocks of memory from a different region of memory.
I can't reproduce the problem, but I can suggest this diagnostic try:
Pass in the address of a buffer, and a hard-coded "size" value.  That is, throw some spaghetti at it an see what sticks:

BYTE p[3000];
nEntries= 0; nSize=254;  dwRet= RasEnumEntriesA(0,0, p, &nSize, &nEntries);
nEntries= 0; nSize=520;  dwRet= RasEnumEntriesA(0,0, p, &nSize, &nEntries);
nEntries= 0; nSize=532;  dwRet= RasEnumEntriesA(0,0, p, &nSize, &nEntries);
nEntries= 0; nSize=1048; dwRet= RasEnumEntriesA(0,0, p, &nSize, &nEntries);

nEntries= 0; nSize=254;  dwRet= RasEnumEntriesW(0,0, p, &nSize, &nEntries);
nEntries= 0; nSize=520;  dwRet= RasEnumEntriesW(0,0, p, &nSize, &nEntries);
nEntries= 0; nSize=532;  dwRet= RasEnumEntriesW(0,0, p, &nSize, &nEntries);
nEntries= 0; nSize=1048; dwRet= RasEnumEntriesW(0,0, p, &nSize, &nEntries);

A longshot:  
Perhaps the "ERROR_BUFFER_INVALID" is referrring to the second parameter.  The meaning of this parm has changed over the years...

Finally, examine the Debug output window to verify which DLL is being called -- the path, filename, and version/date  There might be several RaxXxxxx DLLs in the executable path and perhaps a corrupt one is getting loaded.

-- Dan
Avatar of jhance

ASKER

Very odd indeed....

OK, perhaps I'm asking the wrong question here.  Perhaps RasEnumEntries() has never worked on Win98.  The MSDN docs have been known to be wrong.

Using SoftICE I set a breakpoint on both RasEnumEntriesA and RasEnumEntriesW and I do not even get a break, even when opening the Dial-Up Networking window.  I find this odd but I do see that RasEnumConnections is being called.  Since the way MS does this is "right" by default, perhaps I've been approaching this the wrong way.
RasEnumEntries is being resolved into a DLL function call -- *something* is being called, *somewhere*.  The DLL that gets loaded should be listed in the debug window.  Perhaps in older version of the RAS dll, that fn just ends up at a stub that returns an error code.

Does GetProcAddress return a fn ptr?

Another longshot:
Maybe you have some sort of stealth API hooking going on that is redirecting the call.

-- Dan
Avatar of jhance

ASKER

Sure, the file is:

C:\WINDOWS\SYSTEM\RASAPI32.DLL

the file is version 4.10.2222

I searched my system and this is the only copy of the DLL on the hard drive.
ASKER CERTIFIED SOLUTION
Avatar of DanRollins
DanRollins
Flag of United States of America image

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
Avatar of jhance

ASKER

That looks promising.  I'll give it a shot and let you know.

>>If I were you I'd get a new version of the DLL.

Not an option.  The RASAPI32.DLL is NOT redistributable.  I have to live with whatever is on the system.  

This also appears to be the "latest and greatest" for Win98 SE since my test system is up-to-date and this is the original RASAPI32.DLL installed from the Win98 SE CDROM.  So even if I could update it, what would I update it to?  I think the chances of the W2K RASAPI32.DLL actually working on Win98 is remote even if it were legal to redistribute it.
Avatar of jhance

ASKER

Dan,

That did the trick...  Good find on that error.

Thanks much!!
Thanks for the points.  I'm 33 points away from making the board in this TA.

Is it possible that updating IE would update that DLL?  If so, it would explain why the problem seems to relatively rare.
-- Dan
Avatar of jhance

ASKER

The system in question has IE5.5.  So I don't think that's the answer.
Avatar of jhance

ASKER

I'll see if I can come up with another good question for you to answer and see if we can get you over the top!!
I'm having a similar problem to this one, only using the RasEnumConnections API rather than RasEnumEntries.  Unfortunately, the solution suggested in the linked threads (essentially #define WINVER 0x400) is not possible for my project, as it also needs the RasConnectionNotification API, which is only defined for WINVER 0x401 and above, despite being available since Win98.  Does anyone know what can be done about this?  What is the correct WINVER to use for Win98 compatibility?
hi jules_h_3141,
Welcome to EE.  Please do not 'piggyback' your own question onto another.  Just ask a new question.  Thanks!  -- Dan