首先,在VC里面封装为DLL.函数如下:
EXPORT VOID ObjectToDBItem(void *lpBin, POSDB_ITEM *lpDBItem)
{
memcpy(lpDBItem, (void*)lpBin, sizeof(POSDB_ITEM));
char buf[200];
sprintf(buf,"ID:%d    BaseID:%d    Hp:%d    Attrib:%s    Status:%d    ",lpDBItem->ID,lpDBItem->BaseID,lpDBItem->Hp,lpDBItem->Attrib,lpDBItem->Status);
MessageBox(NULL,buf,NULL,0);   //在这里输出DLL结果
} 其中POSDB_ITEM 类型定义为:
typedef struct POSDB_ITEM
{
    unsigned long           ID;                 
    unsigned int            BaseID;             
    unsigned char           Hp;                 
    unsigned char           Attrib[5];          
    unsigned char           Status;             
} POSDB_ITEM;然后呢,用C#调用这个函数,申明为:
[ DllImport( "EdrLib.dll" )]
public static extern void ObjectToDBItem( [MarshalAs(UnmanagedType.AsAny)]Object o, ref POSDB_ITEM DBItem);

在C#中,struct定义为:
[ StructLayout( LayoutKind.Sequential, CharSet=CharSet.Ansi)]
public struct POSDB_ITEM 
{
public ulong           ID;                 
public uint            BaseID;             
public byte            Hp;                
[ MarshalAs( UnmanagedType.ByValTStr, SizeConst=5 )]
public String          Attrib;          
public byte            Status;            
}在C#中的实现方式为:
dbItem = new POSDB_ITEM();
dbItem.ID = 54;
dbItem.BaseID = 567;
dbItem.Hp = 33;
dbItem.Attrib = "m4a1";
dbItem.Status = 44;
POSDB_ITEM testItem = new POSDB_ITEM();
ObjectToDBItem((Object)dbItem,ref testItem);
MessageBox.Show("ID:" + testItem.ID.ToString() + "\tBaseID:" + testItem.BaseID.ToString() + "\tHP:" + testItem.Hp.ToString() + "\tAttrib:" + testItem.Attrib + "\tStatus:" + testItem.Status.ToString() );    //在这里输出C#结果然而呢,最终实现的结果如下:(这个DLL文件,我C++的测试程序中没有问题)
在DLL的MessageBox输出结果为:
ID:54    BaseID:0    Hp:55    Attrib:(一个我无法输出的符号,用比划表达,横折)   Status:52
在C#的MessageBox输出结果为:
ID:54    BaseID:567    Hp:33    Attrib:m4   Status:0问题提出:
1.传入DLL的数据几乎是错误的,只有ID是正确的.
2.返回C#的数据从Attrib起出错,Attrib应该是Unicode问题,损失了一个字符,Status为0,可能还是attrib的填充符号.
3.为什么我显示要返回的数据和实际返回的数据严重不一样,其实从传入的数据来分析,已经不一样了(测试过).希望高手指点迷津.谢谢!

解决方案 »

  1.   

    经测试得出如下结果:typedef struct POSDB_ITEM
    {
        unsigned long           ID;   //4字节              
        unsigned int            BaseID; //4字节            
        unsigned char           Hp;   //1字节              
        unsigned char           Attrib[5];//5字节          
        unsigned char           Status;//1字节,经测试,这是第15字节,             
    } POSDB_ITEM;//总共15字节,然后由于内存对齐方式,为16字节第16字节未被初始化![ StructLayout( LayoutKind.Sequential, CharSet=CharSet.Ansi)]
    public struct POSDB_ITEM 
    {
    public ulong           ID; //8字节                
    public uint            BaseID;//4字节          
    public byte            Hp;//1字节                
    [ MarshalAs( UnmanagedType.ByValTStr, SizeConst=5 )]
    public String          Attrib;//5字节          
    public byte            Status;//1字节            
    }//Marshal.Sizeof得出的结果是24字节,也是由于内存对齐方式!试着把ulong ID,改为uint ID,得出的结果为16字节!可能这样传递就对了!