Started skeleton for accurate GC
This commit is contained in:
parent
75fb24e369
commit
edeff09e86
4 changed files with 100 additions and 0 deletions
5
src/Accurate_GC/Makefile
Normal file
5
src/Accurate_GC/Makefile
Normal file
|
|
@ -0,0 +1,5 @@
|
||||||
|
LEVEL := ../..
|
||||||
|
LIBRARYNAME = GC
|
||||||
|
LOADABLE_MODULE = 1
|
||||||
|
|
||||||
|
include $(LEVEL)/Makefile.common
|
||||||
16
src/Accurate_GC/gc.cpp
Normal file
16
src/Accurate_GC/gc.cpp
Normal file
|
|
@ -0,0 +1,16 @@
|
||||||
|
/* // TODO: include these properly
|
||||||
|
#include "llvm/CodeGen/GCStrategy.h"
|
||||||
|
#include "llvm/CodeGen/GCMetadata.h"
|
||||||
|
#include "llvm/Support/Compiler.h"
|
||||||
|
|
||||||
|
using namespace llvm;
|
||||||
|
|
||||||
|
namespace {
|
||||||
|
class LLVM_LIBRARY_VISIBILITY GC : public GCStrategy {
|
||||||
|
public:
|
||||||
|
GC() {}
|
||||||
|
};
|
||||||
|
|
||||||
|
GCRegistry::Add<GC>
|
||||||
|
X("gc", "The bespoken garbage collector.");
|
||||||
|
} */
|
||||||
16
src/Accurate_GC/gc_printer.cpp
Normal file
16
src/Accurate_GC/gc_printer.cpp
Normal file
|
|
@ -0,0 +1,16 @@
|
||||||
|
/* #include "llvm/CodeGen/GCMetadataPrinter.h"
|
||||||
|
#include "llvm/Support/Compiler.h"
|
||||||
|
|
||||||
|
using namespace llvm;
|
||||||
|
|
||||||
|
namespace {
|
||||||
|
class LLVM_LIBRARY_VISIBILITY GCPrinter : public GCMetadataPrinter {
|
||||||
|
public:
|
||||||
|
virtual void beginAssembly(AsmPrinter &AP);
|
||||||
|
|
||||||
|
virtual void finishAssembly(AsmPrinter &AP);
|
||||||
|
};
|
||||||
|
|
||||||
|
GCMetadataPrinterRegistry::Add<MyGCPrinter>
|
||||||
|
X("gc", "The bespoken garbage collector.");
|
||||||
|
} */
|
||||||
63
src/Accurate_GC/shadow_stack.cpp
Normal file
63
src/Accurate_GC/shadow_stack.cpp
Normal file
|
|
@ -0,0 +1,63 @@
|
||||||
|
/* /// The map for a single function's stack frame. One of these is
|
||||||
|
/// compiled as constant data into the executable for each function.
|
||||||
|
///
|
||||||
|
/// Storage of metadata values is elided if the %metadata parameter to
|
||||||
|
/// @llvm.gcroot is null.
|
||||||
|
struct FrameMap {
|
||||||
|
int NumRoots; //< Number of roots in stack frame. (int32_t)
|
||||||
|
int NumMeta; //< Number of metadata entries. May be < NumRoots.
|
||||||
|
const void *Meta[0]; //< Metadata for each root.
|
||||||
|
};
|
||||||
|
|
||||||
|
/// A link in the dynamic shadow stack. One of these is embedded in
|
||||||
|
/// the stack frame of each function on the call stack.
|
||||||
|
struct StackEntry {
|
||||||
|
StackEntry *Next; //< Link to next stack entry (the caller's).
|
||||||
|
const FrameMap *Map; //< Pointer to constant FrameMap.
|
||||||
|
void *Roots[0]; //< Stack roots (in-place array).
|
||||||
|
};
|
||||||
|
|
||||||
|
/// The head of the singly-linked list of StackEntries. Functions push
|
||||||
|
/// and pop onto this in their prologue and epilogue.
|
||||||
|
///
|
||||||
|
/// Since there is only a global list, this technique is not threadsafe.
|
||||||
|
StackEntry *llvm_gc_root_chain;
|
||||||
|
|
||||||
|
/// Calls Visitor(root, meta) for each GC root on the stack.
|
||||||
|
/// root and meta are exactly the values passed to
|
||||||
|
/// @llvm.gcroot.
|
||||||
|
///
|
||||||
|
/// Visitor could be a function to recursively mark live objects. Or it
|
||||||
|
/// might copy them to another heap or generation.
|
||||||
|
///
|
||||||
|
/// @param Visitor A function to invoke for every GC root on the stack.
|
||||||
|
void visitGCRoots(void (*Visitor)(void **Root, const void *Meta)) {
|
||||||
|
for (StackEntry *R = llvm_gc_root_chain; R; R = R->Next) {
|
||||||
|
unsigned i = 0;
|
||||||
|
|
||||||
|
// For roots [0, NumMeta), the metadata pointer is in the FrameMap.
|
||||||
|
for (unsigned e = R->Map->NumMeta; i != e; ++i)
|
||||||
|
Visitor(&R->Roots[i], R->Map->Meta[i]);
|
||||||
|
|
||||||
|
// For roots [NumMeta, NumRoots), the metadata pointer is null.
|
||||||
|
for (unsigned e = R->Map->NumRoots; i != e; ++i)
|
||||||
|
Visitor(&R->Roots[i], nullptr);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// To access the stack map
|
||||||
|
void traverseStackMap() {
|
||||||
|
for (auto I = GCFunctionMetadata::roots_begin(), E = GCFunctionMetadata::end(); I != E; ++I) {
|
||||||
|
GCFunctionInfo *FI = *I;
|
||||||
|
unsigned FrameSize = FI->getFrameSize();
|
||||||
|
size_t RootCount = FI->roots_size();
|
||||||
|
|
||||||
|
for (GCFunctionInfo::roots_iterator RI = FI->roots_begin(),
|
||||||
|
RE = FI->roots_end();
|
||||||
|
RI != RE; ++RI) {
|
||||||
|
int RootNum = RI->Num;
|
||||||
|
int RootStackOffset = RI->StackOffset;
|
||||||
|
Constant *RootMetadata = RI->Metadata;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} */
|
||||||
Loading…
Add table
Add a link
Reference in a new issue