From: Mauro Carvalho Chehab Date: Wed, 27 Feb 2013 08:01:42 +0000 (-0300) Subject: edactool: add one thread per CPU X-Git-Url: https://www.infradead.org/git/?a=commitdiff_plain;h=refs%2Fheads%2Fmaster;p=users%2Fmchehab%2Fedactool.git edactool: add one thread per CPU Signed-off-by: Mauro Carvalho Chehab --- diff --git a/Makefile b/Makefile index 9c70cca..fc931bd 100644 --- a/Makefile +++ b/Makefile @@ -1,7 +1,8 @@ -CC=gcc -CFLAGS = -Wall -FILES = edactool -TRACE_LIB = event-parse.o kbuffer-parse.o parse-filter.o parse-utils.o trace-seq.o +CC = gcc +CFLAGS = -Wall +LDFLAGS = -lpthread +FILES = edactool +TRACE_LIB = event-parse.o kbuffer-parse.o parse-filter.o parse-utils.o trace-seq.o default: $(FILES) diff --git a/edactool.c b/edactool.c index 48671c3..72ee092 100644 --- a/edactool.c +++ b/edactool.c @@ -25,6 +25,7 @@ #include #include #include +#include #include #include #include @@ -309,50 +310,63 @@ static int get_num_cpus(void) return num_cpus; } -static int handle_ras_events_cpu(struct pevent *pevent, int cpu, int page_size) +struct pthread_data { + pthread_t thread; + struct pevent *pevent; + int cpu; + int page_size; +}; + +static void *handle_ras_events_cpu(void *priv) { - int rc, fd; + int fd; struct kbuffer *kbuf; void *page; + char pipe_raw[PATH_MAX]; + struct pthread_data *data = priv; - page = malloc(page_size); + page = malloc(data->page_size); if (!page) { perror("Can't allocate page"); - return errno; + return NULL; } -printf("Endian: %d\n", ENDIAN); + kbuf = kbuffer_alloc(KBUFFER_LSIZE_8, ENDIAN); if (!kbuf) { perror("Can't allocate kbuf"); free(page); - return errno; + return NULL; } - printf("Number of CPUs: %d. For now, opening just cpu0\n", - get_num_cpus()); - /* FIXME: use select to open for all CPUs */ - fd = open(DEBUGFS "tracing/per_cpu/cpu0/trace_pipe_raw", - O_RDONLY); + snprintf(pipe_raw, sizeof(pipe_raw), + DEBUGFS "tracing/per_cpu/cpu%d/trace_pipe_raw", + data->cpu); + + fd = open(pipe_raw, O_RDONLY); if (fd < 0) { perror("Can't open trace_pipe_raw"); kbuffer_free(kbuf); free(page); - return errno; + return NULL; } - rc = read_ras_event(fd, pevent, kbuf, page, page_size); + printf("Listening to events on cpu %d\n", data->cpu); + + read_ras_event(fd, data->pevent, kbuf, page, data->page_size); close(fd); kbuffer_free(kbuf); free(page); - return rc; + + return NULL; } static int handle_ras_events(void) { - int rc, fd, size, page_size; + int rc, fd, size, page_size, i, cpus; struct pevent *pevent; + struct pthread_data *data; void *page; /* Enable RAS events */ @@ -398,8 +412,33 @@ static int handle_ras_events(void) if (rc) goto free_pevent; - /* FIXME: start one thread per CPU */ - rc = handle_ras_events_cpu(pevent, 0, page_size); + cpus = get_num_cpus(); + data = calloc(sizeof(*data), cpus); + if (!data) + goto free_pevent; + + printf("Opening one thread per cpu (%d threads)\n", cpus); + for (i = 0; i < cpus; i++) { + data[i].pevent = pevent; + data[i].cpu = i; + data[i].page_size = page_size; + + rc = pthread_create(&data[i].thread, NULL, + handle_ras_events_cpu, + (void *)&data[i]); + if (rc) { + while (--i) + pthread_cancel(data[i].thread); + goto free_threads; + } + } + + /* Wait for all threads to complete */ + for (i = 0; i < cpus; i++) + pthread_join(data[i].thread, NULL); + +free_threads: + free(data); free_pevent: pevent_free(pevent);