我正在开发一个C++项目,其中包含不同的组件。我们需要将应用程序作为Windows服务启动。该项目是未经管理的C++代码。我编写了一个C# Windows服务和一个C风格的dll,该dll将具有启动不同组件的功能以及停止它们的另一个功能。该dll有两个文件,一个头文件和一个.cpp文件:
RTSS.h:namespace PFDS
{
extern "C" __declspec(dllexport) int runRTS(char*);
}
RTSS.cpp:
using namespace PFDS;
/* ... includes and declarations */
extern "C" __declspec(dllexport) int runRTS(char* service_name)
{
g_reserved_memory = (char*) malloc(sizeof(char) * RESERVED_MEMORY_SIZE);
_set_new_handler(memory_depletion_handler);
// this function is from a C++ .lib which is included in
// the linker input for the RTSS dll project setting.
// SetUnhandledExceptionHandler("RTS");
return 0;
}
在Windows服务的ServiceBase子类中,我有以下内容:
[DllImport("RTSSd.dll")]
public static extern int runRTS(string serviceName);
protected override void OnStart(string[] args)
{
try
{
// the bin directory has all dependencies (dlls needed)
Environment.CurrentDirectory = "D:/work/projects/bin";
eventLog1.WriteEntry("RTSWinService: Starting " + this.ServiceName);
int result = runRTS(this.ServiceName);
eventLog1.WriteEntry("Result of invoking runRTS = " + result);
}
catch (Exception e)
{
eventLog1.WriteEntry("Exception caught: " + e.ToString());
}
}
此外,我有一个控制台测试应用程序,其中的主要代码类似于OnStart中的代码。当注释SetUnhandledException函数时,这两个应用程序都可以正常运行。但是当我取消注释该函数时,Windows控制台应用程序可以正常运行,但Windows服务输出以下异常:
System.DllNotFoundException: 无法加载DLL“RTSSd.dll”:找不到指定的模块。(来自HRESULT的异常:0x8007007E) 在RTSWS.RTSWinService.runRTS(String serviceName) 在D:\ work \ project \ ... \ RTSWinService.cs的RTSWS.RTSWinService.OnStart(String [] args):第39行
我在不同的论坛线程中读到,Windows服务在C:\WINDOWS\System32中启动,通过初始化DirectoryInfo并打印其完整名称可以证实。我尝试使用Environment.CurrentDirectory =“包含Windows服务可执行文件和dll的目录”更改默认启动目录,但没有成功。我还尝试更改进程目录,但也失败了。其他线程得出了这个结论link text,但真的是这样吗?可能有更简单的方法吗?
我应该注意到,SetUnhandledException函数是用C ++编写的,而不是C,并且许多其他需要调用的函数也是如此。所有所需的dll都放置在服务可执行文件旁边。非常感谢您的反馈。
Environment.CurrentDirectory
更改为我的 DLL 所在的目录时,它就可以工作了。 - fjsj