public static void Move(UnsafeBuffer source, int fromIndex, int toIndex, int count) { Assert.Check(source.Ptr != null); AllocHelper.MemMove((byte *)source.Ptr + (toIndex * source.Stride), (byte *)source.Ptr + (fromIndex * source.Stride), count * source.Stride); }
public static Entry *GetEntry(UnsafeHashCollection *collection, int index) { return((Entry *)UnsafeBuffer.Element(collection->Entries.Ptr, index, collection->Entries.Stride)); }
public static void Free(UnsafeHashMap *map) { AllocHelper.Free(map->_collection.Buckets); AllocHelper.Free(map->_collection.FreeHead); UnsafeBuffer.Free(&map->_collection.Entries); }
public static UnsafeHashMap *Allocate(int capacity, int keyStride, int valStride, bool fixedSize = false) { var entryStride = sizeof(UnsafeHashCollection.Entry); // round capacity up to next prime capacity = UnsafeHashCollection.GetNextPrime(capacity); // this has to be true Assert.Check(entryStride == 16); var keyAlignment = AllocHelper.GetAlignmentForArrayElement(keyStride); var valAlignment = AllocHelper.GetAlignmentForArrayElement(valStride); // the alignment for entry/key/val, we can't have less than ENTRY_ALIGNMENT // bytes alignment because entries are 8 bytes with 2 x 32 bit integers var alignment = Math.Max(UnsafeHashCollection.Entry.ALIGNMENT, Math.Max(keyAlignment, valAlignment)); // calculate strides for all elements keyStride = AllocHelper.RoundUpToAlignment(keyStride, alignment); valStride = AllocHelper.RoundUpToAlignment(valStride, alignment); entryStride = AllocHelper.RoundUpToAlignment(sizeof(UnsafeHashCollection.Entry), alignment); // map ptr UnsafeHashMap *map; if (fixedSize) { var sizeOfHeader = AllocHelper.RoundUpToAlignment(sizeof(UnsafeHashMap), alignment); var sizeOfBucketsBuffer = AllocHelper.RoundUpToAlignment(sizeof(UnsafeHashCollection.Entry * *) * capacity, alignment); var sizeofEntriesBuffer = (entryStride + keyStride + valStride) * capacity; // allocate memory var ptr = AllocHelper.MallocAndClear(sizeOfHeader + sizeOfBucketsBuffer + sizeofEntriesBuffer, alignment); // start of memory is the dict itself map = (UnsafeHashMap *)ptr; // buckets are offset by header size map->_collection.Buckets = (UnsafeHashCollection.Entry * *)((byte *)ptr + sizeOfHeader); // initialize fixed buffer UnsafeBuffer.InitFixed(&map->_collection.Entries, (byte *)ptr + (sizeOfHeader + sizeOfBucketsBuffer), capacity, entryStride + keyStride + valStride); } else { // allocate dict, buckets and entries buffer separately map = AllocHelper.MallocAndClear <UnsafeHashMap>(); map->_collection.Buckets = (UnsafeHashCollection.Entry * *)AllocHelper.MallocAndClear(sizeof(UnsafeHashCollection.Entry * *) * capacity, sizeof(UnsafeHashCollection.Entry * *)); // init dynamic buffer UnsafeBuffer.InitDynamic(&map->_collection.Entries, capacity, entryStride + keyStride + valStride); } // header init map->_collection.FreeCount = 0; map->_collection.UsedCount = 0; map->_collection.KeyOffset = entryStride; map->_valueOffset = entryStride + keyStride; return(map); }
static K Key <K>(UnsafeHeapMin *heap, int index) where K : unmanaged { return(*(K *)UnsafeBuffer.Element(heap->_items.Ptr, index, heap->_items.Stride)); }