blob: 7692c9f7a72275661e8c0311b9385ef83748d18a [file] [log] [blame]
Kostya Serebryanybe1d22b2014-02-12 11:28:09 +00001//===-- sanitizer_bvgraph.h -------------------------------------*- C++ -*-===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9//
10// This file is a part of Sanitizer runtime.
11// BVGraph -- a directed graph.
12//
13//===----------------------------------------------------------------------===//
14
15#ifndef SANITIZER_BVGRAPH_H
16#define SANITIZER_BVGRAPH_H
17
18#include "sanitizer_common.h"
19#include "sanitizer_bitvector.h"
20
21namespace __sanitizer {
22
23// Directed graph of fixed size implemented as an array of bit vectors.
24template<class BV>
25class BVGraph {
26 public:
27 enum SizeEnum { kSize = BV::kSize };
28 uptr size() const { return kSize; }
29 // No CTOR.
30 void clear() {
31 for (uptr i = 0; i < size(); i++)
32 v[i].clear();
33 }
34
35 // Returns true if a new edge was added.
36 bool addEdge(uptr from, uptr to) {
37 check(from|to);
38 return v[from].setBit(to);
39 }
40
41 bool hasEdge(uptr from, uptr to) const {
42 check(from|to);
43 return v[from].getBit(to);
44 }
45
46 // Returns true if there is a path from the node 'from'
47 // to any of the nodes in 'target'.
48 bool isReachable(uptr from, const BV &target) {
49 BV to_visit, visited;
50 to_visit.clear();
51 to_visit.setUnion(v[from]);
52 visited.clear();
53 visited.setBit(from);
54 while (!to_visit.empty()) {
55 uptr idx = to_visit.getAndClearFirstOne();
56 if (visited.setBit(idx))
57 to_visit.setUnion(v[idx]);
58 }
59 return target.intersectsWith(visited);
60 }
61
62 private:
63 void check(uptr idx) const { CHECK_LE(idx, size()); }
64 BV v[kSize];
65};
66
67} // namespace __sanitizer
68
69#endif // SANITIZER_BVGRAPH_H