使用非托管dll从VBA到C#的唯一移植代码

时间:2011-05-18 14:03:42

标签: c# vba unmanaged dllimport porting

对于具有VBA和非托管C#知识的人来说,这将是一个巨大的挑战。

首先,我们已经获得了第三方dll几乎没有关于它的API使用的文档但是我们确实使用dll获得了Excel电子表格。问题是当我们尝试将代码移植到C#时,事情变得越来越糟。我有一种有趣的感觉,我们错过了一件小事......

无论如何,电子表格中的代码如下。

Declare Sub someFunction Lib "C:\somedll.dll" _
(types1 As TYPE1, _
vals1 As Double, vals2 As Double, _
type2 As TYPE2, type3 As TYPE3, types4 As TYPE4, _
vals3 As Double)

... 'Logic to fill in the arrays and create UDT's etc.

Call someFunction(types1(0), vals1(0), vals2(0), _
type2, type3, types4(0), vals3(0))

选项Explicit设置为所有数组的尺寸为“Dim”,并且它们使用UDT来处理TYPE1,TYPE2等。

现在的问题是当我移植到C#时,我没有像VBA中看到的那样得到预期的结果。

我的C#代码如下......

    [DllImport("c:\somedll.dll", CallingConvention = CallingConvention.ThisCall)]
    private static extern void someFunction( ref TYPE1[] types1,
                                               ref double[] vals1,
                                               ref double[] vals2,
                                               TYPE2 type2,
                                               TYPE3 type3,
                                               ref TYPE4[] types4,
                                               ref double[] vals3);

 ...

 //in a method after all arrays are initialized etc 

 someFunction(ref types1, ref vals1, ref vals2, type2, type3, ref types4, ref vals3);

 // PInvoke function 'someFunction' has an unbalanced stack. Signatures are off etc.

问题是代码几乎与VBA相同,减去了不是动态的数组和使用编组定义的C#中的结构。这是一个结构的例子......

 [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)]
 public class TYPE3
 {
    public double t1;
    public double t2;
    public double t3;
 }

此外,我注意到即使您传入数组的索引(0),也会操纵在VBA版本中传递的所有数组。这可能与他们将指针传递给VBA中的数组有关吗?

无论如何,由于我已经尝试过包括指针(IntPtr)等在内的所有内容,因此最近让我感到困惑。

甚至尝试从C ++调用dll。但这提出了一系列新问题,我不会在这里讨论。

1 个答案:

答案 0 :(得分:0)

我不认为你的原型是正确的。如果它是ThisCall,则第一个参数应该是对正在调用方法的对象的引用...所以要么它不是这个调用,要么你的第一个参数不是数组。