mirror of
https://github.com/ZDoom/qzdoom.git
synced 2025-06-04 19:00:59 +00:00
- reverted most of the last commit after realizing that trying to manage constructing/destructing per variable is not going to work because it'd require some extensive exception management in the compiled VM code.
- instead add a list of SpecialInits to VMScriptFunction so this can be done transparently when setting up and popping the stack frame. The only drawback is that this requires permanent allocation of stack objects for the entire lifetime of a function but this is a relatively small tradeoff for significantly reduced maintenance work throughout. - removed most #include "vm.h", because nearly all files already pull this in through dobject.h.
This commit is contained in:
parent
30e6e8e25f
commit
d86f03e2e0
30 changed files with 55 additions and 235 deletions
|
@ -2,7 +2,6 @@
|
|||
#define VM_H
|
||||
|
||||
#include "zstring.h"
|
||||
#include "dobject.h"
|
||||
#include "autosegs.h"
|
||||
#include "vectors.h"
|
||||
|
||||
|
@ -815,6 +814,12 @@ public:
|
|||
VM_UHALF MaxParam; // Maximum number of parameters this function has on the stack at once
|
||||
VM_UBYTE NumArgs; // Number of arguments this function takes
|
||||
FString PrintableName; // so that the VM can print meaningful info if something in this function goes wrong.
|
||||
TArray<FTypeAndOffset> SpecialInits; // list of all contents on the extra stack which require construction and destruction
|
||||
|
||||
void InitExtra(void *addr);
|
||||
void DestroyExtra(void *addr);
|
||||
void SetExtraSpecial(PType *type, unsigned offset);
|
||||
int AllocExtraStack(PType *type);
|
||||
};
|
||||
|
||||
class VMFrameStack
|
||||
|
@ -822,7 +827,6 @@ class VMFrameStack
|
|||
public:
|
||||
VMFrameStack();
|
||||
~VMFrameStack();
|
||||
VMFrame *AllocFrame(int numregd, int numregf, int numregs, int numrega);
|
||||
VMFrame *AllocFrame(VMScriptFunction *func);
|
||||
VMFrame *PopFrame();
|
||||
VMFrame *TopFrame()
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
#ifndef VMUTIL_H
|
||||
#define VMUTIL_H
|
||||
|
||||
#include "vm.h"
|
||||
#include "dobject.h"
|
||||
|
||||
class VMFunctionBuilder
|
||||
{
|
||||
|
|
|
@ -31,7 +31,7 @@
|
|||
**
|
||||
*/
|
||||
|
||||
#include "vm.h"
|
||||
#include "dobject.h"
|
||||
#include "c_console.h"
|
||||
#include "templates.h"
|
||||
|
||||
|
|
|
@ -34,7 +34,7 @@
|
|||
#include <math.h>
|
||||
#include <v_video.h>
|
||||
#include <s_sound.h>
|
||||
#include "vm.h"
|
||||
#include "dobject.h"
|
||||
#include "xs_Float.h"
|
||||
#include "math/cmath.h"
|
||||
|
||||
|
|
|
@ -32,7 +32,7 @@
|
|||
*/
|
||||
|
||||
#include <new>
|
||||
#include "vm.h"
|
||||
#include "dobject.h"
|
||||
|
||||
IMPLEMENT_CLASS(VMException, false, false, false, false)
|
||||
IMPLEMENT_CLASS(VMFunction, true, true, false, false)
|
||||
|
@ -162,6 +162,38 @@ size_t VMScriptFunction::PropagateMark()
|
|||
return NumKonstA * sizeof(void *) + Super::PropagateMark();
|
||||
}
|
||||
|
||||
void VMScriptFunction::InitExtra(void *addr)
|
||||
{
|
||||
char *caddr = (char*)addr;
|
||||
|
||||
for (auto tao : SpecialInits)
|
||||
{
|
||||
tao.first->InitializeValue(caddr + tao.second, nullptr);
|
||||
}
|
||||
}
|
||||
|
||||
void VMScriptFunction::DestroyExtra(void *addr)
|
||||
{
|
||||
char *caddr = (char*)addr;
|
||||
|
||||
for (auto tao : SpecialInits)
|
||||
{
|
||||
tao.first->DestroyValue(caddr + tao.second);
|
||||
}
|
||||
}
|
||||
|
||||
void VMScriptFunction::SetExtraSpecial(PType *type, unsigned offset)
|
||||
{
|
||||
type->SetDefaultValue(nullptr, offset, &SpecialInits);
|
||||
}
|
||||
|
||||
int VMScriptFunction::AllocExtraStack(PType *type)
|
||||
{
|
||||
int address = ((ExtraSpace + type->Align - 1) / type->Align) * type->Align;
|
||||
ExtraSpace = address + type->Size;
|
||||
return address;
|
||||
}
|
||||
|
||||
//===========================================================================
|
||||
//
|
||||
// VMFrame :: InitRegS
|
||||
|
@ -223,34 +255,6 @@ VMFrameStack::~VMFrameStack()
|
|||
UnusedBlocks = NULL;
|
||||
}
|
||||
|
||||
//===========================================================================
|
||||
//
|
||||
// VMFrameStack :: AllocFrame
|
||||
//
|
||||
// Allocates a frame from the stack with the desired number of registers.
|
||||
//
|
||||
//===========================================================================
|
||||
|
||||
VMFrame *VMFrameStack::AllocFrame(int numregd, int numregf, int numregs, int numrega)
|
||||
{
|
||||
assert((unsigned)numregd < 255);
|
||||
assert((unsigned)numregf < 255);
|
||||
assert((unsigned)numregs < 255);
|
||||
assert((unsigned)numrega < 255);
|
||||
// To keep the arguments to this function simpler, it assumes that every
|
||||
// register might be used as a parameter for a single call.
|
||||
int numparam = numregd + numregf + numregs + numrega;
|
||||
int size = VMFrame::FrameSize(numregd, numregf, numregs, numrega, numparam, 0);
|
||||
VMFrame *frame = Alloc(size);
|
||||
frame->NumRegD = numregd;
|
||||
frame->NumRegF = numregf;
|
||||
frame->NumRegS = numregs;
|
||||
frame->NumRegA = numrega;
|
||||
frame->MaxParam = numparam;
|
||||
frame->InitRegS();
|
||||
return frame;
|
||||
}
|
||||
|
||||
//===========================================================================
|
||||
//
|
||||
// VMFrameStack :: AllocFrame
|
||||
|
@ -273,6 +277,10 @@ VMFrame *VMFrameStack::AllocFrame(VMScriptFunction *func)
|
|||
frame->MaxParam = func->MaxParam;
|
||||
frame->Func = func;
|
||||
frame->InitRegS();
|
||||
if (func->SpecialInits.Size())
|
||||
{
|
||||
func->InitExtra(frame->GetExtra());
|
||||
}
|
||||
return frame;
|
||||
}
|
||||
|
||||
|
@ -358,6 +366,11 @@ VMFrame *VMFrameStack::PopFrame()
|
|||
{
|
||||
return NULL;
|
||||
}
|
||||
auto Func = static_cast<VMScriptFunction *>(frame->Func);
|
||||
if (Func->SpecialInits.Size())
|
||||
{
|
||||
Func->DestroyExtra(frame->GetExtra());
|
||||
}
|
||||
// Free any string registers this frame had.
|
||||
FString *regs = frame->GetRegS();
|
||||
for (int i = frame->NumRegS; i != 0; --i)
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue