mirror of
https://mirror.ghproxy.com/https://github.com/dexyfex/CodeWalker
synced 2024-11-25 16:32:55 +08:00
Improved conversion of struct arrays to/from byte arrays
This commit is contained in:
parent
df77346daf
commit
9904e92082
@ -1449,21 +1449,31 @@ namespace CodeWalker.GameFiles
|
|||||||
public static byte[] ConvertArrayToBytes<T>(params T[] items) where T : struct
|
public static byte[] ConvertArrayToBytes<T>(params T[] items) where T : struct
|
||||||
{
|
{
|
||||||
if (items == null) return null;
|
if (items == null) return null;
|
||||||
int size = Marshal.SizeOf(typeof(T));
|
|
||||||
int sizetot = size * items.Length;
|
var size = Marshal.SizeOf(typeof(T)) * items.Length;
|
||||||
byte[] arrout = new byte[sizetot];
|
var b = new byte[size];
|
||||||
int offset = 0;
|
GCHandle handle = GCHandle.Alloc(items, GCHandleType.Pinned);
|
||||||
for (int i = 0; i < items.Length; i++)
|
var h = handle.AddrOfPinnedObject();
|
||||||
{
|
Marshal.Copy(h, b, 0, size);
|
||||||
byte[] arr = new byte[size];
|
handle.Free();
|
||||||
IntPtr ptr = Marshal.AllocHGlobal(size);
|
return b;
|
||||||
Marshal.StructureToPtr(items[i], ptr, true);
|
|
||||||
Marshal.Copy(ptr, arr, 0, size);
|
|
||||||
Marshal.FreeHGlobal(ptr);
|
//int size = Marshal.SizeOf(typeof(T));
|
||||||
Buffer.BlockCopy(arr, 0, arrout, offset, size);
|
//int sizetot = size * items.Length;
|
||||||
offset += size;
|
//byte[] arrout = new byte[sizetot];
|
||||||
}
|
//int offset = 0;
|
||||||
return arrout;
|
//for (int i = 0; i < items.Length; i++)
|
||||||
|
//{
|
||||||
|
// byte[] arr = new byte[size];
|
||||||
|
// IntPtr ptr = Marshal.AllocHGlobal(size);
|
||||||
|
// Marshal.StructureToPtr(items[i], ptr, true);
|
||||||
|
// Marshal.Copy(ptr, arr, 0, size);
|
||||||
|
// Marshal.FreeHGlobal(ptr);
|
||||||
|
// Buffer.BlockCopy(arr, 0, arrout, offset, size);
|
||||||
|
// offset += size;
|
||||||
|
//}
|
||||||
|
//return arrout;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -1487,11 +1497,16 @@ namespace CodeWalker.GameFiles
|
|||||||
{
|
{
|
||||||
T[] items = new T[count];
|
T[] items = new T[count];
|
||||||
int itemsize = Marshal.SizeOf(typeof(T));
|
int itemsize = Marshal.SizeOf(typeof(T));
|
||||||
for (int i = 0; i < count; i++)
|
//for (int i = 0; i < count; i++)
|
||||||
{
|
//{
|
||||||
int off = offset + i * itemsize;
|
// int off = offset + i * itemsize;
|
||||||
items[i] = ConvertData<T>(data, off);
|
// items[i] = ConvertData<T>(data, off);
|
||||||
}
|
//}
|
||||||
|
GCHandle handle = GCHandle.Alloc(items, GCHandleType.Pinned);
|
||||||
|
var h = handle.AddrOfPinnedObject();
|
||||||
|
Marshal.Copy(data, offset, h, itemsize * count);
|
||||||
|
handle.Free();
|
||||||
|
|
||||||
return items;
|
return items;
|
||||||
}
|
}
|
||||||
public static T[] ConvertDataArray<T>(Meta meta, MetaName name, Array_StructurePointer array) where T : struct
|
public static T[] ConvertDataArray<T>(Meta meta, MetaName name, Array_StructurePointer array) where T : struct
|
||||||
|
@ -15848,11 +15848,17 @@ namespace CodeWalker.GameFiles
|
|||||||
{
|
{
|
||||||
T[] items = new T[count];
|
T[] items = new T[count];
|
||||||
int itemsize = Marshal.SizeOf(typeof(T));
|
int itemsize = Marshal.SizeOf(typeof(T));
|
||||||
for (int i = 0; i < count; i++)
|
//for (int i = 0; i < count; i++)
|
||||||
{
|
//{
|
||||||
int off = offset + i * itemsize;
|
// int off = offset + i * itemsize;
|
||||||
items[i] = ConvertDataRaw<T>(data, off);
|
// items[i] = ConvertDataRaw<T>(data, off);
|
||||||
}
|
//}
|
||||||
|
|
||||||
|
GCHandle handle = GCHandle.Alloc(items, GCHandleType.Pinned);
|
||||||
|
var h = handle.AddrOfPinnedObject();
|
||||||
|
Marshal.Copy(data, offset, h, itemsize * count);
|
||||||
|
handle.Free();
|
||||||
|
|
||||||
return items;
|
return items;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -369,15 +369,22 @@ namespace CodeWalker.GameFiles
|
|||||||
//var result2 = new T[count];
|
//var result2 = new T[count];
|
||||||
//Buffer.BlockCopy(data, 0, result2, 0, (int)length); //error: "object must be an array of primitives" :(
|
//Buffer.BlockCopy(data, 0, result2, 0, (int)length); //error: "object must be an array of primitives" :(
|
||||||
|
|
||||||
|
//var result = new T[count];
|
||||||
|
//GCHandle handle = GCHandle.Alloc(data, GCHandleType.Pinned);
|
||||||
|
//var h = handle.AddrOfPinnedObject();
|
||||||
|
//for (uint i = 0; i < count; i++)
|
||||||
|
//{
|
||||||
|
// result[i] = Marshal.PtrToStructure<T>(h + (int)(i * structsize));
|
||||||
|
//}
|
||||||
|
//handle.Free();
|
||||||
|
|
||||||
var result = new T[count];
|
var result = new T[count];
|
||||||
GCHandle handle = GCHandle.Alloc(data, GCHandleType.Pinned);
|
GCHandle handle = GCHandle.Alloc(result, GCHandleType.Pinned);
|
||||||
var h = handle.AddrOfPinnedObject();
|
var h = handle.AddrOfPinnedObject();
|
||||||
for (uint i = 0; i < count; i++)
|
Marshal.Copy(data, 0, h, (int)length);
|
||||||
{
|
|
||||||
result[i] = Marshal.PtrToStructure<T>(h + (int)(i * structsize));
|
|
||||||
}
|
|
||||||
handle.Free();
|
handle.Free();
|
||||||
|
|
||||||
|
|
||||||
if (cache) arrayPool[(long)position] = result;
|
if (cache) arrayPool[(long)position] = result;
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
@ -388,13 +395,21 @@ namespace CodeWalker.GameFiles
|
|||||||
var result = new T[count];
|
var result = new T[count];
|
||||||
var length = count * structsize;
|
var length = count * structsize;
|
||||||
byte[] data = ReadBytes((int)length);
|
byte[] data = ReadBytes((int)length);
|
||||||
GCHandle handle = GCHandle.Alloc(data, GCHandleType.Pinned);
|
|
||||||
|
//GCHandle handle = GCHandle.Alloc(data, GCHandleType.Pinned);
|
||||||
|
//var h = handle.AddrOfPinnedObject();
|
||||||
|
//for (uint i = 0; i < count; i++)
|
||||||
|
//{
|
||||||
|
// result[i] = Marshal.PtrToStructure<T>(h + (int)(i * structsize));
|
||||||
|
//}
|
||||||
|
//handle.Free();
|
||||||
|
|
||||||
|
GCHandle handle = GCHandle.Alloc(result, GCHandleType.Pinned);
|
||||||
var h = handle.AddrOfPinnedObject();
|
var h = handle.AddrOfPinnedObject();
|
||||||
for (uint i = 0; i < count; i++)
|
Marshal.Copy(data, 0, h, (int)length);
|
||||||
{
|
|
||||||
result[i] = Marshal.PtrToStructure<T>(h + (int)(i * structsize));
|
|
||||||
}
|
|
||||||
handle.Free();
|
handle.Free();
|
||||||
|
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user