* @param action The ModelAction to find a node for
* @return The CycleNode paired with this action
*/
-CycleNode * CycleGraph::getNode(const ModelAction *action)
+CycleNode * CycleGraph::getNode(ModelAction *action)
{
CycleNode *node = getNode_noCreate(action);
if (node == NULL) {
/* Propagate clock vector changes */
if (tonode->cv->merge(fromnode->cv)) {
- queue->push_back(fromnode);
+ queue->push_back(tonode);
while(!queue->empty()) {
const CycleNode *node = queue->back();
queue->pop_back();
* @param rmw The edge points to this ModelAction; this action must read from
* the ModelAction from
*/
-void CycleGraph::addRMWEdge(const ModelAction *from, const ModelAction *rmw)
+void CycleGraph::addRMWEdge(ModelAction *from, ModelAction *rmw)
{
ASSERT(from);
ASSERT(rmw);
if (tonode != rmwnode) {
rmwnode->addEdge(tonode);
}
+ tonode->removeInEdge(fromnode);
}
fromnode->edges.clear();
-
+
addNodeEdge(fromnode, rmwnode, true);
}
+void CycleGraph::addEdges(SnapList<ModelAction *> * edgeset, ModelAction *to) {
+ for(sllnode<ModelAction*> * it = edgeset->begin();it!=NULL;) {
+ ModelAction *act = it->getVal();
+ CycleNode *node = getNode(act);
+ sllnode<ModelAction*> * it2 = it;
+ it2=it2->getNext();
+ for(;it2!=NULL; ) {
+ ModelAction *act2 = it2->getVal();
+ CycleNode *node2 = getNode(act2);
+ if (checkReachable(node, node2)) {
+ it = edgeset->erase(it);
+ goto endouterloop;
+ } else if (checkReachable(node2, node)) {
+ it2 = edgeset->erase(it2);
+ goto endinnerloop;
+ }
+ it2=it2->getNext();
+endinnerloop:
+ ;
+ }
+ it=it->getNext();
+endouterloop:
+ ;
+ }
+ for(sllnode<ModelAction*> *it = edgeset->begin();it!=NULL;it=it->getNext()) {
+ ModelAction *from = it->getVal();
+ addEdge(from, to, from->get_tid() == to->get_tid());
+ }
+}
+
/**
* @brief Adds an edge between objects
*
* @return True, if new edge(s) are added; otherwise false
*/
-void CycleGraph::addEdge(const ModelAction *from, const ModelAction *to)
+void CycleGraph::addEdge(ModelAction *from, ModelAction *to)
{
ASSERT(from);
ASSERT(to);
addNodeEdge(fromnode, tonode, false);
}
-void CycleGraph::addEdge(const ModelAction *from, const ModelAction *to, bool forceedge)
+void CycleGraph::addEdge(ModelAction *from, ModelAction *to, bool forceedge)
{
ASSERT(from);
ASSERT(to);
return checkReachable(fromnode, tonode);
}
+void CycleGraph::freeAction(const ModelAction * act) {
+ CycleNode *cn = actionToNode.remove(act);
+ for(unsigned int i=0;i<cn->edges.size();i++) {
+ CycleNode *dst = cn->edges[i];
+ dst->removeInEdge(cn);
+ }
+ for(unsigned int i=0;i<cn->inedges.size();i++) {
+ CycleNode *src = cn->inedges[i];
+ src->removeEdge(cn);
+ }
+ delete cn;
+}
+
/**
* @brief Constructor for a CycleNode
* @param act The ModelAction for this node
*/
-CycleNode::CycleNode(const ModelAction *act) :
+CycleNode::CycleNode(ModelAction *act) :
action(act),
hasRMW(NULL),
cv(new ClockVector(NULL, act))
{
}
+CycleNode::~CycleNode() {
+ delete cv;
+}
+
+void CycleNode::removeInEdge(CycleNode *src) {
+ for(unsigned int i=0;i < inedges.size();i++) {
+ if (inedges[i] == src) {
+ inedges[i] = inedges[inedges.size()-1];
+ inedges.pop_back();
+ break;
+ }
+ }
+}
+
+void CycleNode::removeEdge(CycleNode *dst) {
+ for(unsigned int i=0;i < edges.size();i++) {
+ if (edges[i] == dst) {
+ edges[i] = edges[edges.size()-1];
+ edges.pop_back();
+ break;
+ }
+ }
+}
+
/**
* @param i The index of the edge to return
* @returns The CycleNode edge indexed by i
}
/**
- * @brief Remove a (forward) edge from this CycleNode
- * @return The CycleNode which was popped, if one exists; otherwise NULL
+ * @param i The index of the edge to return
+ * @returns The CycleNode edge indexed by i
*/
-CycleNode * CycleNode::removeEdge()
+CycleNode * CycleNode::getInEdge(unsigned int i) const
{
- if (edges.empty())
- return NULL;
+ return inedges[i];
+}
- CycleNode *ret = edges.back();
- edges.pop_back();
- return ret;
+/** @returns The number of edges leaving this CycleNode */
+unsigned int CycleNode::getNumInEdges() const
+{
+ return inedges.size();
}
/**
if (edges[i] == node)
return;
edges.push_back(node);
+ node->inedges.push_back(this);
}
/** @returns the RMW CycleNode that reads from the current CycleNode */