Add implementation

This commit is contained in:
Bob Polis 2024-01-23 16:23:11 +01:00
parent 41244b0a70
commit b2e1b47d31
2 changed files with 90 additions and 0 deletions

60
src/timer.cpp Normal file
View File

@ -0,0 +1,60 @@
#include <bits/types/struct_itimerspec.h>
#include <cmath>
#include <signal.h>
#include <time.h>
#include <libscerror.hpp>
#include "timer.hpp"
using namespace sc;
uint64_t timer::next_id = 0;
std::mutex timer::mutex;
timer::timer(void(*callback)(union sigval), double time, bool repeat)
: _id {}, _time {time}, _repeat {repeat}
{
{
std::lock_guard<std::mutex> lock {mutex};
_id = ++next_id;
}
struct sigevent se;
se.sigev_notify = SIGEV_THREAD;
se.sigev_value.sival_int = 0;
se.sigev_value.sival_ptr = &_id;
se.sigev_notify_function = callback;
se.sigev_notify_attributes = nullptr;
throw_if_min1_msg(timer_create(CLOCK_MONOTONIC, &se, &_tid), "could not create timer");
time_t secs = floor(time / 1000);
long ns = (time - 1000 * secs) * 1000000;
struct itimerspec its;
its.it_value.tv_sec = secs;
its.it_value.tv_nsec = ns;
if (repeat) {
its.it_interval.tv_sec = secs;
its.it_interval.tv_nsec = ns;
} else {
its.it_interval.tv_sec = 0;
its.it_interval.tv_nsec = 0;
}
throw_if_min1_msg(timer_settime(_tid, 0, &its, nullptr), "could not set timer");
}
timer::~timer() {
throw_if_min1_msg(timer_delete(_tid), "could not delete timer");
}
void timer::time(struct itimerspec& cur_value) const {
throw_if_min1_msg(timer_gettime(_tid, &cur_value), "could not get time");
}
double timer::time() const {
struct itimerspec its;
time(its);
return its.it_value.tv_sec + its.it_value.tv_nsec * 1000000000;
}
bool timer::is_armed() const {
struct itimerspec its;
time(its);
return its.it_value.tv_sec != 0 || its.it_value.tv_nsec != 0;
}

30
src/timer.hpp Normal file
View File

@ -0,0 +1,30 @@
#ifndef _timer_H_
#define _timer_H_
#include <cstdint>
#include <mutex>
namespace sc {
class timer {
static uint64_t next_id;
static std::mutex mutex;
timer_t _tid;
uint64_t _id;
double _time;
bool _repeat;
public:
timer(void(*callback)(union sigval), double time, bool repeat = false);
~timer();
void time(struct itimerspec& cur_value) const;
double time() const;
bool is_armed() const;
bool repeat() const { return _repeat; }
};
}
#endif // _timer_H_