From fc4fc7e75353246b56f5a18c70a60090cf1041e0 Mon Sep 17 00:00:00 2001 From: Adam Sutton Date: Wed, 6 Jun 2012 20:31:01 +0100 Subject: [PATCH] Move the read from file descriptor into buffer into generic routine as I intend to reuse this for external epggrab input. --- Makefile | 1 + src/file.c | 80 +++++++++++++++++++++++++++++++++++++++++++++++++++++ src/file.h | 26 +++++++++++++++++ src/spawn.c | 59 ++------------------------------------- 4 files changed, 110 insertions(+), 56 deletions(-) create mode 100644 src/file.c create mode 100644 src/file.h diff --git a/Makefile b/Makefile index d70bc19a..9099ca65 100644 --- a/Makefile +++ b/Makefile @@ -42,6 +42,7 @@ SRCS = src/main.c \ src/tcp.c \ src/http.c \ src/notify.c \ + src/file.c \ src/cron.c \ src/epg.c \ src/epggrab.c\ diff --git a/src/file.c b/src/file.c new file mode 100644 index 00000000..77316871 --- /dev/null +++ b/src/file.c @@ -0,0 +1,80 @@ +/* + * Process file functions + * Copyright (C) 2008 Andreas Ă–man + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + +#define MAX_RDBUF_SIZE 8192 + +#include +#include +#include +#include +#include "queue.h" +#include "file.h" + +typedef struct file_read_buf { + TAILQ_ENTRY(file_read_buf) link; + int size; + char buf[MAX_RDBUF_SIZE]; +} file_read_buf_t; + +TAILQ_HEAD(file_read_buf_queue, file_read_buf); + +size_t file_readall ( int fd, char **outp ) +{ + int r, totalsize = 0; + struct file_read_buf_queue bufs; + file_read_buf_t *b = NULL; + char *outbuf; + + TAILQ_INIT(&bufs); + while(1) { + if(b == NULL) { + b = malloc(sizeof(file_read_buf_t)); + b->size = 0; + TAILQ_INSERT_TAIL(&bufs, b, link); + } + + r = read(fd, b->buf + b->size, MAX_RDBUF_SIZE - b->size); + if(r < 1) + break; + b->size += r; + totalsize += r; + if(b->size == MAX_RDBUF_SIZE) + b = NULL; + } + + close(fd); + + if(totalsize == 0) { + free(b); + *outp = NULL; + return 0; + } + + outbuf = malloc(totalsize + 1); + r = 0; + while((b = TAILQ_FIRST(&bufs)) != NULL) { + memcpy(outbuf + r, b->buf, b->size); + r+= b->size; + TAILQ_REMOVE(&bufs, b, link); + free(b); + } + assert(r == totalsize); + *outp = outbuf; + outbuf[totalsize] = 0; + return totalsize; +} diff --git a/src/file.h b/src/file.h new file mode 100644 index 00000000..9523a908 --- /dev/null +++ b/src/file.h @@ -0,0 +1,26 @@ +/* + * Process file operations + * Copyright (C) 2012 Adam Sutton + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + +#ifndef FILE_H +#define FILE_H + +#include + +size_t file_readall ( int fd, char **outbuf ); + +#endif /* FILE_H */ diff --git a/src/spawn.c b/src/spawn.c index 5fb77761..80dc75d9 100644 --- a/src/spawn.c +++ b/src/spawn.c @@ -28,6 +28,7 @@ #include #include "tvheadend.h" +#include "file.h" #include "spawn.h" extern char **environ; @@ -43,21 +44,6 @@ typedef struct spawn { } spawn_t; -/** - * Structs for reading back output from a spawn via a pipe - */ -TAILQ_HEAD(spawn_output_buf_queue, spawn_output_buf); - -#define MAX_SOB_SIZE 4000 - -typedef struct spawn_output_buf { - TAILQ_ENTRY(spawn_output_buf) sob_link; - int sob_size; - char sob_buf[MAX_SOB_SIZE]; -} spawn_output_buf_t; - - - /** * The reaper is called once a second to finish of any pending spawns */ @@ -135,10 +121,7 @@ int spawn_and_store_stdout(const char *prog, char *const argv[], char **outp) { pid_t p; - int fd[2], r, totalsize = 0, f; - char *outbuf; - struct spawn_output_buf_queue bufs; - spawn_output_buf_t *b = NULL; + int fd[2], f; const char *local_argv[2]; if(argv == NULL) { @@ -194,43 +177,7 @@ spawn_and_store_stdout(const char *prog, char *const argv[], char **outp) close(fd[1]); - TAILQ_INIT(&bufs); - while(1) { - if(b == NULL) { - b = malloc(sizeof(spawn_output_buf_t)); - b->sob_size = 0; - TAILQ_INSERT_TAIL(&bufs, b, sob_link); - } - - r = read(fd[0], b->sob_buf + b->sob_size, MAX_SOB_SIZE - b->sob_size); - if(r < 1) - break; - b->sob_size += r; - totalsize += r; - if(b->sob_size == MAX_SOB_SIZE) - b = NULL; - } - - close(fd[0]); - - if(totalsize == 0) { - free(b); - *outp = NULL; - return 0; - } - - outbuf = malloc(totalsize + 1); - r = 0; - while((b = TAILQ_FIRST(&bufs)) != NULL) { - memcpy(outbuf + r, b->sob_buf, b->sob_size); - r+= b->sob_size; - TAILQ_REMOVE(&bufs, b, sob_link); - free(b); - } - assert(r == totalsize); - *outp = outbuf; - outbuf[totalsize] = 0; - return totalsize; + return file_readall(fd[0], outp); }