libevent: сделать таймер постоянным

У меня есть следующий код:

#include <stdio.h>
#include <sys/time.h>
#include <event.h>

void say_hello(int fd, short event, void *arg){
        printf("Hello\n");
}

int main(int argc, const char* argv[])
{
  struct event ev;
  struct timeval tv;

  tv.tv_sec = 3;
  tv.tv_usec = 0;

  event_init();
  evtimer_set(&ev,say_hello,NULL);
  evtimer_add(&ev, &tv);
  event_dispatch();

  return 0;
}

Проблема в том, что "привет" печатается один раз, а затем программа завершает работу...

Я хочу, чтобы он выводил «привет» на неопределенный срок.

Как это сделать? Спасибо заранее,


person Eamorr    schedule 27.11.2012    source источник


Ответы (5)


Просто чтобы уточнить решение Базиля:

Я тоже был в замешательстве, пока не понял, что "таймер" в этом контексте относится к таймеру одиночного выстрела. Нам нужен интервальный таймер; для этого требуется флаг EV_PERSIST в libevent.

struct timeval time;
time.tv_sec = 1;
time.tv_usec = 0;

event_set(&my_event, 0, EV_PERSIST, my_function, NULL);
evtimer_add(&my_event, &time);
person seo    schedule 22.07.2013

измените код в main для чтения

evtimer_set(&ev,say_hello,&ev);

и сделайте свою функцию say_hello

void say_hello(int fd, short event, void *arg){
    struct event *ev = arg;
    struct timeval tv;


    printf("Hello\n");
    tv.tv_sec = 3;
    tv.tv_usec = 0;

    evtimer_add(ev, &tv);
}
person nos    schedule 24.08.2013
comment
Это единственный правильный ответ на этой странице, который относится к версии библиотеки libevent (1.4.x), о которой спрашивал OP. - person quant; 06.09.2015

Вот пример для libevent2:

#include <event2/event.h>

static int n_calls = 0;

void cb_func(evutil_socket_t fd, short what, void *arg)
{
    struct event *me = arg;

    printf("cb_func called %d times so far.\n", ++n_calls);

    if (n_calls > 100)
       event_del(me);
}

void run(struct event_base *base)
{
    struct timeval one_sec = { 1, 0 };
    struct event *ev;
    /* We're going to set up a repeating timer to get called called 100
       times. */
    ev = event_new(base, -1, EV_PERSIST, cb_func, event_self_cbarg());
    event_add(ev, &one_sec);
    event_base_dispatch(base);
}
person Guy L    schedule 06.10.2014

Вы читали evtimer_set(3) справочную страницу? Пожалуйста, прочтите еще раз.

Вероятно, вы захотите использовать флаг EV_PERSIST или вызвать evtimer_add из обратного вызова say_hello.

person Basile Starynkevitch    schedule 27.11.2012
comment
Я использую не libevent2, а libevent1.4, как в Ubuntu 12.04.1. - person Eamorr; 27.11.2012
comment
Как повторно запустить таймер в функции обратного вызова? Спасибо, - person Eamorr; 27.11.2012

#include <stdio.h>
#include "ev.h"

static void timer_cback_caller(EV_P_ ev_timer* w, int revents)
{
    const int new_timeout_in_ms = 1200; // new delay between timer ticks

    printf("timer tick\n");

    w->repeat = new_timeout_in_ms / 1000.;
    ev_timer_again(EV_A_ w);
}


int main()
{
    struct ev_loop *loop = ev_default_loop(0);
    ev_timer timer;

    const int start_delay_in_ms = 1000; // delay before first timer tick
    const int timeout_in_ms = 1500; // delay between every timer tick

    ev_timer_init(&timer, timer_cback_caller, start_delay_in_ms/1000., timeout_in_ms/1000.);
    ev_timer_start(loop, &timer);
    ev_run(loop, 0); // will never return

    return 0;
}

Дополнительные примеры в документации libev

person vasily-vm    schedule 21.09.2018