Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Certain svgs cause cairosvg to hang (perhaps stuck in an infinite loop) #382

Open
PWhiddy opened this issue Mar 4, 2023 · 5 comments
Open

Comments

@PWhiddy
Copy link

PWhiddy commented Mar 4, 2023

Thanks for making this super useful library!

Rendering certain svgs with an invalid path causes the library to get stuck in an infinite loop.
This svg renders fine in other applications, and cairosvg renders other svgs for me no problem.

Hoping for some insight on this, even being able to timeout/error on these would be helpful!

@PWhiddy PWhiddy changed the title Certain svgs cause cause cairosvg to hang (perhaps stuck in an infinite loop) Certain svgs cause cairosvg to hang (perhaps stuck in an infinite loop) Mar 4, 2023
@PWhiddy
Copy link
Author

PWhiddy commented Mar 4, 2023

Simple reproduction script:

import cairosvg

svg = """<svg xmlns="http://www.w3.org/2000/svg">
  <g>
    <path fill="#FE6502" d="200 312.1h14v14h-14z"></path>
  </g>
</svg>
"""

if __name__ == "__main__":
    cairosvg.svg2png(
        bytestring=svg.encode(),
        write_to="test.png",
        output_width=224, output_height=224
    )

@PWhiddy
Copy link
Author

PWhiddy commented Mar 4, 2023

For anyone facing this same issue, my workaround was to modify path.py to throw an exception when a max depth is reached while parsing paths:

master...PWhiddy:CairoSVG:master

This doesn't make it render successfully, but at least allows the error to be caught so the file can be skipped instead of hanging.

@liZe
Copy link
Member

liZe commented Mar 5, 2023

Hi!

It looks like the content of the d parameter of the path tag is wrong (or I don’t know this syntax, which is also possible because a lot of things are possible in this parameter 😁).

By design, CairoSVG is bad at handling invalid SVG images and "easily" crashes / hangs in these cases. So, if the SVG is not valid, we won’t add anything to CairoSVG to handle this case.

@PWhiddy
Copy link
Author

PWhiddy commented Mar 6, 2023

Hey thanks for your response!

I think the design of easily crashing on invalid svgs is great, although hanging indefinitely makes things very difficult for some use cases. Particularly in a multiprocessing environment because it's not easy to gracefully timeout from outside the library itself. In my case I'm rendering a huge dataset of millions of svgs, a small number of which are invalid.

Anyway, totally respect the design of not being overly concerned with invalid inputs, but just want to say that just a simple iteration limit to detect infinite loops (perhaps as an optional argument) similar to the one I used above would make many applications much easier to build.

PS
I was very impressed with the speed once I got it running. With 16 processes I can render 3600 images/second!

@liZe
Copy link
Member

liZe commented Mar 6, 2023

Anyway, totally respect the design of not being overly concerned with invalid inputs, but just want to say that just a simple iteration limit to detect infinite loops (perhaps as an optional argument) similar to the one I used above would make many applications much easier to build.

The easiest way for you is probably to define a global timeout. Using func_timeout is a great way to avoid a lot of different problems or attacks (malformed SVG, huge images, common SVG attacks…)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants