1

我不明白 EVLOOP_NO_EXIT_ON_EMPTY 标志应该如何在 libevent 的 2.1.x 版本中工作。

如果我不向我的 event_base 添加任何事件

event_base_loop(my_base, EVLOOP_NO_EXIT_ON_EMPTY);

call 立即返回,这根本不是我认为应该做的。

如果我添加一个事件,它会与该未决事件循环,直到它被激活,然后循环退出,我希望不会发生。

目标:

有一个命名管道打开和 libevent 监听读取。每当我

echo "something" > pipe

应该调用注册的回调。如果回调已完成,则事件将返回到挂起状态,并且循环等待另一个回显。

这是我到目前为止得到的:(省略了错误检查)

#include <fcntl.h>
#include <stdio.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <event.h>
#include <unistd.h>

#define PIPE "/tmp/ev_pipe"


void cb_func(evutil_socket_t fd, short what, void *arg)
{
  printf("foo\n");
}

int main(void)
{
  /* create & open named pipe */
  mkfifo(PIPE, 0666);
  int socket = open(PIPE, O_RDONLY | O_NONBLOCK);

  /* libevent specific stuff */
  struct event_base *ev_base = event_base_new();
  struct event *ev = event_new(ev_base, (evutil_socket_t) socket, EV_READ, cb_func, NULL);
  event_add(ev, NULL);

  /* loop forever */
  event_base_loop(ev_base, EVLOOP_NO_EXIT_ON_EMPTY);

  printf("a\n");

  /* clean up */
  unlink(PIPE);
  event_base_free(ev_base);
  close(socket);

  return 0;
}

我错过了什么?事件循环在第一次写入队列后退出:/

谢谢你的帮助!

4

2 回答 2

1

该功能的实现看起来有问题!我在 2.1.x 版本中遇到了同样的问题。正如@Wizzard 指出的那样,解决这个问题的一种方法是。解决此问题的另一种方法是将标志 EV_PERSIST 或标记到函数 event_new 的 events 参数中:

struct event *ev = event_new(ev_base, 
    (evutil_socket_t) socket, EV_READ|EV_PERSIST, cb_func, NULL);

这将防止事件被删除。https://github.com/libevent/libevent/blob/master/include/event2/event.h +872

请注意,当管道上有数据时,您可能会收到多个回调。

于 2013-11-07T18:38:48.973 回答
0

只需使用event_base_dispatch (ev_base);代替event_base_loop ()``, it will loop and handle all attached events either until you explicitly delete all attached events or callevent_base_loopbreak()```函数。

于 2013-11-07T01:45:26.287 回答