on those platforms where "add, delete, dispatch" is not the same
as "no-op, dispatch", we want the no-op behavior.
+ As well as checking the current operation we should also check
+ the original set of events to make sure were not ignoring
+ the case where the add operation is present on an event that
+ was already set.
+
If we have a no-op item, we could remove it it from the list
entirely, but really there's not much point: skipping the no-op
change when we do the dispatch later is far cheaper than rejuggling
the array now.
+
+ As this stands, it also lets through deletions of events that are
+ not currently set.
*/
if (events & (EV_READ|EV_SIGNAL)) {
- if (change->read_change & EV_CHANGE_ADD)
+ if (!(change->old_events & (EV_READ | EV_SIGNAL)) &&
+ (change->read_change & EV_CHANGE_ADD))
change->read_change = 0;
else
change->read_change = EV_CHANGE_DEL;
}
if (events & EV_WRITE) {
- if (change->write_change & EV_CHANGE_ADD)
+ if (!(change->old_events & EV_WRITE) &&
+ (change->write_change & EV_CHANGE_ADD))
change->write_change = 0;
else
change->write_change = EV_CHANGE_DEL;
EXTRA_DIST = regress.rpc regress.gen.h regress.gen.c test.sh
noinst_PROGRAMS = test-init test-eof test-weof test-time regress \
- bench bench_cascade bench_http bench_httpclient test-ratelim
+ bench bench_cascade bench_http bench_httpclient test-ratelim \
+ test-changelist
noinst_HEADERS = tinytest.h tinytest_macros.h regress.h
TESTS = $(top_srcdir)/test/test.sh
test_init_LDADD = ../libevent_core.la
test_eof_SOURCES = test-eof.c
test_eof_LDADD = ../libevent_core.la
+test_changelist_SOURCES = test-changelist.c
+test_changelist_LDADD = ../libevent_core.la
test_weof_SOURCES = test-weof.c
test_weof_LDADD = ../libevent_core.la
test_time_SOURCES = test-time.c
verify: check
-bench test-init test-eof test-weof test-time: ../libevent.la
+bench test-init test-eof test-weof test-time test-changelist: ../libevent.la
regress_main.obj regress_minheap.obj regress_iocp.obj
OTHER_OBJS=test-init.obj test-eof.obj test-weof.obj test-time.obj \
- bench.obj bench_cascade.obj bench_http.obj bench_httpclient.obj
+ bench.obj bench_cascade.obj bench_http.obj bench_httpclient.obj \
+ test-changelist.obj
PROGRAMS=regress.exe \
- test-init.exe test-eof.exe test-weof.exe test-time.exe
+ test-init.exe test-eof.exe test-weof.exe test-time.exe \
+ test-changelist.exe
# Disabled for now:
# bench.exe bench_cascade.exe bench_http.exe bench_httpclient.exe
$(CC) $(CFLAGS) $(LIBS) test-init.obj
test-eof.exe: test-eof.obj
$(CC) $(CFLAGS) $(LIBS) test-eof.obj
+test-changelist.exe: test-changelist.obj
+ $(CC) $(CFLAGS) $(LIBS) test-changelist.obj
test-weof.exe: test-weof.obj
$(CC) $(CFLAGS) $(LIBS) test-weof.obj
test-time.exe: test-time.obj
--- /dev/null
+/*
+ * based on test-eof.c
+ */
+
+#include "event-config.h"
+
+#ifdef WIN32
+#include <winsock2.h>
+#else
+#include <unistd.h>
+#endif
+#include <sys/types.h>
+#include <sys/stat.h>
+#ifdef _EVENT_HAVE_SYS_TIME_H
+#include <sys/time.h>
+#endif
+
+
+
+#ifdef _EVENT_HAVE_SYS_SOCKET_H
+#include <sys/socket.h>
+#endif
+#include <fcntl.h>
+#include <stdlib.h>
+#include <stdio.h>
+#include <string.h>
+#include <errno.h>
+
+#include <event2/event.h>
+#include <event2/util.h>
+#include <time.h>
+
+
+static void
+write_cb(evutil_socket_t fd, short event, void *arg)
+{
+ printf("write callback. should only see this once\n");
+
+ /* got what we want remove the event */
+ event_del(*(struct event**)arg);
+
+ /* opps changed my mind add it back again */
+ event_add(*(struct event**)arg,NULL);
+
+ /* not a good day for decisiveness, I really didn't want it after all */
+ event_del(*(struct event**)arg);
+
+}
+
+static void
+timeout_cb(evutil_socket_t fd, short event, void *arg)
+{
+
+ char buf[256];
+ int len;
+
+ printf("timeout fired, time to end test\n");
+ event_del(*(struct event**)arg);
+ return;
+}
+
+int
+main(int argc, char **argv)
+{
+ struct event* ev;
+ struct event* timeout;
+ struct event_base* base;
+
+ int pair[2];
+ int res;
+ int tickspassed;
+ struct timeval timeBegin;
+ struct timeval timeEnd;
+ struct timeval tv;
+
+ clock_t ticksBegin;
+ clock_t ticksEnd;
+ double usage;
+
+#ifdef WIN32
+ WORD wVersionRequested;
+ WSADATA wsaData;
+ int err;
+
+ wVersionRequested = MAKEWORD(2, 2);
+
+ err = WSAStartup(wVersionRequested, &wsaData);
+#endif
+ if (evutil_socketpair(AF_UNIX, SOCK_STREAM, 0, pair) == -1)
+ return (1);
+
+ /* Initalize the event library */
+ base = event_base_new();
+
+ /* Initalize a timeout to terminate the test */
+ timeout = evtimer_new(base,timeout_cb,&timeout);
+ /* and watch for writability on one end of the pipe */
+ ev = event_new(base,pair[1],EV_WRITE | EV_PERSIST, write_cb, &ev);
+
+ tv.tv_sec = 5;
+ tv.tv_usec = 0;
+
+ evtimer_add(timeout, &tv);
+
+ event_add(ev, NULL);
+
+ ticksBegin = clock();
+
+ evutil_gettimeofday(&timeBegin,NULL);
+
+ res = event_base_dispatch(base);
+
+ evutil_gettimeofday(&timeEnd,NULL);
+
+ ticksEnd = clock();
+
+ /* attempt to calculate our cpu usage over the test should be
+ virtually nil */
+
+ tickspassed = ((((timeEnd.tv_sec - timeBegin.tv_sec) * 1000000.0) +
+ (timeEnd.tv_usec - timeBegin.tv_usec)) *
+ ((1.0 * CLOCKS_PER_SEC) / 1000000));
+
+ usage = 100.0 * (((int)(ticksEnd-ticksBegin) * 1.0) / tickspassed);
+
+ printf("ticks used=%d, ticks passed=%d, cpu usage=%.2f%%\n",
+ (int)(ticksEnd-ticksBegin),
+ tickspassed,
+ usage);
+
+ if (usage > 50.0) /* way too high */
+ return 1;
+
+ return 0;
+}
+