Skip to content

Instantly share code, notes, and snippets.

@andrew-raphael-lukasik
Last active November 29, 2022 23:24
Show Gist options
  • Save andrew-raphael-lukasik/b5cd9eb0c6f36388069d3211554409de to your computer and use it in GitHub Desktop.
Save andrew-raphael-lukasik/b5cd9eb0c6f36388069d3211554409de to your computer and use it in GitHub Desktop.
MemCpy between unmanaged and managed arrays
// src* https://gist.github.com/andrew-raphael-lukasik/b5cd9eb0c6f36388069d3211554409de
using UnityEngine;
using Unity.Collections;
using Unity.Collections.LowLevel.Unsafe;
// Project Settings/Player/Other Settings/Script Compilation/Allow `Unsafe` Code = ☑
public static class Mem
{
public static unsafe bool Cpy<SRC, DST>(NativeArray<SRC> src, DST[] dst)
where SRC : unmanaged
where DST : unmanaged
{
int srcSize = src.Length * UnsafeUtility.SizeOf<SRC>();
int dstSize = dst.Length * UnsafeUtility.SizeOf<DST>();
if (srcSize == dstSize)
{
void* srcPtr = NativeArrayUnsafeUtility.GetUnsafePtr(src);
void* dstPtr = UnsafeUtility.PinGCArrayAndGetDataAddress(dst, out ulong dstHandle);
UnsafeUtility.MemCpy(destination: dstPtr, source: srcPtr, size: srcSize);
UnsafeUtility.ReleaseGCObject(dstHandle);
return true;
}
else
{
Debug.LogError($"<b>{nameof(src)}</b> ({srcSize}[b]) and <b>{nameof(dst)}</b> ({dstSize}[b]) must be of equal size. MemCpy aborted.");
return false;
}
}
public static unsafe bool Cpy<SRC, DST>(NativeArray<SRC> src, DST[,] dst)
where SRC : unmanaged
where DST : unmanaged
{
int srcSize = src.Length * UnsafeUtility.SizeOf<SRC>();
int dstSize = dst.Length * UnsafeUtility.SizeOf<DST>();
if (srcSize == dstSize)
{
void* srcPtr = NativeArrayUnsafeUtility.GetUnsafePtr(src);
void* dstPtr = UnsafeUtility.PinGCArrayAndGetDataAddress(dst, out ulong dstHandle);
UnsafeUtility.MemCpy(destination: dstPtr, source: srcPtr, size: srcSize);
UnsafeUtility.ReleaseGCObject(dstHandle);
return true;
}
else
{
Debug.LogError($"<b>{nameof(src)}</b> ({srcSize}[b]) and <b>{nameof(dst)}</b> ({dstSize}[b]) must be of equal size. MemCpy aborted.");
return false;
}
}
public static unsafe bool Cpy<SRC, DST>(NativeArray<SRC> src, DST[,,] dst)
where SRC : unmanaged
where DST : unmanaged
{
int srcSize = src.Length * UnsafeUtility.SizeOf<SRC>();
int dstSize = dst.Length * UnsafeUtility.SizeOf<DST>();
if (srcSize == dstSize)
{
void* srcPtr = NativeArrayUnsafeUtility.GetUnsafePtr(src);
void* dstPtr = UnsafeUtility.PinGCArrayAndGetDataAddress(dst, out ulong dstHandle);
UnsafeUtility.MemCpy(destination: dstPtr, source: srcPtr, size: srcSize);
UnsafeUtility.ReleaseGCObject(dstHandle);
return true;
}
else
{
Debug.LogError($"<b>{nameof(src)}</b> ({srcSize}[b]) and <b>{nameof(dst)}</b> ({dstSize}[b]) must be of equal size. MemCpy aborted.");
return false;
}
}
public static unsafe bool Cpy<SRC, DST>(SRC[] src, NativeArray<DST> dst)
where SRC : unmanaged
where DST : unmanaged
{
int srcSize = src.Length * UnsafeUtility.SizeOf<SRC>();
int dstSize = dst.Length * UnsafeUtility.SizeOf<DST>();
if (srcSize == dstSize)
{
void* srcPtr = UnsafeUtility.PinGCArrayAndGetDataAddress(src, out ulong dstHandle);
void* dstPtr = NativeArrayUnsafeUtility.GetUnsafePtr(dst);
UnsafeUtility.MemCpy(destination: dstPtr, source: srcPtr, size: dstSize);
UnsafeUtility.ReleaseGCObject(dstHandle);
return true;
}
else
{
Debug.LogError($"<b>{nameof(src)}</b> ({srcSize}[b]) and <b>{nameof(dst)}</b> ({dstSize}[b]) must be of equal size. MemCpy aborted.");
return false;
}
}
public static unsafe bool Cpy<SRC, DST>(SRC[,] src, NativeArray<DST> dst)
where SRC : unmanaged
where DST : unmanaged
{
int srcSize = src.Length * UnsafeUtility.SizeOf<SRC>();
int dstSize = dst.Length * UnsafeUtility.SizeOf<DST>();
if (srcSize == dstSize)
{
void* srcPtr = UnsafeUtility.PinGCArrayAndGetDataAddress(src, out ulong dstHandle);
void* dstPtr = NativeArrayUnsafeUtility.GetUnsafePtr(dst);
UnsafeUtility.MemCpy(destination: dstPtr, source: srcPtr, size: dstSize);
UnsafeUtility.ReleaseGCObject(dstHandle);
return true;
}
else
{
Debug.LogError($"<b>{nameof(src)}</b> ({srcSize}[b]) and <b>{nameof(dst)}</b> ({dstSize}[b]) must be of equal size. MemCpy aborted.");
return false;
}
}
public static unsafe bool Cpy<SRC, DST>(SRC[,,] src, NativeArray<DST> dst)
where SRC : unmanaged
where DST : unmanaged
{
int srcSize = src.Length * UnsafeUtility.SizeOf<SRC>();
int dstSize = dst.Length * UnsafeUtility.SizeOf<DST>();
if (srcSize == dstSize)
{
void* srcPtr = UnsafeUtility.PinGCArrayAndGetDataAddress(src, out ulong dstHandle);
void* dstPtr = NativeArrayUnsafeUtility.GetUnsafePtr(dst);
UnsafeUtility.MemCpy(destination: dstPtr, source: srcPtr, size: dstSize);
UnsafeUtility.ReleaseGCObject(dstHandle);
return true;
}
else
{
Debug.LogError($"<b>{nameof(src)}</b> ({srcSize}[b]) and <b>{nameof(dst)}</b> ({dstSize}[b]) must be of equal size. MemCpy aborted.");
return false;
}
}
}
@andrew-raphael-lukasik
Copy link
Author

andrew-raphael-lukasik commented Apr 13, 2022

Mem.Cpy<float3,Vector3>( nativeArrayOrList , managedArray );
Mem.Cpy<Vector2,float2>( managedArray , nativeArrayOrList );

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment