title: CUDAfy.Net / OpenCL, struct containing byte array results in non-blittable exception
body: <p>Ok, so I'm using CUDAfy.Net, and I have the following 3 structs:</p>
  
  <pre><code>[Cudafy]
  public struct Collider
  {
      public int Index;
      public int Type;
      public Sphere Sphere;
      public Plane Plane;
      public Material Material;
  }
  
  [Cudafy]
  public struct Material
  {
      public Color Color;
      public Texture Texture;
      public float Shininess;
  }
  
  [Cudafy]
  public struct Texture
  {
      public int Width, Height;
      public byte[ ] Data;
  }
  </code></pre>
  
  <p>Now, as soon as I send over an array of Collider objects to the GPU, using</p>
  
  <pre><code>CopyToDevice&lt;GPU.Collider&gt;( ColliderArray );
  </code></pre>
  
  <p>I get the following error:</p>
  
  <pre><code>An unhandled exception of type 'System.ArgumentException' occurred in mscorlib.dll
  Additional information: Object contains non-primitive or non-blittable data.
  </code></pre>
  
  <p>Does anyone with any experience with either CUDAfy.Net, or OpenCL ( since it basically compiles down into OpenCL ), have any idea how I could accomplish this? The whole problem lies in the byte array of Texture, since everything worked just fine when I didn't have a Texture struct and the array is the non-blittable part as far as I know.
  I had found several questions regarding the same problem, and they fixed it using fixed-size arrays. However, I am unable to do this as these are textures, which can have greatly varying sizes.</p>
  
  <p>EDIT:
  Right now, I'm doing the following on the CPU:</p>
  
  <pre><code>    public unsafe static GPU.Texture CreateGPUTexture( Cudafy.Host.GPGPU _GPU, System.Drawing.Bitmap Image )
      {
          GPU.Texture T = new GPU.Texture( );
          T.Width = Image.Width;
          T.Height = Image.Height;
          byte[ ] Data = new byte[ Image.Width * Image.Height * 3 ];
  
  
          for ( int X = 0; X &lt; Image.Width; X++ )
              for ( int Y = 0; Y &lt; Image.Height; Y++ )
              {
                  System.Drawing.Color C = Image.GetPixel( X, Y );
                  int ID = ( X + Y * Image.Width ) * 3;
                  Data[ ID ] = C.R;
                  Data[ ID + 1 ] = C.G;
                  Data[ ID + 2 ] = C.B;
              }
  
          byte[ ] _Data = _GPU.CopyToDevice&lt;byte&gt;( Data );
          IntPtr Pointer = _GPU.GetDeviceMemory( _Data ).Pointer;
          T.Data = ( byte* )Pointer.ToPointer( );
  
          return T;
      }
  </code></pre>
  
  <p>I then attach this Texture struct to the colliders, and send them to the GPU. This all goes without any errors.
  However, as soon as I try to USE a texture on the GPU, like this:</p>
  
  <pre><code>    [Cudafy]
      public static Color GetTextureColor( int X, int Y, Texture Tex )
      {
          int ID = ( X + Y * Tex.Width ) * 3;
          unsafe
          {
              byte R = Tex.Data[ ID ];
              byte G = Tex.Data[ ID + 1 ];
              byte B = Tex.Data[ ID + 2 ];
  
              return CreateColor( ( float )R / 255f, ( float )G / 255f, ( float )B / 255f );
          }
      }
  </code></pre>
  
  <p>I get the following error:</p>
  
  <pre><code>An unhandled exception of type 'Cloo.InvalidCommandQueueComputeException' occurred in Cudafy.NET.dll
  Additional information: OpenCL error code detected: InvalidCommandQueue.
  </code></pre>
  
  <p>The Texture struct looks like this, by the way:</p>
  
  <pre><code>    [Cudafy]
      public unsafe struct Texture
      {
          public int Width, Height;
          public byte* Data;
      }
  </code></pre>
  
  <p>I'm completely at a loss again..</p>