[btr] Split btr_del_node() into two functions.
authorAndre Noll <maan@systemlinux.org>
Tue, 5 Jan 2010 02:50:07 +0000 (03:50 +0100)
committerAndre Noll <maan@systemlinux.org>
Tue, 5 Jan 2010 02:50:07 +0000 (03:50 +0100)
Also, close filter/receiver nodes in filter.c/recv.c instead of in
each post_select().

16 files changed:
aacdec_filter.c
amp_filter.c
buffer_tree.c
buffer_tree.h
compress_filter.c
error.h
filter.c
http_recv.c
mp3dec_filter.c
oggdec_filter.c
recv.c
stdin.c
stdout.c
wav_filter.c
wmadec_filter.c
write.c

index ad1c06a..602df63 100644 (file)
@@ -326,9 +326,8 @@ out:
        }
 err:
        assert(ret < 0);
-       aacdec_close(fn);
        t->error = ret;
-       btr_del_node(btrn);
+       btr_remove_node(btrn);
 }
 
 /**
index 1012246..3154735 100644 (file)
@@ -153,8 +153,7 @@ next_buffer:
 err:
        assert(ret < 0);
        t->error = ret;
-       btr_del_node(btrn);
-       amp_close(fn);
+       btr_remove_node(btrn);
 }
 
 /**
index 3b00154..022a411 100644 (file)
@@ -216,20 +216,26 @@ static void flush_input_queue(struct btr_node *btrn)
                btr_drop_buffer_reference(br);
 }
 
-void btr_del_node(struct btr_node *btrn)
+void btr_free_node(struct btr_node *btrn)
+{
+       if (!btrn)
+               return;
+       free(btrn->name);
+       free(btrn);
+}
+
+void btr_remove_node(struct btr_node *btrn)
 {
        struct btr_node *ch;
 
        if (!btrn)
                return;
-       PARA_NOTICE_LOG("deleting %s\n", btrn->name);
+       PARA_NOTICE_LOG("removing btr node %s from buffer tree\n", btrn->name);
        FOR_EACH_CHILD(ch, btrn)
                ch->parent = NULL;
        flush_input_queue(btrn);
        if (btrn->parent)
                list_del(&btrn->node);
-       free(btrn->name);
-       free(btrn);
 }
 
 size_t btr_get_input_queue_size(struct btr_node *btrn)
@@ -261,8 +267,6 @@ void btr_splice_out_node(struct btr_node *btrn)
                        list_move(&ch->node, &btrn->parent->children);
        }
        assert(list_empty(&btrn->children));
-       free(btrn->name);
-       free(btrn);
 }
 
 /**
index a95d167..d02eefc 100644 (file)
@@ -6,7 +6,8 @@ typedef int (*btr_command_handler)(struct btr_node *btrn,
 
 struct btr_node *btr_new_node(const char *name, struct btr_node *parent,
                btr_command_handler handler, void *context);
-void btr_del_node(struct btr_node *btrn);
+void btr_remove_node(struct btr_node *btrn);
+void btr_free_node(struct btr_node *btrn);
 void btr_add_output(char *buf, size_t size, struct btr_node *btrn);
 bool btr_no_children(struct btr_node *btrn);
 size_t btr_bytes_pending(struct btr_node *btrn);
index 142ad89..7c39274 100644 (file)
@@ -150,9 +150,8 @@ next_buffer:
        goto next_buffer;
 err:
        assert(ret < 0);
-       close_compress(fn);
        t->error = ret;
-       btr_del_node(btrn);
+       btr_remove_node(btrn);
 }
 
 /** TODO: Add sanity checks */
diff --git a/error.h b/error.h
index 739eb6c..5854dd3 100644 (file)
--- a/error.h
+++ b/error.h
@@ -41,7 +41,7 @@ extern const char **para_errlist[];
        PARA_ERROR(BTR_EOF, "buffer tree: end of file"), \
 
 #define STDOUT_ERRORS \
