Add a basic fuzzer with the afl crate

Fuzzer code courtesy of Bastien Orivel <eijebong@bananium.fr>

We need a dictionary suitable for SVG/CSS, it seems.
parent 418e6749
Pipeline #86775 passed with stages
in 33 minutes and 25 seconds
......@@ -3,6 +3,7 @@ members = [
"librsvg_crate",
"rsvg_internals",
]
exclude = [ "afl-fuzz" ]
[profile.release]
lto = true
......
[package]
name = "rsvg-afl-fuzz"
version = "0.0.1"
authors = [
"Bastien Orivel <eijebong@bananium.fr>",
]
edition = "2018"
[dependencies]
afl = "0.4"
cairo-rs = { version = "0.6.0", features=["svg"] }
glib = "0.7.0"
gio = { version="0.6.0", features=["v2_48"] } # per configure.ac
librsvg = { path = "../librsvg_crate/" }
[profile.release]
lto = true
debug = true
[profile.bench]
lto = true
Fuzzing with afl-fuzz
=====================
FIXME: this README sucks, and running these commands sucks, too. Need
a script or something.
```
cargo afl build --release
AFL_SKIP_CPUFREQ=1 cargo afl fuzz -i input/ -o out -S f0 target/release/rsvg-afl-fuzz
```
For each CPU core, change `-S f0` for `-S f1`, `-S f2`, etc.
AFL complained when my kernel's configuration for corefiles was this:
```
$ cat /proc/sys/kernel/core_pattern
|/bin/false
```
Set it with `echo core > /proc/sys/kernel/core_pattern` and AFL was
happy.
<?xml version="1.0" encoding="UTF-8"?>
<svg xmlns="http://www.w3.org/2000/svg" width="50" height="50">
<g opacity="0.5">
<rect x="10" y="10" width="30" height="30" fill="blue"/>
</g>
</svg>
<?xml version="1.0" encoding="UTF-8"?>
<svg xmlns="http://www.w3.org/2000/svg" width="100" height="100">
<g transform="translate(20, 20)">
<rect x="0" y="0" width="60" height="60" style="fill:blue; opacity:0.5;"/>
</g>
</svg>
<?xml version="1.0" encoding="UTF-8"?>
<svg version="1.1" baseProfile="basic" id="svg-root"
width="100%" height="100%" viewBox="0 0 480 360"
xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g>
<g opacity="0.5">
<rect x="60" y="230" width="80" height="40" fill="#0000ff" opacity=".5"/>
<rect x="70" y="240" width="80" height="40" fill="#00ff00" opacity=".5"/>
</g>
</g>
</svg>
<?xml version="1.0" encoding="UTF-8"?>
<svg version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="321.00" height="27.00" viewBox="0 0 6420 540">
<defs>
<mask id="Mask_big_ex_small" maskUnits="userSpaceOnUse" x="0" y="0" width="6420" height="540">
<g>
<use xlink:href="#big" fill="white"/>
<use xlink:href="#small" fill="black"/>
</g>
</mask>
<g id="big_ex_small">
<use xlink:href="#big" mask="url(#Mask_big_ex_small)"/>
</g>
<mask id="Region0" maskUnits="userSpaceOnUse" x="0" y="0" width="6420" height="540" fill-rule="nonzero">
<use xlink:href="#big_ex_small" fill="white"/>
</mask>
<rect id="big" x="0" y="0" width="6420" height="540"/>
<rect id="small" x="2760" y="20" width="900" height="480"/>
</defs>
<g mask="url(#Region0)">
<g transform="matrix(1.66667 0 0 1.66667 0 0)">
<rect x="0" y="0" width="6420" height="540" fill="black"/>
</g>
</g>
</svg>
<?xml version="1.0" encoding="UTF-8"?>
<svg xmlns="http://www.w3.org/2000/svg" width="48" height="48">
<rect x="8" y="8" width="32" height="32" fill="blue"/>
</svg>
<?xml version="1.0" encoding="UTF-8"?>
<svg xmlns="http://www.w3.org/2000/svg" width="48" height="48">
<g transform="translate(-10, -10)">
<path fill="blue" d="M 18 18 l 32 0 l 0 32 l -32 0 z"/>
</g>
</svg>
<?xml version="1.0" encoding="UTF-8"?>
<svg xmlns="http://www.w3.org/2000/svg" width="100" height="100">
<defs>
<clipPath id="one" clipPathUnits="objectBoundingBox">
<path d="M 0.5 0.0 L 1.0 0.5 L 0.5 1.0 L 0.0 0.5 Z"/>
</clipPath>
</defs>
<g clip-path="url(#one)">
<rect x="10" y="10" width="40" height="40" fill="blue"/>
<rect x="50" y="50" width="40" height="40" fill="#00ff00"/>
</g>
</svg>
<?xml version="1.0" encoding="UTF-8"?>
<svg xmlns="http://www.w3.org/2000/svg" width="100" height="100">
<defs>
<mask id="one" maskContentUnits="objectBoundingBox">
<path d="M 0.5 0.0 L 1.0 0.5 L 0.5 1.0 L 0.0 0.5 Z" fill="white"/>
</mask>
</defs>
<g mask="url(#one)">
<rect x="10" y="10" width="40" height="40" fill="blue"/>
<rect x="50" y="50" width="40" height="40" fill="#00ff00"/>
</g>
</svg>
<?xml version="1.0" encoding="UTF-8"?>
<svg xmlns="http://www.w3.org/2000/svg"/>
<?xml version="1.0" encoding="UTF-8"?>
<svg xmlns="http://www.w3.org/2000/svg" width="10cm" height="20" viewBox="0 0 100 200"/>
<?xml version="1.0" encoding="UTF-8"?>
<svg xmlns="http://www.w3.org/2000/svg" width="100%" height="100%">
<rect x="10" y="20" width="30" height="40"/>
</svg>
<?xml version="1.0" encoding="UTF-8"?>
<svg xmlns="http://www.w3.org/2000/svg" width="100%" height="100%">
<rect id="foo" x="10" y="20" width="30" height="40"/>
</svg>
<?xml version="1.0" encoding="UTF-8"?>
<svg xmlns="http://www.w3.org/2000/svg" width="100" height="400" viewBox="0 0 100 400">
<rect id="one" x="0" y="0" width="100" height="200" fill="rgb(0,255,0)"/>
<rect id="two" x="0" y="200" width="100" height="200" fill="rgb(0,0,255)"/>
</svg>
<?xml version="1.0" encoding="UTF-8"?>
<svg xmlns="http://www.w3.org/2000/svg" width="100%" height="100%"/>
#[macro_use]
extern crate afl;
extern crate cairo;
extern crate glib;
extern crate librsvg;
fn main() {
fuzz!(|data: &[u8]| {
let width = 96.;
let height = 96.;
let output = "/dev/null";
let bytes = glib::Bytes::from(data);
let stream = gio::MemoryInputStream::new_from_bytes(&bytes);
let handle = librsvg::Loader::new().read_stream(&stream, None, None);
if let Ok(handle) = handle {
let renderer = librsvg::CairoRenderer::new(&handle);
let surface = cairo::svg::File::new(width, height, output);
let cr = cairo::Context::new(&surface);
renderer.render_element_to_viewport(
&cr,
None,
&cairo::Rectangle {
x: 0.0,
y: 0.0,
width,
height,
},
);
}
});
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment