void PClass::BuildArrayPointers() { if (ArrayPointers != nullptr) { // Already built: Do nothing. return; } else if (ParentClass == nullptr) { // No parent (i.e. DObject: FlatPointers is the same as Pointers. ArrayPointers = &TheEnd; } else { ParentClass->BuildArrayPointers(); TArray<size_t> ScriptPointers; // Collect all arrays to pointers in scripted fields. for (auto field : Fields) { if (!(field->Flags & VARF_Native)) { field->Type->SetPointerArray(Defaults, unsigned(field->Offset), &ScriptPointers); } } if (ScriptPointers.Size() == 0) { // No new pointers: Just use the same ArrayPointers as the parent. ArrayPointers = ParentClass->ArrayPointers; } else { // New pointers: Create a new FlatPointers array and add them. int numSuperPointers; // Count pointers defined by superclasses. for (numSuperPointers = 0; ParentClass->ArrayPointers[numSuperPointers] != ~(size_t)0; numSuperPointers++) { } // Concatenate them into a new array size_t *flat = (size_t*)ClassDataAllocator.Alloc(sizeof(size_t) * (numSuperPointers + ScriptPointers.Size() + 1)); if (numSuperPointers > 0) { memcpy(flat, ParentClass->ArrayPointers, sizeof(size_t)*numSuperPointers); } if (ScriptPointers.Size() > 0) { memcpy(flat + numSuperPointers, &ScriptPointers[0], sizeof(size_t) * ScriptPointers.Size()); } flat[numSuperPointers + ScriptPointers.Size()] = ~(size_t)0; ArrayPointers = flat; } } }
void PClass::StaticShutdown () { if (WP_NOCHANGE != nullptr) { delete WP_NOCHANGE; } // delete all variables containing pointers to script functions. for (auto p : FunctionPtrList) { *p = nullptr; } FunctionPtrList.Clear(); VMFunction::DeleteAll(); // Make a full garbage collection here so that all destroyed but uncollected higher level objects // that still exist are properly taken down before the low level data is deleted. GC::FullGC(); // From this point onward no scripts may be called anymore because the data needed by the VM is getting deleted now. // This flags DObject::Destroy not to call any scripted OnDestroy methods anymore. bVMOperational = false; // PendingWeapon must be cleared manually because it is not subjected to the GC if it contains WP_NOCHANGE, which is just RUNTIME_CLASS(AWWeapon). // But that will get cleared here, confusing the GC if the value is left in. for (auto &p : players) { p.PendingWeapon = nullptr; } Namespaces.ReleaseSymbols(); // This must be done in two steps because the native classes are not ordered by inheritance, // so all meta data must be gone before deleting the actual class objects. for (auto cls : AllClasses) cls->DestroyMeta(cls->Meta); for (auto cls : AllClasses) delete cls; // Unless something went wrong, anything left here should be class and type objects only, which do not own any scripts. bShutdown = true; TypeTable.Clear(); ClassDataAllocator.FreeAllBlocks(); AllClasses.Clear(); PClassActor::AllActorClasses.Clear(); ClassMap.Clear(); FAutoSegIterator probe(CRegHead, CRegTail); while (*++probe != nullptr) { auto cr = ((ClassReg *)*probe); cr->MyClass = nullptr; } }
msecnode_t *P_GetSecnode() { msecnode_t *node; if (headsecnode) { node = headsecnode; headsecnode = headsecnode->m_snext; } else { node = (msecnode_t *)secnodearena.Alloc(sizeof(*node)); } return node; }
//========================================================================== // // // //========================================================================== HWSprite *HWDrawList::NewSprite() { auto sprite = (HWSprite*)RenderDataAllocator.Alloc(sizeof(HWSprite)); drawitems.Push(HWDrawItem(DrawType_SPRITE, sprites.Push(sprite))); return sprite; }
//========================================================================== // // // //========================================================================== HWFlat *HWDrawList::NewFlat() { auto flat = (HWFlat*)RenderDataAllocator.Alloc(sizeof(HWFlat)); drawitems.Push(HWDrawItem(DrawType_FLAT,flats.Push(flat))); return flat; }
HWWall *HWDrawList::NewWall() { auto wall = (HWWall*)RenderDataAllocator.Alloc(sizeof(HWWall)); drawitems.Push(HWDrawItem(DrawType_WALL, walls.Push(wall))); return wall; }
void ResetRenderDataAllocator() { RenderDataAllocator.FreeAll(); }