-
Notifications
You must be signed in to change notification settings - Fork 14
/
Copy pathserver.cpp
117 lines (91 loc) · 2.78 KB
/
server.cpp
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
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
#include <capnp/ez-rpc.h>
#include <capnp/message.h>
#include <iostream>
#include <thread>
#include "log.hpp"
#include "schema.capnp.h"
#include "server.hpp"
namespace kvak::server {
class ChannelImpl : public Service::Channel::Server {
public:
ChannelImpl(kvak::channel &channel, std::mutex &mutex)
:
channel(channel),
mutex(mutex)
{
}
kj::Promise<void> getInfo(Service::Channel::Server::GetInfoContext context) override
{
auto results = context.getResults();
results.initInfo();
auto info = results.getInfo();
// This is slightly iffy - The client is going to do something like:
// for ch in channels:
// ch.getInfo()
// Releasing and relocking the mutex again and again, which could
// possibly leading to very large latency
std::lock_guard<std::mutex> lock(this->mutex);
//auto chinfo = this->demod.get_info();
info.setTimingOffset(this->channel.demod.get_timing_offset());
info.setFrequencyOffset(this->channel.demod.get_frequency_offset());
info.setPowerLevel(this->channel.get_power()); // Not yet implemented
info.setIsMuted(this->channel.is_muted());
return kj::READY_NOW;
}
kj::Promise<void> mute(Service::Channel::Server::MuteContext context) override
{
auto params = context.getParams();
std::lock_guard<std::mutex> lock(this->mutex);
this->channel.mute(params.getMute());
return kj::READY_NOW;
}
private:
kvak::channel &channel;
std::mutex &mutex;
};
class ServiceImpl : public Service::Server {
public:
ServiceImpl(std::vector<kvak::channel> &channels, std::mutex &mutex)
:
start_time(std::chrono::steady_clock::now()),
channels(channels),
mutex(mutex)
{
}
kj::Promise<void> getInfo(Service::Server::GetInfoContext context) override
{
auto results = context.getResults();
results.initInfo();
auto info = results.getInfo();
std::chrono::duration<double> diff =
std::chrono::steady_clock::now() - this->start_time;
info.setUptime(diff.count());
return kj::READY_NOW;
}
kj::Promise<void> listChannels(Service::Server::ListChannelsContext context) override
{
auto results = context.getResults();
std::lock_guard<std::mutex> lock(this->mutex);
results.initList(this->channels.size());
auto list = results.getList();
for (std::size_t i = 0; i < this->channels.size(); i++) {
list.set(i, kj::heap<ChannelImpl>(channels[i], this->mutex));
}
return kj::READY_NOW;
}
private:
std::chrono::steady_clock::time_point start_time;
std::vector<kvak::channel> &channels;
std::mutex &mutex;
};
server::server(const std::string &bind,
std::vector<kvak::channel> &channels,
std::mutex &mutex)
:
ezrpc(kj::heap<ServiceImpl>(channels, mutex), bind)
{
kvak::log::info << "Server starting up on " << bind;
kj::NEVER_DONE.wait(this->ezrpc.getWaitScope());
kvak::log::info << "Server finished";
}
}