程序中调用c++的dll,需要声明一些变量,和封装一些方法。我把这些和这个dll有关的东西写在单独的一个InitDll.cs文件作为一个类使用,其中的变量为private,方法为public static。在form中每秒调用InitDll.cs.GetDSPData的方法。程序用usb与dsp仪器连接。dsp仪器接上若干传感器。使用正常,但我拔掉传感器,程序自动退出。我把 InitDll.cs文件里的成员和方法 挪到form 中,就是和调用函数同一个文件中,把成员,方法都变成private后,使用时拔掉传感器程序正常!所以就迷惑不解了。说说为什么呢?
InitDll.cs 文件如下:
using System;
using System.Collections;
using System.Collections.Generic;
using System.Data;
using System.IO;
using System.Runtime.InteropServices;
using System.Text;
using System.Windows.Forms;
using UtilClass;
namespace FireAlarmSystem
{
public class InitDll
{
#region struc declare const int MaxSensorCountPerChannel = 30;
const int MaxFreq = 150;
const int MaxChannelNum = 11;
[StructLayout(LayoutKind.Sequential)]
public struct SensorList
{
public int nSensorCount;
[MarshalAs(UnmanagedType.ByValArray, SizeConst = MaxSensorCountPerChannel)]
public float[] fWaveLengthVec;
[MarshalAs(UnmanagedType.ByValArray, SizeConst = MaxSensorCountPerChannel)]
public float[] fPowerDBVec;
}
[StructLayout(LayoutKind.Sequential)]
public struct PerChannel
{
public int nChNum;
public int nFreq;
[MarshalAs(UnmanagedType.ByValArray, SizeConst = MaxFreq)]
public SensorList[] tSensorListVec;
}
#endregion #region import dll
[DllImport("ReadData.dll")]
private static extern int SEN_Init(); [DllImport("ReadData.dll")]
private static extern void SEN_Close(); [DllImport("ReadData.dll")]
private static extern void SEN_ReadDSPData(IntPtr pp); [DllImport("ReadData.dll")]
private static extern bool SEN_IsConnected(); [DllImport("ReadData.dll")]
private static extern int SEN_SendParaData();
#endregion public static int DllInit()
{
int rtn = -1;
try
{
rtn = SEN_Init();
}
catch
{
rtn = -2;
}
return rtn;
} public static int IsConnected()
{
int ret = 0;
if (!SEN_IsConnected())
{
ret = -1;
}
return ret;
} public static int SendParaData()
{
int ret = 0;
if (SEN_SendParaData() != 0)
{
ret = -2;
}
return ret;
} public static void DspClose()
{
SEN_Close();
} public static PerChannel[] GetDataUseDll()
{
PerChannel[] channelList = new PerChannel[MaxChannelNum]; try
{
for (int i = 0; i < channelList.Length; i++)
{
channelList[i] = new PerChannel();
} IntPtr[] ptArray = new IntPtr[1];
IntPtr pt = Marshal.AllocHGlobal(Marshal.SizeOf(typeof(PerChannel)) * MaxChannelNum);
Marshal.Copy(ptArray, 0, pt, 1); // 获取数据
try
{
SEN_ReadDSPData(pt);
}
catch (Exception ex1)
{
SomeMethods.WriteErrorLogs(ex1.Message);
}
// 得到结果分析
for (int i = 0; i < channelList.Length; i++)
{
channelList[i] = (PerChannel)Marshal.PtrToStructure((IntPtr)((UInt32)pt + i * Marshal.SizeOf(typeof(PerChannel))), typeof(PerChannel));
}
// 清理内存
Marshal.FreeHGlobal(pt);
}
catch (Exception ex)
{
SomeMethods.WriteErrorLogs(ex.Message);
}
return channelList;
}
}
}
InitDll.cs 文件如下:
using System;
using System.Collections;
using System.Collections.Generic;
using System.Data;
using System.IO;
using System.Runtime.InteropServices;
using System.Text;
using System.Windows.Forms;
using UtilClass;
namespace FireAlarmSystem
{
public class InitDll
{
#region struc declare const int MaxSensorCountPerChannel = 30;
const int MaxFreq = 150;
const int MaxChannelNum = 11;
[StructLayout(LayoutKind.Sequential)]
public struct SensorList
{
public int nSensorCount;
[MarshalAs(UnmanagedType.ByValArray, SizeConst = MaxSensorCountPerChannel)]
public float[] fWaveLengthVec;
[MarshalAs(UnmanagedType.ByValArray, SizeConst = MaxSensorCountPerChannel)]
public float[] fPowerDBVec;
}
[StructLayout(LayoutKind.Sequential)]
public struct PerChannel
{
public int nChNum;
public int nFreq;
[MarshalAs(UnmanagedType.ByValArray, SizeConst = MaxFreq)]
public SensorList[] tSensorListVec;
}
#endregion #region import dll
[DllImport("ReadData.dll")]
private static extern int SEN_Init(); [DllImport("ReadData.dll")]
private static extern void SEN_Close(); [DllImport("ReadData.dll")]
private static extern void SEN_ReadDSPData(IntPtr pp); [DllImport("ReadData.dll")]
private static extern bool SEN_IsConnected(); [DllImport("ReadData.dll")]
private static extern int SEN_SendParaData();
#endregion public static int DllInit()
{
int rtn = -1;
try
{
rtn = SEN_Init();
}
catch
{
rtn = -2;
}
return rtn;
} public static int IsConnected()
{
int ret = 0;
if (!SEN_IsConnected())
{
ret = -1;
}
return ret;
} public static int SendParaData()
{
int ret = 0;
if (SEN_SendParaData() != 0)
{
ret = -2;
}
return ret;
} public static void DspClose()
{
SEN_Close();
} public static PerChannel[] GetDataUseDll()
{
PerChannel[] channelList = new PerChannel[MaxChannelNum]; try
{
for (int i = 0; i < channelList.Length; i++)
{
channelList[i] = new PerChannel();
} IntPtr[] ptArray = new IntPtr[1];
IntPtr pt = Marshal.AllocHGlobal(Marshal.SizeOf(typeof(PerChannel)) * MaxChannelNum);
Marshal.Copy(ptArray, 0, pt, 1); // 获取数据
try
{
SEN_ReadDSPData(pt);
}
catch (Exception ex1)
{
SomeMethods.WriteErrorLogs(ex1.Message);
}
// 得到结果分析
for (int i = 0; i < channelList.Length; i++)
{
channelList[i] = (PerChannel)Marshal.PtrToStructure((IntPtr)((UInt32)pt + i * Marshal.SizeOf(typeof(PerChannel))), typeof(PerChannel));
}
// 清理内存
Marshal.FreeHGlobal(pt);
}
catch (Exception ex)
{
SomeMethods.WriteErrorLogs(ex.Message);
}
return channelList;
}
}
}
HEAP[ReadDSPtest.exe]: Invalid Address specified to RtlFreeHeap( 00A40000, 7A2DA91C )
The thread 'Win32 Thread' (0xf04) has exited with code 0 (0x0).
The thread 'Win32 Thread' (0x704) has exited with code 0 (0x0).
The thread 'Win32 Thread' (0xf1c) has exited with code 0 (0x0).
The thread 'Win32 Thread' (0xf18) has exited with code 0 (0x0).
The program '[1636] ReadDSPtest.exe: Managed' has exited with code 0 (0x0).
The program '[1636] ReadDSPtest.exe: Native' has exited with code 0 (0x0).终于找到这样的错误提示!不知道如何解决。
c#调用 dspdata = GetDataUseDll();
我每秒只执行一次上面的调用,一切都挺好的。但是我接下来处理这些数据的时候就会有问题
for (int i = 0; i < dspdata.Length; i++)
{
DataTable dtperch = GetPerChannelDatatable(dspdata[i]);
if (dtperch == null) continue;
_dsDatasFromDsp.Tables.Add(dtperch);
}
后,插拔传感器不定在什么时候会自动退出
后,插拔传感器不定在什么时候会自动退出