Microsoft KB Archive/153586

= How To Call C Functions That Use the _cdecl Calling Convention =

Article ID: 153586

Article Last Modified on 6/29/2004

-

APPLIES TO


 * Microsoft Visual Basic 5.0 Learning Edition
 * Microsoft Visual Basic 6.0 Learning Edition
 * Microsoft Visual Basic 5.0 Professional Edition
 * Microsoft Visual Basic 6.0 Professional Edition
 * Microsoft Visual Basic 5.0 Enterprise Edition
 * Microsoft Visual Basic 6.0 Enterprise Edition
 * Microsoft Visual Basic 4.0 Standard Edition
 * Microsoft Visual Basic 4.0 Professional Edition
 * Microsoft Visual Basic 4.0 32-Bit Enterprise Edition

-



This article was previously published under Q153586



SUMMARY
It is not possible to directly call a C function in a DLL if that function uses the _cdecl calling convention. This is because Visual Basic uses the _stdcall calling convention for calling functions. This is a problem because if _cdecl is used, the calling function is responsible for cleaning up the stack. However, if _stdcall is used, the called function is responsible for cleaning up the stack.

NOTE: An .EXE file created in Visual Basic will allow you to call a DLL function that has been declared with the _cdecl calling convention without an error. It is only when you try to call such a function when running a program from the Visual Basic IDE, that Visual Basic generates the following error:

Run-time Error '49':

Bad DLL Calling Convention

The fact that the EXE version allows you to call such functions has been confirmed to be a bug by Microsoft. You should not rely on this behavior as this might change in future versions of Visual Basic.



MORE INFORMATION
If it is necessary to call functions that use the _cdecl calling convention (such as the MSTEST DLLs), wrap the _cdecl call inside a _stdcall call that is exposed or exported to Visual Basic. This is demonstrated in the following step-by-step example.

Step-by-Step Example
  Create a 32-bit Windows C DLL with the following functions: long _cdecl PassStr(LPSTR pStr) {      MessageBox (NULL, pStr, "Test DLL", MB_OK); return 1; }

long _stdcall PassStrStdCall(LPSTR pStr) {      return PassStr(pStr); }

Export the functions in a .DEF file as follows: LIBRARY  TESTDLL

CODE     PRELOAD MOVEABLE DISCARDABLE DATA     PRELOAD SINGLE

EXPORTS PassStr           @1 PassStrStdCall    @2

Name this DLL Testdll.dll, and save the file to the Windows\System directory in Windows 95 or Windows 98, or the Windows\System32 directory in Windows NT or Windows 2000.   Create a new project in Visual Basic. Form1 is created by default. Add the following code to the general declarations portion of Form1: Private Declare Function PassStrStdCall Lib "testdll.dll" _ (ByVal s As String) As Long

Private Sub Form_Click ret& = PassStrStdCall("hello") Print ret& End Sub

 Run the Visual Basic program, and click the form. A Msgbox will show the value of the passed string.

Keywords: kbhowto kbapi KB153586

-

[mailto:TECHNET@MICROSOFT.COM Send feedback to Microsoft]

© Microsoft Corporation. All rights reserved.