7 #include <event2/bufferevent.h>
8 #include <event2/buffer.h>
9 #include <event2/listener.h>
10 #include <event2/util.h>
11 #include <event2/event.h>
15 #define MAX_LINE 16384
17 static const char MESSAGE[] = "Hello, World!\n";
19 static const char PATH[] = "./roura";
21 static void listener_cb(struct evconnlistener *, evutil_socket_t, struct sockaddr *, int socklen, void *);
22 static void conn_read_cb(struct bufferevent *, void *);
23 static void conn_write_cb(struct bufferevent *, void *);
24 static void conn_event_cb(struct bufferevent *, short, void *);
25 static void signal_cb(evutil_socket_t, short, void *);
27 int main(int argc, char **argv) {
28 struct event_base *base;
29 struct evconnlistener *listener;
30 struct event *signal_event;
32 struct sockaddr_un sun;
34 base = event_base_new();
36 fprintf(stderr, "Could not initialize libevent!\n");
40 memset(&sun, 0, sizeof (sun));
41 sun.sun_family = AF_UNIX;
42 strcpy(sun.sun_path, PATH);
44 listener = evconnlistener_new_bind(base, listener_cb, (void *) base,
45 LEV_OPT_REUSEABLE | LEV_OPT_CLOSE_ON_FREE, -1,
46 (struct sockaddr*) &sun,
50 fprintf(stderr, "Could not create domain socket: %s!\n", PATH);
54 signal_event = evsignal_new(base, SIGINT, signal_cb, (void *) base);
56 if (!signal_event || event_add(signal_event, NULL) < 0) {
57 fprintf(stderr, "Could not create/add a signal event!\n");
61 event_base_dispatch(base);
63 evconnlistener_free(listener);
64 event_free(signal_event);
65 event_base_free(base);
67 // smažeme soket na disku / soubor -- jinak by program příště spadl na evconnlistener_new_bind()
74 static void listener_cb(struct evconnlistener *listener, evutil_socket_t fd, struct sockaddr *sa, int socklen, void *user_data) {
75 struct event_base *base = (event_base *) user_data;
76 struct bufferevent *bev;
78 //bev = bufferevent_socket_new(base, fd, BEV_OPT_CLOSE_ON_FREE); // zavírá spojení
79 bev = bufferevent_socket_new(base, fd, 0); // nezavírá spojení
81 fprintf(stderr, "Error constructing bufferevent!");
82 event_base_loopbreak(base);
85 bufferevent_setcb(bev, conn_read_cb, conn_write_cb, conn_event_cb, NULL);
86 bufferevent_setwatermark(bev, EV_READ, 0, MAX_LINE);
87 bufferevent_enable(bev, EV_READ | EV_WRITE);
89 printf("někdo se k nám připojil! / %p\n", bev);
91 bufferevent_write(bev, MESSAGE, strlen(MESSAGE));
94 static void conn_read_cb(struct bufferevent *bev, void *user_data) {
95 /* This callback is invoked when there is data to read on bev. */
96 struct evbuffer *input = bufferevent_get_input(bev);
97 struct evbuffer *output = bufferevent_get_output(bev);
98 struct event_base *base = (event_base *) user_data;
100 size_t len = evbuffer_get_length(input);
102 data = (char*) malloc(len);
103 evbuffer_copyout(input, data, len);
105 printf("we got some data: %s / %d\n", data, memcmp(data, "exit", len));
107 if (memcmp(data, "exit\n", len) == 0) {
108 struct timeval delay = {2, 123};
109 event_base_loopexit(base, &delay);
112 /* Copy all the data from the input buffer to the output buffer. */
113 evbuffer_add_buffer(output, input);
117 static void conn_write_cb(struct bufferevent *bev, void *user_data) {
118 struct evbuffer *output = bufferevent_get_output(bev);
119 if (evbuffer_get_length(output) == 0) {
120 printf("flushed answer / %p\n", bev);
121 bufferevent_free(bev);
125 static void conn_event_cb(struct bufferevent *bev, short events, void *user_data) {
126 if (events & BEV_EVENT_EOF) {
127 printf("Connection closed.\n");
128 } else if (events & BEV_EVENT_ERROR) {
129 printf("Got an error on the connection: %s\n", strerror(errno));
132 // None of the other events can happen here, since we haven't enabled timeouts
133 bufferevent_free(bev);
136 static void signal_cb(evutil_socket_t sig, short events, void *user_data) {
137 struct event_base *base = (event_base *) user_data;
138 struct timeval delay = {2, 123};
140 printf("Zachycen SIGINT (Ctrl+C); ukončuji program během %ld sekund a %ld mikrosekund.\n", delay.tv_sec, delay.tv_usec);
142 event_base_loopexit(base, &delay);