在struct中的C#StringBuilder结构中导入C dll

时间:2014-07-16 12:08:40

标签: c# c marshalling stringbuilder

我需要为C dll导入一个函数GDPI,我想在一个C#应用程序中使用。 我的问题是,一个参数是一个结构CFSPI,在这个结构中我有其他结构: PII PPI LPPCC LPPOL LPPOP

我的问题在于LPPOL的原始结构是C是

typedef struct tagCFS_PRINT_OVLINFO {
DWORD dwOverlayType;
TCHAR szFormPath[MAX_PATH];
DWORD dwFormID;
BOOL bFormIdFixed;
} CFS_PRINT_OVLINFO, *LPCFS_PRINT_OVLINFO;

CFSPI结构是:

typedef struct tagCFS_PRINTINFO {
DWORD wCopies;
DWORD dwPrintInterval;
DWORD dwPrintSpeed;
DWORD dwPageID;
DWORD dwJobID;
CFS_PRINT_IMGINFO pii;
CFS_PRINT_PAPERINFO ppi;
LPCFS_PRINT_CCORRECTINFO lppcc;
LPCFS_PRINT_OVLINFO lppol;
LPCFS_PRINT_OPTION lppop;
LPVOID lpReserve1;
LPVOID lpReserve2;
DWORD dwReserve1;
DWORD dwReserve2;
} CFS_PRINTINFO, *LPCFS_PRINTINFO;

功能定义是

int CFTGetDefaultPrintInfo(
IN LPTSTR lptPrinterName, // Printer name to obtain the print information
OUT CFSPI* lpPrtInfo // Default print information
);

我尝试用C#定义

[DllImport("mydll.dll")]
internal static extern int CFTGetDefaultPrintInfo(string lptPrinterName, CFSPI lpPrtInfo);

internal struct CFS_PRINTINFO
{
    internal uint dwCopies;
    internal uint dwPrintInterval;
    internal uint dwPrintSpeed;
    internal uint dwPageID;
    internal uint dwJobID;
    internal CFS_PRINT_IMGINFO pii;
    internal CFS_PRINT_PAPERINFO ppi;
    internal CFS_PRINT_CCORRECTINFO lppcc;
    internal CFS_PRINT_OVLINFO lppol;
    internal CFS_PRINT_OPTION lppop; 
    internal IntPtr lpReserve1; 
    internal IntPtr lpReserve2;
    internal uint dwReserve1;
    internal uint dwReserve2;
}

internal struct CFS_PRINT_OVLINFO
{
    internal uint dwOverlayType; // Overlay, Print type
    internal StringBuilder szFormPath; // Form file path
    internal uint dwFormID; // Form file ID
    internal bool bFormIdFixed; // Wether to fix the form ID
}

当我调用我有的功能时

  

Blockquote Impossible de marshaler le champ'lppol'de type'App.CFS_PRINTINFO':Laéfinitiondetype de ce champpossèdedesinformations de disposition,maiselleprésenteunecombinaison detypesmanagés/nonmanagésnonvalide ou elle ne peut pasêtremarshalée。

我尝试使用字符串但不成功..

你有什么想法吗?

谢谢

1 个答案:

答案 0 :(得分:0)

要创建固定缓冲区,请不要使用StringBuilder

internal unsafe struct CFS_PRINT_OVLINFO
{
    internal uint dwOverlayType; // Overlay, Print type
    internal fixed char szFormPath[MAX_PATH]; // Form file path
    internal uint dwFormID; // Form file ID
    internal bool bFormIdFixed; // Wether to fix the form ID
}

您必须启用不安全的代码才能使其正常工作。

但是C代码与您在C#中创建的内容之间存在更多不兼容性: lppcclppollppop是指针,因此应将其创建为指针或IntPtr

internal unsafe struct CFS_PRINTINFO
{
    internal uint dwCopies;
    internal uint dwPrintInterval;
    internal uint dwPrintSpeed;
    internal uint dwPageID;
    internal uint dwJobID;
    internal CFS_PRINT_IMGINFO pii;
    internal CFS_PRINT_PAPERINFO ppi;
    internal CFS_PRINT_CCORRECTINFO* lppcc;
    internal CFS_PRINT_OVLINFO* lppol;
    internal CFS_PRINT_OPTION* lppop; 
    internal IntPtr lpReserve1; 
    internal IntPtr lpReserve2;
    internal uint dwReserve1;
    internal uint dwReserve2;
}

甚至extern方法定义不正确,应该是(假设CFSPICFS_PRINTINFO):

[DllImport("mydll.dll")]
internal static extern int CFTGetDefaultPrintInfo(string lptPrinterName, out CFSPI lpPrtInfo);