Goddess of Justice DB, the database used for storage on IzaroDFS
Vous ne pouvez pas sélectionner plus de 25 sujets Les noms de sujets doivent commencer par une lettre ou un nombre, peuvent contenir des tirets ('-') et peuvent comporter jusqu'à 35 caractères.
 
 
 

113 lignes
3.4 KiB

#include <chrono>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <string.h>
#include <sstream>
#include <string>
#include <endian.hpp>
#include <network.hpp>
#include <array>
#include <thread>
#include <algorithm>
using namespace std::chrono_literals;
int main(int, char** argv){
int64_t offset=0;
std::array<int64_t, 4096> offsets;
std::array<int64_t, 4096> offsets_smooth;
std::array<int64_t, 4096> offset_variations;
size_t pos = 0;
int64_t max_offset_variation;
int64_t max_oscillation = 0;
int64_t min_ever = std::numeric_limits<int64_t>::max();
int64_t max_ever = 0;
std::stringstream ip_stream{argv[1]};
std::array<uint8_t, 4> ip;
std::string token;
std::getline(ip_stream, token, '.');
ip[0] = std::stoi(token);
std::getline(ip_stream, token, '.');
ip[1] = std::stoi(token);
std::getline(ip_stream, token, '.');
ip[2] = std::stoi(token);
std::getline(ip_stream, token, '.');
ip[3] = std::stoi(token);
uint16_t port = std::stoi(argv[2]);
auto soc = socket(AF_INET, SOCK_DGRAM, 0);
struct sockaddr_in server;
server.sin_family = AF_INET;
server.sin_addr.s_addr = *(in_addr_t*)ip.data();
server.sin_port = htons(port);
struct timeval tv;
tv.tv_sec = 5;
tv.tv_usec = 0;
setsockopt(soc, SOL_SOCKET, SO_RCVTIMEO, (const char*)&tv, sizeof tv);
std::cerr << "Connecting..." <<std::endl;
connect(soc, (struct sockaddr*)&server, sizeof(server));
req_rep buffer;
uint64_t cnt = 0;
uint64_t old_time = 0;
while(true)
{
uint64_t tmp;
buffer.id = 16;
buffer.client_ts = std::chrono::duration_cast<std::chrono::microseconds>(std::chrono::high_resolution_clock::now().time_since_epoch()).count();
send(soc, (void*)&buffer, (socklen_t)sizeof(req_rep), 0);
recv(soc, (void*)&buffer, (socklen_t)sizeof(req_rep), 0);
if(buffer.server_ts != old_time)
{
tmp = std::chrono::duration_cast<std::chrono::microseconds>(std::chrono::high_resolution_clock::now().time_since_epoch()).count() - buffer.client_ts;
int64_t n_offset = std::chrono::duration_cast<std::chrono::microseconds>(std::chrono::high_resolution_clock::now().time_since_epoch()).count() - buffer.server_ts;
n_offset /= 2;
offset_variations[pos] = ((long long)(offset-n_offset));
if(cnt != 0)
{
offsets[pos] = n_offset;
} else {
offsets.fill(n_offset);
offsets_smooth.fill(n_offset);
}
max_offset_variation = std::max(*std::max_element(offset_variations.begin(), offset_variations.end()), std::abs((int64_t)*std::min_element(offset_variations.begin(), offset_variations.end())));
offset = (
7 * (std::accumulate(offsets_smooth.begin(), offsets_smooth.end(), 0)/offsets_smooth.size())
+ std::accumulate(offsets.begin(), offsets.end(), 0)/offsets.size()
) / 8;
offsets_smooth[pos] = offset;
pos=(pos+1)%offset_variations.size();
if(cnt > offsets.size()*2)
{
for(auto i : offsets_smooth)
for(auto j : offsets_smooth)
{
max_oscillation = std::max(
std::abs(i-j),
max_oscillation
);
}
min_ever = std::min(min_ever, offset);
max_ever = std::max(max_ever, offset);
}
else if (cnt < offsets.size()) {
offsets_smooth[pos] = n_offset;
}
old_time = buffer.server_ts;
std::cout << cnt << "\t"<< min_ever << "\t" << offset << "\t" << max_ever << "\t" << max_oscillation << "\t" << offset-n_offset << "\t" << max_offset_variation <<std::endl;
}
cnt++;
//std::this_thread::sleep_for(6ms);
}
}