Posix線程肯定授予之間前臺和後臺任務更快的通信速度,但如果你想精密我會建議使用clock_nanosleep跟蹤的時間在一個實時內核之上。
您可以使用以下基本功能來塑造你的任務生命週期:
#ifndef __TIMERS_H__
#define __TIMERS_H__
#include <stdint.h> /* uint64_t */
#include <time.h> /* clockid_t of clock_nanosleep() */
/*--------------------------------------------------------------------------------------*/
/* Common facility functions needed for
* high precision timers usage
*/
/*--------------------------------------------------------------------------------------*/
#define SEC_VAL 1000000000ULL
enum return_values {
RETURN_FAILURE = 0,
RETURN_SUCCESS = 1,
RETURN_EMPTY = 2
};
typedef void* timespec_ptr;
typedef struct timespec timespec_t;
/* Adds time_us microseconds to timer ts
*/
void timespec_add_ns(timespec_ptr ts,
uint64_t time_ns);
/* Makes the thread wait for the next activation of the timer ts
*/
void wait_next_activation(timespec_ptr ts); /*** @ Tasks ***/
/* Starts the periodic timer
*/
int start_periodic_timer(timespec_ptr ts,
uint64_t init_offs_ns);
/* Computes the difference among two clocks
*/
long calcdiff(struct timespec t1,
struct timespec t2);
/*--------------------------------------------------------------------------------------*/
extern int clock_nanosleep(clockid_t clock_id, int flags,
const struct timespec* request,
struct timespec* remain);
/*--------------------------------------------------------------------------------------*/
#endif
這裏有實現文件:
#include "timers.h"
#include <stdio.h> /* fprintf */
/*--------------------------------------------------------------------------------------*/
/* Adds time_us microseconds to timer ts
*/
void timespec_add_ns(timespec_ptr ts,
uint64_t time_ns)
{
if (ts)
{
timespec_t* ts_ = (timespec_t*) ts;
time_ns += ts_->tv_nsec;
ts_->tv_sec += time_ns/SEC_VAL;
ts_->tv_nsec = time_ns%SEC_VAL;
} else {
fprintf(stderr, "Warning (%s): input argument is NULL, \
request ignored.\n", __FUNCTION__);
}
}
/* Makes the thread wait for the next activation of the timer ts
*/
void wait_next_activation(timespec_ptr ts)
{
if (ts)
{
timespec_t* ts_ = (timespec_t*) ts;
clock_nanosleep(CLOCK_MONOTONIC, TIMER_ABSTIME, ts_, NULL);
} else {
fprintf(stderr, "Warning (%s): input parameter is NULL, \
request ignored.\n", __FUNCTION__);
}
}
/* Starts the periodic timer
*/
int start_periodic_timer(timespec_ptr ts,
uint64_t init_offs_ns) /*** @ Tasks ***/
{
if (ts)
{
timespec_t* ts_ = (timespec_t*) ts;
clock_gettime(CLOCK_MONOTONIC, ts_);
timespec_add_ns(ts, init_offs_ns);
return RETURN_SUCCESS;
} else {
fprintf(stderr, "Warning (%s): input parameter is NULL, \
request ignored.\n", __FUNCTION__);
return RETURN_FAILURE;
}
}
/* Computes the difference among two clocks
*/
long calcdiff(struct timespec t1,
struct timespec t2) /*** @ Tasks ***/
{
long diff;
diff = SEC_VAL * ((int) t1.tv_sec - (int) t2.tv_sec);
diff += ((int) t1.tv_nsec - (int) t2.tv_nsec);
return diff;
}
/*--------------------------------------------------------------------------------------*/
後臺任務應主要做到以下幾點:
void run (void *args) {
start_periodict_timer(&timer_, offset);
while (true) {
wait_next_activation(&timer_);
timespec_add_ns(&timer_, period);
/* do your periodic task */
}
}
其中偏移我是您開始執行任務時等待的初始時間,而期間是您在一次調用任務和另一次調用之間等待的時間。
你有什麼理由爲什麼你現在的解決方案不夠好? –
嗯,是的。 std :: sleep_for不是很準確,所以我必須在非常小的時間間隔內執行,並檢查是否已調用loopFunction()的時間。在其他線程中,人們也表示計時時間測量非常昂貴。 – keyboard
@keyboard - 由於我犯有提及定時器可能代價高昂的問題,因此將使用的實際增量時間是多少?如果它真的是0.0166,不要介意我對定時器性能的評論(除非你啓動100個並行線程)。再一次,如果你真的想要性能,在每個平臺上使用本機等待計時器,但我認爲這樣的超時時間太長了。 –