Late binding to a FORTRAN DLL routine with a string paramter

Late binding to a FORTRAN DLL routine with a string paramter

am 23.10.2007 15:38:01 von dnv21

Hi
I'm trying to call into a FORTRAN DLL using ModuleBuilder, MethodBuilder and
then doing an Invoke to allow users to specify the Fortran DLL Signature etc.
at runtime. All works fine with ints and doubles etc., but I just can't get
the string to work (AccessViolationException).

I am including the hidden length parameter in a fortran call so it isn't that.

The FORTRAN method is defined as follows:

! Stringtest.f90
!
! FUNCTIONS/SUBROUTINES exported from Stringtest.dll:
! Stringtest - subroutine
!
subroutine Stringtest(STRING, ITEST, LENOUT)

! Expose subroutine Stringtest to users of this DLL
!
!DEC$ ATTRIBUTES DLLEXPORT::Stringtest

! Variables
CHARACTER , INTENT(IN) :: &
STRING*(*) ! String argument

INTEGER, INTENT(OUT) :: &
ITEST, & ! Some calculation on string
LENOUT ! Length of string as check

and the code I use to try and access it (in a simple console application) is
as follows:

string fileName =
Path.Combine(Path.GetDirectoryName(Assembly.GetExecutingAsse mbly().Location),
"stringtest.dll");

string entryPointName = "STRINGTEST";
CallingConvention callingConvention = CallingConvention.Winapi;
CharSet charSet = CharSet.Ansi;

//...Set up the parameters:
Type[] parameterTypes = new Type[4];

parameterTypes[0] = typeof(string);
parameterTypes[1] = typeof(int);
parameterTypes[2] = typeof(int).MakeByRefType();
parameterTypes[3] = typeof(int).MakeByRefType();

AssemblyName assemblyName = new AssemblyName();
assemblyName.Name = "Assembly Name";
AssemblyBuilder dynamicAsm =
AppDomain.CurrentDomain.DefineDynamicAssembly(assemblyName,
AssemblyBuilderAccess.Run);
ModuleBuilder moduleBuilder =
dynamicAsm.DefineDynamicModule("StringTest");

MethodBuilder methodBuilder =
moduleBuilder.DefinePInvokeMethod(entryPointName,

fileName,

MethodAttributes.Static | MethodAttributes.Public |
MethodAttributes.PinvokeImpl,

CallingConventions.Standard,

typeof(void),

parameterTypes,

callingConvention,

charSet);


methodBuilder.SetImplementationFlags(MethodImplAttributes.Pr eserveSig);
moduleBuilder.CreateGlobalFunctions();

// Get a MethodInfo for the PInvoke method and store it away for
later use:
MethodInfo methodInfo = moduleBuilder.GetMethod(entryPointName);

//...Set up the parameters:
object[] parameterValues = new object[parameterTypes.Length];

parameterValues[0] = "Hello";
parameterValues[1] = 5;
parameterValues[2] = 0;
parameterValues[3] = 0;

ParameterModifier parameterModifiers = new ParameterModifier();

//object returnValue = typeof(void);

try
{
/*returnValue = */methodInfo.Invoke(null, parameterValues);

int loop = 0;
foreach (object parameterValue in parameterValues)
{
Console.WriteLine(String.Format("{0}. {1}", loop,
parameterValue.ToString()));
loop++;
}
}
catch (Exception exception)
{
Console.WriteLine(exception.ToString());
}

Console.ReadKey();
}

If anyone can shed any light on this that would be great.

Best regards

Marek

RE: Late binding to a FORTRAN DLL routine with a string paramter

am 24.10.2007 08:24:47 von wawang

Hi Marek,

Are you able to call it using DllImport? If DllImport works, it might be
related to the code that defines the dynamic PInvoke.

Are you using .NET 2.0, if yes, there's a better approach that using
Marshal.GetDelegateForFunctionPointer:

#Junfeng Zhang's Windows Programming Notes : Dynamic PInvoke
http://blogs.msdn.com/junfeng/archive/2004/07/14/181932.aspx

#Late binding with unmanaged code
http://www.msnewsgroups.net/group/microsoft.public.dotnet.la nguages.csharp/t
opic19848.aspx


Regards,
Walter Wang (wawang@online.microsoft.com, remove 'online.')
Microsoft Online Community Support

==================================================
When responding to posts, please "Reply to Group" via your newsreader so
that others may learn and benefit from your issue.
==================================================

This posting is provided "AS IS" with no warranties, and confers no rights.