+/**
+ * Checks whether one ModelAction/Promise can reach another ModelAction/Promise
+ * @param from The ModelAction or Promise from which to begin exploration
+ * @param to The ModelAction or Promise to reach
+ * @return True, @a from can reach @a to; otherwise, false
+ */
+template <typename T, typename U>
+bool CycleGraph::checkReachable(const T *from, const U *to) const
+{
+ CycleNode *fromnode = getNode_noCreate(from);
+ CycleNode *tonode = getNode_noCreate(to);
+
+ if (!fromnode || !tonode)
+ return false;
+
+ return checkReachable(fromnode, tonode);
+}
+/* Instantiate four forms of CycleGraph::checkReachable */
+template bool CycleGraph::checkReachable(const ModelAction *from,
+ const ModelAction *to) const;
+template bool CycleGraph::checkReachable(const ModelAction *from,
+ const Promise *to) const;
+template bool CycleGraph::checkReachable(const Promise *from,
+ const ModelAction *to) const;
+template bool CycleGraph::checkReachable(const Promise *from,
+ const Promise *to) const;
+
+/** @return True, if the promise has failed; false otherwise */
+bool CycleGraph::checkPromise(const ModelAction *fromact, Promise *promise) const
+{
+ discovered->reset();
+ queue->clear();
+ CycleNode *from = actionToNode.get(fromact);
+
+ queue->push_back(from);
+ discovered->put(from, from);
+ while (!queue->empty()) {
+ const CycleNode *node = queue->back();
+ queue->pop_back();
+
+ if (node->getPromise() == promise)
+ return true;
+ if (!node->is_promise())
+ promise->eliminate_thread(node->getAction()->get_tid());
+
+ for (unsigned int i = 0; i < node->getNumEdges(); i++) {
+ CycleNode *next = node->getEdge(i);
+ if (!discovered->contains(next)) {
+ discovered->put(next, next);
+ queue->push_back(next);