Second attemmpt at fixing critical bug in Node::unref()

This commit is contained in:
Sam Vervaeck 2023-05-31 13:14:46 +02:00
parent 717a2a663a
commit b64b18216a
Signed by: samvv
SSH key fingerprint: SHA256:dIg0ywU1OP+ZYifrYxy8c5esO72cIKB+4/9wkZj1VaY
2 changed files with 18 additions and 16 deletions

View file

@ -197,12 +197,7 @@ namespace bolt {
++RefCount; ++RefCount;
} }
inline void unref() { void unref();
--RefCount;
if (RefCount == 0) {
delete this;
}
}
void setParents(); void setParents();
@ -249,7 +244,7 @@ namespace bolt {
virtual Scope* getScope(); virtual Scope* getScope();
virtual ~Node(); virtual ~Node() {}
}; };

View file

@ -289,20 +289,27 @@ namespace bolt {
} }
Node::~Node() { void Node::unref() {
--RefCount;
if (RefCount == 0) {
// You may be wondering why we aren't unreffing the children in the
// destructor. This is due to a behaviour in Clang where a top-level
// destructor ~Node() wont get access to the fields in derived classes
// because they may already have been destroyed.
struct UnrefVisitor : public CSTVisitor<UnrefVisitor> { struct UnrefVisitor : public CSTVisitor<UnrefVisitor> {
void visit(Node* N) { void visit(Node* N) {
visitEachChild(N);
N->unref(); N->unref();
} }
}; };
UnrefVisitor V; UnrefVisitor V;
V.visitEachChild(this); V.visitEachChild(this);
delete this;
}
} }
bool Identifier::isTypeVar() const { bool Identifier::isTypeVar() const {