-
Notifications
You must be signed in to change notification settings - Fork 0
/
page_tracker.h
93 lines (75 loc) · 1.66 KB
/
page_tracker.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
#ifndef SLOPE_PAGE_TRACKER_H_
#define SLOPE_PAGE_TRACKER_H_
#include <condition_variable>
#include <cstdint>
#include <cstdio>
#include <cstdlib>
#include <map>
#include <mutex>
#include <set>
#include "debug.h"
namespace slope {
namespace ds {
namespace impl {
template <typename T>
class PriorityChannel {
std::condition_variable cv_;
std::set<T> q_;
std::mutex m_;
bool is_closed_;
public:
PriorityChannel() : is_closed_(false) {}
T block_to_pop() {
std::unique_lock<std::mutex> lk(m_);
cv_.wait(lk, [&] { return !q_.empty() || is_closed_; });
if (q_.empty()) {
throw std::exception();
}
auto ret = std::move(*q_.begin());
q_.erase(q_.begin());
lk.unlock();
cv_.notify_all();
return ret;
}
void close() {
{
std::lock_guard<std::mutex> lk(m_);
is_closed_ = 1;
}
cv_.notify_all();
}
void push(T&& val) {
{
std::lock_guard<std::mutex> lk(m_);
q_.insert(std::forward<T>(val));
}
cv_.notify_all();
}
};
} // namespace impl
struct Page {
uintptr_t addr;
uint32_t sz;
uint32_t lkey;
uint32_t remote_rkey;
Page(uintptr_t, uint32_t, uint32_t, uint32_t);
Page();
};
class PageTracker {
public:
void add(Page p);
void prioritize(uintptr_t addr);
Page pop();
void close();
enum class PageState : int { awaiting, prioritized, finalized };
enum class Priority : int { high = 0, low };
PageTracker();
private:
impl::PriorityChannel<std::pair<int, uintptr_t>> channel_;
std::mutex m_;
std::map<uintptr_t, PageState> page_states;
std::map<uintptr_t, Page> addr_to_page;
};
} // namespace ds
} // namespace slope
#endif // SLOPE_PAGE_TRACKER_H_