From 3116c0d381733d84714ec9d78bb8a56610fdc1f9 Mon Sep 17 00:00:00 2001 From: Pierre Habouzit Date: Mon, 23 Jun 2008 15:21:29 +0200 Subject: [PATCH] Add draw_parser_data_{init,wipe}. Use it everywhere needed instead of wrong p_clear's, this fixes memory leaks. Signed-off-by: Pierre Habouzit --- common/draw.c | 23 ++++++++++++++++++----- common/draw.h | 3 +++ mouse.c | 6 ++++++ widgets/taglist.c | 3 +++ widgets/textbox.c | 3 +++ 5 files changed, 33 insertions(+), 5 deletions(-) diff --git a/common/draw.c b/common/draw.c index cd21954b..3586c536 100644 --- a/common/draw.c +++ b/common/draw.c @@ -47,6 +47,18 @@ #include "common/markup.h" #include "common/xutil.h" +void draw_parser_data_init(draw_parser_data_t *pdata) +{ + p_clear(pdata, 1); + buffer_init(&pdata->text); +} + +void draw_parser_data_wipe(draw_parser_data_t *pdata) +{ + buffer_wipe(&pdata->text); + draw_image_delete(&pdata->bg_image); +} + /** Convert text from any charset to UTF-8 using iconv * \param iso the ISO string to convert * \return NULL if error, otherwise pointer to the new converted string @@ -277,6 +289,7 @@ draw_text_markup_expand(draw_parser_data_t *data, } /* stole text */ + buffer_wipe(&data->text); data->text = p.text; buffer_init(&p.text); markup_parser_data_wipe(&p); @@ -305,7 +318,7 @@ draw_text(draw_context_t *ctx, font_t *font, if(!pdata) { - p_clear(&parser_data, 1); + draw_parser_data_init(&parser_data); parser_data.connection = ctx->connection; parser_data.phys_screen = ctx->phys_screen; if(draw_text_markup_expand(&parser_data, text, len)) @@ -381,7 +394,8 @@ draw_text(draw_context_t *ctx, font_t *font, pango_cairo_update_layout(ctx->cr, ctx->layout); pango_cairo_show_layout(ctx->cr, ctx->layout); - buffer_wipe(&pdata->text); + if (pdata == &parser_data) + draw_parser_data_wipe(&parser_data); } /** Setup color-source for cairo (gradient or mono). @@ -974,7 +988,8 @@ draw_rotate(draw_context_t *ctx, * \return Text height and width. */ area_t -draw_text_extents(xcb_connection_t *conn, int phys_screen, font_t *font, const char *text, draw_parser_data_t *parser_data) +draw_text_extents(xcb_connection_t *conn, int phys_screen, font_t *font, + const char *text, draw_parser_data_t *parser_data) { cairo_surface_t *surface; cairo_t *cr; @@ -984,8 +999,6 @@ draw_text_extents(xcb_connection_t *conn, int phys_screen, font_t *font, const c area_t geom = { 0, 0, 0, 0 }; ssize_t len; - p_clear(parser_data, 1); - if(!(len = a_strlen(text))) return geom; diff --git a/common/draw.h b/common/draw.h index 62b8a5a9..71b08c17 100644 --- a/common/draw.h +++ b/common/draw.h @@ -174,6 +174,9 @@ typedef struct } shadow; } draw_parser_data_t; +void draw_parser_data_init(draw_parser_data_t *); +void draw_parser_data_wipe(draw_parser_data_t *); + void draw_text(draw_context_t *, font_t *, area_t, const char *, draw_parser_data_t *); void draw_rectangle(draw_context_t *, area_t, float, bool, xcolor_t); void draw_rectangle_gradient(draw_context_t *, area_t, float, bool, area_t, xcolor_t *, xcolor_t *, xcolor_t *); diff --git a/mouse.c b/mouse.c index c6165c03..87943946 100644 --- a/mouse.c +++ b/mouse.c @@ -465,6 +465,7 @@ mouse_client_move(client_t *c, int snap, bool infobox) xcb_window_t root; draw_parser_data_t pdata; + draw_parser_data_init(&pdata); layout = layout_get_current(c->screen); root = xutil_screen_get(globalconf.connection, c->phys_screen)->root; @@ -551,6 +552,7 @@ mouse_client_move(client_t *c, int snap, bool infobox) } xcb_aux_sync(globalconf.connection); + draw_parser_data_wipe(&pdata); } @@ -574,6 +576,7 @@ mouse_client_resize_floating(client_t *c, corner_t corner, bool infobox) int top, bottom, left, right; draw_parser_data_t pdata; + draw_parser_data_init(&pdata); screen = xutil_screen_get(globalconf.connection, c->phys_screen); /* get current mouse position */ @@ -706,6 +709,7 @@ mouse_client_resize_floating(client_t *c, corner_t corner, bool infobox) draw_context_delete(&ctx); simplewindow_delete(&sw); } + draw_parser_data_wipe(&pdata); } /** Resize the master column/row of a tiled layout @@ -831,6 +835,7 @@ mouse_client_resize_magnified(client_t *c, bool infobox) xcb_window_t root; draw_parser_data_t pdata; + draw_parser_data_init(&pdata); tag = tags_get_current(c->screen)[0]; root = xutil_screen_get(globalconf.connection, c->phys_screen)->root; @@ -921,6 +926,7 @@ mouse_client_resize_magnified(client_t *c, bool infobox) draw_context_delete(&ctx); simplewindow_delete(&sw); } + draw_parser_data_wipe(&pdata); } /** Resize a client with the mouse. diff --git a/widgets/taglist.c b/widgets/taglist.c index a570a5bc..46f72a38 100644 --- a/widgets/taglist.c +++ b/widgets/taglist.c @@ -168,6 +168,7 @@ taglist_draw(draw_context_t *ctx, int screen, widget_node_t *w, p_realloc(&pdata, i + 1); text[i] = taglist_text_get(tag, data); text[i] = tag_markup_parse(tag, text[i], a_strlen(text[i])); + draw_parser_data_init(&pdata[i]); area = draw_text_extents(ctx->connection, ctx->phys_screen, globalconf.font, text[i], &pdata[i]); @@ -188,12 +189,14 @@ taglist_draw(draw_context_t *ctx, int screen, widget_node_t *w, if(!data->show_empty && !tag->selected && !tag_isoccupied(tag)) { p_delete(&text[i]); + draw_parser_data_wipe(&pdata[i]); continue; } r->x = w->area.x + prev_width; prev_width += r->width; draw_text(ctx, globalconf.font, *r, text[i], &pdata[i]); + draw_parser_data_wipe(&pdata[i]); p_delete(&text[i]); if(tag_isoccupied(tag)) diff --git a/widgets/textbox.c b/widgets/textbox.c index c01ef147..731454e4 100644 --- a/widgets/textbox.c +++ b/widgets/textbox.c @@ -49,6 +49,7 @@ textbox_draw(draw_context_t *ctx, int screen __attribute__ ((unused)), w->area.width = ctx->width - used; else { + draw_parser_data_init(&pdata); w->area.width = MIN(draw_text_extents(ctx->connection, ctx->phys_screen, globalconf.font, d->text, &pdata).width, @@ -65,6 +66,8 @@ textbox_draw(draw_context_t *ctx, int screen __attribute__ ((unused)), w->area.y = 0; draw_text(ctx, globalconf.font, w->area, d->text, pdata_arg); + if (pdata_arg) + draw_parser_data_wipe(pdata_arg); return w->area.width; }