-       PARA_ERROR(ORPHAN, "orphaned (EOF)"), \
+       PARA_ERROR(STDOUT_EOF, "stdout: end of file"), \
 
 
 #define BITSTREAM_ERRORS \
index ed8cde4..832ca22 100644 (file)
--- a/filter.c
+++ b/filter.c
@@ -161,19 +161,22 @@ static int __noreturn main_btr(void)
        int i, ret;
        struct filter *f;
        struct btr_node *parent;
+       struct filter_node **fns;
 
        sit->btrn = btr_new_node("stdin", NULL, NULL, NULL);
        stdin_set_defaults(sit);
        register_task(&sit->task);
 
+       fns = para_malloc(conf.filter_given * sizeof(*fns));
        for (i = 0, parent = sit->btrn; i < conf.filter_given; i++) {
                char *fa = conf.filter_arg[i];
-               struct filter_node *fn = para_calloc(sizeof(*fn));
+               struct filter_node *fn;
 
+               fn = fns[i] = para_calloc(sizeof(*fn));
                ret = check_filter_arg(fa, &fn->conf);
                if (ret < 0) {
                        free(fn);
-                       goto err;
+                       goto out;
                }
                fn->filter_num = ret;
                f = filters + fn->filter_num;
@@ -194,7 +197,19 @@ static int __noreturn main_btr(void)
        s.default_timeout.tv_usec = 0;
        btr_log_tree(sit->btrn, LL_INFO);
        ret = schedule(&s);
-err:
+out:
+       for (i--; i >= 0; i--) {
+               struct filter_node *fn = fns[i];
+
+               f = filters + fn->filter_num;
+               f->close(fn);
+               btr_free_node(fn->btrn);
+               free(fn->conf);
+               free(fn);
+       }
+       free(fns);
+       btr_free_node(sit->btrn);
+       btr_free_node(sot->btrn);
        if (ret < 0)
                PARA_EMERG_LOG("%s\n", para_strerror(-ret));
        exit(ret < 0? EXIT_FAILURE : EXIT_SUCCESS);
index cf93076..8f4ca2b 100644 (file)
@@ -168,7 +168,7 @@ static void http_recv_post_select(struct sched *s, struct task *t)
        return;
 err:
        if (conf->buffer_tree_given) {
-               btr_del_node(rn->btrn);
+               btr_remove_node(rn->btrn);
                rn->btrn = NULL;
        }
 }
@@ -176,10 +176,7 @@ err:
 static void http_recv_close(struct receiver_node *rn)
 {
        struct private_http_recv_data *phd = rn->private_data;
-       struct http_recv_args_info *conf = rn->conf;
 
-       if (conf->buffer_tree_given)
-               btr_del_node(rn->btrn);
        close(phd->fd);
        free(rn->buf);
        free(rn->private_data);
index a6a628e..2383fba 100644 (file)
@@ -179,6 +179,7 @@ static void mp3dec_close(struct filter_node *fn)
 
        free(fn->buf);
        fn->buf = NULL;
+       mp3dec_cmdline_parser_free(fn->conf);
        free(pmd);
        fn->private_data = NULL;
 }
@@ -257,9 +258,8 @@ next_frame:
        goto next_frame;
 err:
        assert(ret < 0);
-       mp3dec_close(fn);
        t->error = ret;
-       btr_del_node(btrn);
+       btr_remove_node(btrn);
 }
 
 static void mp3dec_open(struct filter_node *fn)
index 34a04db..956af85 100644 (file)
@@ -260,9 +260,8 @@ static void ogg_post_select(__a_unused struct sched *s, struct task *t)
 
 err:
        assert(ret < 0);
-       ogg_close(fn);
        t->error = ret;
-       btr_del_node(btrn);
+       btr_remove_node(btrn);
 }
 
 static ssize_t ogg_convert(char *inbuffer, size_t len, struct filter_node *fn)
