Passing Objects from Visual Basic to Fortran

August 29, 2010 12:00

There are many, many articles out there discussing the data types in Fortran, and how they are all set up with regard to the number of bytes each type utilizes. This article will not be discussing these simple data types, but rather taking the next step up and working with groups of these peices of data. In particular, I will be discussing how it is that you can successfully pass objects and structures created in Visual Basic, to a Fortran DLL.

It's always best to start off simple, so let's jump into it. Let's assume we have a structure that we are using to store a point somewhere in 3-dimensional space. To store that data, let's make a simple Structure
Public Structure pointIn3D
   Public x As Double
   Public y As Double
   Public z As Double
End Structure
Fortunately, Fortran has a way to store a structure in the exact same way we have defined here. To do so, we use the keyword "type". The type keyword in Fortran is the way we can store multiple variables wrapped in single peice. Since Doubles in Visual Basic are represented by eight bytes, we must also ensure that every variable is represented the same way. To finalize it, we wrap it all in something called a module. the end result looks like the following:
module test
   type Point
      double precision x, y, z
   end type Point
end module test
So now, we have the exact representation of the Visual Basic code in Fortran. Passing the data to Fortran is now trvial since we have already defined what the strucutre looks like in both languages.
subroutine modX(ThreeDubs)
   use test
   type (Point) :: ThreeDubs
   ThreeDubs%x = 5.5
end subroutine
The above code is a simple routine that accepts a Point as a parameter, changes the x value to 5.5, and returns control to the caller. "use test" specifies that in this method, we will be using the test module that we specified in the code before the method. In the next line, we specify that the input paramter is indeed of the Point type, and we then change the x value to 5.5. A simple method.

Passing a structure of type pointIn3D to the method modX is now as simple as if it were written in Visual Basic. For, this is indeed the point of writing a DLL. But now a problem, if we were to create an object instead of a structure and try to pass it to the same method, we will encounter problems, the memory location of the variables inside the obeject will not match where Fortran expects them to be. So, it appears that the strucuture of Objects is a tad different than Structures in Visual Basic. Luckily for us though, there is a nice little peice of information that we can insert right before the class that will force the object to be structured in a manner in which the Fortran method we have already written will be able to read it.
<StructLayout(LayoutKind.Sequential)> _
Public Class CustomPoint3d
   Public x As Double
   Public y As Double
   Public z As Double
End Class
If we pass an object of type CustomPoint3d to the previously written Fortran routine, we will now find that the object is read correctly. That's all there is to it! Now, to be able to use this method both of these ways in the same Visual Basic project, it's simply a matter of defining the method twice with two different signatures.
<DllImport("passPoint3d.dll")> _
Public Shared Function PrintX(ByRef point As pointIn3D) As Boolean
End Function

<DllImport("passPoint3d.dll")> _
Public Shared Function PrintX(ByRef point As CustomPoint3d) As Boolean
End Function

Got something to say? Tell me!






What about passing strings in structures or arrays in structures? I am having trouble with this.