svadev AT lists.siebelschool.illinois.edu
Subject: Svadev mailing list
List archive
- From: John Criswell <criswell AT illinois.edu>
- To: Daniel Huang <dan.e.huang AT gmail.com>
- Cc: "<svadev AT cs.illinois.edu>" <svadev AT cs.illinois.edu>
- Subject: Re: [svadev] sva types
- Date: Mon, 3 Dec 2012 13:18:46 -0600
- List-archive: <http://lists.cs.uiuc.edu/pipermail/svadev/>
- List-id: <svadev.cs.uiuc.edu>
- Organization: University of Illinois
On 11/30/12 1:01 PM, John Criswell wrote:
Dear Daniel,
Vikram and I met yesterday, and we agreed that I should help you get this working. Our current plan is to see if I can get the pool querying interface for poolalloc working again; since your pass will be a simple analysis pass that doesn't require any other passes, we can probably get this to work even though it breaks the "a pass should either be an analysis pass or a transform pass but not both" rule.
I've started looking into poolalloc and the existing pool query interface. I'll let you know what I come up with.
Okay. I think I have a basic prototype working. Attached is a patch to poolalloc (you can apply it with patch -p0 < papatch in the poolalloc source tree) that adds a getPool() method to the poolalloc pass. Simply call it with the Value* of the value you want the pool for and the function in which the value is being used, and you should get a Value* back that represents the region.
To get the region's type, use the getDSNode() method of poolalloc. It should take the same parameters as getPool().
I've only done a spot test, so bugs are quite possible. Please let me know if you have any problems with the code.
I've been trying to move away from having passes query poolalloc about regions (since it breaks assumptions imposed by LLVM's pass manager and requires that I disable -Werror in the Makefiles to permit compilation), so I haven't committed the code to the poolalloc SVN repository.
-- John T.
Index: include/poolalloc/PoolAllocate.h
===================================================================
--- include/poolalloc/PoolAllocate.h (revision 169129)
+++ include/poolalloc/PoolAllocate.h (working copy)
@@ -160,6 +160,7 @@
PoolAllocateGroup (char * IDp = &ID) : ModulePass (*IDp) { }
virtual ~PoolAllocateGroup () {return;}
+ virtual bool runOnModule(Module &M);
virtual PA::FuncInfo *getFuncInfo(const Function &F) { return 0;}
virtual PA::FuncInfo *getFuncInfoOrClone(const Function &F) {return 0;}
@@ -189,6 +190,7 @@
virtual Value * getGlobalPool (const DSNode * Node) {return 0;}
+ Value * getPoolHandle (const Value *V, Function *F) {return 0;}
};
/// PoolAllocate - The main pool allocation pass
@@ -360,6 +362,12 @@
//
virtual Value * getPool (const DSNode * N, Function & F) {
//
+ // If the DSNode is NULL, then there is no pool.
+ //
+ if (!N)
+ return 0;
+
+ //
// Grab the structure containing information about the function and its
// clones.
//
@@ -420,6 +428,112 @@
return I->second;
}
+ DSNode *
+ getDSNodeForGlobalVariable(const GlobalValue * GV) {
+ if (isa<Function>(GV))
+ return 0;
+ DSGraph * GlobalsGraph = getGlobalsGraph ();
+ DSNode * Node = GlobalsGraph->getNodeForValue(GV).getNode();
+ if (Node) {
+ // Fast-path
+ return Node;
+ } else if (isa<GlobalAlias>(GV)) {
+ // DSA does not handle this...
+ return NULL;
+ } else {
+ // We have to dig into the globalEC of the DSGraph to find the DSNode.
+ const GlobalValue * V =
GlobalsGraph->getGlobalECs().getLeaderValue(GV);
+ return GlobalsGraph->getNodeForValue(V).getNode();
+ }
+ }
+
+ DSNode* getDSNode (const Value *VOrig, Function *F) {
+ //
+ // If this function has a clone, then try to grab the original.
+ //
+ bool isClone = false;
+ Value * Vnew = (Value *)(VOrig);
+ if (!(getFuncInfo(*F))) {
+ isClone = true;
+ F = getOrigFunctionFromClone(F);
+ if (!F) return 0;
+ PA::FuncInfo *FI = getFuncInfoOrClone(*F);
+ if (!FI->NewToOldValueMap.empty()) {
+ Vnew = FI->MapValueToOriginal (Vnew);
+ }
+ assert (F && "No Function Information from Pool Allocation!\n");
+ }
+
+ // Ensure that the function has a DSGraph
+ assert (hasDSGraph(*F) && "No DSGraph for function!\n");
+
+ //
+ // Lookup the DSNode for the value in the function's DSGraph.
+ //
+ const Value * V = (Vnew) ? Vnew : VOrig;
+ DSGraph * TDG = getDSGraph(*F);
+ DSNode *DSN = TDG->getNodeForValue(V).getNode();
+
+ if (DSN) {
+ return DSN;
+ } else if (isa<GlobalValue>(V)) {
+ //
+ // If the value wasn't found in the function's DSGraph, then maybe we
can
+ // find the value in the globals graph.
+ //
+ return getDSNodeForGlobalVariable(cast<GlobalValue>(V));
+ } else {
+ // Not much we can do
+ return NULL;
+ }
+
+ return DSN;
+ }
+
+ //
+ // Method: getPoolHandle()
+ //
+ // Description:
+ // Return the pool handle assigned to this value.
+ //
+ // Inputs:
+ // V - The value for which we seek the pool handle.
+ // F - The function in which the value is used.
+ //
+ // Return value:
+ // 0 - No pool handle was found.
+ // Otherwise, returns either the pool handle or a pointer to a NULL pool
+ // handle.
+ //
+ Value *
+ getPoolHandle (const Value *V, Function *F) {
+ //
+ // First, strip all pointers casts off of the value. In some cases,
+ // additional casts have been added for which we cannot find the pool
+ // handle. Since a cast should exist within the same pool as the
original
+ // pointer, just find the original pointer.
+ //
+ V = V->stripPointerCasts();
+
+ //
+ // Get the DSNode for the value. Don't worry about mapping back to the
+ // original function because getDSNode() will take care of that for us.
+ //
+ const DSNode *Node = getDSNode (V, F);
+
+ //
+ // Get the pool handle from the pool allocation pass. Use the original
+ // function because we want to ensure that whatever pool handle we get
back
+ // is accessible from the function.
+ //
+ Value * PH = this->getPool (Node, *F);
+
+ //
+ // If we found the pool handle, then return it to the caller.
+ //
+ return PH;
+ }
+
/// getNumInitialPoolArguments - If the passed function name is recognized
/// as a runtime check, return the number of initial pool arguments for
/// the runtime check. Otherwise return 0.
Index: include/LinkPA.h
===================================================================
--- include/LinkPA.h (revision 169129)
+++ include/LinkPA.h (working copy)
@@ -1,6 +1,6 @@
namespace {
- struct ForceDSALinking {
- ForceDSALinking() {
+ struct ForcePALinking {
+ ForcePALinking() {
// We must reference the passes in such a way that compilers will not
// delete it all as dead code, even with whole program optimization,
// yet is effectively a NO-OP. As the compiler isn't smart enough
@@ -9,15 +9,8 @@
return;
(void)new EntryPointAnalysis();
- (void)new llvm::BasicDataStructures();
- (void)new llvm::LocalDataStructures();
- (void)new llvm::StdLibDataStructures();
- (void)new llvm::BUDataStructures();
- (void)new llvm::CompleteBUDataStructures();
- (void)new llvm::EquivBUDataStructures();
- (void)new llvm::TDDataStructures();
- (void)new llvm::EQTDDataStructures();
- (void)new llvm::RTAssociate();
+ (void)new llvm::PoolAllocate();
+ (void)new llvm::PoolAllocateGroup();
}
- } ForceDSALinking; // Force link by creating a global definition.
+ } ForcePALinking; // Force link by creating a global definition.
}
Index: lib/PoolAllocate/PoolAllocate.cpp
===================================================================
--- lib/PoolAllocate/PoolAllocate.cpp (revision 169129)
+++ lib/PoolAllocate/PoolAllocate.cpp (working copy)
@@ -222,6 +222,10 @@
AU.addRequired<DataLayout>();
}
+bool PoolAllocateGroup::runOnModule(Module &M) {
+ return false;
+}
+
bool PoolAllocate::runOnModule(Module &M) {
if (M.begin() == M.end()) return false;
CurModule = &M;
Index: Makefile.common.in
===================================================================
--- Makefile.common.in (revision 169129)
+++ Makefile.common.in (working copy)
@@ -19,7 +19,7 @@
# Set the root directory of this project's install prefix
PROJ_INSTALL_ROOT := @prefix@
-CXXFLAGS += -Werror -Wall -Wno-deprecated
+CXXFLAGS += -Wall -Wno-deprecated
#
# Paths to various utilities
- Re: [svadev] sva types, John Criswell, 12/03/2012
Archive powered by MHonArc 2.6.16.