From 2a34739c83b609bf84ca89c32d200591229c5956 Mon Sep 17 00:00:00 2001 From: NeilBrown Date: Fri, 11 Dec 2015 17:15:32 +1100 Subject: [PATCH] First step to plugable event loops. attach libevent via an plugin command. Signed-off-by: NeilBrown --- Makefile | 6 ++- core.h | 4 +- display-ncurses.c | 28 +++++------- edlib.c | 9 ++-- lib-libevent.c | 112 ++++++++++++++++++++++++++++++++++++++++++++++ 5 files changed, 133 insertions(+), 26 deletions(-) create mode 100644 lib-libevent.c diff --git a/Makefile b/Makefile index 2256abca..57e3fe75 100644 --- a/Makefile +++ b/Makefile @@ -3,7 +3,7 @@ # May be distrubuted under terms of GPLv2 - see file:COPYING # -LDLIBS= -levent -ldl +LDLIBS= -ldl CPPFLAGS= -I. CFLAGS=-g -Wall -Werror -Wstrict-prototypes -Wextra -Wno-unused-parameter @@ -16,7 +16,7 @@ SHOBJ = O/doc-text.o O/doc-dir.o \ O/render-hex.o O/render-lines.o \ O/render-format.o O/render-complete.o \ O/lib-view.o O/lib-tile.o O/lib-popup.o O/lib-line-count.o O/lib-keymap.o \ - O/lib-search.o O/lib-messageline.o O/lib-input.o \ + O/lib-search.o O/lib-messageline.o O/lib-input.o O/lib-libevent.o \ O/lang-python.o \ O/mode-emacs.o \ O/display-ncurses.o @@ -28,6 +28,8 @@ INC-lang-python = -I/usr/include/python2.7 LIBS-display-ncurses = -lncursesw INC-display-ncurses = -I/usr/include/ncursesw +LIBS-lib-libevent = -levent + SO = $(patsubst O/%.o,lib/edlib-%.so,$(SHOBJ)) H = list.h core.h misc.h edlib: $(OBJ) lib/libedlib.so diff --git a/core.h b/core.h index a614608c..09577ef0 100644 --- a/core.h +++ b/core.h @@ -81,7 +81,6 @@ struct doc_data { struct editor { struct pane root; - struct event_base *base; struct doc *docs; /* document containing all documents */ struct map *commands; }; @@ -491,7 +490,7 @@ static inline int call3(char *key, struct pane *focus, int numeric, struct mark } static inline int call_home(struct pane *home, char *key, struct pane *focus, - int numeric, struct mark *m) + int numeric, struct mark *m, struct command *comm) { struct cmd_info ci = {0}; @@ -500,6 +499,7 @@ static inline int call_home(struct pane *home, char *key, struct pane *focus, ci.home = home; ci.numeric = numeric; ci.mark = m; + ci.comm2 = comm; return key_handle_focus(&ci); } diff --git a/display-ncurses.c b/display-ncurses.c index 39fb2f2f..505a811d 100644 --- a/display-ncurses.c +++ b/display-ncurses.c @@ -20,7 +20,6 @@ #include #include #include -#include #include #include @@ -42,8 +41,6 @@ static void set_screen(SCREEN *scr) current_screen = scr; } -static void input_handle(int fd, short ev, void *P); - static void move_cursor(struct pane *p) { int ox; @@ -62,13 +59,15 @@ static void move_cursor(struct pane *p) } } +DEF_CMD(input_handle); +DEF_CMD(handle_winch); + DEF_CMD(nc_misc) { struct pane *p = ci->home; - struct editor *ed = pane2ed(p); if (strcmp(ci->str, "exit") == 0) - event_base_loopbreak(ed->base); + call3("event:deactivate", p, 0, NULL); else if (strcmp(ci->str, "refresh") == 0) { clear(); pane_damaged(p, DAMAGED_SIZE); @@ -158,12 +157,10 @@ DEF_CMD(ncurses_handle) return 0; } -static void handle_winch(int sig, short ev, void *null); static struct pane *ncurses_init(struct editor *ed) { WINDOW *w = initscr(); struct pane *p; - struct event *l; struct display_data *dd = malloc(sizeof(*dd)); start_color(); @@ -184,18 +181,15 @@ static struct pane *ncurses_init(struct editor *ed) getmaxyx(stdscr, p->h, p->w); p->h-=1; - l = event_new(ed->base, 0, EV_READ|EV_PERSIST, input_handle, p); - event_add(l, NULL); - l = event_new(ed->base, SIGWINCH, EV_SIGNAL|EV_PERSIST, - handle_winch, p); - event_add(l, NULL); + call_home(p, "event:read", p, 0, NULL, &input_handle); + call_home(p, "event:signal", p, SIGWINCH, NULL, &handle_winch); pane_damaged(p, DAMAGED_SIZE); return pane_attach(p, "input", NULL, NULL); } -static void handle_winch(int sig, short ev, void *vpane) +REDEF_CMD(handle_winch) { - struct pane *p = vpane; + struct pane *p = ci->home; struct winsize size; ioctl(1, TIOCGWINSZ, &size); resize_term(size.ws_row, size.ws_col); @@ -203,6 +197,7 @@ static void handle_winch(int sig, short ev, void *vpane) clear(); pane_damaged(p, DAMAGED_SIZE); pane_refresh(p); + return 1; } static void ncurses_clear(struct pane *p, int attr, int x, int y, int w, int h) @@ -373,9 +368,9 @@ static void send_mouse(MEVENT *mev, struct pane *p) do_send_mouse(p, x, y, "MouseMove"); } -static void input_handle(int fd, short ev, void *P) +REDEF_CMD(input_handle) { - struct pane *p = P; + struct pane *p = ci->home; wint_t c; int is_keycode; @@ -388,6 +383,7 @@ static void input_handle(int fd, short ev, void *P) send_key(is_keycode, c, p); } pane_refresh(p); + return 1; } DEF_CMD(display_ncurses) diff --git a/edlib.c b/edlib.c index c50cb734..050166a8 100644 --- a/edlib.c +++ b/edlib.c @@ -10,7 +10,6 @@ #include #include #include -#include #include #include #include @@ -52,7 +51,6 @@ DEF_CMD(take_pane) int main(int argc, char *argv[]) { - struct event_base *base; struct pane *root, *global; struct pane *b, *p= NULL; struct cmd_info ci = {0}; @@ -63,13 +61,12 @@ int main(int argc, char *argv[]) ed = pane2ed(vroot); setlocale(LC_ALL, ""); setlocale(LC_CTYPE, "enUS.UTF-8"); - base = event_base_new(); - event_base_priority_init(base, 2); - ed->base = base; editor_load_module(ed, "lib-line-count"); editor_load_module(ed, "lib-search"); + editor_load_module(ed, "lib-libevent"); editor_load_module(ed, "display-ncurses"); + call3("libevent:activate", vroot, 0, NULL); ci.home = ci.focus = vroot; ci.key = "display-ncurses"; cr.c = take_pane; @@ -96,7 +93,7 @@ int main(int argc, char *argv[]) key_handle(&ci); pane_refresh(&ed->root); - event_base_dispatch(base); + call3("event:run", vroot, 0, NULL); } pane_close(&ed->root); exit(0); diff --git a/lib-libevent.c b/lib-libevent.c new file mode 100644 index 00000000..c1fac008 --- /dev/null +++ b/lib-libevent.c @@ -0,0 +1,112 @@ +/* + * Copyright Neil Brown ©2015 + * May be distributed under terms of GPLv2 - see file:COPYING + * + * libevent support for edlib. + * + * Register command "libevent:activate". + * When that is called, register: + * "event:read" + * "event:signal" + * "event:run" + * "event:deactivate" + * + * When "event:deactivate" is called, cause event:run to abort. + */ + + +#include +#include +#include "core.h" + +static struct event_base *base; +static struct list_head event_list; + +struct evt { + struct event *l; + struct pane *home; + struct command *comm; + struct list_head lst; +}; + +static void call_event(int thing, short sev, void *evv) +{ + struct evt *ev = evv; + struct cmd_info ci = {0}; + + ci.key = "callback:event"; + ci.home = ci.focus = ev->home; + ci.comm = ev->comm; + ci.numeric = thing; + ev->comm->func(&ci); +} + +DEF_CMD(libevent_read) +{ + struct evt *ev = malloc(sizeof(*ev)); + ev->l = event_new(base, ci->numeric, EV_READ|EV_PERSIST, + call_event, ev); + ev->home = ci->focus; + ev->comm = ci->comm2; + list_add(&ev->lst, &event_list); + event_add(ev->l, NULL); + return 1; +} + +DEF_CMD(libevent_signal) +{ + struct evt *ev = malloc(sizeof(*ev)); + ev->l = event_new(base, ci->numeric, EV_SIGNAL|EV_PERSIST, + call_event, ev); + ev->home = ci->focus; + ev->comm = ci->comm2; + list_add(&ev->lst, &event_list); + event_add(ev->l, NULL); + return 1; +} + +DEF_CMD(libevent_run) +{ + struct event_base *b = base; + event_base_dispatch(b); + while (!list_empty(&event_list)) { + struct evt *ev = list_first_entry(&event_list, struct evt, lst); + list_del(&ev->lst); + event_del(ev->l); + event_free(ev->l); + } + event_base_free(b); + return 1; +} + +DEF_CMD(libevent_deactivate) +{ + event_base_loopbreak(base); + base = NULL; + return 1; +} + +DEF_CMD(libevent_activate) +{ + if (base) + return 1; + base = event_base_new(); + INIT_LIST_HEAD(&event_list); + + call_comm("global-set-command", ci->focus, 0, NULL, "event:read", + 0, &libevent_read); + call_comm("global-set-command", ci->focus, 0, NULL, "event:signal", + 0, &libevent_signal); + call_comm("global-set-command", ci->focus, 0, NULL, "event:run", + 0, &libevent_run); + call_comm("global-set-command", ci->focus, 0, NULL, "event:deactivate", + 0, &libevent_deactivate); + + return 1; +} + +void edlib_init(struct editor *ed) +{ + call_comm("global-set-command", &ed->root, 0, NULL, "libevent:activate", + 0, &libevent_activate); +} -- 2.39.5