在C#中创建一个API,可以从它的DLL调用

时间:2010-12-23 09:05:37

标签: c# api dll

我知道标题对我的问题有点混乱。

让我解释一下: - 我的老年人编写了一些DLL,我在C#中使用它们如下:

说,现有的DLL名称是SeniorDLL,我想使用该DLL的函数SeniorFunc。 我的工作是: -

private delegate int SeniorFunc(IntPtr Blah);

[DllImport("kernel32")]
public extern static IntPtr LoadLibrary(string lpFileName);

[DllImport("kernel32", CharSet = CharSet.Ansi)]
public extern static IntPtr GetProcAddress(IntPtr hModule, string lpProcName);

SeniorFunc fp_Senior;

在函数中我想使用这个函数,在第一次函数调用之前我写:

IntPtr句柄;

    handle = IntPtr.Zero;
    handle = LoadLibrary("<DLL Path>");

    IntPtr fPtr = GetProcAddress(handle, "SeniorFunc");
    fp_Senior = (SeniorFunc)Marshal.GetDelegateForFunctionPointer(fPtr, typeof(SeniorFunc));

然后我通过fp_Senior(<Parameter>);

使用此功能

现在我想在C#中为我创建这样的DLL,通过它我可以从DLL调用函数。 目前我创建了一个DLL,但我在DLL中创建了一个类实例,然后必须像ClassInstance.MyFunction(<Parameters>)那样访问;

如何在不创建实例的情况下直接进行函数调用? 换句话说,(我不知道我是对还是错)我怎样才能创建API?

谢谢!

2 个答案:

答案 0 :(得分:1)

这里不需要实例,一切都可以是静态的。这样的事情,添加了必要的错误检查:

using System;
using System.ComponentModel;
using System.Runtime.InteropServices;

internal static class NativeMethods {
    public static void SeniorFunc(IntPtr arg) {
        if (fp_Senior == null) lookUpSenior();
        fp_Senior(arg);
    }

    private static void lookUpSenior() {
        loadSenior();
        IntPtr addr = GetProcAddress(SeniorModule, "seniorfunc");
        if (addr == IntPtr.Zero) throw new Win32Exception();
        fp_Senior = (SeniorFuncDelegate)Marshal.GetDelegateForFunctionPointer(addr, typeof(SeniorFuncDelegate));
    }
    private static void loadSenior() {
        if (SeniorModule == IntPtr.Zero) {
            SeniorModule = LoadLibrary("mumble.dll");
            if (SeniorModule == IntPtr.Zero) throw new Win32Exception();
        }
    }
    private static IntPtr SeniorModule;

    private delegate int SeniorFuncDelegate(IntPtr Blah);
    private static SeniorFuncDelegate fp_Senior;

    [DllImport("kernel32", CharSet = CharSet.Auto, SetLastError = true)]
    private extern static IntPtr LoadLibrary(string lpFileName);

    [DllImport("kernel32", CharSet = CharSet.Ansi, SetLastError = true)]
    public extern static IntPtr GetProcAddress(IntPtr hModule, string lpProcName);

}

在单独的方法中保持lookupSenior的目的是允许SeniorFunc()内联,因此它很快。如果您知道总是在程序中使用这些函数,那么您也可以为该类编写静态构造函数并在那里进行查找。保存空检查但是使异常更难解释。

答案 1 :(得分:0)

C#中没有类外的方法。因此,如果必须调用方法,则必须指定类名。

与您当前使用的DLL的不同之处在于,这些DLL是用C / C ++或其他非.NET语言编写的,这些语言不强制执行像C#那样严格的面向对象的方法。

因此,在从.NET库调用方法时,没有什么会强迫您创建类的实例。如果方法声明为static,则可以通过ClassName.MethodName()直接调用它。