}
err:
assert(ret < 0);
- aacdec_close(fn);
t->error = ret;
- btr_del_node(btrn);
+ btr_remove_node(btrn);
}
/**
err:
assert(ret < 0);
t->error = ret;
- btr_del_node(btrn);
- amp_close(fn);
+ btr_remove_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)
list_move(&ch->node, &btrn->parent->children);
}
assert(list_empty(&btrn->children));
- free(btrn->name);
- free(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);
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 */
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 \
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;
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);
return;
err:
if (conf->buffer_tree_given) {
- btr_del_node(rn->btrn);
+ btr_remove_node(rn->btrn);
rn->btrn = NULL;
}
}
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);
free(fn->buf);
fn->buf = NULL;
+ mp3dec_cmdline_parser_free(fn->conf);
free(pmd);
fn->private_data = NULL;
}
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)
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)
ret = schedule(&s);
out:
+ if (conf.buffer_tree_given)
+ btr_free_node(sot.btrn);
if (r_opened)
r->close(&rn);
if (r)
{
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;
return;
err:
free(buf);
- btr_del_node(sit->btrn);
- sit->btrn = NULL;
+ btr_remove_node(sit->btrn);
}
/**
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;
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.
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));
}
}
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,
}
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)
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);
}