Web assembly #6

Merged
Mergul merged 38 commits from WebAssembly into master 2020-04-14 17:44:27 +02:00
14 changed files with 722 additions and 868 deletions
Showing only changes of commit 41f1c6474b - Show all commits

View file

@ -40,6 +40,38 @@
"-Hdimport/", "-Hdimport/",
"-op" "-op"
] ]
},
{
"name" : "library-betterC",
"targetType" : "library",
"excludedSourceFiles":[
"source\/win_dll.d"
],
"dflags": [
"-betterC",
"-defaultlib="
]
},
{
"name" : "dynlib-betterC",
"targetType" : "dynamicLibrary",
"dflags": [
"-betterC",
"-defaultlib=",
"--fvisibility=hidden"
]
},
{
"name" : "tests-betterC",
"targetType" : "executable",
"sourcePaths" : ["source\/","tests\/"],
"excludedSourceFiles":[
"source\/win_dll.d"
],
"dflags": [
"-betterC",
"-defaultlib="
]
} }
] ]
} }

View file

@ -1,9 +1,10 @@
module ecs.block_allocator; module ecs.block_allocator;
import ecs.manager; import ecs.manager;
import ecs.std;
/*
import std.experimental.allocator; import std.experimental.allocator;
import std.experimental.allocator.mallocator : AlignedMallocator, Mallocator; import std.experimental.allocator.mallocator : AlignedMallocator, Mallocator;*/
struct BlockAllocator//(uint block_size, uint blocks_in_allocation) struct BlockAllocator//(uint block_size, uint blocks_in_allocation)
{ {
@ -37,13 +38,13 @@ struct BlockAllocator//(uint block_size, uint blocks_in_allocation)
private void allocBlock() nothrow @nogc private void allocBlock() nothrow @nogc
{ {
next_block = cast(void*) AlignedMallocator.instance.alignedAllocate( next_block = cast(void*) Mallocator.alignAlloc(
block_size * blocks_in_allocation, block_size); block_size * blocks_in_allocation, block_size);
if(pointers is null)pointers = Mallocator.instance.make!BlockPointers; if(pointers is null)pointers = Mallocator.make!BlockPointers;
if(pointers.numberof >= 32) if(pointers.numberof >= 32)
{ {
BlockPointers* new_pointers = Mallocator.instance.make!BlockPointers; BlockPointers* new_pointers = Mallocator.make!BlockPointers;
new_pointers.next_pointers = pointers; new_pointers.next_pointers = pointers;
pointers = new_pointers; pointers = new_pointers;
} }
@ -65,10 +66,10 @@ struct BlockAllocator//(uint block_size, uint blocks_in_allocation)
{ {
foreach(i;0..pointers.numberof) foreach(i;0..pointers.numberof)
{ {
AlignedMallocator.instance.dispose(pointers.blocks[i]); Mallocator.alignDispose(pointers.blocks[i]);
} }
BlockPointers* next_pointers = pointers.next_pointers; BlockPointers* next_pointers = pointers.next_pointers;
Mallocator.instance.dispose(pointers); Mallocator.dispose(pointers);
pointers = next_pointers; pointers = next_pointers;
} }
} }

View file

@ -9,21 +9,6 @@ static struct ECS
{ {
__gshared ushort system_id; __gshared ushort system_id;
uint __ecs_jobs_count = jobs_count; uint __ecs_jobs_count = jobs_count;
/*EntityManager.Job[] _ecs_jobs;
void __ecsInitialize() nothrow @nogc
{
import std.experimental.allocator.mallocator;
import std.experimental.allocator;
_ecs_jobs = Mallocator.instance.makeArray!(EntityManager.Job)(jobs_count);
}
void __ecsDeinitialize() nothrow @nogc
{
import std.experimental.allocator.mallocator;
import std.experimental.allocator;
Mallocator.instance.dispose(_ecs_jobs);
}*/
} }
mixin template Component() mixin template Component()

View file

@ -1,339 +0,0 @@
module ecs.ecs;
import std.stdio;
version(Design):
alias SytemFuncType = void function(ref SystemCallData data, void* componentsStart);
struct HasComponentsStore
{
ulong[4] bits; //256 components
bool has(HasComponentsStore components)
{
return true;
}
bool notIn(HasComponentsStore components)
{
return true;
}
int length()
{
assert(0);
}
}
// Informacje o kompnencie
struct ComponentInfo
{
int size;
int aligment;
SerializeJSON funsSerJ;
SerializeBiN funcSerB;
}
struct System
{
HasComponentsStore requiredComponents;
HasComponentsStore absenComponents;
HasComponentsStore maybeComponents;
bool enabled;
int priority;
SytemFuncType func;
}
// Informacje o systemie dla konkretnego entitiesa
struct SystemCallData
{
System* system;
int[] componentsDt;
}
// Informacje o entitiesie danego typu
struct EntityTypeData
{
HasComponentsStore components;
int[] deltas;
int totalSize;
int totalAligment = 8;
SystemCallData[] systems;
}
struct EntitiesBlock
{
EntityTypeData* typeData;
Entity* freeEntitySlot;
EntitiesBlock* nextBlock;
}
struct EntityID
{
ulong id = ulong.max;
static immutable notUsedValue = EntityID(ulong.max);
}
// Dane konkretnego Entitiesa
struct Entity
{
EntityID entityID = EntityID.notUsedValue;
union
{
string name;
Entity* nextFreeSlot;
}
//string eventOnDestroy;
uint group;
EntityID entityID;
//ubyte[XX] thereIsComponentsMemory;
}
struct Template
{
HasComponentsStore hasComp;
Entity* entity;
}
struct Manager
{
EntityAllocator entityArrayAllcoator;
ComponentInfo[] components;
System[] systems;
HashMap!(HasComponentsStore, EntitiesBlock*) entitiesDatas;
HashMapTwoWays!(string, Entity*) nameMap;
HashMapTwoWays!(EntityID, Entity*) idMap;
EntitiesBlock* getEntitiesBlock(HasComponentsStore hasComponents)
{
EntitiesBlock* block = entitiesDatas.get(hasComponents, null);
if (block is null)
{
// If such component combination was never present, add it
block = addNewBlock(hasComponents, block);
return block;
}
// Iterate over list of components until free slot is found or lists ends
do
{
if (block.freeEntitySlot !is null)
{
return block;
}
if (block.nextBlock is null)
{
block = addNewBlock(hasComponents);
return block;
}
block = block.nextBlock;
}
while (block.nextBlock !is null);
}
EntitiesBlock* addNewBlock(HasComponentsStore hasComponents, EntitiesBlock* firstBlock)
{
// Get last block so order of blocks is preserved, and first blocks are filled first
EntitiesBlock* lastBlock = firstBlock;
if (lastBlock !is null)
{
while (lastBlock.nextBlock !is null)
{
lastBlock = lastBlock.nextBlock;
}
}
assert(lastBlock is null || lastBlock.nextBlock is null);
ubyte[] memory = new ubyte[](4096);
EntitiesBlock* block = cast(EntitiesBlock*) memory.ptr;
if (lastBlock is null)
{
EntityTypeData* entityTypeData = newEntityTypeData(hasComponents);
block.typeData = entityTypeData;
block.nextBlock = null;
entitiesDatas.add(hasComponents, block);
}
else
{
lastBlock.nextBlock = block;
block.typeData = lastBlock.typeData;
block.nextBlock = null;
}
}
void alignNum(ref int num, int aligment)
{
int reminder = num % aligment;
if (reminder != 0)
{
num += aligment - reminder;
}
}
EntityTypeData* newEntityTypeData(HasComponentsStore hasComponents)
{
EntityTypeData* typeData = new EntityTypeData();
typeData.components = hasComponents;
ComponentInfo[] components = getComponentsInfo(hasComponents);
typeData.deltas.length = hasComponents.length;
foreach (i, comp; components)
{
typeData.deltas[i] = typeData.totalSize;
typeData.totalAligment.max(comp.aligment);
typeData.totalSize += comp.size;
alignNum(typeData.totalSize, comp.aligment);
}
alignNum(typeData.totalSize, typeData.totalAligment);
foreach (sys; systems)
{
if (!typeData.hasComp.has(sys.requiredComponents)
|| !typeData.hasComp.notIn(sys.absenComponents))
{
continue;
}
entTypeData.systems ~= sys;
}
return typeData;
}
void addEntity(Template* templ)
{
EntitiesBlock* block = getEntitiesBlock(templ.hasComp);
Entity* newEntity = block.freeEntitySlot;
block.freeEntitySlot = newEntity.nextFreeSlot;
// from to size
memcpy(temp.entity, newEntity, block.typeData.totalSize);
}
void addSystem(Func)(int priority)
{
HasComponentsStore requiredComponents;
HasComponentsStore absenComponents;
HasComponentsStore maybeComponents;
void systemCaller(ref SystemCallData data, void * componentsStart)
{
Func(cast(FUnc.par1Type)(componentsStart + data.componentsDt[0]),
cast(FUnc.par1Type)(componentsStart + data.componentsDt[1])/*...*/);
}
System* system = new System(&systemCaller, entTypeData);
systems ~= system;
foreach (ref entTypeData; entitiesDatas)
{
if (!entTypeData.hasComp.has(requiredComponents)
|| !entTypeData.hasComp.notIn(absenComponents))
{
continue;
}
entTypeData.systems ~= system;
}
}
}
void someSystem(CompA a, CompB b, CompC* c)
{
}
void main()
{
writeln("Edit source/app.d to start your project.");
}
class System
{
void start()
{
}
void end()
{
}
void update(ref ObjRend a)
{
}
void useEvent(EventData evvv, ref ObjRend a)
{
}
}
alias SerializeVector = ubyte[];
__gshared EntityManager gEntityManager;
unittest
{
struct ComponentA
{
__gshared static int component_id;
int a;
ulong b;
static void serializeComponent(ref ComponentA comp, SerializeVector output)
{
}
static void deerializeComponent(ref ComponentA comp, ubyte[] data)
{
}
}
gEM.addComponet!ComponentA();
assert(ComponentA.component_id == 0);
ComponentData* ccc = &gEM.componnets[ComponentA.component_id];
assert(ccc.totalAligment == 8);
assert(ccc.totalSize == 8);
HasComponentsStore hasComponents;
hasComponents.addComponet(ComponentA.component_id);
EntityTempalte* tmpl = gEM.allocateTemplate(hasComponents);
ComponentA* comp = tmpl.getComponent!ComponentA(ComponentA.component_id);
comp.a = 111;
comp.b = 222;
gEM.addEntity(tmpl);
struct SystemAdd
{
void update(ref ComponentA a)
{
a.a+=1000;
b.b+=2000;
}
void handleEvent(EventData evvv, ref ComponentA a)
{
}
}
int priority=10;
gEM.registerSystem!(SystemAdd)(priority);
gEM.updateStepAll();
foreach(EntityID id; gEM.IterateByAllEntiteis){
assert(id.getComponent(ComponentA.component_id));
ComponentA* ccc=id.getComponent(ComponentA.component_id);
assert(ccc.a==1111);
assert(ccc.b==2222);
}
}

View file

@ -3,12 +3,13 @@ module ecs.events;
import ecs.manager; import ecs.manager;
import ecs.block_allocator; import ecs.block_allocator;
import ecs.entity; import ecs.entity;
import ecs.std;
/*
import std.experimental.allocator; import std.experimental.allocator;
import std.experimental.allocator.mallocator : AlignedMallocator, Mallocator; import std.experimental.allocator.mallocator : AlignedMallocator, Mallocator;*/
import std.algorithm.comparison : max; import std.algorithm.comparison : max;
import core.sync.mutex; //import core.sync.mutex;
/*struct Event /*struct Event
{ {
@ -20,67 +21,22 @@ import core.sync.mutex;
struct EventManager struct EventManager
{ {
//@disable this(); void initialize(EntityManager* m) nothrow @nogc
/*this(EntityManager m)
{
manager = m;
}*/
/*void sendSelfEvent(Ev)(EntityID id, Ev event)
{
ushort size = cast(ushort)(Ev.sizeof); // + EntityID.sizeof + ushort.sizeof);
ushort alignment = cast(ushort)(Ev.alignof);
EventList* list = &process_events;
if (list.current_block is null)
{
list.current_block = cast(EventBlock*) allocator.getBlock();
list.first_block = list.current_block;
list.current_block.index = cast(ushort)((void*).sizeof + ushort.sizeof);
}
ushort index = cast(ushort)(
list.current_block.index + ushort.sizeof + EntityID.sizeof + ushort.sizeof);
ushort aligned_index = index; //cast(ushort)(list.current_block.index);
alignNum(aligned_index, alignment);
if (aligned_index + Ev.sizeof > events_block_size)
{
list.current_block.next = cast(EventBlock*) allocator.getBlock();
list.current_block = list.current_block.next;
list.current_block.index = cast(ushort)((void*).sizeof + ushort.sizeof);
index = cast(ushort)((void*)
.sizeof + ushort.sizeof + ushort.sizeof + EntityID.sizeof + ushort.sizeof); // + EntityID.sizeof + ushort.sizeof;
aligned_index = index;
alignNum(aligned_index, alignment);
}
EventBlock* block = list.current_block;
ushort align_ = cast(ushort)(aligned_index - index);
*cast(ushort*)&block.data[block.index] = align_;
index = cast(ushort)(aligned_index - (EntityID.sizeof + ushort.sizeof));
*cast(ushort*)&block.data[index] = Ev.event_id;
*cast(EntityID*)&block.data[index + 2] = id;
*cast(Ev*)&block.data[aligned_index] = event;
block.index = cast(ushort)(aligned_index + Ev.sizeof);
}*/
void initialize(EntityManager m) nothrow @nogc
{ {
allocator = BlockAllocator(events_block_size, events_blocks_in_allocation); allocator = BlockAllocator(events_block_size, events_blocks_in_allocation);
event_block_alloc_mutex = Mallocator.instance.make!Mutex; event_block_alloc_mutex = Mallocator.make!Mutex;
event_block_alloc_mutex.initialize();
manager = m; manager = m;
} }
void destroy() void destroy() nothrow @nogc
{ {
Mallocator.instance.dispose(event_block_alloc_mutex); if(event_block_alloc_mutex)
{
event_block_alloc_mutex.destroy();
Mallocator.dispose(event_block_alloc_mutex);
event_block_alloc_mutex = null;
}
} }
export void sendEvent(Ev)(EntityID id, Ev event, uint thread_id = 0) nothrow @nogc export void sendEvent(Ev)(EntityID id, Ev event, uint thread_id = 0) nothrow @nogc
@ -94,9 +50,9 @@ struct EventManager
if(block is null) if(block is null)
{ {
event_block_alloc_mutex.lock_nothrow(); event_block_alloc_mutex.lock();
scope (exit) scope (exit)
event_block_alloc_mutex.unlock_nothrow(); event_block_alloc_mutex.unlock();
block = cast(EventBlock*) allocator.getBlock(); block = cast(EventBlock*) allocator.getBlock();
*block = EventBlock(); *block = EventBlock();
@ -106,9 +62,9 @@ struct EventManager
if(block.count >= data.max_events) if(block.count >= data.max_events)
{ {
event_block_alloc_mutex.lock_nothrow(); event_block_alloc_mutex.lock();
scope (exit) scope (exit)
event_block_alloc_mutex.unlock_nothrow(); event_block_alloc_mutex.unlock();
EventBlock* new_block = cast(EventBlock*) allocator.getBlock(); EventBlock* new_block = cast(EventBlock*) allocator.getBlock();
*new_block = EventBlock(); *new_block = EventBlock();
@ -117,9 +73,6 @@ struct EventManager
data.blocks[block_id] = block; data.blocks[block_id] = block;
} }
/*void* start = cast(void*)block + data.data_offset + block.count * info.size;
Ev* event_ptr = cast(Ev*)start;
*event_ptr = event;*/
Ev* event_array = cast(Ev*)(cast(void*)block + data.data_offset); Ev* event_array = cast(Ev*)(cast(void*)block + data.data_offset);
event_array[block.count] = event; event_array[block.count] = event;
block.count++; block.count++;
@ -172,30 +125,16 @@ struct EventManager
block = null; block = null;
} }
} }
/*EventList tmp = current_events;
current_events = process_events;
process_events = tmp;
EventBlock* block = process_events.first_block;
while (block)
{
EventBlock* free = block;
block = block.next;
allocator.freeBlock(free);
}
process_events.first_block = null;
process_events.current_block = null;*/
} }
void allocateData(uint threads_count) nothrow @nogc void allocateData(uint threads_count) nothrow @nogc
{ {
disposeData(); disposeData();
events = Mallocator.instance.makeArray!EventData(gEM.events.length); events = Mallocator.makeArray!EventData(gEM.events.length);
foreach(i,ref event;events) foreach(i,ref event;events)
{ {
event.blocks = Mallocator.instance.makeArray!(EventBlock*)(threads_count*2); event.blocks = Mallocator.makeArray!(EventBlock*)(threads_count*2);
event.first_blocks = Mallocator.instance.makeArray!(EventBlock*)(threads_count*2); event.first_blocks = Mallocator.makeArray!(EventBlock*)(threads_count*2);
event.data_offset = EventBlock.sizeof;//gEM.events[i]. event.data_offset = EventBlock.sizeof;//gEM.events[i].
gEM.alignNum(event.data_offset, gEM.events[i].alignment); gEM.alignNum(event.data_offset, gEM.events[i].alignment);
@ -216,16 +155,16 @@ struct EventManager
if(block)next_block = first_block.next; if(block)next_block = first_block.next;
while(block) while(block)
{ {
Mallocator.instance.dispose(block); Mallocator.dispose(block);
block = next_block; block = next_block;
if(block)next_block = block.next; if(block)next_block = block.next;
} }
} }
Mallocator.instance.dispose(event.blocks); Mallocator.dispose(event.blocks);
Mallocator.instance.dispose(event.first_blocks); Mallocator.dispose(event.first_blocks);
} }
Mallocator.instance.dispose(events); Mallocator.dispose(events);
} }
allocator.freeMemory(); allocator.freeMemory();
} }
@ -233,10 +172,6 @@ struct EventManager
~this() nothrow @nogc ~this() nothrow @nogc
{ {
disposeData(); disposeData();
/*foreach(i,ref event;events)
{
EventBlock* block = event.first_blocks;
}*/
} }
///Single page size. Must be power of two. ///Single page size. Must be power of two.
@ -246,26 +181,10 @@ struct EventManager
struct EventBlock struct EventBlock
{ {
/*union
{
struct
{
EventBlock* next;
ushort index = 2;
}
ubyte[events_block_size] data;
}*/
EventBlock* next; EventBlock* next;
ushort count = 0; ushort count = 0;
} }
/*struct EventList
{
EventBlock* first_block;
EventBlock* current_block;
}*/
struct EventData struct EventData
{ {
ushort data_offset; ushort data_offset;
@ -276,12 +195,10 @@ struct EventManager
//EventBlock*[] current_blocks; //EventBlock*[] current_blocks;
} }
/*EventList current_events;
EventList process_events;*/
uint current_index = 0; uint current_index = 0;
EventData[] events; EventData[] events;
Mutex event_block_alloc_mutex; Mutex* event_block_alloc_mutex;
BlockAllocator/*!(events_block_size, events_blocks_in_allocation)*/ allocator; BlockAllocator allocator;
EntityManager manager; EntityManager* manager;
} }

View file

@ -30,6 +30,7 @@ export ulong hashInt(ulong x) nothrow @nogc @safe {
struct HashMap(KeyPar, ValuePar, alias hashFunc = defaultHashFunc) { struct HashMap(KeyPar, ValuePar, alias hashFunc = defaultHashFunc) {
alias Key = KeyPar; alias Key = KeyPar;
alias Value = ValuePar; alias Value = ValuePar;
nothrow:
enum rehashFactor = 0.75; enum rehashFactor = 0.75;
enum size_t getIndexEmptyValue = size_t.max; enum size_t getIndexEmptyValue = size_t.max;
@ -262,7 +263,7 @@ struct HashMap(KeyPar, ValuePar, alias hashFunc = defaultHashFunc) {
return result; return result;
} }
export int byKey(scope int delegate(Key k) dg) { export int byKey(scope int delegate(Key k) nothrow dg) {
int result; int result;
foreach (ref Key k; this) { foreach (ref Key k; this) {
result = dg(k); result = dg(k);
@ -272,7 +273,7 @@ struct HashMap(KeyPar, ValuePar, alias hashFunc = defaultHashFunc) {
return result; return result;
} }
export int byValue(scope int delegate(ref Value k) dg) { export int byValue(scope int delegate(ref Value k) nothrow dg) {
int result; int result;
foreach (ref Value v; this) { foreach (ref Value v; this) {
result = dg(v); result = dg(v);
@ -282,7 +283,7 @@ struct HashMap(KeyPar, ValuePar, alias hashFunc = defaultHashFunc) {
return result; return result;
} }
export int byKeyValue(scope int delegate(ref Key k, ref Value v) dg) { export int byKeyValue(scope int delegate(ref Key k, ref Value v) nothrow dg) {
int result; int result;
foreach (ref Key k, ref Value v; this) { foreach (ref Key k, ref Value v; this) {
result = dg(k, v); result = dg(k, v);

View file

@ -1,14 +1,15 @@
module ecs.id_manager; module ecs.id_manager;
/*
import std.experimental.allocator; import std.experimental.allocator;
import std.experimental.allocator.mallocator : AlignedMallocator, Mallocator; import std.experimental.allocator.mallocator : AlignedMallocator, Mallocator;*/
import ecs.entity; import ecs.entity;
import ecs.vector; import ecs.vector;
import ecs.std;
import core.atomic; import core.atomic;
import core.stdc.string : memcpy; import core.stdc.string : memcpy;
import core.sync.mutex; //import core.sync.mutex;
/************************************************************************************************************************ /************************************************************************************************************************
*IDManager is responsible for assignment and removing IDs. IDs are unique throughtout a whole duration of the program. *IDManager is responsible for assignment and removing IDs. IDs are unique throughtout a whole duration of the program.
@ -35,13 +36,13 @@ begin:
uint block_id = local_id >> 16; uint block_id = local_id >> 16;
if (block_id >= m_blocks_count) if (block_id >= m_blocks_count)
{ {
add_mutex.lock_nothrow(); add_mutex.lock();
if(block_id >= m_blocks_count) if(block_id >= m_blocks_count)
{ {
m_blocks[m_blocks_count].alloc(); m_blocks[m_blocks_count].alloc();
m_blocks_count++; m_blocks_count++;
} }
add_mutex.unlock_nothrow(); add_mutex.unlock();
} }
} }
@ -145,30 +146,34 @@ begin:
void initialize() nothrow @nogc void initialize() nothrow @nogc
{ {
m_ids_array = Mallocator.instance.makeArray!Data(65536); m_ids_array = Mallocator.makeArray!Data(65536);
m_free_stack = Mallocator.instance.makeArray!uint(65536); m_free_stack = Mallocator.makeArray!uint(65536);
m_blocks = Mallocator.instance.makeArray!Block(64); m_blocks = Mallocator.makeArray!Block(64);
foreach(ref block;m_blocks)block = Block();
m_blocks_count = 1; m_blocks_count = 1;
m_blocks[0].alloc(); m_blocks[0].alloc();
add_mutex = Mallocator.instance.make!Mutex(); add_mutex = Mallocator.make!Mutex();
add_mutex.initialize();
} }
void deinitialize() @trusted @nogc void deinitialize() @trusted @nogc nothrow
{ {
if(m_ids_array)Mallocator.instance.dispose(m_ids_array); if(m_ids_array)Mallocator.dispose(m_ids_array);
if(m_free_stack)Mallocator.instance.dispose(m_free_stack); if(m_free_stack)Mallocator.dispose(m_free_stack);
if(m_blocks) if(m_blocks)
{ {
foreach(ref block;m_blocks) foreach(ref block;m_blocks)
{ {
if(block.data)block.free(); if(block.data)block.free();
} }
Mallocator.instance.dispose(m_blocks); Mallocator.dispose(m_blocks);
} }
if(add_mutex) if(add_mutex)
{ {
Mallocator.instance.dispose(cast(void*)add_mutex); //workaround for compiler bug add_mutex.destroy();
Mallocator.dispose(add_mutex);//cast(void*)add_mutex); //workaround for compiler bug
add_mutex = null;
} }
} }
@ -178,14 +183,14 @@ begin:
if(m_last_id > m_ids_array.length) if(m_last_id > m_ids_array.length)
{ {
uint begin = cast(uint)m_ids_array.length; uint begin = cast(uint)m_ids_array.length;
Data[] new_array = Mallocator.instance.makeArray!Data(begin + (m_blocks_count << 16)); Data[] new_array = Mallocator.makeArray!Data(begin + (m_blocks_count << 16));
memcpy(new_array.ptr, m_ids_array.ptr, m_ids_array.length * Data.sizeof); memcpy(new_array.ptr, m_ids_array.ptr, m_ids_array.length * Data.sizeof);
Mallocator.instance.dispose(m_ids_array); Mallocator.dispose(m_ids_array);
m_ids_array = new_array; m_ids_array = new_array;
uint[] new_stack = Mallocator.instance.makeArray!uint(m_ids_array.length); uint[] new_stack = Mallocator.makeArray!uint(m_ids_array.length);
memcpy(new_stack.ptr,m_free_stack.ptr,m_free_stack.length * uint.sizeof); memcpy(new_stack.ptr,m_free_stack.ptr,m_free_stack.length * uint.sizeof);
Mallocator.instance.dispose(m_free_stack); Mallocator.dispose(m_free_stack);
m_free_stack = new_stack; m_free_stack = new_stack;
foreach(block;m_blocks[0..m_blocks_count-1]) foreach(block;m_blocks[0..m_blocks_count-1])
@ -204,13 +209,13 @@ begin:
void alloc() nothrow @nogc void alloc() nothrow @nogc
{ {
assert(data is null); assert(data is null);
data = Mallocator.instance.makeArray!Data(65536); data = Mallocator.makeArray!Data(65536);
} }
void free() nothrow @nogc void free() nothrow @nogc
{ {
assert(data !is null); assert(data !is null);
Mallocator.instance.dispose(data); Mallocator.dispose(data);
data = null; data = null;
} }
@ -225,7 +230,7 @@ begin:
} }
private: private:
Mutex add_mutex; Mutex* add_mutex;
//shared uint m_next_id = 0; //shared uint m_next_id = 0;
//shared uint m_last_id = 0; //shared uint m_last_id = 0;
@ -261,5 +266,4 @@ unittest
assert(id3 == EntityID(2, 1)); assert(id3 == EntityID(2, 1));
assert(manager.isExist(id3)); assert(manager.isExist(id3));
assert(!manager.isExist(EntityID(0, 1))); assert(!manager.isExist(EntityID(0, 1)));
} }

File diff suppressed because it is too large Load diff

View file

@ -1,7 +1,9 @@
module ecs.simple_vector; module ecs.simple_vector;
/*
import std.experimental.allocator; import std.experimental.allocator;
import std.experimental.allocator.mallocator; import std.experimental.allocator.mallocator;*/
import ecs.std;
import core.stdc.string; import core.stdc.string;
@ -14,8 +16,8 @@ struct SimpleVector
{ {
while(used >= data.length) while(used >= data.length)
{ {
if(data is null)data = Mallocator.instance.makeArray!ubyte(1024); if(data is null)data = Mallocator.makeArray!ubyte(1024);
else Mallocator.instance.expandArray(data,data.length); else data = Mallocator.expandArray(data,data.length);
} }
data[used++] = el; data[used++] = el;
} }
@ -24,8 +26,8 @@ struct SimpleVector
{ {
while(used + el.length >= data.length) while(used + el.length >= data.length)
{ {
if(data is null)data = Mallocator.instance.makeArray!ubyte(1024); if(data is null)data = Mallocator.makeArray!ubyte(1024);
else Mallocator.instance.expandArray(data,data.length); else data = Mallocator.expandArray(data,data.length);
} }
memcpy(data.ptr + used, el.ptr, el.length); memcpy(data.ptr + used, el.ptr, el.length);
used += el.length; used += el.length;

227
source/ecs/std.d Normal file
View file

@ -0,0 +1,227 @@
module ecs.std;
import core.stdc.stdlib : malloc, free, realloc;
import core.stdc.string : memcpy;
import std.traits;
import core.time;
version (Windows)
{
import core.sys.windows.windows;
extern(Windows) void* _aligned_malloc(size_t size,size_t alignment) @nogc nothrow @system;
extern(Windows) void _aligned_free(void* ptr) @nogc nothrow @system;
version(LDC)
{
/*extern(Windows) void* __alloca(size_t size) @nogc nothrow @system;
alias alloca = __alloca;*/
private const uint max_alloca = 10000;
private char[max_alloca] alloca_array;
private uint alloca_pos = 0;
void* alloca(size_t length) @nogc nothrow
{
if(alloca_pos + length > max_alloca)alloca_pos = 0;
void* ret = &alloca_array[alloca_pos];
alloca_pos += length;
return ret;
}
extern(Windows) void ___chkstk_ms() @nogc nothrow @system;
extern(Windows) void __chkstk()
{
___chkstk_ms();
}
}
else
{
private const uint max_alloca = 10000;
private char[max_alloca] alloca_array;
private uint alloca_pos = 0;
void* alloca(size_t length) @nogc nothrow
{
if(alloca_pos + length > max_alloca)alloca_pos = 0;
void* ret = &alloca_array[alloca_pos];
alloca_pos += length;
return ret;
}
}
}
else version (Posix)
{
import core.sys.posix.pthread;
import core.sys.posix.stdlib;
public import core.stdc.stdlib : alloca;
}
static struct Mallocator
{
static T[] makeArray(T)(size_t length) nothrow @nogc
{
T[] ret = (cast(T*)malloc(T.sizeof * length))[0 .. length];
/*static if(__traits(isPOD, T))
{
static immutable T init = T.init;
foreach(i;0..ret.length)
{
memcpy(&ret[i], &init, T.sizeof);
}
}
else
{*/
static import std.conv;
foreach(i;0..ret.length)
{
std.conv.emplace(&ret[i]);
}
// }
//static if(is(T == struct))std.conv.emplace(ret);
//static import std.conv;
//emplace
/*foreach(i;0..ret.length)
{
memcpy(ret);
}*/
return ret;
}
static T[] makeArray(T)(size_t length, T initializer) nothrow @nogc
{
T[] ret = (cast(T*)malloc(T.sizeof * length))[0 .. length];
foreach(ref v; ret)v = initializer;
return ret;
//return (cast(T*)ret)[0 .. length];
}
static T[] expandArray(T)(T[] array, size_t length) nothrow @nogc
{
size_t new_length = array.length + length;
return (cast(T*)realloc(array.ptr, T.sizeof * new_length))[0 .. new_length];
}
static T[] makeArray(T)(T[] array) nothrow @nogc
{
T[] ret = (cast(T*)malloc(T.sizeof * array.length))[0 .. array.length];//Mallocator.makeArray!(T)(array.length);
foreach(i, ref v;ret)v = array[i];
//ret[0 .. $] = array;
return ret;
}
static T* make(T, Args...)(Args args)
{
T* ret = cast(T*)malloc(T.sizeof);
//*ret = T.init;
//static immutable T init = T();
//memcpy(ret, &init, T.sizeof);
//static if(__traits(hasMember, T, "__ctor"))ret.__ctor(args);
static import std.conv;
static if(__traits(isPOD, T))
{
static immutable T init = T.init;
memcpy(ret, &init, T.sizeof);
}
else static if(is(T == struct))std.conv.emplace(ret, args);
//else std.conv.emplace(ret, args);
return ret;
}
static void* alignAlloc(size_t length, size_t alignment) nothrow @nogc
{
void* ret;
version(Posix)ret = aligned_alloc(alignment, length);
else version(Windows)ret = _aligned_malloc(length, alignment);
else static assert(0, "Unimplemented platform!");
//posix_memalign(&ret, alignment, length);
return ret;
}
static void dispose(T)(T object) nothrow @nogc
{
static if(__traits(hasMember, T, "__dtor"))object.__dtor();
free(cast(void*)object);
}
static void alignDispose(T)(T object)
{
static if(__traits(hasMember, T, "__dtor"))object.__dtor();
version(Posix)aligned_free(cast(void*)object);
else version(Windows)_aligned_free(cast(void*)object);
else static assert(0, "Unimplemented platform!");
}
}
struct Mutex
{
version (Windows)
{
void initialize() nothrow @nogc
{
InitializeCriticalSection(cast(CRITICAL_SECTION*) &m_handle);
}
void destroy() nothrow @nogc
{
DeleteCriticalSection(&m_handle);
}
void lock() nothrow @nogc
{
EnterCriticalSection(&m_handle);
}
void unlock() nothrow @nogc
{
LeaveCriticalSection(&m_handle);
}
int tryLock() nothrow @nogc
{
return TryEnterCriticalSection(&m_handle) != 0;
}
CRITICAL_SECTION m_handle;
}
else version (Posix)
{
void initialize() nothrow @nogc
{
pthread_mutexattr_t attr = void;
pthread_mutexattr_init(&attr);
pthread_mutexattr_settype(&attr, PTHREAD_MUTEX_RECURSIVE);
pthread_mutex_init(cast(pthread_mutex_t*) &m_handle, &attr);
pthread_mutexattr_destroy(&attr);
}
void destroy() nothrow @nogc
{
pthread_mutex_destroy(&m_handle);
}
void lock() nothrow @nogc
{
pthread_mutex_lock(&m_handle);
}
void unlock() nothrow @nogc
{
pthread_mutex_unlock(&m_handle);
}
int tryLock() nothrow @nogc
{
return pthread_mutex_trylock(&m_handle) == 0;
}
private pthread_mutex_t m_handle;
}
}

View file

@ -125,14 +125,14 @@ package:
//void function(ref EntityManager.CallData data) m_update; //void function(ref EntityManager.CallData data) m_update;
void* m_update; ///workaroud for DMD bug with upper line void* m_update; ///workaroud for DMD bug with upper line
/*void function(void* system_pointer) m_enable; //void function(void* system_pointer) m_enable;
void function(void* system_pointer) m_disable; //void function(void* system_pointer) m_disable;
void function(void* system_pointer) m_create; //void function(void* system_pointer) m_create;
void function(void* system_pointer) m_destroy; //void function(void* system_pointer) m_destroy;
void function(void* system_pointer) m_begin; //void function(void* system_pointer) m_begin;
void function(void* system_pointer) m_end;*/ //void function(void* system_pointer) m_end;
void* m_enable; void* m_enable;
void* m_disable; void* m_disable;

View file

@ -3,7 +3,7 @@ module ecs.vector;
import core.bitop; import core.bitop;
import core.stdc.stdlib : free, malloc; import core.stdc.stdlib : free, malloc;
import core.stdc.string : memcpy, memset; import core.stdc.string : memcpy, memset;
import std.algorithm : swap; //import std.algorithm : swap;
import std.conv : emplace; import std.conv : emplace;
import std.traits : hasMember, isCopyable, TemplateOf, Unqual; import std.traits : hasMember, isCopyable, TemplateOf, Unqual;
@ -28,7 +28,7 @@ public:
} }
static if (isCopyable!T) { /*static if (isCopyable!T) {
export this(this) { export this(this) {
T[] tmp = array[0 .. used]; T[] tmp = array[0 .. used];
array = null; array = null;
@ -37,7 +37,9 @@ public:
} }
} else { } else {
@disable this(this); @disable this(this);
} }*/
@disable this(this);
export ~this() { export ~this() {
clear(); clear();
@ -167,7 +169,8 @@ public:
export void remove(size_t elemNum) { export void remove(size_t elemNum) {
destroy(array[elemNum]); destroy(array[elemNum]);
swap(array[elemNum], array[used - 1]); //swap(array[elemNum], array[used - 1]);
array[elemNum] = array[used - 1];
used--; used--;
} }

View file

@ -7,7 +7,7 @@ import core.sys.windows.windows;
extern(Windows) bool DllMain(void* hInstance, uint ulReason, void*) extern(Windows) bool DllMain(void* hInstance, uint ulReason, void*)
{ {
switch (ulReason) /*switch (ulReason)
{ {
default: assert(0); default: assert(0);
case DLL_PROCESS_ATTACH: case DLL_PROCESS_ATTACH:
@ -26,5 +26,6 @@ extern(Windows) bool DllMain(void* hInstance, uint ulReason, void*)
dll_thread_detach( true, true ); dll_thread_detach( true, true );
break; break;
} }
return true; return true;*/
return 0;
} }

View file

@ -1,7 +1,7 @@
module tests.tests; module tests.tests;
/*
import std.experimental.allocator; import std.experimental.allocator;
import std.experimental.allocator.mallocator; import std.experimental.allocator.mallocator;*/
import ecs.entity; import ecs.entity;
import ecs.events; import ecs.events;
@ -13,6 +13,21 @@ import ecs.core;
import core.time; import core.time;
import std.stdio; import std.stdio;
version(Windows)
{
import core.sys.windows.windows;
struct Time
{
static long getUSecTime()
{
LARGE_INTEGER time, freq;
QueryPerformanceFrequency(&freq);
QueryPerformanceCounter(&time);
return time.QuadPart / (freq.QuadPart / 1000_000);
}
}
}
struct TestEvent struct TestEvent
{ {
mixin ECS.Event; //__gshared ushort event_id; mixin ECS.Event; //__gshared ushort event_id;
@ -124,17 +139,20 @@ struct ChangeTestSystem
void onCreate() void onCreate()
{ {
writeln("On Change Test System create."); //writeln("On Change Test System create.");
printf("On Change Test System create.");
} }
void onCreate(int i) void onCreate(int i)
{ {
writeln("On Change Test System create."); //writeln("On Change Test System create.");
printf("On Change Test System create.");
} }
void onDestroy() void onDestroy()
{ {
writeln("On Change Test System destroy."); //writeln("On Change Test System destroy.");
printf("On Change Test System destroy.");
} }
void onAddEntity(EntitiesData data) void onAddEntity(EntitiesData data)
@ -142,30 +160,30 @@ struct ChangeTestSystem
//printf("Entity added! ID: "); //printf("Entity added! ID: ");
foreach (i; 0 .. data.length) foreach (i; 0 .. data.length)
printf("Entity added! ID: %u\n",data.entites[i].id); printf("Entity added! ID: %u\n",data.entites[i].id);
//writeln("Entity added! ID: ", data.entites[i].id); ////writeln("Entity added! ID: ", data.entites[i].id);
} }
void onRemoveEntity(EntitiesData data) void onRemoveEntity(EntitiesData data)
{ {
//writeln("Entity removed! ID: ", data.entites[0].id); ////writeln("Entity removed! ID: ", data.entites[0].id);
printf("Entity removed! ID: %u\n",data.entites[0].id); printf("Entity removed! ID: %u\n",data.entites[0].id);
} }
void onChangeEntity(EntitiesData data) void onChangeEntity(EntitiesData data)
{ {
//writeln("Entity changed! ID: ", data.entites[0].id); ////writeln("Entity changed! ID: ", data.entites[0].id);
printf("Entity changed! ID: %u\n",data.entites[0].id); printf("Entity changed! ID: %u\n",data.entites[0].id);
} }
bool onBegin() bool onBegin()
{ {
//writeln("On Test System begin."); ////writeln("On Test System begin.");
return true; return true;
} }
void onEnd() void onEnd()
{ {
//writeln("On Test System end."); ////writeln("On Test System end.");
} }
void initialize(ref Entity entity, ref TestComp comp) void initialize(ref Entity entity, ref TestComp comp)
@ -196,34 +214,36 @@ struct TestSystem
void onCreate() void onCreate()
{ {
writeln("On Test System create."); //writeln("On Test System create.");
printf("On Change Test System create.");
} }
void onDestroy() void onDestroy()
{ {
writeln("On Test System destroy."); //writeln("On Test System destroy.");
printf("On Change Test System destroy.");
} }
void onAddEntity(EntitiesData data) void onAddEntity(EntitiesData data)
{ {
//foreach(i;0..data.length) //foreach(i;0..data.length)
//writeln("Entity added ID: ",data.entites[i].id.id); ////writeln("Entity added ID: ",data.entites[i].id.id);
} }
/* /*
void onRemoveEntity(EntitiesData data) void onRemoveEntity(EntitiesData data)
{ {
//writeln("Entity destroyed ID: ",data.entites[0].id); ////writeln("Entity destroyed ID: ",data.entites[0].id);
}*/ }*/
bool onBegin() bool onBegin()
{ {
//writeln("On Test System begin."); ////writeln("On Test System begin.");
return true; return true;
} }
void onEnd() void onEnd()
{ {
//writeln("On Test System end."); ////writeln("On Test System end.");
} }
void initialize(ref Entity entity, ref TestComp comp) void initialize(ref Entity entity, ref TestComp comp)
@ -400,14 +420,16 @@ struct TestSystem2
{ {
import std.stdio; import std.stdio;
writeln("TestSystem2 enabled"); //writeln("TestSystem2 enabled");
printf("TestSystem2 enabled");
} }
void onDisable() void onDisable()
{ {
import std.stdio; import std.stdio;
writeln("TestSystem2 disabled"); //writeln("TestSystem2 disabled");
printf("TestSystem2 disabled");
} }
void initialize(ref Entity entity, ref TestComp comp) void initialize(ref Entity entity, ref TestComp comp)
@ -446,35 +468,38 @@ struct TestSystem2
}*/ }*/
} }
int main() extern(C) int main()
{ {
void dispatch(EntityManager.JobGroup jobs) nothrow @nogc void dispatch(EntityManager.JobGroup jobs) nothrow @nogc
{ {
foreach (job; jobs.jobs) foreach (job; jobs.jobs)
{ {
//writeln(job); ////writeln(job);
job.execute(); job.execute();
} }
} }
void writeEntityComponents(Entity* entity) void writeEntityComponents(Entity* entity)
{ {
write(entity.id);
printf("EntityID(%u, %u)",entity.id.id,entity.id.counter);
//write(entity.id);
TestComp* test_comp = entity.getComponent!TestComp; TestComp* test_comp = entity.getComponent!TestComp;
if (test_comp) if (test_comp)
write(*test_comp); printf("TestComp(%u, %u)",test_comp.a,test_comp.b);//write(*test_comp);
TestComp2* test_comp2 = entity.getComponent!TestComp2; TestComp2* test_comp2 = entity.getComponent!TestComp2;
if (test_comp2) if (test_comp2)
write(*test_comp2); printf("TestComp2(%u, %u)",test_comp2.a,test_comp2.b);//write(*test_comp2);
TestComp3* test_comp3 = entity.getComponent!TestComp3; TestComp3* test_comp3 = entity.getComponent!TestComp3;
if (test_comp3) if (test_comp3)
write(*test_comp3); printf("TestComp3(%u, %u)",test_comp3.gg,test_comp3.bg);//write(*test_comp3);
TestComp4* test_comp4 = entity.getComponent!TestComp4; TestComp4* test_comp4 = entity.getComponent!TestComp4;
if (test_comp4) if (test_comp4)
write(*test_comp4); printf("TestComp4(%u, %u, %u, %u, %u, %u)",test_comp4.gg,test_comp4.bg,test_comp4.a,test_comp4.b,test_comp4.c,test_comp4.g);//write(*test_comp4);
writeln(); printf("\n");
//writeln((cast(uint*) pp)[0 .. 14], " ", pp); //writeln();
////writeln((cast(uint*) pp)[0 .. 14], " ", pp);
} }
EntityManager.initialize(1); EntityManager.initialize(1);
@ -484,7 +509,8 @@ int main()
gEM.beginRegister(); gEM.beginRegister();
gEM.registerPass("fixed"); gEM.registerPass("fixed");
MonoTime time = MonoTime.currTime; //MonoTime time = MonoTime.currTime;
long time = Time.getUSecTime();
gEM.registerComponent!TestComp2; gEM.registerComponent!TestComp2;
gEM.registerComponent!TestComp4; gEM.registerComponent!TestComp4;
@ -495,10 +521,13 @@ int main()
gEM.registerEvent!TestEvent; gEM.registerEvent!TestEvent;
gEM.registerEvent!TestEvent2; gEM.registerEvent!TestEvent2;
ulong dur = (MonoTime.currTime - time).total!"usecs"; /*ulong dur = (MonoTime.currTime - time).total!"usecs";
writeln("Components register: ", dur, " usecs"); //writeln("Components register: ", dur, " usecs");
time = MonoTime.currTime; time = MonoTime.currTime;*/
printf("Components register: %f usecs\n",cast(float)(Time.getUSecTime() - time));
time = Time.getUSecTime();
gEM.registerSystem!TestSystemWithHighPriority(100, "fixed"); gEM.registerSystem!TestSystemWithHighPriority(100, "fixed");
gEM.registerSystem!TestSystem(0); gEM.registerSystem!TestSystem(0);
@ -507,13 +536,15 @@ int main()
gEM.registerSystem!Sys2(-100); gEM.registerSystem!Sys2(-100);
gEM.registerSystem!Sys3(-2); gEM.registerSystem!Sys3(-2);
//gEM.registerSystem!TestSystemWithHighPriority(100); //gEM.registerSystem!TestSystemWithHighPriority(100);
//gEM.registerSystem!TestSystem2(0); //gEM.registerSystem!TestSystem2(0);*/
gEM.endRegister(); gEM.endRegister();
dur = (MonoTime.currTime - time).total!"usecs"; /*dur = (MonoTime.currTime - time).total!"usecs";
writeln("Systems register: ", dur, " usecs"); //writeln("Systems register: ", dur, " usecs");
time = MonoTime.currTime; time = MonoTime.currTime;*/
printf("Systems register: %f usecs\n",cast(float)(Time.getUSecTime() - time));
time = Time.getUSecTime();
//ushort[3] ids = [TestComp2.component_id, TestComp.component_id, TestComp4.component_id]; //ushort[3] ids = [TestComp2.component_id, TestComp.component_id, TestComp4.component_id];
ushort[2] ids = [TestComp2.component_id, TestComp.component_id]; ushort[2] ids = [TestComp2.component_id, TestComp.component_id];
@ -522,11 +553,13 @@ int main()
//ushort[3] ids2 = [TestComp3.component_id, TestComp.component_id, TestComp4.component_id]; //ushort[3] ids2 = [TestComp3.component_id, TestComp.component_id, TestComp4.component_id];
ushort[2] ids2 = [TestComp3.component_id, TestComp.component_id]; ushort[2] ids2 = [TestComp3.component_id, TestComp.component_id];
EntityTemplate* tmpl2 = gEM.allocateTemplate(ids2); EntityTemplate* tmpl2 = gEM.allocateTemplate(ids2);
//writeln(tmpl.info.components[]); ////writeln(tmpl.info.components[]);
//*cast(EntityID*) tmpl.entity_data.ptr = EntityID(1, 1); //*cast(EntityID*) tmpl.entity_data.ptr = EntityID(1, 1);
dur = (MonoTime.currTime - time).total!"usecs"; //dur = (MonoTime.currTime - time).total!"usecs";
writeln("Template allocating: ", dur, " usecs"); //writeln("Template allocating: ", dur, " usecs");
printf("Template allocating: %f usecs\n",cast(float)(Time.getUSecTime() - time));
time = Time.getUSecTime();
EntityID entity; EntityID entity;
@ -536,18 +569,21 @@ int main()
EntityManager.EntitiesBlock* block = EntityManager.instance.getMetaData( EntityManager.EntitiesBlock* block = EntityManager.instance.getMetaData(
gEM.getEntity(entity)); gEM.getEntity(entity));
EntityManager.EntityInfo* info = block.type_info; EntityManager.EntityInfo* info = block.type_info;
writeln(info.add_listeners); //writeln(info.add_listeners);
//if(info)assert(0); //if(info)assert(0);
} }
time = MonoTime.currTime; //time = MonoTime.currTime;
time = Time.getUSecTime();
//foreach(i; 0..1_000_000)gEM.addEntity(tmpl); //foreach(i; 0..1_000_000)gEM.addEntity(tmpl);
//foreach(i; 0..1_000_000)gEM.removeEntity(gEM.addEntity(tmpl).id); //foreach(i; 0..1_000_000)gEM.removeEntity(gEM.addEntity(tmpl).id);
EntityID[] idss = Mallocator.instance.makeArray!EntityID(5000);//[5000] import ecs.std;
scope(exit)Mallocator.instance.dispose(idss);
EntityID[] idss = Mallocator.makeArray!EntityID(5000);//[5000]
//scope(exit)Mallocator.dispose(idss);
foreach (i; 0 .. 200) foreach (i; 0 .. 200)
{ {
@ -560,8 +596,10 @@ int main()
} }
gEM.commit(); gEM.commit();
dur = (MonoTime.currTime - time).total!"usecs"; //dur = (MonoTime.currTime - time).total!"usecs";
writeln("Entities adding: ", dur, " usecs"); //writeln("Entities adding: ", dur, " usecs");
printf("Entities adding: %f usecs\n",cast(float)(Time.getUSecTime() - time));
time = Time.getUSecTime();
uint blocks = 0; uint blocks = 0;
foreach (info; &gEM.entities_infos.byValue) foreach (info; &gEM.entities_infos.byValue)
@ -573,7 +611,8 @@ int main()
blocks++; blocks++;
} }
} }
writeln("Entities blocks: ", blocks); //writeln("Entities blocks: ", blocks);
printf("Entities blocks: %u\n",blocks);
//foreach(j; 0..1_000)gEM.addEntity(tmpl); //foreach(j; 0..1_000)gEM.addEntity(tmpl);
@ -590,9 +629,10 @@ int main()
EntityID entity2; EntityID entity2;
time = MonoTime.currTime; //time = MonoTime.currTime;
time = Time.getUSecTime();
EntityID[] entities = Mallocator.instance.makeArray!EntityID(1_000_000); EntityID[] entities = Mallocator.makeArray!EntityID(1_000_000);
foreach (i; 0 .. 500_000) foreach (i; 0 .. 500_000)
{ {
entity2 = gEM.addEntity(tmpl).id; entity2 = gEM.addEntity(tmpl).id;
@ -601,10 +641,12 @@ int main()
} }
gEM.commit(); gEM.commit();
dur = (MonoTime.currTime - time).total!"usecs"; //dur = (MonoTime.currTime - time).total!"usecs";
writeln("Entities adding2: ", dur, " usecs"); //writeln("Entities adding2: ", dur, " usecs");
time = MonoTime.currTime; //time = MonoTime.currTime;
printf("Entities adding2: %f usecs\n",cast(float)(Time.getUSecTime() - time));
time = Time.getUSecTime();
foreach (i; 0 .. 1_000_000) foreach (i; 0 .. 1_000_000)
{ {
@ -613,10 +655,12 @@ int main()
} }
gEM.commit(); gEM.commit();
dur = (MonoTime.currTime - time).total!"usecs"; //dur = (MonoTime.currTime - time).total!"usecs";
writeln("Components adding: ", dur, " usecs"); //writeln("Components adding: ", dur, " usecs");
time = MonoTime.currTime; //time = MonoTime.currTime;
printf("Components adding: %f usecs\n",cast(float)(Time.getUSecTime() - time));
time = Time.getUSecTime();
foreach (i; 0 .. 1_000_000) foreach (i; 0 .. 1_000_000)
{ {
@ -625,44 +669,52 @@ int main()
} }
gEM.commit(); gEM.commit();
dur = (MonoTime.currTime - time).total!"usecs"; //dur = (MonoTime.currTime - time).total!"usecs";
writeln("Components removing: ", dur, " usecs"); //writeln("Components removing: ", dur, " usecs");
printf("Components removing: %f usecs\n",cast(float)(Time.getUSecTime() - time));
time = Time.getUSecTime();
Mallocator.instance.dispose(entities); Mallocator.dispose(entities);
time = MonoTime.currTime; //time = MonoTime.currTime;
time = Time.getUSecTime();
gEM.begin(); gEM.begin();
//gEM.updateMT(); //gEM.updateMT();
gEM.update(); gEM.update();
gEM.end(); gEM.end();
dur = (MonoTime.currTime - time).total!"usecs"; //dur = (MonoTime.currTime - time).total!"usecs";
writeln("Update: ", dur, " usecs"); //writeln("Update: ", dur, " usecs");
printf("Update: %f usecs\n",cast(float)(Time.getUSecTime() - time));
writeEntityComponents(gEM.getEntity(entity2)); writeEntityComponents(gEM.getEntity(entity2));
time = MonoTime.currTime; //time = MonoTime.currTime;
time = Time.getUSecTime();
gEM.begin(); gEM.begin();
gEM.updateMT(); gEM.updateMT();
//gEM.update(); //gEM.update();
gEM.end(); gEM.end();
dur = (MonoTime.currTime - time).total!"usecs"; //dur = (MonoTime.currTime - time).total!"usecs";
writeln("Update: ", dur, " usecs"); //writeln("Update: ", dur, " usecs");
printf("Update: %f usecs\n",cast(float)(Time.getUSecTime() - time));
writeEntityComponents(gEM.getEntity(entity2)); writeEntityComponents(gEM.getEntity(entity2));
time = MonoTime.currTime; //time = MonoTime.currTime;
time = Time.getUSecTime();
gEM.begin(); gEM.begin();
gEM.updateMT(); gEM.updateMT();
//gEM.update(); //gEM.update();
gEM.end(); gEM.end();
dur = (MonoTime.currTime - time).total!"usecs"; //dur = (MonoTime.currTime - time).total!"usecs";
writeln("Update: ", dur, " usecs"); //writeln("Update: ", dur, " usecs");
printf("Update: %f usecs\n",cast(float)(Time.getUSecTime() - time));
writeEntityComponents(gEM.getEntity(entity2)); writeEntityComponents(gEM.getEntity(entity2));
@ -673,10 +725,10 @@ int main()
gEM.end(); gEM.end();
//Entity* pp;// = gEM.getEntity(entity.id); //Entity* pp;// = gEM.getEntity(entity.id);
//writeln((cast(uint*) pp)[0 .. 14], " ", pp); ////writeln((cast(uint*) pp)[0 .. 14], " ", pp);
writeEntityComponents(gEM.getEntity(entity)); writeEntityComponents(gEM.getEntity(entity));
writeln("Entity, its copy, and template, and default filled tempalte"); //writeln("Entity, its copy, and template, and default filled tempalte");
gEM.addEntity(tmpl); gEM.addEntity(tmpl);
writeEntityComponents(gEM.getEntity(entity)); writeEntityComponents(gEM.getEntity(entity));
writeEntityComponents(gEM.addEntityCopy(entity)); writeEntityComponents(gEM.addEntityCopy(entity));
@ -705,16 +757,22 @@ int main()
gEM.removeComponents!(TestComp4)(entity); gEM.removeComponents!(TestComp4)(entity);
gEM.commit();//*/ gEM.commit();
printf("pre end\n");
writeEntityComponents(gEM.getEntity(entity)); writeEntityComponents(gEM.getEntity(entity));
//import std.stdio; //import std.stdio;
//writeln((cast(uint*)tmpl.info.first_block)[0..48]); ////writeln((cast(uint*)tmpl.info.first_block)[0..48]);
gEM.freeTemplate(tmpl); gEM.freeTemplate(tmpl);
gEM.freeTemplate(tmpl2); gEM.freeTemplate(tmpl2);
gEM.freeTemplate(copy_tempalte); gEM.freeTemplate(copy_tempalte);
gEM.freeTemplate(copy_default_tempalte); gEM.freeTemplate(copy_default_tempalte);
EntityManager.destroy(); EntityManager.destroy();
Mallocator.dispose(idss);
printf("end\n");//*/
return 0; return 0;
} }