This commit is contained in:
DCFApixels 2025-05-21 17:41:28 +08:00
parent 54f25eaaad
commit 71bf7064e1
3 changed files with 44 additions and 51 deletions

View File

@ -230,7 +230,7 @@ namespace DCFApixels.DragonECS
ref var page = ref _groupSparsePagePool[i]; ref var page = ref _groupSparsePagePool[i];
if (page.IsEmpty == false) if (page.IsEmpty == false)
{ {
MemoryAllocator.Free(ref page); MemoryAllocator.FreeAndClear(ref page);
} }
} }
_groupSparsePagePoolCount = 0; _groupSparsePagePoolCount = 0;

View File

@ -6,6 +6,10 @@ using DCFApixels.DragonECS.Core.Internal;
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Runtime.CompilerServices; using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
#if ENABLE_IL2CPP
using Unity.IL2CPP.CompilerServices;
#endif
namespace DCFApixels.DragonECS namespace DCFApixels.DragonECS
{ {
@ -105,16 +109,22 @@ namespace DCFApixels.DragonECS.Core
//TODO добавить Any //TODO добавить Any
#if ENABLE_IL2CPP
[Il2CppSetOption(Option.NullChecks, false)]
[Il2CppSetOption(Option.ArrayBoundsChecks, false)]
#endif
public readonly unsafe struct WorldStateVersionsChecker : IDisposable public readonly unsafe struct WorldStateVersionsChecker : IDisposable
{ {
private readonly EcsWorld _world; private readonly EcsWorld _world;
private readonly int[] _maskInc; private readonly MemoryAllocator.Handler _handler;
private readonly int[] _maskExc; private readonly int* _componentIDs;
// [0] world version // _versions[0] world version
// [-> _maskInc.Length] inc versions // _versions[-> EcsMask.Inc.Length] inc versions
// [-> _maskExc.Length] exc versions // _versions[-> EcsMask.Exc.Length] exc versions
// _versions[-> EcsMask.Any.Length] any versions
private readonly long* _versions; private readonly long* _versions;
private readonly int _count; private readonly int _count;
private readonly bool _isNotOnlyExc;
public long Version public long Version
{ {
[MethodImpl(MethodImplOptions.AggressiveInlining)] [MethodImpl(MethodImplOptions.AggressiveInlining)]
@ -124,11 +134,20 @@ namespace DCFApixels.DragonECS.Core
public WorldStateVersionsChecker(EcsMask mask) public WorldStateVersionsChecker(EcsMask mask)
{ {
_world = mask.World; _world = mask.World;
_maskInc = mask._incs; _count = 1 + mask._incs.Length + mask._excs.Length + mask._anys.Length;
_maskExc = mask._excs;
_count = 1 + mask._incs.Length + mask._excs.Length;
_versions = UnmanagedArrayUtility.NewAndInit<long>(_count); _handler = MemoryAllocator.AllocAndInit<int>(_count * 2 + _count);
_versions = _handler.As<long>();
_componentIDs = (int*)(_handler.As<long>() + _count);
var ptr = _componentIDs + 1;
Marshal.Copy(mask._incs, 0, (IntPtr)ptr, mask._incs.Length);
ptr += mask._incs.Length;
Marshal.Copy(mask._excs, 0, (IntPtr)ptr, mask._excs.Length);
ptr += mask._excs.Length;
Marshal.Copy(mask._anys, 0, (IntPtr)ptr, mask._anys.Length);
_isNotOnlyExc = mask._incs.Length > 0 || mask._anys.Length > 0;
} }
public bool Check() public bool Check()
{ {
@ -137,20 +156,10 @@ namespace DCFApixels.DragonECS.Core
return true; return true;
} }
long* versionsPtr = _versions;
var slots = _world._poolSlots; var slots = _world._poolSlots;
foreach (var slotIndex in _maskInc) for (int i = 1; i < _count; i++)
{ {
versionsPtr++; if(_versions[i] == slots[_componentIDs[i]].version)
if (*versionsPtr != slots[slotIndex].version)
{
return false;
}
}
foreach (var slotIndex in _maskExc)
{
versionsPtr++;
if (*versionsPtr != slots[slotIndex].version)
{ {
return false; return false;
} }
@ -161,17 +170,10 @@ namespace DCFApixels.DragonECS.Core
{ {
*_versions = _world.Version; *_versions = _world.Version;
long* versionsPtr = _versions;
var slots = _world._poolSlots; var slots = _world._poolSlots;
foreach (var slotIndex in _maskInc) for (int i = 1; i < _count; i++)
{ {
versionsPtr++; _versions[i] = slots[_componentIDs[i]].version;
*versionsPtr = slots[slotIndex].version;
}
foreach (var slotIndex in _maskExc)
{
versionsPtr++;
*versionsPtr = slots[slotIndex].version;
} }
} }
public bool CheckAndNext() public bool CheckAndNext()
@ -182,27 +184,14 @@ namespace DCFApixels.DragonECS.Core
} }
*_versions = _world.Version; *_versions = _world.Version;
long* versionsPtr = _versions;
var slots = _world._poolSlots; var slots = _world._poolSlots;
// Так как проверки EXC работают не правильно при отсутсвии INC, bool result = _isNotOnlyExc;
// то проверки без INC должны всегда возвращать false. for (int i = 1; i < _count; i++)
bool result = _maskInc.Length > 0;
foreach (var slotIndex in _maskInc)
{ {
versionsPtr++; if (_versions[i] != slots[_componentIDs[i]].version)
if (*versionsPtr != slots[slotIndex].version)
{ {
result = false; result = false;
*versionsPtr = slots[slotIndex].version; _versions[i] = slots[_componentIDs[i]].version;
}
}
foreach (var slotIndex in _maskExc)
{
versionsPtr++;
if (*versionsPtr != slots[slotIndex].version)
{
result = false;
*versionsPtr = slots[slotIndex].version;
} }
} }
return result; return result;
@ -210,7 +199,7 @@ namespace DCFApixels.DragonECS.Core
public void Dispose() public void Dispose()
{ {
UnmanagedArrayUtility.Free(_versions); MemoryAllocator.Free(_handler);
} }
} }
} }

View File

@ -143,7 +143,11 @@ namespace DCFApixels.DragonECS.Core.Internal
#endregion #endregion
#region Free #region Free
public static void Free(ref Handler target) public static void Free(Handler target)
{
Free_Internal(target.GetHandledPtr());
}
public static void FreeAndClear(ref Handler target)
{ {
Free_Internal(target.GetHandledPtr()); Free_Internal(target.GetHandledPtr());
target = default; target = default;
@ -335,7 +339,7 @@ namespace DCFApixels.DragonECS.Core.Internal
{ {
public static void Dispose(this ref MemoryAllocator.Handler self) public static void Dispose(this ref MemoryAllocator.Handler self)
{ {
MemoryAllocator.Free(ref self); MemoryAllocator.FreeAndClear(ref self);
} }
} }
} }