aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorIsaac Freund <ifreund@ifreund.xyz>2020-06-02 13:45:56 +0200
committerIsaac Freund <ifreund@ifreund.xyz>2020-06-02 13:45:56 +0200
commit9856bc92ec3ae8c2334baa76b4093a473bff8fa7 (patch)
treeeeec95069a84ef7245975f7580bc2cfbda79b143
parenteaf13f3bcf855df2bd40c37c3ac06ddfdbbe9ca5 (diff)
downloadriver-9856bc92ec3ae8c2334baa76b4093a473bff8fa7.tar.gz
river-9856bc92ec3ae8c2334baa76b4093a473bff8fa7.tar.xz
Clean up some memory leaks
-rw-r--r--include/bindings.c4
-rw-r--r--include/bindings.h1
-rw-r--r--river/Config.zig6
-rw-r--r--river/Control.zig3
-rw-r--r--river/Decoration.zig13
-rw-r--r--river/Root.zig14
-rw-r--r--river/Server.zig11
7 files changed, 42 insertions, 10 deletions
diff --git a/include/bindings.c b/include/bindings.c
index 0eaf76d..7b16c09 100644
--- a/include/bindings.c
+++ b/include/bindings.c
@@ -35,3 +35,7 @@ struct wlr_output *river_wlr_noop_add_output(struct wlr_backend *backend) {
bool river_wlr_output_is_noop(struct wlr_output *output) {
return wlr_output_is_noop(output);
}
+
+void river_wlr_backend_destory(struct wlr_backend *backend) {
+ wlr_backend_destroy(backend);
+}
diff --git a/include/bindings.h b/include/bindings.h
index d8b9358..9643836 100644
--- a/include/bindings.h
+++ b/include/bindings.h
@@ -31,5 +31,6 @@ struct wlr_session *river_wlr_backend_get_session(struct wlr_backend *backend);
struct wlr_backend *river_wlr_noop_backend_create(struct wl_display *display);
struct wlr_output *river_wlr_noop_add_output(struct wlr_backend *backend);
bool river_wlr_output_is_noop(struct wlr_output *output);
+void river_wlr_backend_destory(struct wlr_backend *backend);
#endif // RIVER_BINDINGS_H
diff --git a/river/Config.zig b/river/Config.zig
index 541e82b..5f39fb3 100644
--- a/river/Config.zig
+++ b/river/Config.zig
@@ -62,6 +62,10 @@ pub fn init(self: *Self, allocator: *std.mem.Allocator) !void {
pub fn deinit(self: Self, allocator: *std.mem.Allocator) void {
self.mode_to_id.deinit();
- for (self.modes.items) |*mode| mode.deinit();
+ for (self.modes.items) |mode| {
+ for (mode.items) |mapping| mapping.deinit(allocator);
+ mode.deinit();
+ }
self.modes.deinit();
+ self.float_filter.deinit();
}
diff --git a/river/Control.zig b/river/Control.zig
index e9ae576..1c12b42 100644
--- a/river/Control.zig
+++ b/river/Control.zig
@@ -85,12 +85,13 @@ fn runCommand(
const seat = self.server.input_manager.default_seat;
var args = std.ArrayList([]const u8).init(allocator);
+ defer args.deinit();
var i: usize = 0;
const data = @ptrCast([*]const u8, wl_array.?.data);
while (i < wl_array.?.size) {
const slice = std.mem.spanZ(@ptrCast([*:0]const u8, &data[i]));
- args.append(std.mem.dupe(allocator, u8, slice) catch unreachable) catch unreachable;
+ args.append(slice) catch unreachable;
i += slice.len + 1;
}
diff --git a/river/Decoration.zig b/river/Decoration.zig
index 91c5bed..b96450c 100644
--- a/river/Decoration.zig
+++ b/river/Decoration.zig
@@ -27,6 +27,7 @@ const DecorationManager = @import("DecorationManager.zig");
decoration_manager: *DecorationManager,
wlr_xdg_toplevel_decoration: *c.wlr_xdg_toplevel_decoration_v1,
+listen_destroy: c.wl_listener,
listen_request_mode: c.wl_listener,
pub fn init(
@@ -37,12 +38,24 @@ pub fn init(
self.decoration_manager = decoration_manager;
self.wlr_xdg_toplevel_decoration = wlr_xdg_toplevel_decoration;
+ self.listen_destroy.notify = handleDestroy;
+ c.wl_signal_add(&self.wlr_xdg_toplevel_decoration.events.destroy, &self.listen_destroy);
+
self.listen_request_mode.notify = handleRequestMode;
c.wl_signal_add(&self.wlr_xdg_toplevel_decoration.events.request_mode, &self.listen_request_mode);
handleRequestMode(&self.listen_request_mode, self.wlr_xdg_toplevel_decoration);
}
+fn handleDestroy(listener: ?*c.wl_listener, data: ?*c_void) callconv(.C) void {
+ const self = @fieldParentPtr(Self, "listen_destroy", listener.?);
+ const allocator = self.decoration_manager.server.allocator;
+ const node = @fieldParentPtr(std.SinglyLinkedList(Self).Node, "data", self);
+
+ self.decoration_manager.decorations.remove(node);
+ allocator.destroy(node);
+}
+
fn handleRequestMode(listener: ?*c.wl_listener, data: ?*c_void) callconv(.C) void {
const self = @fieldParentPtr(Self, "listen_request_mode", listener.?);
// TODO: we might need to take this configure serial and do a transaction
diff --git a/river/Root.zig b/river/Root.zig
index 562aa3c..fe07e7e 100644
--- a/river/Root.zig
+++ b/river/Root.zig
@@ -79,11 +79,17 @@ pub fn init(self: *Self, server: *Server) !void {
}
pub fn deinit(self: *Self) void {
- while (self.outputs.pop()) |output_node| {
- output_node.data.deinit();
- self.server.allocator.destroy(output_node);
- }
+ // Need to remove these listeners as the noop output will be destroyed with
+ // the noop backend triggering the destroy event. However,
+ // Output.handleDestroy is not intended to handle the noop output being
+ // destroyed.
+ c.wl_list_remove(&self.noop_output.listen_destroy.link);
+ c.wl_list_remove(&self.noop_output.listen_frame.link);
+ c.wl_list_remove(&self.noop_output.listen_mode.link);
+
c.wlr_output_layout_destroy(self.wlr_output_layout);
+
+ if (c.wl_event_source_remove(self.transaction_timer) < 0) unreachable;
}
pub fn addOutput(self: *Self, wlr_output: *c.wlr_output) void {
diff --git a/river/Server.zig b/river/Server.zig
index e46a619..f700746 100644
--- a/river/Server.zig
+++ b/river/Server.zig
@@ -136,13 +136,16 @@ pub fn init(self: *Self, allocator: *std.mem.Allocator) !void {
/// Free allocated memory and clean up
pub fn deinit(self: *Self) void {
// Note: order is important here
- if (build_options.xwayland) {
- c.wlr_xwayland_destroy(self.wlr_xwayland);
- }
+ if (build_options.xwayland) c.wlr_xwayland_destroy(self.wlr_xwayland);
+
c.wl_display_destroy_clients(self.wl_display);
+
+ self.root.deinit();
+
c.wl_display_destroy(self.wl_display);
+ c.river_wlr_backend_destory(self.noop_backend);
+
self.input_manager.deinit();
- self.root.deinit();
self.config.deinit(self.allocator);
}