C#动态调用C DLL时报错“尝试读取或写入受保护的内存”
各位好,在做程式调试时使用C打个了DLL包,定义如下。然后尝试在C#中做动态调用,代码编译通过,但是在执行时报错:"尝试读取或写入受保护的内存”
DLL 打包时传入一个结构指针,传出一个结构指针。已经调试了几天,还是不知道问题在哪里。请各位多多帮忙!
多谢!!!
// C structure define
struct PinDef {
int Slot;
int Channel;
char PinName[20];
char PinType[5];
char DataType[5];};
struct PtnLst {
char PtnName[15];
int Load; };
struct DCIn {
double VIH;
double VIL; };
struct DCOut {
double VOH;
double VOL;};
struct DCInOut {
double VIH;
double VIL;
double VOH;
double VOL;};
struct DPS {
char PwrPin[5];
double Force;
double Clamp;};
struct DCLevels {
char LevelName[15];
struct DCIn DCLvlInput;
struct DCOut DCLvlOutput;
struct DCInOut DCLvlInOutput;
struct DPS DCLvlDPS; };
struct Period {
char Resource[15];
double Value; };
struct TDomain {
char TimingName[15];
int SlotRef;
double SlotDelay;
struct Period Period; };
struct Timing {
char TimingName[15];
struct TDomain TimingDomain; };
struct DCTest {
char TestName[15];
char Exec[50];
struct Timing TimingBlk;
struct DCLevels DCLevelsBlk;
struct PtnLst Pattern;
struct PinDef SigRefList[255];
char SignalRefStategy[20];
double Force;
double FRange;
double MeaRange;
double Delay;
double Limits;
double TimeOut; };
struct TestResult {
int ErrCode;
char ErrMsg[1024];
char PinName[5];
char TestRslt[10];
double TestVal;};
// C DLL包接口定义
void DummyTemplate2(struct DCTest* pRcvData, struct TestResult* ReturnData) {
double Value = 0.0;
if ( !(strcmp (pRcvData->SigRefList[0].PinName, "DummyPin"))) {
strcpy(ReturnData->TestRslt,"Pass");
Value = 2.0; }
else {
strcpy(ReturnData->TestRslt,"Fail");
Value = 1.0; }
strcpy(ReturnData->PinName, pRcvData->SigRefList[0].PinName);
ReturnData->TestVal = Value;
}
// C# 结构定义
using System;
using System.Runtime.InteropServices;
using System.Collections.Generic;
using System.Linq;
using System.Text;
namespace Etid
{
[StructLayout(LayoutKind.Sequential, CharSet=CharSet.Unicode,Pack = 1)]
public struct PinDef {
public int Slot;
public int Channel;
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 20)]
public string PinName;
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 5)]
public string PinType;
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 5)]
public string DataType; }
[StructLayout(LayoutKind.Sequential, Pack = 1)]
public struct PtnLst {
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 15)]
public string PtnName;
public int Load; }
[StructLayout(LayoutKind.Sequential, Pack = 1)]
public struct DCIn {
public double VIH;
public double VIL; }
[StructLayout(LayoutKind.Sequential, Pack = 1)]
public struct DCOut {
public double VOH;
public double VOL; }
[StructLayout(LayoutKind.Sequential, Pack = 1)]
public struct DCInOut {
public double VIH;
public double VIL;
public double VOH;
public double VOL; }
[StructLayout(LayoutKind.Sequential, Pack = 1)]
public struct DPS {
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 5)]
public string PwrPin;
public double Force;
public double Clamp; }
[StructLayout(LayoutKind.Sequential, Pack = 1)]
public struct DCLevels {
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 15)]
public string LevelName;
public DCIn DCLvlInput;
public DCOut DCLvlOutput;
public DCInOut DCLvlInOutput;
public DPS DCLvlDPS; }
[StructLayout(LayoutKind.Sequential, Pack = 1)]
public struct Period {
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 15)]
public string Resource;
public double Value; }
[StructLayout(LayoutKind.Sequential, Pack = 1)]
public struct TDomain {
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 15)]
public string TimingName;
public int SlotRef;
public double SlotDelay;
public Period Period; }
[StructLayout(LayoutKind.Sequential, Pack = 1)]
public struct Timing {
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 15)]
public string TimingName;
public TDomain TimingDomain; }
[StructLayout(LayoutKind.Sequential, Pack = 1)]
public struct DCTest {
[MarshalAs(UnmanagedType.ByValTStr, SizeConst=15)]
public string TestName;
[MarshalAs(UnmanagedType.ByValTStr, SizeConst=50)]
public string Exec;
public Timing TimingBlk;
public DCLevels DCLevelsBlk;
public PtnLst Pattern;
[MarshalAs(UnmanagedType.ByValArray, SizeConst=255)]
public PinDef[] SigRefList;
[MarshalAs(UnmanagedType.ByValTStr, SizeConst=20)]
public string SignalRefStategy;
public double Force;
public double FRange;
public double MeaRange;
public double Delay;
public double Limits;
public double TimeOut; }
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode, Pack = 1)]
public struct TestResult {
public int ErrCode;
[MarshalAs(UnmanagedType.ByValTStr, SizeConst=1024)]
public string ErrMsg;
[MarshalAs(UnmanagedType.ByValTStr, SizeConst=5)]
public string PinName;
[MarshalAs(UnmanagedType.ByValTStr, SizeConst=10)]
public string TestRslt;
public double TestVal; }
public class TestDataContainer {}
}
// -----------------------------------------------
// C# 动态调用DLL
// -----------------------------------------------
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.IO;
using System.Runtime.InteropServices;
using System.Xml;
namespace Etid
{
public partial class ETID : Form
{
public delegate void DummyTemplate2(ref DCTest DcEnv, ref TestResult NodeResult);
DCTest nodeDcTestEnv = new DCTest();
TestResult nodeTestRslt = new TestResult();
// Initialize nodeDcTestEnv
nodeDcTestEnv.TestName = ("DummyTest");
nodeDcTestEnv.Exec = ("DummyTemplate2");
nodeDcTestEnv.TimingBlk = new Timing();
nodeDcTestEnv.TimingBlk.TimingName = ("SIM_Timing");
nodeDcTestEnv.TimingBlk.TimingDomain = new TDomain();
nodeDcTestEnv.TimingBlk.TimingDomain.Period = new Period();
nodeDcTestEnv.TimingBlk.TimingDomain.TimingName = "DomainName";
nodeDcTestEnv.TimingBlk.TimingDomain.SlotDelay = 1.0;
nodeDcTestEnv.TimingBlk.TimingDomain.SlotRef = 5;
nodeDcTestEnv.TimingBlk.TimingDomain.Period.Resource = "Internal";
nodeDcTestEnv.TimingBlk.TimingDomain.Period.Value = 200;
nodeDcTestEnv.DCLevelsBlk = new DCLevels();
nodeDcTestEnv.DCLevelsBlk.DCLvlInput = new DCIn();
nodeDcTestEnv.DCLevelsBlk.DCLvlInput.VIH = 0.0;
nodeDcTestEnv.DCLevelsBlk.DCLvlInput.VIL = 0.0;
nodeDcTestEnv.DCLevelsBlk.DCLvlOutput = new DCOut();
nodeDcTestEnv.DCLevelsBlk.DCLvlOutput.VOH = 0.0;
nodeDcTestEnv.DCLevelsBlk.DCLvlOutput.VOL = 0.0;
nodeDcTestEnv.DCLevelsBlk.DCLvlInOutput = new DCInOut();
nodeDcTestEnv.DCLevelsBlk.DCLvlInOutput.VIH = 0.0;
nodeDcTestEnv.DCLevelsBlk.DCLvlInOutput.VIL = 0.0;
nodeDcTestEnv.DCLevelsBlk.DCLvlInOutput.VOH = 0.0;
nodeDcTestEnv.DCLevelsBlk.DCLvlInOutput.VOL = 0.0;
nodeDcTestEnv.DCLevelsBlk.DCLvlDPS = new DPS();
nodeDcTestEnv.DCLevelsBlk.DCLvlDPS.PwrPin = "VCC";
nodeDcTestEnv.DCLevelsBlk.DCLvlDPS.Force = 0.0;
nodeDcTestEnv.DCLevelsBlk.DCLvlDPS.Clamp = 0.0;
nodeDcTestEnv.DCLevelsBlk.LevelName = ("SIM_Levels");
nodeDcTestEnv.Pattern = new PtnLst();
nodeDcTestEnv.Pattern.PtnName = ("SIM_Pattern");
nodeDcTestEnv.Pattern.Load = 0;
nodeDcTestEnv.SigRefList = new PinDef[255];
PinDef tmpSList = new PinDef();
tmpSList.PinName = ("Du");
tmpSList.Slot = 3;
tmpSList.PinType = "In";
tmpSList.Channel = 6;
tmpSList.DataType = "WDT";
for (int i = 0; i < 255; i++ )
{
nodeDcTestEnv.SigRefList[i] = tmpSList;
}
nodeDcTestEnv.SignalRefStategy = ("Single");
nodeDcTestEnv.Force = 0.02;
nodeDcTestEnv.FRange = 1.0;
nodeDcTestEnv.MeaRange = 200.0;
nodeDcTestEnv.Delay = 5.0;
nodeDcTestEnv.Limits = 110.0;
nodeDcTestEnv.TimeOut = 10.0;
// Initialize nodeDcTestEnv
nodeTestRslt.TestVal = 0.0;
nodeTestRslt.ErrCode = 100;
nodeTestRslt.PinName = "";
nodeTestRslt.ErrMsg = "";
nodeTestRslt.TestRslt = "";
// 建立动态调用环境,都执行通过。 以下3行以说明为主。
// string curDllPath = currentPath + "\\" + "DLL" + "\\" + "DummyTemplate2.dll";
// DynamicLoadDLL dll = new DynamicLoadDLL(curDllPath);
// DummyTemplate2 api = (DummyTemplate2)dll.Invoke("DummyTemplate2", typeof(DummyTemplate2));
// 执行DLL, 执行下面一行时报错
api(ref nodeDcTestEnv, ref nodeTestRslt);
}
}
// -----------------------------------------------
// 编译通过,下面是报错信息。
// -----------------------------------------------
Message "尝试读取或写入受保护的内存。这通常指示其他内存已损坏。"
StackTrace "
在 Etid.ETID.DummyTemplate2.Invoke(DCTest& DcEnv, TestResult& NodeResult)\r\n