[Date Index]
[Thread Index]
[Author Index]
Re: Re: Re: Net/Link: Problem with DLL (2)
*To*: mathgroup at smc.vnet.net
*Subject*: [mg49055] Re: [mg48918] Re: [mg48888] Re: Net/Link: Problem with DLL (2)
*From*: Todd Gayley <tgayley at wolfram.com>
*Date*: Tue, 29 Jun 2004 04:50:46 -0400 (EDT)
*References*: <200406220931.FAA10242@smc.vnet.net>
*Sender*: owner-wri-mathgroup at wolfram.com
At 01:51 AM 6/23/2004, Peter S Aptaker wrote:
>After more reading and experimenting have now got something 'working' but
>have some more questions:
>
>My Fortran DLLs are imported to Excel via VBA (see below). I have tried to
>use the 'self documenting VB format for clarity but have
>only beem able to preserve it precisely for Double scalars as:
>
>(1) Comment: To get Int32 I have replaced Long by long; I recall .Net has
>longer
>default Integers.
Peter,
To get Int32 you can use Int32, Integer or long (the latter being a Win32 C
long).
>(2) Comment: the OUT array "second from last arg" seems to only be
>possible with Double[].
Yes, you need to declare "out" arrays as array types. This is also the case
in C# and Visual Basic .NET. Your example VB declaration below uses 'ByRef
res As Double' for this argument, but that won't work for VB. ByRef As
Double will cause VB to pass the address of a double to the DLL, which is
fine if the DLL function is going to write a single value into this
address. But if the function expects to fill an array of values starting
from that address it won't work. If the function writes a lot of data it
might crash, and even if it doesn't you will just get back the first value
of the array in the double slot.
In VB .NET you would use 'ByVal res() As Double' for that argument, and in
C# you would use 'double[]'. Either of those type specifications will work
fine in DefineDLLFunction. Mathematica's DefineDLLFunction uses the same
type specifications as you would need to use in Visual Basic .NET or C# for
all arguments.
>(3) Question: .. How can I make this a two dmensional array OUT. As you will
>see I currently use a 1-D array and
>Partition[]?
Partitioning after the fact is the right way. To the DLL function, a
multidimensional array is just a flat block of memory, so treat it that way
on the .NET side and let Mathematica restore the partitioning later.
>(4) Comment: the OUT "last arg" seems best as, out int ; as the manual
>suggests.
>
>I guess this hybrid style is a mess but it was hard getting it working!
As you say, the manual recommends using the C#-style "out int" declaration
for arguments that are "the address of a single integer". You can use
VB-style "ByRef x As Integer" if you like, but if you pass a ByRef
parameter, .NET/Link doesn't know that the function isn't expecting a value
of the right type going in, so you need to assign the symbol a throwaway
value of the correct type to make the call:
(* In C, foo is declared as void foo(int* x) and it writes an integer
into x. *)
DefineDLLFunction["foo", "somelib.dll", "Void", {"ByRef x As Integer"}]
x = 42; (* Must assign garbage int value because ByRef was used in
the declaration *)
foo[x]
(* x has a new integer value now *)
If you declare the argument as "out int" instead, then .NET/Link doesn't
care what value, if any, x has going into the function. VB .NET has no
"out-only" notation, so it's often best to switch to C#-style notation for
these types of arguments. In all other cases you can use pure VB.NET-style
syntax if you prefer it.
Todd Gayley
Wolfram Research
>Note that a real DLL would be needed to actually test this
>
>Mathematica
>=========
>In[407]:=
>Clear[psaInductanceDLL, psaInductancedll];
>psaInductancedll =
>DefineDLLFunction["psaMagIndMr2", "maths0000.dll",
>"Void", {"ByVal m As long", "ByVal rp As Double", "Double[]",
>"ByVal np As long", "ByVal rq As Double", "Double[]",
>"ByVal nq As long", "ByVal gpp As long", "ByVal gpq As long",
>"double[]", "out int"}]
>
>psaInductanceDLL[m_,rp_, zpl_List, rq_, zql_List, opt___Rule] :=
>Module[{ores},
>ores = MakeNETObject[Table[0.0, {np*nq}]];
>psaInductancedll[m, rp, zpl, np, rq, zql, nq, 4, 3, ores, status];
>res = Partition[NETObjectToExpression[ores] , {np}]
>]
>psaInductanceDLL is fast.
>
>My VBA (i.e. VB6) delaration is:
>=======================
>Declare Sub psaMagIndMr3 Lib "maths0000.dll" ( _
>ByVal m As Long, _
>ByVal rp As Double, ByRef zpl As Double, ByVal np As Long, _
>ByVal rq As Double, ByRef zql As Double, ByVal nq As Long, _
>ByVal gpp As Long, ByVal gpq As Long, _
>ByRef res As Double, ByRef status As Long)
>
>
>Thanks
>
>Peter Aptaker
>
>----- Original Message -----
>From: "psa" <psa at laplacian.co.uk>
To: mathgroup at smc.vnet.net
>To: mathgroup at smc.vnet.net
>Subject: [mg49055] [mg48918] [mg48888] Re: Net/Link: Problem with DLL (2)
>
>etc etc
Prev by Date:
**Re: Simplifying with assumptions**
Next by Date:
**Palettes on a Mac Help**
Previous by thread:
**Re: Re: Net/Link: Problem with DLL (2)**
Next by thread:
**Finding Recursive Pattern**
| |