Improved array caching for ResourceAnalyzer

This commit is contained in:
dexy 2020-03-13 23:23:54 +11:00
parent 7712807c36
commit 4941f86193
4 changed files with 81 additions and 31 deletions

View File

@ -4097,7 +4097,7 @@ namespace CodeWalker.GameFiles
Counts[i] = reader.ReadUInt32();
}
ulong[] ptrlist = reader.ReadUlongsAt(ptr, 8);
ulong[] ptrlist = reader.ReadUlongsAt(ptr, 8, false);
//if (ptr != (ulong)reader.Position)
//{ }//no hit
@ -4105,7 +4105,7 @@ namespace CodeWalker.GameFiles
for (int i = 0; i < 8; i++)
{
Items[i] = reader.ReadUintsAt(ptrlist[i], Counts[i]);
Items[i] = reader.ReadUintsAt(ptrlist[i], Counts[i], false);
//if (ptrlist[i] != ptr)
//{ ptr = ptrlist[i]; }//no hit

View File

@ -539,7 +539,7 @@ namespace CodeWalker.GameFiles
break;
default:
offset += 16 * p.DataType;
p.Data = reader.ReadStructsAt<Vector4>(p.DataPointer, p.DataType);
p.Data = reader.ReadStructsAt<Vector4>(p.DataPointer, p.DataType, false);
break;
}
}
@ -2041,7 +2041,26 @@ namespace CodeWalker.GameFiles
{
public override long BlockLength
{
get { return 48; }
get
{
var off = (long)48;
//off += (GeometriesCount1 * 2); //ShaderMapping
//if (GeometriesCount1 == 1) off += 6;
//else off += ((16 - (off % 16)) % 16);
//off += (GeometriesCount1 * 8); //Geometries pointers
//off += ((16 - (off % 16)) % 16);
//off += (GeometriesCount1 + ((GeometriesCount1 > 1) ? 1 : 0)) * 32; //BoundsData
//for (int i = 0; i < GeometriesCount1; i++)
//{
// var geom = Geometries?.data_items[i];
// if (geom != null)
// {
// off += ((16 - (off % 16)) % 16);
// off += geom.BlockLength; //Geometries
// }
//}
return off;
}
}
// structure data
@ -2158,14 +2177,10 @@ namespace CodeWalker.GameFiles
// read reference data
this.Geometries = reader.ReadBlockAt<ResourcePointerArray64<DrawableGeometry>>(
this.GeometriesPointer, // offset
this.GeometriesCount1
);
this.Geometries = reader.ReadBlockAt<ResourcePointerArray64<DrawableGeometry>>(this.GeometriesPointer, this.GeometriesCount1);
this.BoundsData = reader.ReadStructsAt<AABB_s>(this.BoundsPointer, (uint)(this.GeometriesCount1 > 1 ? this.GeometriesCount1 + 1 : this.GeometriesCount1));
this.ShaderMapping = reader.ReadUshortsAt(this.ShaderMappingPointer, this.GeometriesCount1);
if (Geometries?.data_items != null)
{
for (int i = 0; i < Geometries.data_items.Length; i++)
@ -2181,6 +2196,41 @@ namespace CodeWalker.GameFiles
////just testing!
//var pos = (ulong)reader.Position;
//var off = (ulong)0;
//if (ShaderMappingPointer != (pos+off))
//{ }//no hit
//off += (ulong)(GeometriesCount1 * 2); //ShaderMapping
//if (GeometriesCount1 == 1) off += 6;
//else off += ((16 - (off % 16)) % 16);
//if (GeometriesPointer != (pos+off))
//{ }//no hit
//off += (ulong)(GeometriesCount1 * 8); //Geometries pointers
//off += ((16 - (off % 16)) % 16);
//if (BoundsPointer != (pos+off))
//{ }//no hit
//off += (ulong)((GeometriesCount1 + ((GeometriesCount1 > 1) ? 1 : 0)) * 32); //BoundsData
//if ((Geometries?.data_pointers != null) && (Geometries?.data_items != null))
//{
// for (int i = 0; i < GeometriesCount1; i++)
// {
// var geomptr = Geometries.data_pointers[i];
// var geom = Geometries.data_items[i];
// if (geom != null)
// {
// off += ((16 - (off % 16)) % 16);
// if (geomptr != (pos + off))
// { }//no hit
// off += (ulong)geom.BlockLength;
// }
// else
// { }//no hit
// }
//}
//else
//{ }//no hit
//if (SkeletonBindUnk2 != 0)
//{ }//no hit
//switch (SkeletonBindUnk1)
@ -2396,7 +2446,7 @@ namespace CodeWalker.GameFiles
this.IndexBuffer = reader.ReadBlockAt<IndexBuffer>(
this.IndexBufferPointer // offset
);
this.BoneIds = reader.ReadUshortsAt(this.BoneIdsPointer, this.BoneIdsCount);
this.BoneIds = reader.ReadUshortsAt(this.BoneIdsPointer, this.BoneIdsCount, false);
if (this.BoneIds != null) //skinned mesh bones to use? peds, also yft props...
{
}

View File

@ -1408,7 +1408,7 @@ namespace CodeWalker.GameFiles
int numElements = Convert.ToInt32(parameters[0]);
data_pointers = reader.ReadUlongsAt((ulong)reader.Position, (uint)numElements);
data_pointers = reader.ReadUlongsAt((ulong)reader.Position, (uint)numElements, false);
data_items = new T[numElements];

View File

@ -235,7 +235,7 @@ namespace CodeWalker.GameFiles
}
public byte[] ReadBytesAt(ulong position, uint count)
public byte[] ReadBytesAt(ulong position, uint count, bool cache = true)
{
long pos = (long)position;
if ((pos <= 0) || (count == 0)) return null;
@ -243,16 +243,16 @@ namespace CodeWalker.GameFiles
Position = pos;
var result = ReadBytes((int)count);
Position = posbackup;
arrayPool[(long)position] = result;
if (cache) arrayPool[(long)position] = result;
return result;
}
public ushort[] ReadUshortsAt(ulong position, uint count)
public ushort[] ReadUshortsAt(ulong position, uint count, bool cache = true)
{
if ((position <= 0) || (count == 0)) return null;
var result = new ushort[count];
var length = count * 2;
byte[] data = ReadBytesAt(position, length);
byte[] data = ReadBytesAt(position, length, false);
Buffer.BlockCopy(data, 0, result, 0, (int)length);
//var posbackup = Position;
@ -264,29 +264,29 @@ namespace CodeWalker.GameFiles
//}
//Position = posbackup;
arrayPool[(long)position] = result;
if (cache) arrayPool[(long)position] = result;
return result;
}
public short[] ReadShortsAt(ulong position, uint count)
public short[] ReadShortsAt(ulong position, uint count, bool cache = true)
{
if ((position <= 0) || (count == 0)) return null;
var result = new short[count];
var length = count * 2;
byte[] data = ReadBytesAt(position, length);
byte[] data = ReadBytesAt(position, length, false);
Buffer.BlockCopy(data, 0, result, 0, (int)length);
arrayPool[(long)position] = result;
if (cache) arrayPool[(long)position] = result;
return result;
}
public uint[] ReadUintsAt(ulong position, uint count)
public uint[] ReadUintsAt(ulong position, uint count, bool cache = true)
{
if ((position <= 0) || (count == 0)) return null;
var result = new uint[count];
var length = count * 4;
byte[] data = ReadBytesAt(position, length);
byte[] data = ReadBytesAt(position, length, false);
Buffer.BlockCopy(data, 0, result, 0, (int)length);
//var posbackup = Position;
@ -298,17 +298,17 @@ namespace CodeWalker.GameFiles
//}
//Position = posbackup;
arrayPool[(long)position] = result;
if (cache) arrayPool[(long)position] = result;
return result;
}
public ulong[] ReadUlongsAt(ulong position, uint count)
public ulong[] ReadUlongsAt(ulong position, uint count, bool cache = true)
{
if ((position <= 0) || (count == 0)) return null;
var result = new ulong[count];
var length = count * 8;
byte[] data = ReadBytesAt(position, length);
byte[] data = ReadBytesAt(position, length, false);
Buffer.BlockCopy(data, 0, result, 0, (int)length);
//var posbackup = Position;
@ -320,17 +320,17 @@ namespace CodeWalker.GameFiles
//}
//Position = posbackup;
arrayPool[(long)position] = result;
if (cache) arrayPool[(long)position] = result;
return result;
}
public float[] ReadFloatsAt(ulong position, uint count)
public float[] ReadFloatsAt(ulong position, uint count, bool cache = true)
{
if ((position <= 0) || (count == 0)) return null;
var result = new float[count];
var length = count * 4;
byte[] data = ReadBytesAt(position, length);
byte[] data = ReadBytesAt(position, length, false);
Buffer.BlockCopy(data, 0, result, 0, (int)length);
//var posbackup = Position;
@ -342,17 +342,17 @@ namespace CodeWalker.GameFiles
//}
//Position = posbackup;
arrayPool[(long)position] = result;
if (cache) arrayPool[(long)position] = result;
return result;
}
public T[] ReadStructsAt<T>(ulong position, uint count)//, uint structsize)
public T[] ReadStructsAt<T>(ulong position, uint count, bool cache = true)
{
if ((position <= 0) || (count == 0)) return null;
uint structsize = (uint)Marshal.SizeOf(typeof(T));
var length = count * structsize;
byte[] data = ReadBytesAt(position, length);
byte[] data = ReadBytesAt(position, length, false);
//var result2 = new T[count];
//Buffer.BlockCopy(data, 0, result2, 0, (int)length); //error: "object must be an array of primitives" :(
@ -366,7 +366,7 @@ namespace CodeWalker.GameFiles
}
handle.Free();
arrayPool[(long)position] = result;
if (cache) arrayPool[(long)position] = result;
return result;
}