some work on event selector
This commit is contained in:
@@ -6,7 +6,7 @@ CFLAGS=-Wall -g -pthread -DT_TRACER -I.
|
|||||||
LIBS=-lX11 -lm
|
LIBS=-lX11 -lm
|
||||||
|
|
||||||
PROG=tracer_remote
|
PROG=tracer_remote
|
||||||
OBJS=remote_old.o plot.o database.o gui.o
|
OBJS=remote_old.o plot.o database.o gui.o utils.o
|
||||||
|
|
||||||
$(PROG): gui/gui.a $(OBJS)
|
$(PROG): gui/gui.a $(OBJS)
|
||||||
$(CC) $(CFLAGS) -o $(PROG) $(OBJS) gui/gui.a $(LIBS)
|
$(CC) $(CFLAGS) -o $(PROG) $(OBJS) gui/gui.a $(LIBS)
|
||||||
|
|||||||
@@ -1,4 +1,5 @@
|
|||||||
#include "database.h"
|
#include "database.h"
|
||||||
|
#include "utils.h"
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
@@ -453,3 +454,48 @@ int number_of_ids(void *_d)
|
|||||||
database *d = _d;
|
database *d = _d;
|
||||||
return d->isize;
|
return d->isize;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int database_get_ids(void *_d, char ***ids)
|
||||||
|
{
|
||||||
|
database *d = _d;
|
||||||
|
int i;
|
||||||
|
*ids = malloc(d->isize * sizeof(char **));
|
||||||
|
for (i = 0; i < d->isize; i++) (*ids)[i] = d->i[i].name;
|
||||||
|
return d->isize;
|
||||||
|
}
|
||||||
|
|
||||||
|
int database_get_groups(void *_d, char ***groups)
|
||||||
|
{
|
||||||
|
database *d = _d;
|
||||||
|
int i;
|
||||||
|
*groups = malloc(d->gsize * sizeof(char **));
|
||||||
|
for (i = 0; i < d->gsize; i++) (*groups)[i] = d->g[i].name;
|
||||||
|
return d->gsize;
|
||||||
|
}
|
||||||
|
|
||||||
|
int database_pos_to_id(void *_d, int pos)
|
||||||
|
{
|
||||||
|
database *d = _d;
|
||||||
|
return d->i[pos].id;
|
||||||
|
}
|
||||||
|
|
||||||
|
void database_get_generic_description(void *_d, int id,
|
||||||
|
char **name, char **desc)
|
||||||
|
{
|
||||||
|
database *d = _d;
|
||||||
|
OBUF o;
|
||||||
|
int i;
|
||||||
|
*name = strdup(d->i[id].name);
|
||||||
|
o.osize = o.omaxsize = 0;
|
||||||
|
o.obuf = NULL;
|
||||||
|
PUTS(&o, *name);
|
||||||
|
for (i = 0; i < d->i[id].asize; i++) {
|
||||||
|
PUTC(&o, ' ');
|
||||||
|
PUTS(&o, d->i[id].arg_name[i]);
|
||||||
|
PUTS(&o, " [");
|
||||||
|
PUTS(&o, d->i[id].arg_name[i]);
|
||||||
|
PUTS(&o, "]");
|
||||||
|
}
|
||||||
|
PUTC(&o, 0);
|
||||||
|
*desc = o.obuf;
|
||||||
|
}
|
||||||
|
|||||||
@@ -10,6 +10,11 @@ void on_off(void *d, char *item, int *a, int onoff);
|
|||||||
char *event_name_from_id(void *database, int id);
|
char *event_name_from_id(void *database, int id);
|
||||||
int event_id_from_name(void *database, char *name);
|
int event_id_from_name(void *database, char *name);
|
||||||
int number_of_ids(void *database);
|
int number_of_ids(void *database);
|
||||||
|
int database_get_ids(void *database, char ***ids);
|
||||||
|
int database_get_groups(void *database, char ***groups);
|
||||||
|
int database_pos_to_id(void *database, int pos);
|
||||||
|
void database_get_generic_description(void *database, int id,
|
||||||
|
char **name, char **desc);
|
||||||
|
|
||||||
/****************************************************************************/
|
/****************************************************************************/
|
||||||
/* get format of an event */
|
/* get format of an event */
|
||||||
|
|||||||
@@ -1,13 +1,106 @@
|
|||||||
#include "event_selector.h"
|
#include "event_selector.h"
|
||||||
#include "gui/gui.h"
|
#include "gui/gui.h"
|
||||||
|
#include "database.h"
|
||||||
|
#include "utils.h"
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
void setup_event_selector(gui *g, void *database, int socket, int *is_on)
|
struct event_selector {
|
||||||
|
int *is_on;
|
||||||
|
int red;
|
||||||
|
int green;
|
||||||
|
gui *g;
|
||||||
|
widget *events;
|
||||||
|
widget *groups;
|
||||||
|
void *database;
|
||||||
|
int nevents;
|
||||||
|
int ngroups;
|
||||||
|
int socket;
|
||||||
|
};
|
||||||
|
|
||||||
|
static void scroll(void *private, gui *g,
|
||||||
|
char *notification, widget *w, void *notification_data)
|
||||||
{
|
{
|
||||||
|
int visible_lines;
|
||||||
|
int start_line;
|
||||||
|
int number_of_lines;
|
||||||
|
int new_line;
|
||||||
|
int inc;
|
||||||
|
|
||||||
|
text_list_state(g, w, &visible_lines, &start_line, &number_of_lines);
|
||||||
|
inc = 10;
|
||||||
|
if (inc > visible_lines - 2) inc = visible_lines - 2;
|
||||||
|
if (inc < 1) inc = 1;
|
||||||
|
if (!strcmp(notification, "scrollup")) inc = -inc;
|
||||||
|
|
||||||
|
new_line = start_line + inc;
|
||||||
|
if (new_line > number_of_lines - visible_lines)
|
||||||
|
new_line = number_of_lines - visible_lines;
|
||||||
|
if (new_line < 0) new_line = 0;
|
||||||
|
|
||||||
|
text_list_set_start_line(g, w, new_line);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void click(void *private, gui *g,
|
||||||
|
char *notification, widget *w, void *notification_data)
|
||||||
|
{
|
||||||
|
int *d = notification_data;
|
||||||
|
struct event_selector *this = private;
|
||||||
|
int set_on;
|
||||||
|
int line = d[0];
|
||||||
|
int button = d[1];
|
||||||
|
char *text;
|
||||||
|
int color;
|
||||||
|
int i;
|
||||||
|
char t;
|
||||||
|
|
||||||
|
if (button != 1 && button != 3) return;
|
||||||
|
|
||||||
|
if (button == 1) set_on = 1; else set_on = 0;
|
||||||
|
|
||||||
|
if (w == this->events)
|
||||||
|
text_list_get_line(this->g, this->events, line, &text, &color);
|
||||||
|
else
|
||||||
|
text_list_get_line(this->g, this->groups, line, &text, &color);
|
||||||
|
|
||||||
|
on_off(this->database, text, this->is_on, set_on);
|
||||||
|
|
||||||
|
for (i = 0; i < this->nevents; i++)
|
||||||
|
text_list_set_color(this->g, this->events, i,
|
||||||
|
this->is_on[database_pos_to_id(this->database, i)] ?
|
||||||
|
this->green : this->red);
|
||||||
|
|
||||||
|
for (i = 0; i < this->ngroups; i++)
|
||||||
|
text_list_set_color(this->g, this->groups, i, FOREGROUND_COLOR);
|
||||||
|
if (w == this->groups)
|
||||||
|
text_list_set_color(this->g, this->groups, line,
|
||||||
|
set_on ? this->green : this->red);
|
||||||
|
|
||||||
|
t = 1;
|
||||||
|
socket_send(this->socket, &t, 1);
|
||||||
|
socket_send(this->socket, &this->nevents, sizeof(int));
|
||||||
|
socket_send(this->socket, this->is_on, this->nevents * sizeof(int));
|
||||||
|
}
|
||||||
|
|
||||||
|
event_selector *setup_event_selector(gui *g, void *database, int socket,
|
||||||
|
int *is_on)
|
||||||
|
{
|
||||||
|
struct event_selector *ret;
|
||||||
widget *win;
|
widget *win;
|
||||||
widget *main_container;
|
widget *main_container;
|
||||||
widget *container;
|
widget *container;
|
||||||
widget *left, *right;
|
widget *left, *right;
|
||||||
widget *events, *groups;
|
widget *events, *groups;
|
||||||
|
char **ids;
|
||||||
|
char **gps;
|
||||||
|
int n;
|
||||||
|
int i;
|
||||||
|
int red, green;
|
||||||
|
|
||||||
|
ret = calloc(1, sizeof(struct event_selector)); if (ret == NULL) abort();
|
||||||
|
|
||||||
|
red = new_color(g, "#944");
|
||||||
|
green = new_color(g, "#272");
|
||||||
|
|
||||||
win = new_toplevel_window(g, 610, 800, "event selector");
|
win = new_toplevel_window(g, 610, 800, "event selector");
|
||||||
main_container = new_container(g, VERTICAL);
|
main_container = new_container(g, VERTICAL);
|
||||||
@@ -38,4 +131,40 @@ void setup_event_selector(gui *g, void *database, int socket, int *is_on)
|
|||||||
widget_add_child(g, right, groups, -1);
|
widget_add_child(g, right, groups, -1);
|
||||||
container_set_child_growable(g, left, events, 1);
|
container_set_child_growable(g, left, events, 1);
|
||||||
container_set_child_growable(g, right, groups, 1);
|
container_set_child_growable(g, right, groups, 1);
|
||||||
|
|
||||||
|
n = database_get_ids(database, &ids);
|
||||||
|
for (i = 0; i < n; i++) {
|
||||||
|
text_list_add(g, events, ids[i], -1,
|
||||||
|
is_on[database_pos_to_id(database, i)] ? green : red);
|
||||||
|
}
|
||||||
|
free(ids);
|
||||||
|
|
||||||
|
ret->nevents = n;
|
||||||
|
|
||||||
|
n = database_get_groups(database, &gps);
|
||||||
|
for (i = 0; i < n; i++) {
|
||||||
|
text_list_add(g, groups, gps[i], -1, FOREGROUND_COLOR);
|
||||||
|
}
|
||||||
|
free(gps);
|
||||||
|
|
||||||
|
ret->ngroups = n;
|
||||||
|
|
||||||
|
ret->g = g;
|
||||||
|
ret->is_on = is_on;
|
||||||
|
ret->red = red;
|
||||||
|
ret->green = green;
|
||||||
|
ret->events = events;
|
||||||
|
ret->groups = groups;
|
||||||
|
ret->database = database;
|
||||||
|
ret->socket = socket;
|
||||||
|
|
||||||
|
register_notifier(g, "scrollup", events, scroll, ret);
|
||||||
|
register_notifier(g, "scrolldown", events, scroll, ret);
|
||||||
|
register_notifier(g, "click", events, click, ret);
|
||||||
|
|
||||||
|
register_notifier(g, "scrollup", groups, scroll, ret);
|
||||||
|
register_notifier(g, "scrolldown", groups, scroll, ret);
|
||||||
|
register_notifier(g, "click", groups, click, ret);
|
||||||
|
|
||||||
|
return ret;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -3,6 +3,9 @@
|
|||||||
|
|
||||||
#include "gui/gui.h"
|
#include "gui/gui.h"
|
||||||
|
|
||||||
void setup_event_selector(gui *g, void *database, int socket, int *is_on);
|
typedef void event_selector;
|
||||||
|
|
||||||
|
event_selector *setup_event_selector(gui *g, void *database, int socket,
|
||||||
|
int *is_on);
|
||||||
|
|
||||||
#endif /* _EVENT_SELECTOR_H_ */
|
#endif /* _EVENT_SELECTOR_H_ */
|
||||||
|
|||||||
@@ -118,6 +118,7 @@ int main(int n, char **v)
|
|||||||
textlog *textlog;
|
textlog *textlog;
|
||||||
gui *g;
|
gui *g;
|
||||||
int gui_mode = 0;
|
int gui_mode = 0;
|
||||||
|
view *out;
|
||||||
|
|
||||||
on_off_name = malloc(n * sizeof(char *)); if (on_off_name == NULL) abort();
|
on_off_name = malloc(n * sizeof(char *)); if (on_off_name == NULL) abort();
|
||||||
on_off_action = malloc(n * sizeof(int)); if (on_off_action == NULL) abort();
|
on_off_action = malloc(n * sizeof(int)); if (on_off_action == NULL) abort();
|
||||||
@@ -153,26 +154,30 @@ int main(int n, char **v)
|
|||||||
|
|
||||||
h = new_handler(database);
|
h = new_handler(database);
|
||||||
|
|
||||||
textlog = new_textlog(h, database,
|
|
||||||
"ENB_UL_CHANNEL_ESTIMATE",
|
|
||||||
"ev: {} eNB_id [eNB_ID] frame [frame] subframe [subframe]");
|
|
||||||
|
|
||||||
g = gui_init();
|
g = gui_init();
|
||||||
new_thread(gui_thread, g);
|
new_thread(gui_thread, g);
|
||||||
|
|
||||||
if (gui_mode) {
|
if (gui_mode) {
|
||||||
view *tout;
|
|
||||||
widget *w, *win;
|
widget *w, *win;
|
||||||
// w = new_text_list(g, 600, 20, 0);
|
// w = new_text_list(g, 600, 20, 0);
|
||||||
w = new_text_list(g, 600, 20, new_color(g, "#ffabab"));
|
w = new_text_list(g, 600, 20, new_color(g, "#ffabab"));
|
||||||
win = new_toplevel_window(g, 600, 20*12, "textlog");
|
win = new_toplevel_window(g, 600, 20*12, "textlog");
|
||||||
widget_add_child(g, win, w, -1);
|
widget_add_child(g, win, w, -1);
|
||||||
tout = new_textlist(1000, 10, g, w);
|
out = new_textlist(1000, 10, g, w);
|
||||||
//tout = new_textlist(7, 4, g, w);
|
//tout = new_textlist(7, 4, g, w);
|
||||||
textlog_add_view(textlog, tout);
|
|
||||||
} else {
|
} else {
|
||||||
view *sout = new_stdout();
|
out = new_stdout();
|
||||||
textlog_add_view(textlog, sout);
|
}
|
||||||
|
|
||||||
|
for (i = 0; i < number_of_events; i++) {
|
||||||
|
char *name, *desc;
|
||||||
|
database_get_generic_description(database, i, &name, &desc);
|
||||||
|
textlog = new_textlog(h, database, name, desc);
|
||||||
|
// "ENB_UL_CHANNEL_ESTIMATE",
|
||||||
|
// "ev: {} eNB_id [eNB_ID] frame [frame] subframe [subframe]");
|
||||||
|
textlog_add_view(textlog, out);
|
||||||
|
free(name);
|
||||||
|
free(desc);
|
||||||
}
|
}
|
||||||
|
|
||||||
for (i = 0; i < on_off_n; i++)
|
for (i = 0; i < on_off_n; i++)
|
||||||
|
|||||||
@@ -327,23 +327,6 @@ void get_message(int s)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void new_thread(void *(*f)(void *), void *data)
|
|
||||||
{
|
|
||||||
pthread_t t;
|
|
||||||
pthread_attr_t att;
|
|
||||||
|
|
||||||
if (pthread_attr_init(&att))
|
|
||||||
{ fprintf(stderr, "pthread_attr_init err\n"); exit(1); }
|
|
||||||
if (pthread_attr_setdetachstate(&att, PTHREAD_CREATE_DETACHED))
|
|
||||||
{ fprintf(stderr, "pthread_attr_setdetachstate err\n"); exit(1); }
|
|
||||||
if (pthread_attr_setstacksize(&att, 10000000))
|
|
||||||
{ fprintf(stderr, "pthread_attr_setstacksize err\n"); exit(1); }
|
|
||||||
if (pthread_create(&t, &att, f, data))
|
|
||||||
{ fprintf(stderr, "pthread_create err\n"); exit(1); }
|
|
||||||
if (pthread_attr_destroy(&att))
|
|
||||||
{ fprintf(stderr, "pthread_attr_destroy err\n"); exit(1); }
|
|
||||||
}
|
|
||||||
|
|
||||||
void usage(void)
|
void usage(void)
|
||||||
{
|
{
|
||||||
printf(
|
printf(
|
||||||
|
|||||||
@@ -2,6 +2,7 @@
|
|||||||
#include "handler.h"
|
#include "handler.h"
|
||||||
#include "database.h"
|
#include "database.h"
|
||||||
#include "view/view.h"
|
#include "view/view.h"
|
||||||
|
#include "utils.h"
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
@@ -32,55 +33,30 @@ struct textlog {
|
|||||||
view **v;
|
view **v;
|
||||||
int vsize;
|
int vsize;
|
||||||
/* local output buffer */
|
/* local output buffer */
|
||||||
int osize;
|
OBUF o;
|
||||||
int omaxsize;
|
|
||||||
char *obuf;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
static void PUTC(struct textlog *l, char c)
|
|
||||||
{
|
|
||||||
if (l->osize == l->omaxsize) {
|
|
||||||
l->omaxsize += 512;
|
|
||||||
l->obuf = realloc(l->obuf, l->omaxsize);
|
|
||||||
if (l->obuf == NULL) abort();
|
|
||||||
}
|
|
||||||
l->obuf[l->osize] = c;
|
|
||||||
l->osize++;
|
|
||||||
}
|
|
||||||
|
|
||||||
static void PUTS(struct textlog *l, char *s)
|
|
||||||
{
|
|
||||||
while (*s) PUTC(l, *s++);
|
|
||||||
}
|
|
||||||
|
|
||||||
static void PUTI(struct textlog *l, int i)
|
|
||||||
{
|
|
||||||
char s[64];
|
|
||||||
sprintf(s, "%d", i);
|
|
||||||
PUTS(l, s);
|
|
||||||
}
|
|
||||||
|
|
||||||
static void _event(void *p, event e)
|
static void _event(void *p, event e)
|
||||||
{
|
{
|
||||||
struct textlog *l = p;
|
struct textlog *l = p;
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
l->osize = 0;
|
l->o.osize = 0;
|
||||||
|
|
||||||
for (i = 0; i < l->fsize; i++)
|
for (i = 0; i < l->fsize; i++)
|
||||||
switch(l->f[i].type) {
|
switch(l->f[i].type) {
|
||||||
case INSTRING: PUTS(l, l->f[i].s); break;
|
case INSTRING: PUTS(&l->o, l->f[i].s); break;
|
||||||
case INT: PUTI(l, e.e[l->f[i].event_arg].i); break;
|
case INT: PUTI(&l->o, e.e[l->f[i].event_arg].i); break;
|
||||||
case STRING: PUTS(l, e.e[l->f[i].event_arg].s); break;
|
case STRING: PUTS(&l->o, e.e[l->f[i].event_arg].s); break;
|
||||||
case BUFFER:
|
case BUFFER:
|
||||||
PUTS(l, "{buffer size:");
|
PUTS(&l->o, "{buffer size:");
|
||||||
PUTI(l, e.e[l->f[i].event_arg].bsize);
|
PUTI(&l->o, e.e[l->f[i].event_arg].bsize);
|
||||||
PUTS(l, "}");
|
PUTS(&l->o, "}");
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
PUTC(l, 0);
|
PUTC(&l->o, 0);
|
||||||
|
|
||||||
for (i = 0; i < l->vsize; i++) l->v[i]->append(l->v[i], l->obuf);
|
for (i = 0; i < l->vsize; i++) l->v[i]->append(l->v[i], l->o.obuf);
|
||||||
}
|
}
|
||||||
|
|
||||||
enum chunk_type { C_ERROR, C_STRING, C_ARG_NAME, C_EVENT_NAME };
|
enum chunk_type { C_ERROR, C_STRING, C_ARG_NAME, C_EVENT_NAME };
|
||||||
|
|||||||
@@ -3,6 +3,7 @@
|
|||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <pthread.h>
|
#include <pthread.h>
|
||||||
#include <time.h>
|
#include <time.h>
|
||||||
|
#include <unistd.h>
|
||||||
|
|
||||||
void new_thread(void *(*f)(void *), void *data)
|
void new_thread(void *(*f)(void *), void *data)
|
||||||
{
|
{
|
||||||
@@ -59,3 +60,46 @@ list *list_append(list *l, void *data)
|
|||||||
l->last = new;
|
l->last = new;
|
||||||
return l;
|
return l;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/****************************************************************************/
|
||||||
|
/* socket */
|
||||||
|
/****************************************************************************/
|
||||||
|
|
||||||
|
void socket_send(int socket, void *buffer, int size)
|
||||||
|
{
|
||||||
|
char *x = buffer;
|
||||||
|
int ret;
|
||||||
|
while (size) {
|
||||||
|
ret = write(socket, x, size);
|
||||||
|
if (ret <= 0) abort();
|
||||||
|
size -= ret;
|
||||||
|
x += ret;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/****************************************************************************/
|
||||||
|
/* buffer */
|
||||||
|
/****************************************************************************/
|
||||||
|
|
||||||
|
void PUTC(OBUF *o, char c)
|
||||||
|
{
|
||||||
|
if (o->osize == o->omaxsize) {
|
||||||
|
o->omaxsize += 512;
|
||||||
|
o->obuf = realloc(o->obuf, o->omaxsize);
|
||||||
|
if (o->obuf == NULL) abort();
|
||||||
|
}
|
||||||
|
o->obuf[o->osize] = c;
|
||||||
|
o->osize++;
|
||||||
|
}
|
||||||
|
|
||||||
|
void PUTS(OBUF *o, char *s)
|
||||||
|
{
|
||||||
|
while (*s) PUTC(o, *s++);
|
||||||
|
}
|
||||||
|
|
||||||
|
void PUTI(OBUF *o, int i)
|
||||||
|
{
|
||||||
|
char s[64];
|
||||||
|
sprintf(s, "%d", i);
|
||||||
|
PUTS(o, s);
|
||||||
|
}
|
||||||
|
|||||||
@@ -16,4 +16,24 @@ typedef struct list {
|
|||||||
list *list_remove_head(list *l);
|
list *list_remove_head(list *l);
|
||||||
list *list_append(list *l, void *data);
|
list *list_append(list *l, void *data);
|
||||||
|
|
||||||
|
/****************************************************************************/
|
||||||
|
/* socket */
|
||||||
|
/****************************************************************************/
|
||||||
|
|
||||||
|
void socket_send(int socket, void *buffer, int size);
|
||||||
|
|
||||||
|
/****************************************************************************/
|
||||||
|
/* buffer */
|
||||||
|
/****************************************************************************/
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
int osize;
|
||||||
|
int omaxsize;
|
||||||
|
char *obuf;
|
||||||
|
} OBUF;
|
||||||
|
|
||||||
|
void PUTC(OBUF *o, char c);
|
||||||
|
void PUTS(OBUF *o, char *s);
|
||||||
|
void PUTI(OBUF *o, int i);
|
||||||
|
|
||||||
#endif /* _UTILS_H_ */
|
#endif /* _UTILS_H_ */
|
||||||
|
|||||||
Reference in New Issue
Block a user