diff --git a/recv.c b/recv.c
index 6f05c47..c8edb59 100644 (file)
--- a/recv.c
+++ b/recv.c
@@ -113,6 +113,8 @@ int main(int argc, char *argv[])
 
        ret = schedule(&s);
 out:
+       if (conf.buffer_tree_given)
+               btr_free_node(sot.btrn);
        if (r_opened)
                r->close(&rn);
        if (r)
diff --git a/stdin.c b/stdin.c
index c8ee808..079865f 100644 (file)
--- a/stdin.c
+++ b/stdin.c
@@ -52,12 +52,6 @@ static void stdin_pre_select_btr(struct sched *s, struct task *t)
 {
        struct stdin_task *sit = container_of(t, struct stdin_task, task);
 
-       if (btr_no_children(sit->btrn)) { /* TODO: defer node deletion to post select */
-               t->error = -E_STDIN_NO_CHILD;
-               btr_del_node(sit->btrn);
-               sit->btrn = NULL;
-               return;
-       }
        t->error = 0;
        if (btr_bytes_pending(sit->btrn) > STDIN_MAX_PENDING)
                sit->check_fd = 0;
@@ -131,8 +125,7 @@ static void stdin_post_select_btr(struct sched *s, struct task *t)
        return;
 err:
        free(buf);
-       btr_del_node(sit->btrn);
-       sit->btrn = NULL;
+       btr_remove_node(sit->btrn);
 }
 
 /**
index d167cd1..bf4a923 100644 (file)
--- a/stdout.c
+++ b/stdout.c
@@ -107,7 +107,7 @@ static void stdout_post_select_btr(struct sched *s, struct task *t)
        t->error = 0;
        if (!sot->check_fd) {
                if (sz == 0 && btr_no_parent(sot->btrn)) {
-                       t->error = -E_ORPHAN;
+                       t->error = -E_STDOUT_EOF;
                        goto err;
                }
                return;
@@ -125,7 +125,7 @@ static void stdout_post_select_btr(struct sched *s, struct task *t)
        btr_consume(sot->btrn, ret);
        return;
 err:
-       btr_del_node(sot->btrn);
+       btr_remove_node(sot->btrn);
 }
 /**
  * Initialize a stdout task structure with default values.
index 91d87e7..1acbfde 100644 (file)
@@ -150,11 +150,10 @@ static void wav_post_select(__a_unused struct sched *s, struct task *t)
        ret = -E_WAV_SUCCESS;
 err:
        t->error = ret;
-       wav_close(fn);
        if (ret == -E_WAV_SUCCESS)
                btr_splice_out_node(btrn);
        else {
-               btr_del_node(btrn);
+               btr_remove_node(btrn);
                PARA_ERROR_LOG("%s\n", para_strerror(-ret));
        }
 }
index d214b42..8d6af40 100644 (file)
@@ -1282,9 +1282,8 @@ success:
        goto next_buffer;
 err:
        assert(ret < 0);
-       wmadec_close(fn);
        t->error = ret;
-       btr_del_node(btrn);
+       btr_remove_node(btrn);
 }
 
 static ssize_t wmadec_convert(char *inbuffer, size_t len,
diff --git a/write.c b/write.c
index 9577f04..f79daf2 100644 (file)
--- a/write.c
+++ b/write.c
@@ -194,7 +194,7 @@ out:
        }
 err:
        if (t->error < 0)
-               btr_del_node(cwt->btrn);
+               btr_remove_node(cwt->btrn);
 }
 
 static void initial_delay_pre_select(struct sched *s, struct task *t)
@@ -326,7 +326,7 @@ out:
                struct writer *w = writers + wn->writer_num;
 
                w->close(wn);
-               btr_del_node(wn->btrn);
+               btr_free_node(wn->btrn);
                free(wn->conf);
                free(wn);
        }