标签: dllimport

参数化DllImport用于C#应用程序

我们有一个供应商,提供访问其硬件的库.不幸的是,如果您有多个设备,则需要多次导入其库,并使用不同的dll名称.因此,我们有一吨重复的代码,我担心它很快就会成为维护的噩梦.

我们现在所拥有的是:

namespace MyNamespace {
    public static class Device01 {
        public const string DLL_NAME = @"Device01.dll";

        [DllImport(DLL_NAME, EntryPoint = "_function1")]
        public static extern int Function1(byte[] param);
Run Code Online (Sandbox Code Playgroud)

...

        [DllImport(DLL_NAME, EntryPoint = "_function99")]
        public static extern int Function99(int param);
    }
Run Code Online (Sandbox Code Playgroud)

....

    public static class Device16 {
        public const string DLL_NAME = @"Device16.dll";

        [DllImport(DLL_NAME, EntryPoint = "_function1")]
        public static extern int Function1(byte[] param);
Run Code Online (Sandbox Code Playgroud)

...

        [DllImport(DLL_NAME, EntryPoint = "_function99")]
        public static extern int Function99(int param);
    }
}
Run Code Online (Sandbox Code Playgroud)

如果我使用的是C或C++,我只会在静态类中定义一个文件和#include它们多次,不是很好但是比替代方案好,但在C#中我没有那个选项.

如果有人对如何有效地定义工厂有任何聪明的想法,这将允许我们生成尽可能多的静态设备类,我会非常感兴趣.

谢谢,

编辑:函数原型是非常多变的,所以任何依赖它们的方法都是不合适的.感谢到目前为止的建议,我并没有如此迅速地阐述这么多想法.

c# dllimport .net-3.5 c#-3.0

11
推荐指数
2
解决办法
5562
查看次数

来自C#的C++:C++函数(在DLL中)返回false,但C#认为它是真的!

我正在编写一个C#app,它在C++ API中调用了一些函数.我将C++代码构建到DLL中,C#代码使用DllImport调用API.(我使用.DEF文件作为C++ DLL,因此我不需要extern"C".)

到目前为止,API有一个功能,目前绝对没有任何功能:

bool Foo()
{
  return false;
}
Run Code Online (Sandbox Code Playgroud)

在C#中,我有以下内容:

public class FooAPI
{
    [DllImport("Foo.dll")]
    public static extern bool Foo();
}

...

bool b = FooAPI.Foo(); 
if (!b) 
{ 
    // Throw an exception 
} 
Run Code Online (Sandbox Code Playgroud)

我的问题是,由于某种原因,b总是评估为TRUE.我在if(!b)上有一个断点,调试器将其报告为'true',与C++函数返回的内容无关.

C#bool和C++ bool一样吗?虽然事实并非如此,但我仍然不知道如何找到返回值为'true':)

任何人都可以帮我解决这个奇怪的差异吗?

提前致谢!

c# c++ dll boolean dllimport

11
推荐指数
2
解决办法
2933
查看次数

为什么使用DllImport属性作为添加引用?

我见过几个这样的例子:

[DllImport("user32.dll")]
static extern bool TranslateMessage([In] ref Message lpMsg);

[DllImport("user32.dll")]
static extern IntPtr DispatchMessage([In] ref Message lpmsg);
Run Code Online (Sandbox Code Playgroud)

但是,我不明白的是为什么有人会这样做只是像引用其他库一样引用DLL?MSDN声明:"在托管应用程序中重用现有的非托管代码时,DllImport属性非常有用.例如,托管应用程序可能需要调用非托管WIN32 API." 但是,那是说引用一个非托管的dll或者不可能引用它是没用的吗?

c# dll reference dllimport visual-studio

11
推荐指数
3
解决办法
1万
查看次数

与Native C++相比,C++/CLI性能如何?

早上好,

我正在编写一个拼写检查程序,对于这种情况,它是性能关键的.既然如此,由于我打算连接到数据库并使用C#创建GUI,我在C中编写了一个编辑距离计算例程,并编译为我在C#中使用的DLL DllImport.问题是,我认为(虽然我可能是错误的),其编组字一个一个从Stringchar *导致大量的开销.就是这样,我考虑使用C++/CLI以便我可以String直接使用.NET中的类型...我的问题是,C++/CLI性能如何与用于繁重数学计算和数组访问的本机C代码相比较?

非常感谢你.

c# performance c++-cli dllimport native-code

11
推荐指数
1
解决办法
3437
查看次数

来自user32.dll的FindWindowEx使用dllimport返回零句柄和错误代码127

我需要以编程方式处理另一个Windows应用程序,搜索谷歌我找到了一个使用DLLImport属性处理Windows计算器的示例,并在C#中将user32.dll函数导入托管应用程序.

应用程序正在运行,我正在获取主窗口的句柄,即计算器本身,但后续代码不起作用.FindWindowEx方法不返回计算器子项的句柄,如按钮和文本框.

我尝试在DLLImport上使用SetLastError = True,发现我收到错误代码127,即"找不到过程".

这是我从中获取示例应用程序的链接:

http://www.codeproject.com/script/Articles/ArticleVersion.aspx?aid=14519&av=34503

如果有人知道如何解决它,请帮忙.

更新:DLLImport是:

[DllImport("user32.dll", SetLastError = true)]
        public static extern IntPtr FindWindowEx(IntPtr parentHandle, IntPtr childAfter, string className,  string  windowTitle);
Run Code Online (Sandbox Code Playgroud)

不起作用的守则是:

hwnd=FindWindow(null,"Calculator"); // This is working, I am getting handle of Calculator

