传递CUDAfy结构内的数组(Passing an array within a structure

2019-09-01 18:08发布

使用VS 2012,.NET 4.5,64位和CUDAfy 1.12,我有概念以下证明

using System;
using System.Runtime.InteropServices;
using Cudafy;
using Cudafy.Host;
using Cudafy.Translator;

namespace Test
{
[Cudafy(eCudafyType.Struct)]
[StructLayout(LayoutKind.Sequential)]
public struct ChildStruct
{
    [MarshalAs(UnmanagedType.LPArray)]
    public float[] FArray;
    public long FArrayLength;
}

[Cudafy(eCudafyType.Struct)]
[StructLayout(LayoutKind.Sequential)]
public struct ParentStruct
{
    public ChildStruct Child;
}

public class Program
{
    [Cudafy]
    public static void KernelFunction(GThread gThread, ParentStruct parent)
    {
        long length = parent.Child.FArrayLength;
    }

    public static void Main(string[] args)
    {
        var module = CudafyTranslator.Cudafy(
          ePlatform.x64, eArchitecture.sm_35,
          new[] {typeof(ChildStruct), typeof(ParentStruct), typeof(Program)});
        var dev = CudafyHost.GetDevice();
        dev.LoadModule(module);

        float[] hostFloat = new float[10];
        for (int i = 0; i < hostFloat.Length; i++) { hostFloat[i] = i; }

        ParentStruct parent = new ParentStruct
        {
            Child = new ChildStruct
            {
                FArray = dev.Allocate(hostFloat),
                FArrayLength = hostFloat.Length
            }
        };

        dev.Launch(1, 1, KernelFunction, parent);

        Console.ReadLine();
    }
}
}

当程序运行时,我得到的dev.Launch以下错误:

Type 'Test.ParentStruct' cannot be marshaled as an unmanaged structure; no meaningful size or offset can be computed.

如果我从ChildStruct删除float数组,它按预期工作。

在C / C ++ / CLI和CUDA C,在过去工作过,我知道错误的性质。 这个错误的一些解决方案建议设置使用手动的结构尺寸Size的参数MarshalAs ,但这是不可能的,由于该品种的结构内的类型。

我看着所产生的.CU文件,并将其在产生所述浮子阵列作为float *这是我的预期。

有没有办法通过一个结构内核中的一个数组? 而如果没有什么是最好的第二选择? 此问题不会在CUDA C存在,因为我们是从CLR编组它只存在。

Answer 1:

我花了好时间阅读CUDAfy的源代码,看看是否有这个问题的解决方案。

CUDAfy正在努力使事情.NET开发过于简单,从保护他们离开IntPtr和其他指针的概念。 然而,抽象的水平,因此很难认为回答这个问题,没有出现大的重构到该库的工作方式。

不能够一个结构内发送的浮子阵列是显示止动器。 我最后做的PInvoke到CUDA运行时和不使用CUDAfy。



Answer 2:

这是.NET的限制,不CUDAfy。 数据必须是blittable和非固定尺寸数组不是。 这是有效的,基于在CodePlex上的CUDAfy单元测试:

[Cudafy]
[StructLayout(LayoutKind.Sequential, Size=64, CharSet = CharSet.Unicode)]
public unsafe struct PrimitiveStruct
{
    public fixed sbyte Message[32];
    public fixed char MessageChars[16];
}

也没有理由来存储数组长度明确,因为你可以使用设备代码中的长度属性。



文章来源: Passing an array within a structure in CUDAfy