After an evaluation, GNOME has moved from Bugzilla to GitLab. Learn more about GitLab.
No new issues can be reported in GNOME Bugzilla anymore.
To report an issue in a GNOME project, go to GNOME GitLab.
Do not go to GNOME Gitlab for: Bluefish, Doxygen, GnuCash, GStreamer, java-gnome, LDTP, NetworkManager, Tomboy.
Bug 665824 - librsvg leaks memory when parsing <desc> tags
librsvg leaks memory when parsing <desc> tags
Status: RESOLVED FIXED
Product: librsvg
Classification: Core
Component: general
git master
Other Linux
: Normal normal
: ---
Assigned To: librsvg maintainers
librsvg maintainers
Depends on:
Blocks:
 
 
Reported: 2011-12-08 23:21 UTC by Angus Gratton
Modified: 2012-01-05 11:50 UTC
See Also:
GNOME target: ---
GNOME version: ---


Attachments
PATCH: Fix memory leak when parsing <desc> tags (819 bytes, patch)
2011-12-08 23:21 UTC, Angus Gratton
none Details | Review
Possible patch: Fix leak when document contains multiple <desc> or <title> tags (1.04 KB, patch)
2011-12-12 23:04 UTC, Angus Gratton
none Details | Review
Possible patch: only parse metadata tags <title>, <desc> & <metadata> when immediate children of <svg> (3.78 KB, patch)
2011-12-13 01:10 UTC, Angus Gratton
rejected Details | Review
Fix bug introduced by fix, rendering <text> elements (900 bytes, patch)
2012-01-05 01:24 UTC, Angus Gratton
committed Details | Review

Description Angus Gratton 2011-12-08 23:21:48 UTC
Created attachment 203126 [details] [review]
PATCH: Fix memory leak when parsing <desc> tags

Whenever librsvg parses a <desc> tag it leaks the string containing the contents of the tag.

The string is allocated in rsvg_start_desc() but is never freed.

A patch is attached against git master. It fixes the leak by freeing the string when the desc handler is freed.


Thanks for working on a very handy library. :)
Comment 1 Christian Persch 2011-12-11 13:22:18 UTC
I don't think this is correct. First, the desc string is needed after parsing (rsvg_handle_get_desc()) so you cannot free it at this point. Furthermore, the RsvgHandle:instance_dispose func does free this string. (on rsvg git master at least). Do you have an actual testcase (or valgrind run of some programme) that shows this leak, using librsvg master?
Comment 2 Angus Gratton 2011-12-12 23:01:48 UTC
Sorry Christian, I had misunderstood the way that librsvg was using <desc> here. I now understand this comment in rsvg-base.c:

/* This isn't quite the correct behavior - in theory, any graphics
element may contain a metadata or desc element */


That describes my SVG document - it has dozens of <desc> tags. If you look at the parsing behaviour, as each an additional <desc> is parsed it will leak the old one.

I did have a valgrind leak-check run that showed this behaviour quite clearly but I unfortunately deleted it after I found the bug. If you're still not seeing it then I'm happy to recreate.


In the meantime, I've attached an alternative patch that just frees the old 'desc' or 'title' string if one already exists, when parsing the new one. This will give the same behaviour as currently exists for multiple <desc> or <title> tags, except without leaking.
Comment 3 Angus Gratton 2011-12-12 23:04:07 UTC
Created attachment 203305 [details] [review]
Possible patch: Fix leak when document contains multiple <desc> or <title> tags
Comment 4 Christian Persch 2011-12-12 23:20:51 UTC
Ok; I see the problem. (And <metadata> has the same problem.)

I don't really like making the rsvg_handle_get_{title,desc,metadata} API (more) wrong though which the patch does since it'll return the one from the last element to have one, instead of the one from the toplevel element as intended in the API...

I guess since it's not really used anywhere (google codesearch finds no real users of rsvg_handle_get_desc/title/metadata) we could just make them always return NULL and just throw away these element's content.
Comment 5 Angus Gratton 2011-12-13 00:14:52 UTC
Yeah - well the patch doesn't change the same bad behaviour you describe. At the moment those calls still return the last element that had one of those tags.

I was trying to think of a way to guarantee that the API will always return the <desc> or <title> from the top. I suppose you'd need to look at the SAX parser context and see if your parent is <svg> or something else, and decide on that basis.

I can try and put together a patch along those lines if you're interested.
Comment 6 Christian Persch 2011-12-13 00:49:02 UTC
I don't think it's worth fixing since there's no users of this API. So unless the other librsvg developers disagree, I think we can just deprecate these APIs (and make them just return NULL (or "" ?) always).
Comment 7 Angus Gratton 2011-12-13 01:10:03 UTC
Created attachment 203312 [details] [review]
Possible patch: only parse metadata tags <title>, <desc> & <metadata> when immediate children of <svg>

Fair enough. I just saw this now, but I also just knocked together this alternative patch which should give the original documented API behaviour. Have run it under valgrind for my basic use case.

Obviously I'm not fussed which path the developers take, myself - I'm not using the API either! :)

Cheers

- Angus
Comment 8 Angus Gratton 2011-12-14 00:44:56 UTC
Review of attachment 203312 [details] [review]:

Urgh, please disregard this last patch totally. It may run under valgrind but it doesn't work in actual daily use (the metadata tags' content get parsed in as content for any <text> element.)

My mistake for rushing it. Given that you've said you want to remove the whole feature, I won't bother amending it unless you've changed your mind.
Comment 9 Christian Persch 2011-12-15 14:38:30 UTC
Fixed on master.
Comment 10 Angus Gratton 2012-01-05 01:24:29 UTC
Created attachment 204645 [details] [review]
Fix bug introduced by fix, rendering <text> elements

Thanks for that Christian.

Unfortunately the fix on mainline introduces the same regression as my patch 203312 - specifically, that if a <text> element contains a <desc> element or similar as a child, the contents of the <desc> gets rendered as text.

It seems this is caused by setting 'characters' to NULL, which causes the SAX parser to fall back on another handler.

The fix is very simple - because 'string' is NULL in these cases the characters handler can be safely called. Patch attached.

Thanks again

- Angus
Comment 11 Christian Persch 2012-01-05 11:49:51 UTC
Pushed to master; thanks!