【问题标题】:C# unmanaged Export of an Array to FortranC# 将数组非托管导出到 Fortran
【发布时间】:2015-03-23 10:44:12
【问题描述】:

下面我使用Robert Giesecke 的模板来制作非托管的dll。 我尝试使用以下代码成功地将值从 C# 传递到 Fortran:

using System;
using System.Collections.Generic;
using System.Text;
using RGiesecke.DllExport;

namespace AddDll
{
    class MyAddDll
    {
        [DllExport("Add", CallingConvention = System.Runtime.InteropServices.CallingConvention.Cdecl)]
        public static int Add(int a, int b)
        {
            return a + b;
        }
    }
}

在 Fortran 方面:

MODULE MYEXTERNALS
USE iso_c_binding
INTERFACE
FUNCTION Add(a,b) RESULT(ret) bind(c, name="Add")
USE, intrinsic :: iso_c_binding
INTEGER(c_int), VALUE, intent(in) :: a,b
INTEGER(c_int) :: ret
END FUNCTION
END INTERFACE
END MODULE MYEXTERNALS


PROGRAM CallAdd
USE MYEXTERNALS
IMPLICIT NONE
INTEGER a, b
a = 4
b = 3
PRINT*, 'a + b =', Add(a, b)
PAUSE
END PROGRAM CallAdd

效果很好! 现在我想通过以下代码传递一个数组:

using System;
using System.Collections.Generic;
using System.Text;
using RGiesecke.DllExport;

namespace AddDll
{
    class MyAddDll
    {

        [DllExport("Arr", CallingConvention = System.Runtime.InteropServices.CallingConvention.Cdecl)]
        public static void Arr(int [] a)
        {
            a[0] = 1;
            a[1] = 2;

        }
    }
}

在 Fortran 方面:

MODULE MYEXTERNALS
USE iso_c_binding
INTERFACE
FUNCTION Arr(a) RESULT(ret) bind(c, name="Arr")
USE, intrinsic :: iso_c_binding
INTEGER(c_int), intent(in) :: a(2)
INTEGER(c_int) :: ret
END FUNCTION
END INTERFACE
END MODULE MYEXTERNALS


PROGRAM CallArray
USE MYEXTERNALS
IMPLICIT NONE
INTEGER a(2)
PRINT*, Arr(a)
PAUSE
END PROGRAM CallArray

这给了我错误:

谁能帮我把一个数组从 C# 传递到 Fortran?

【问题讨论】:

  • 它显示的异常代码 0x4f4d 是托管异常的异常代码 0xe0434f4d 的低 16 位。许多可能的原因,当您使用 Gieseke 的工具时,您对 .NET 异常视而不见。使用托管调试器进行调试是明智的,您可以诊断“找不到文件”之类的简单内容。返回值类型是错误的,但这通常不会爆炸。也许你需要 ref 来讨论这个论点。

标签: c# arrays fortran unmanaged managed


【解决方案1】:

您的 C# 代码定义了一个 void 函数,它对应于 FORTRAN subroutine。因此,它没有返回值,您应该call 它。 我认为以下应该可行:

MODULE MYEXTERNALS
USE iso_c_binding
INTERFACE
SUBROUTINE Arr(a) bind(c, name="Arr")
USE, intrinsic :: iso_c_binding
INTEGER(c_int), intent(in) :: a(2)
!INTEGER(c_int) :: ret
END SUBROUTINE
END INTERFACE
END MODULE MYEXTERNALS


PROGRAM CallArray
USE MYEXTERNALS
IMPLICIT NONE
INTEGER a(2)
call Arr(a)
print*,a
!PAUSE
END PROGRAM CallArray

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2011-09-15
    • 2023-03-11
    • 1970-01-01
    • 1970-01-01
    • 2013-06-12
    • 1970-01-01
    • 2013-02-09
    • 1970-01-01
    相关资源
    最近更新 更多