// The following is not working, I am getting hwndChild=0 and err = 127
hwndChild = FindWindowEx((IntPtr)hwnd,IntPtr.Zero,"Button","1");

                Int32 err = Marshal.GetLastWin32Error();
Run Code Online (Sandbox Code Playgroud)

c# pinvoke winapi dllimport findwindow

11
推荐指数
1
解决办法
6万
查看次数

即使dll与可执行文件位于同一文件夹中,DllImport也找不到dll

我正在尝试使用llvm-fs项目,该项目为F#提供llvm绑定.我已编译该LLVM-3.1.dll文件,--enable-shared它现在与我编译的可执行文件(我查看过Environment.CurrentDirectory)位于同一目录中.将DllImport在LLVM-FS是这样的:

[<DllImport(
    "LLVM-3.1.dll",
    EntryPoint="LLVMModuleCreateWithName",
    CallingConvention=CallingConvention.Cdecl,
    CharSet=CharSet.Ansi)>]
extern void* (* LLVMModuleRef *) moduleCreateWithNameNative(string ModuleID)
Run Code Online (Sandbox Code Playgroud)

然而,当我运行我的应用程序时,它出错:

Unable to load DLL 'LLVM-3.1.dll': The specified module could not be found.
(Exception from HRESULT: 0x8007007E)
Run Code Online (Sandbox Code Playgroud)

如何加载DLL?作为参考,这是我正在尝试加载的确切DLL.

.net f# dllimport llvm llvm-fs

11
推荐指数
2
解决办法
7566
查看次数

尝试使用VS安装加载带有错误格式异常的程序

我设计了一个C#Windows appln,它也在内部调用一些函数[通过DllImport()从C++ DLL导入]

我的C++代码在Win32平台中构建为.DLL,而我的C#构建为"任何CPU"平台.

当我在我的测试机器中运行.EXE(C#)时,我面临一个错误

尝试从hresult 0x8007000B加载具有不正确格式异常的程序

但是,如果我在我的机器中安装VSS 2010然后运行EXE,则不会遇到此错误.

1)出现此错误的原因?2)安装VSS时为什么没有观察到错误?

我使用Win7 OS(64位)在AnyCPU平台上构建.EXE(C#),而后者依赖于Win32内置的DLL(使用DllImport在C#中导入的C++ Dll)

c# dllimport visual-studio-2010

11
推荐指数
1
解决办法
2万
查看次数

DllImport如何真正起作用?

我想知道它是如何DllImport工作的.我需要一个简单的英语解释 - 意思是简单的解释.

它是否与DLL中的导出方法静态链接,如"包含文件"指令/静态库?

或者当它到达C#程序中的执行点时,它是否从DLL动态调用该方法?

c# dll pinvoke dllimport

11
推荐指数
2
解决办法
3053
查看次数

如何创建一个nim dll并从c#中调用它

我看过几乎每一个例子,我可以通过谷歌找到,并不能完成任务的最简单的创建一个dll (窗口) nim

任何人都可以一步一步地解释它吗?

我正在使用nimIDE - aporia生成代码.

构建a是否dll需要使用命令行?我想有一个解决方法.

使用aporia IDE\ command line,如何通过编译下面的代码来实现与以下代码相同的结果dll:

extern "C" __declspec(dllexport) int __stdcall return_multiply(int num1, int num2)
{
    return num1 * num2;
}
Run Code Online (Sandbox Code Playgroud)

您可能知道的代码可以从中调用 c#

c# dll ffi dllimport nim-lang

11
推荐指数
1
解决办法
1403
查看次数

如何使用C#获取char**?

我需要以下列形式将参数传递给不安全的DllImported函数:

[DllImport("third_party.dll")]
private static extern unsafe int start(int argc, char** argv);
Run Code Online (Sandbox Code Playgroud)

我假设它是一个字符串数组.但是,当我尝试执行以下操作时,我得到'无法从字符串[]转换为char**'错误.我如何让这个工作?谢谢.

string[] argv = new string[] { };
start(0, argv);
Run Code Online (Sandbox Code Playgroud)

编辑1: 问题被标记为重复,但看着可能重复的问题,我仍然没有看到如何使这个工作.

编辑2:进一步确认问题和所需参数.它看起来像您的标准argc/argv参数(参数计数,然后是参数值).与启动ac程序的方式相同:int main(int argc, char** argv); 对于这个特殊问题,我根本不想传递任何参数(因此count为0).

编辑3: 我从第三方库供应商那里获得了更多信息.这里是:

  • 第一个参数是参数计数
  • 第二个参数是一个空终止字符串数组
  • 字符串是ANSI编码的

编辑4:使用工作解决方案进行最终编辑(至少在我的情况下).我会把它作为答案,但不能,因为这个问题被标记为重复.这是一个帮助我最多的问题的链接.最后,dll函数需要一个指向带有ANSI字符串的缓冲区的指针数组. 所以我的最终方法(基于相关问题)如下.在内存中创建一个数组来保存指针,然后将每个字符串分配到内存中的其他位置,并在第一个指针数组中写入指向这些字符串的指针.此代码适用于生产:

[DllImport("third_party.dll", CallingConvention = CallingConvention.Cdecl, CharSet = CharSet.Ansi)]
private static extern int start(Int32 args, IntPtr argv);

public bool start(params string[] arguments)
{
    int result;

    if (arguments == null || arguments.Length == 0)
    {
        result = dll_system_startup(0, IntPtr.Zero);
    }
    else …
Run Code Online (Sandbox Code Playgroud)

c# unsafe marshalling dllimport char

11
推荐指数
1
解决办法
2194
查看次数