Comment 5 for bug 825497

Revision history for this message
Kees Cook (kees) wrote :

When building nodes, librsvg will take all nodes, regardless of name. if a name is unknown, it makes it a group (RsvgNodeGroup) -- see rsvg_standard_element_start(). However, the filter renderer checks for names, not object types, so if a name starts with "fe", it treats it as a filter (RsvgFilterPrimitive), and rsvg_filter_primitive_render() will end up trying to call ->render() off the edge of the allocated RsvgNodeGroup.

There needs to be some way to identify the child node type without relying on ->super.type->str, since it could be anything.

It seems that ->render can line up with the contents of RsvgState, but it depends on the g_malloc behavior of the other program threads, so exploitation would likely be unstable, but possible:

(gdb) p ((RsvgNodeGroup*)0x7c1ea0)->super->state->personal_affine
$37 = {1, 0, 0, 1, 0, 0}
(gdb) set var ((RsvgFilterPrimitive*)0x7c1ea0)->render = 0xffffffffffffffff
(gdb) p ((RsvgNodeGroup*)0x7c1ea0)->super->state->personal_affine
$38 = {1, 0, -nan(0xfffffffffffff), 1, 0, 0}
(gdb) cont
Continuing.

Program received signal SIGSEGV, Segmentation fault.
0xffffffffffffffff in ?? ()