user2481095
user2481095

Reputation: 2106

Marshaling Parameters to C++ API Function Call From C# Application

I'm calling calling a C/C++ function from a dll within my C# application. I can't for the life of me figure out how to properly Marshall the data.

Here's the information on the API function I am trying to call:

LONG LoginDialog(HWND hWndParent, LPCWSTR lpctstrTitle, ULONG ulFlags, LPWSTR lptstrDataSource, LONG lDSLength, LPCWSTR lpctstrUsername, LPCWSTR lpctstrPassword, LPCWSTR lpctstrSchema);

Parameters:
[in] hWndParent Specifies parent window handle for the Login dialog to display.
[in] lpctstrTitle Pointer to the null-terminated string specifying title for the Login dialog to display. Specify NULL pointer to use the default Login dialog title.
[in] ulFlags Specifies login operation and dialog style mask. It can be 0 or a bit-wise OR combination of flags listed in Login Dialog Style Flags.
[in,out] lptstrDataSource Pointer to the null-terminated string buffer specifying name of the datasource to log into. On output this buffer receives name of the datasource the user was logged into (in case datasource name was changed within the Login dialog).
[in] lDSLength Specifies length of the string buffer specified by lptstrDataSource.
[in] lpctstrUsername Pointer to the null-terminated string specifying user name.
[in] lpctstrPassword Pointer to the null-terminated string specifying password.
[in] lpctstrSchema Pointer to the null-terminated string specifying full path of the schema file. Specify NULL pointer if schema is not needed.

Here's my code:

[DllImport("dmawin.dll", CharSet = CharSet.Unicode)] 
private static extern int LoginDialog(IntPtr pWndParent, string pStrTitle, 
uint pFlags, [MarshalAs(UnmanagedType.LPWStr)] ref StringBuilder pStrDataSource, 
int pDSLength, string pStrUsername, string pStrPassword, string pStrSchema);


private bool Login(string pDataSource, string pLoginName, 
string pPassword, string pScheme)
{
    private const int MAX_DB_NAME = 256;
    IntPtr handle = ParentForm.Handle;
    var sb = new StringBuilder(pDataSource, MAX_DB_NAME);

    //function call
    LoginDialog(handle, null, flags, ref sb, MAX_DB_NAME, pLoginName, 
    pPassword, pScheme);
}

I'm pretty sure that I am marshaling the 4th parameter wrong (LPWSTR lptstrDataSource). I've tried different answers I've found online but none have worked so far for me.

I'm also getting this warning first. Sorry for not clarifying:

Managed Debugging Assistant 'LoadFromContext' has detected a problem ..

Additional information: The assembly was loaded from 'the dll location' using the LoadFrom context. The use of this context can result in unexpected behavior for serialization, casting and dependency resolution. In almost all cases, it is recommended that the LoadFrom context be avoided. This can be done by installing assemblies in the Global Assembly Cache or in the ApplicationBase directory and using Assembly.Load when explicitly loading assemblies.

Upvotes: 0

Views: 98

Answers (0)

Related Questions