aboutsummaryrefslogtreecommitdiffstats
path: root/klippy/serialqueue.c
diff options
context:
space:
mode:
authorKevin O'Connor <kevin@koconnor.net>2016-11-30 01:58:45 -0500
committerKevin O'Connor <kevin@koconnor.net>2016-11-30 13:33:16 -0500
commit7cb71df02cbe417798067a4f68a62dcbca8be025 (patch)
tree0a556bf2d5bbd15045c3347017353bc092412002 /klippy/serialqueue.c
parent55fc11ff024958bb86331bfafc5abc11a82a48fe (diff)
downloadkutter-7cb71df02cbe417798067a4f68a62dcbca8be025.tar.gz
kutter-7cb71df02cbe417798067a4f68a62dcbca8be025.tar.xz
kutter-7cb71df02cbe417798067a4f68a62dcbca8be025.zip
mcu: Be careful to free memory allocated in C code
Free steppersync, stepcompress, and commandqueue objects. Signed-off-by: Kevin O'Connor <kevin@koconnor.net>
Diffstat (limited to 'klippy/serialqueue.c')
-rw-r--r--klippy/serialqueue.c64
1 files changed, 46 insertions, 18 deletions
diff --git a/klippy/serialqueue.c b/klippy/serialqueue.c
index 6c1b9d63..0700ecc3 100644
--- a/klippy/serialqueue.c
+++ b/klippy/serialqueue.c
@@ -130,6 +130,18 @@ pollreactor_setup(struct pollreactor *pr, int num_fds, int num_timers
pr->timers[i].waketime = PR_NEVER;
}
+// Free resources associated with a 'struct pollreactor' object
+static void
+pollreactor_free(struct pollreactor *pr)
+{
+ free(pr->fds);
+ pr->fds = NULL;
+ free(pr->fd_callbacks);
+ pr->fd_callbacks = NULL;
+ free(pr->timers);
+ pr->timers = NULL;
+}
+
// Add a callback for when a file descriptor (fd) becomes readable
static void
pollreactor_add_fd(struct pollreactor *pr, int pos, int fd, void *callback)
@@ -358,6 +370,18 @@ message_free(struct queue_message *qm)
free(qm);
}
+// Free all the messages on a queue
+void
+message_queue_free(struct list_head *root)
+{
+ while (!list_empty(root)) {
+ struct queue_message *qm = list_first_entry(
+ root, struct queue_message, node);
+ list_del(&qm->node);
+ message_free(qm);
+ }
+}
+
/****************************************************************
* Serialqueue interface
@@ -438,18 +462,6 @@ debug_queue_add(struct list_head *root, struct queue_message *qm)
message_free(old);
}
-// Free all the messages on a queue
-static void
-queue_free(struct list_head *root)
-{
- while (!list_empty(root)) {
- struct queue_message *qm = list_first_entry(
- root, struct queue_message, node);
- list_del(&qm->node);
- message_free(qm);
- }
-}
-
// Wake up the receiver thread if it is waiting
static void
check_wake_receive(struct serialqueue *sq)
@@ -863,21 +875,24 @@ serialqueue_exit(struct serialqueue *sq)
void
serialqueue_free(struct serialqueue *sq)
{
+ if (!sq)
+ return;
if (!pollreactor_is_exit(&sq->pr))
serialqueue_exit(sq);
pthread_mutex_lock(&sq->lock);
- queue_free(&sq->sent_queue);
- queue_free(&sq->receive_queue);
- queue_free(&sq->old_sent);
- queue_free(&sq->old_receive);
+ message_queue_free(&sq->sent_queue);
+ message_queue_free(&sq->receive_queue);
+ message_queue_free(&sq->old_sent);
+ message_queue_free(&sq->old_receive);
while (!list_empty(&sq->pending_queues)) {
struct command_queue *cq = list_first_entry(
&sq->pending_queues, struct command_queue, node);
list_del(&cq->node);
- queue_free(&cq->ready_queue);
- queue_free(&cq->stalled_queue);
+ message_queue_free(&cq->ready_queue);
+ message_queue_free(&cq->stalled_queue);
}
pthread_mutex_unlock(&sq->lock);
+ pollreactor_free(&sq->pr);
free(sq);
}
@@ -892,6 +907,19 @@ serialqueue_alloc_commandqueue(void)
return cq;
}
+// Free a 'struct command_queue'
+void
+serialqueue_free_commandqueue(struct command_queue *cq)
+{
+ if (!cq)
+ return;
+ if (!list_empty(&cq->ready_queue) || !list_empty(&cq->stalled_queue)) {
+ fprintf(stderr, "Memory leak! Can't free non-empty commandqueue\n");
+ return;
+ }
+ free(cq);
+}
+
// Add a batch of messages to the given command_queue
void
serialqueue_send_batch(struct serialqueue *sq, struct command_queue *cq