DCOM across domains



I'm trying to instantiate a COM control in another domain. I need to
provide credentials for the second domain, so I am assuming i need to
create CoCreateInstance.. however I am unable to get this to work..
I'm at the following code right now, and my CoCreateInstance is
throwing an argument out of range exception.

Can someone help me identify what I'm doing wrong? I removed some
error checks and cleanup for brevity.


[StructLayout(LayoutKind.Sequential, Pack=4, CharSet =
CharSet.Unicode)]
public struct MULTI_QI
{
public IntPtr pIID;
public IntPtr pItf;
public int hr;
}

[StructLayout(LayoutKind.Sequential, Pack=4, CharSet =
CharSet.Unicode)]
public struct COAUTHIDENTITY
{
public IntPtr User;
public uint UserLength;
public IntPtr Domain;
public uint DomainLength;
public IntPtr Password;
public uint PasswordLength;
public uint Flags;
}


[StructLayout(LayoutKind.Sequential, Pack=4, CharSet =
CharSet.Unicode)]
public struct COAUTHINFO
{
public Authn dwAuthnSvc;
public Authz dwAuthzSvc;
public IntPtr pwszServerPrincName;
public AuthnLevel dwAuthnLevel;
public uint dwImpersonationLevel;
public IntPtr pAuthIdentityData;
public uint dwCapabilities;
}

[StructLayout(LayoutKind.Sequential, Pack = 4, CharSet =
CharSet.Unicode)]
public struct COSERVERINFO
{
public uint dwReserved1;
public IntPtr pwszName;
public IntPtr pAuthInfo;
public uint dwReserved2;
}

public enum Authn
{
RPC_C_AUTHN_NONE = 0 ,
RPC_C_AUTHN_DCE_PRIVATE = 1 ,
RPC_C_AUTHN_DCE_PUBLIC = 2 ,
RPC_C_AUTHN_DEC_PUBLIC = 4 ,
RPC_C_AUTHN_GSS_NEGOTIATE = 9 ,
RPC_C_AUTHN_WINNT = 10 ,
RPC_C_AUTHN_GSS_SCHANNEL = 14 ,
RPC_C_AUTHN_GSS_KERBEROS = 16 ,
RPC_C_AUTHN_MSN = 17 ,
RPC_C_AUTHN_DPA = 18 ,
RPC_C_AUTHN_MQ = 100 ,
RPC_C_AUTHN_DEFAULT = -1
};

public enum Authz
{
RPC_C_AUTHZ_NONE = 0,
RPC_C_AUTHZ_NAME = 1,
RPC_C_AUTHZ_DCE = 2,
RPC_C_AUTHZ_DEFAULT = -1
};


public class someclass
{
const int SEC_WINNT_AUTH_IDENTITY_UNICODE = 2;

[DllImport("ole32.dll", CharSet = CharSet.Unicode,
ExactSpelling = true, PreserveSig = false)]
static extern void CoCreateInstanceEx(
[In, MarshalAs(UnmanagedType.LPStruct)] Guid rclsid,
[MarshalAs(UnmanagedType.IUnknown)] object pUnkOuter,
CLSCTX dwClsCtx,
[In] ref COSERVERINFO pServerInfo,
uint cmq,
[In, Out] ref MULTI_QI[] pResults);


public void somefunction()
{
COAUTHIDENTITY ci = new COAUTHIDENTITY() {
User = Marshal.StringToBSTR(_username),
UserLength = (uint)_username.Length,
Password = Marshal.StringToBSTR(_password),
PasswordLength = (uint)_password.Length,
Domain = Marshal.StringToBSTR(_domain),
DomainLength = (uint)_domain.Length,
Flags = SEC_WINNT_AUTH_IDENTITY_UNICODE
};

COAUTHINFO ca = new COAUTHINFO() {
dwAuthnLevel = AuthnLevel.RPC_C_AUTHN_LEVEL_CONNECT,
dwAuthzSvc = Authz.RPC_C_AUTHZ_NONE,
dwAuthnSvc = Authn.RPC_C_AUTHN_WINNT,
dwCapabilities = 0,
dwImpersonationLevel = 3,
pwszServerPrincName = IntPtr.Zero
};

ca.pAuthIdentityData = Marshal.AllocCoTaskMem
(Marshal.SizeOf(ci));
Marshal.StructureToPtr(ci, ca.pAuthIdentityData, true);

COSERVERINFO cs = new COSERVERINFO();
cs.pwszName = Marshal.StringToBSTR(_serverAddress);
cs.pAuthInfo = Marshal.AllocCoTaskMem(Marshal.SizeOf(ca));
Marshal.StructureToPtr(ca, cs.pAuthInfo, true);


Type ServerType = Type.GetTypeFromProgID
("MyRemoteObject.xyzzy", _serverAddress);

MULTI_QI[] qi = new MULTI_QI[1];

MULTI_QI qiInstance = new MULTI_QI();
qiInstance.hr = 0;
qiInstance.pItf = IntPtr.Zero;
qiInstance.pIID = Marshal.AllocCoTaskMem(Marshal.SizeOf
(qiInstance) * 2);
Marshal.StructureToPtr(ServerType.GUID, qiInstance.pIID,
false);

qi[0] = qiInstance;

CoCreateInstanceEx(ServerType.GUID, IntPtr.Zero,
CLSCTX.CLSCTX_REMOTE_SERVER, ref cs, 1, ref qi);

}

}
.



Relevant Pages

  • RE: Run app as specified user from ASP.NET 2.0
    ... const int SecurityImpersonation = 2; ... string commandLinePath; ... public uint dwX; ... public IntPtr lpReserved2; ...
    (microsoft.public.dotnet.framework.aspnet)
  • Manipulating win32 app menus from c# using pinvoke...
    ... supplying the fMask of the MENUITEMINFO with the MF_OWNERDRAW constant from ... public uint cbSize; ... public IntPtr hbmpChecked; ... private static extern IntPtr GetSubMenu ...
    (microsoft.public.dotnet.languages.csharp)
  • Re: Access Denied executing Batch File from CreateProcessAsUser
    ... > public uint dwX; ... > public IntPtr lpReserved2; ... > private extern static bool CreateProcessAsUser(IntPtr hToken, ... > lpApplicationName, String lpCommandLine, ref SECURITY_ATTRIBUTES ...
    (microsoft.public.dotnet.framework.aspnet.security)
  • Function WaveInOpen doesnt return meesage MM_WIM_OPEN?
    ... public IntPtr hWaveOut = IntPtr.Zero; ... public uint nAvgBytesPerSec; ... public static extern int waveInOpen(ref IntPtr lphWaveIn, ... IntPtr dwCallback, uint dwInstance, uint dwFlags); ...
    (microsoft.public.dotnet.languages.csharp)