diff options
author | Federico Mena Quintero <federico@gnome.org> | 2018-01-22 13:18:53 -0600 |
---|---|---|
committer | Federico Mena Quintero <federico@gnome.org> | 2018-01-22 13:18:53 -0600 |
commit | 828d222fc76078ba4cb0ef2a6d1874fba3a5b19e (patch) | |
tree | 85ff6d10c6a8b67009931f4b2d0c6427665c3fc3 /rust | |
parent | 3b2b9b010cebf5844c618437025e8bc2a5e81ba7 (diff) | |
parent | f7ac35cf0e7f4a77eb5fd2ec3fc4875c5178f90e (diff) | |
download | librsvg-828d222fc76078ba4cb0ef2a6d1874fba3a5b19e.tar.gz |
gitlab#182 - Merge branch 'parse-transform-with-cssparser'
We no longer use lalrpop to parse SVG's "transform" attribute. We do
it by hand with rust-cssparser. Lalrpop currently suffers from having
to recompile its regexps on each invocation of the parser, so SVGs
with many "transform" attributes are parsed slower than they should
be.
The grammar for the "transform" attribute is very small, anyway, and
doesn't require an industrial-strength parser. Rust-cssparser is
perfectly capable of dealing with it.
https://gitlab.gnome.org/GNOME/librsvg/issues/182
Diffstat (limited to 'rust')
-rw-r--r-- | rust/Cargo.lock | 275 | ||||
-rw-r--r-- | rust/Cargo.toml | 7 | ||||
-rw-r--r-- | rust/build.rs | 5 | ||||
-rw-r--r-- | rust/src/error.rs | 8 | ||||
-rw-r--r-- | rust/src/lib.rs | 2 | ||||
-rw-r--r-- | rust/src/parsers.rs | 6 | ||||
-rw-r--r-- | rust/src/transform.rs | 202 |
7 files changed, 240 insertions, 265 deletions
diff --git a/rust/Cargo.lock b/rust/Cargo.lock index bbc7b728..a9fcef5c 100644 --- a/rust/Cargo.lock +++ b/rust/Cargo.lock @@ -1,43 +1,29 @@ -[[package]] -name = "aho-corasick" -version = "0.6.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "memchr 2.0.1 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "ascii-canvas" -version = "1.0.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "term 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "atty" -version = "0.1.2" -source = "registry+https://github.com/rust-lang/crates.io-index" +[root] +name = "rsvg_internals" +version = "0.0.1" dependencies = [ - "kernel32-sys 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)", - "libc 0.2.35 (registry+https://github.com/rust-lang/crates.io-index)", - "winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)", + "cairo-rs 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)", + "cairo-sys-rs 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", + "cssparser 0.22.1 (registry+https://github.com/rust-lang/crates.io-index)", + "downcast-rs 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)", + "glib 0.4.1 (registry+https://github.com/rust-lang/crates.io-index)", + "glib-sys 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", + "itertools 0.7.6 (registry+https://github.com/rust-lang/crates.io-index)", + "libc 0.2.36 (registry+https://github.com/rust-lang/crates.io-index)", + "pango 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)", + "pango-sys 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", + "regex 0.2.5 (registry+https://github.com/rust-lang/crates.io-index)", ] [[package]] -name = "bit-set" -version = "0.4.0" +name = "aho-corasick" +version = "0.6.4" source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ - "bit-vec 0.4.4 (registry+https://github.com/rust-lang/crates.io-index)", + "memchr 2.0.1 (registry+https://github.com/rust-lang/crates.io-index)", ] [[package]] -name = "bit-vec" -version = "0.4.4" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] name = "bitflags" version = "1.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" @@ -54,9 +40,9 @@ source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ "c_vec 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)", "cairo-sys-rs 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", - "glib 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", + "glib 0.4.1 (registry+https://github.com/rust-lang/crates.io-index)", "glib-sys 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", - "libc 0.2.35 (registry+https://github.com/rust-lang/crates.io-index)", + "libc 0.2.36 (registry+https://github.com/rust-lang/crates.io-index)", "winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)", ] @@ -65,21 +51,24 @@ name = "cairo-sys-rs" version = "0.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ - "libc 0.2.35 (registry+https://github.com/rust-lang/crates.io-index)", + "libc 0.2.36 (registry+https://github.com/rust-lang/crates.io-index)", "pkg-config 0.3.9 (registry+https://github.com/rust-lang/crates.io-index)", "winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)", ] [[package]] name = "cssparser" -version = "0.18.2" +version = "0.22.1" source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ "cssparser-macros 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)", + "dtoa-short 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", + "itoa 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)", "matches 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)", "phf 0.7.21 (registry+https://github.com/rust-lang/crates.io-index)", "procedural-masquerade 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", "quote 0.3.15 (registry+https://github.com/rust-lang/crates.io-index)", + "smallvec 0.4.4 (registry+https://github.com/rust-lang/crates.io-index)", "syn 0.11.11 (registry+https://github.com/rust-lang/crates.io-index)", ] @@ -95,39 +84,26 @@ dependencies = [ ] [[package]] -name = "diff" -version = "0.1.11" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "docopt" -version = "0.7.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "lazy_static 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)", - "regex 0.2.5 (registry+https://github.com/rust-lang/crates.io-index)", - "rustc-serialize 0.3.24 (registry+https://github.com/rust-lang/crates.io-index)", - "strsim 0.6.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] name = "downcast-rs" version = "1.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" [[package]] -name = "either" -version = "1.4.0" +name = "dtoa" +version = "0.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" [[package]] -name = "ena" -version = "0.5.0" +name = "dtoa-short" +version = "0.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "dtoa 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)", +] [[package]] -name = "fixedbitset" -version = "0.1.8" +name = "either" +version = "1.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" [[package]] @@ -146,14 +122,14 @@ source = "registry+https://github.com/rust-lang/crates.io-index" [[package]] name = "glib" -version = "0.4.0" +version = "0.4.1" source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ "bitflags 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)", "glib-sys 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", "gobject-sys 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", - "lazy_static 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)", - "libc 0.2.35 (registry+https://github.com/rust-lang/crates.io-index)", + "lazy_static 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)", + "libc 0.2.36 (registry+https://github.com/rust-lang/crates.io-index)", ] [[package]] @@ -162,7 +138,7 @@ version = "0.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ "bitflags 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)", - "libc 0.2.35 (registry+https://github.com/rust-lang/crates.io-index)", + "libc 0.2.36 (registry+https://github.com/rust-lang/crates.io-index)", "pkg-config 0.3.9 (registry+https://github.com/rust-lang/crates.io-index)", ] @@ -173,20 +149,12 @@ source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ "bitflags 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)", "glib-sys 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", - "libc 0.2.35 (registry+https://github.com/rust-lang/crates.io-index)", + "libc 0.2.36 (registry+https://github.com/rust-lang/crates.io-index)", "pkg-config 0.3.9 (registry+https://github.com/rust-lang/crates.io-index)", ] [[package]] name = "itertools" -version = "0.5.10" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "either 1.4.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "itertools" version = "0.7.6" source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ @@ -194,72 +162,8 @@ dependencies = [ ] [[package]] -name = "kernel32-sys" -version = "0.2.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)", - "winapi-build 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "lalrpop" -version = "0.13.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "ascii-canvas 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)", - "atty 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", - "bit-set 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", - "diff 0.1.11 (registry+https://github.com/rust-lang/crates.io-index)", - "docopt 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)", - "ena 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", - "itertools 0.5.10 (registry+https://github.com/rust-lang/crates.io-index)", - "lalrpop-intern 0.13.1 (registry+https://github.com/rust-lang/crates.io-index)", - "lalrpop-snap 0.13.1 (registry+https://github.com/rust-lang/crates.io-index)", - "lalrpop-util 0.13.1 (registry+https://github.com/rust-lang/crates.io-index)", - "petgraph 0.4.11 (registry+https://github.com/rust-lang/crates.io-index)", - "regex 0.2.5 (registry+https://github.com/rust-lang/crates.io-index)", - "regex-syntax 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)", - "rustc-serialize 0.3.24 (registry+https://github.com/rust-lang/crates.io-index)", - "term 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)", - "unicode-xid 0.0.4 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "lalrpop-intern" -version = "0.13.1" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "lalrpop-snap" -version = "0.13.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "ascii-canvas 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)", - "atty 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", - "bit-set 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", - "diff 0.1.11 (registry+https://github.com/rust-lang/crates.io-index)", - "docopt 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)", - "ena 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", - "itertools 0.5.10 (registry+https://github.com/rust-lang/crates.io-index)", - "lalrpop-intern 0.13.1 (registry+https://github.com/rust-lang/crates.io-index)", - "lalrpop-util 0.13.1 (registry+https://github.com/rust-lang/crates.io-index)", - "petgraph 0.4.11 (registry+https://github.com/rust-lang/crates.io-index)", - "regex 0.2.5 (registry+https://github.com/rust-lang/crates.io-index)", - "regex-syntax 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)", - "rustc-serialize 0.3.24 (registry+https://github.com/rust-lang/crates.io-index)", - "term 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)", - "unicode-xid 0.0.4 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "lalrpop-util" -version = "0.13.1" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "lazy_static" -version = "0.2.11" +name = "itoa" +version = "0.3.4" source = "registry+https://github.com/rust-lang/crates.io-index" [[package]] @@ -269,7 +173,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" [[package]] name = "libc" -version = "0.2.35" +version = "0.2.36" source = "registry+https://github.com/rust-lang/crates.io-index" [[package]] @@ -282,24 +186,19 @@ name = "memchr" version = "2.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ - "libc 0.2.35 (registry+https://github.com/rust-lang/crates.io-index)", + "libc 0.2.36 (registry+https://github.com/rust-lang/crates.io-index)", ] [[package]] -name = "ordermap" -version = "0.3.4" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] name = "pango" version = "0.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ "bitflags 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)", - "glib 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", + "glib 0.4.1 (registry+https://github.com/rust-lang/crates.io-index)", "glib-sys 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", "gobject-sys 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", - "libc 0.2.35 (registry+https://github.com/rust-lang/crates.io-index)", + "libc 0.2.36 (registry+https://github.com/rust-lang/crates.io-index)", "pango-sys 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", ] @@ -311,20 +210,11 @@ dependencies = [ "bitflags 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)", "glib-sys 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", "gobject-sys 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", - "libc 0.2.35 (registry+https://github.com/rust-lang/crates.io-index)", + "libc 0.2.36 (registry+https://github.com/rust-lang/crates.io-index)", "pkg-config 0.3.9 (registry+https://github.com/rust-lang/crates.io-index)", ] [[package]] -name = "petgraph" -version = "0.4.11" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "fixedbitset 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)", - "ordermap 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] name = "phf" version = "0.7.21" source = "registry+https://github.com/rust-lang/crates.io-index" @@ -379,7 +269,7 @@ version = "0.3.20" source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ "fuchsia-zircon 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)", - "libc 0.2.35 (registry+https://github.com/rust-lang/crates.io-index)", + "libc 0.2.36 (registry+https://github.com/rust-lang/crates.io-index)", ] [[package]] @@ -400,37 +290,13 @@ version = "0.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" [[package]] -name = "rsvg_internals" -version = "0.0.1" -dependencies = [ - "cairo-rs 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)", - "cairo-sys-rs 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", - "cssparser 0.18.2 (registry+https://github.com/rust-lang/crates.io-index)", - "downcast-rs 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)", - "glib 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", - "glib-sys 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", - "itertools 0.7.6 (registry+https://github.com/rust-lang/crates.io-index)", - "lalrpop 0.13.1 (registry+https://github.com/rust-lang/crates.io-index)", - "lalrpop-util 0.13.1 (registry+https://github.com/rust-lang/crates.io-index)", - "libc 0.2.35 (registry+https://github.com/rust-lang/crates.io-index)", - "pango 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)", - "pango-sys 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", - "regex 0.2.5 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "rustc-serialize" -version = "0.3.24" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] name = "siphasher" version = "0.2.2" source = "registry+https://github.com/rust-lang/crates.io-index" [[package]] -name = "strsim" -version = "0.6.0" +name = "smallvec" +version = "0.4.4" source = "registry+https://github.com/rust-lang/crates.io-index" [[package]] @@ -452,15 +318,6 @@ dependencies = [ ] [[package]] -name = "term" -version = "0.4.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "kernel32-sys 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)", - "winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] name = "thread_local" version = "0.3.5" source = "registry+https://github.com/rust-lang/crates.io-index" @@ -497,50 +354,31 @@ name = "winapi" version = "0.2.8" source = "registry+https://github.com/rust-lang/crates.io-index" -[[package]] -name = "winapi-build" -version = "0.1.1" -source = "registry+https://github.com/rust-lang/crates.io-index" - [metadata] "checksum aho-corasick 0.6.4 (registry+https://github.com/rust-lang/crates.io-index)" = "d6531d44de723825aa81398a6415283229725a00fa30713812ab9323faa82fc4" -"checksum ascii-canvas 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)" = "b385d69402821a1c254533a011a312531cbcc0e3e24f19bbb4747a5a2daf37e2" -"checksum atty 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "d0fd4c0631f06448cc45a6bbb3b710ebb7ff8ccb96a0800c994afe23a70d5df2" -"checksum bit-set 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "d9bf6104718e80d7b26a68fdbacff3481cfc05df670821affc7e9cbc1884400c" -"checksum bit-vec 0.4.4 (registry+https://github.com/rust-lang/crates.io-index)" = "02b4ff8b16e6076c3e14220b39fbc1fabb6737522281a388998046859400895f" "checksum bitflags 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)" = "b3c30d3802dfb7281680d6285f2ccdaa8c2d8fee41f93805dba5c4cf50dc23cf" "checksum c_vec 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "6237ac5a4b1e81c213c24c6437964c61e646df910a914b4ab1487b46df20bd13" "checksum cairo-rs 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "b6b5695f59fd036fe5741bc5a4eb20c78fbe42256e3b08a2af26bbcbe8070bf3" "checksum cairo-sys-rs 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)" = "7c6e18fecaeac51809db57f45f4553cc0975225a7eb435a7a7e91e5e8113a84d" -"checksum cssparser 0.18.2 (registry+https://github.com/rust-lang/crates.io-index)" = "c89e2d77451da8a55f1f2fcaf7eb86c32da9296890c6a474c7e4047f2429b2f4" +"checksum cssparser 0.22.1 (registry+https://github.com/rust-lang/crates.io-index)" = "2debe29d742180c2d5772c82fd3b024dc399b34afaf04fc7a30ed81af3dc6d67" "checksum cssparser-macros 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "079adec4af52bb5275eadd004292028c79eb3c5f5b4ee8086a36d4197032f6df" -"checksum diff 0.1.11 (registry+https://github.com/rust-lang/crates.io-index)" = "3c2b69f912779fbb121ceb775d74d51e915af17aaebc38d28a592843a2dd0a3a" -"checksum docopt 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ab32ea6e284d87987066f21a9e809a73c14720571ef34516f0890b3d355ccfd8" "checksum downcast-rs 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)" = "917042ca6e6c9fe735a63cd4d5d4c43c64ea8deb456fc5465d3f78df24e68d86" +"checksum dtoa 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)" = "09c3753c3db574d215cba4ea76018483895d7bff25a31b49ba45db21c48e50ab" +"checksum dtoa-short 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "068d4026697c1a18f0b0bb8cfcad1b0c151b90d8edb9bf4c235ad68128920d1d" "checksum either 1.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "740178ddf48b1a9e878e6d6509a1442a2d42fd2928aae8e7a6f8a36fb01981b3" -"checksum ena 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)" = "cabe5a5078ac8c506d3e4430763b1ba9b609b1286913e7d08e581d1c2de9b7e5" -"checksum fixedbitset 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)" = "85cb8fec437468d86dc7c83ca7cfc933341d561873275f22dd5eedefa63a6478" "checksum fuchsia-zircon 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)" = "2e9763c69ebaae630ba35f74888db465e49e259ba1bc0eda7d06f4a067615d82" "checksum fuchsia-zircon-sys 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)" = "3dcaa9ae7725d12cdb85b3ad99a434db70b468c09ded17e012d86b5c1010f7a7" -"checksum glib 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "450247060df7d52fdad31e1d66f30d967e925c9d1d26a0ae050cfe33dcd00d08" +"checksum glib 0.4.1 (registry+https://github.com/rust-lang/crates.io-index)" = "b9b0452824cc63066940f01adc721804919f0b76cdba3cfab977b00b87f16d4a" "checksum glib-sys 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)" = "d9693049613ff52b93013cc3d2590366d8e530366d288438724b73f6c7dc4be8" "checksum gobject-sys 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)" = "60d507c87a71b1143c66ed21a969be9b99a76df234b342d733e787e6c9c7d7c2" -"checksum itertools 0.5.10 (registry+https://github.com/rust-lang/crates.io-index)" = "4833d6978da405305126af4ac88569b5d71ff758581ce5a987dbfa3755f694fc" "checksum itertools 0.7.6 (registry+https://github.com/rust-lang/crates.io-index)" = "b07332223953b5051bceb67e8c4700aa65291535568e1f12408c43c4a42c0394" -"checksum kernel32-sys 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "7507624b29483431c0ba2d82aece8ca6cdba9382bff4ddd0f7490560c056098d" -"checksum lalrpop 0.13.1 (registry+https://github.com/rust-lang/crates.io-index)" = "8ebe5a5c90d5edeecb7f62f6ebec0a3d0f6faf4759a052708348cda99fd311a0" -"checksum lalrpop-intern 0.13.1 (registry+https://github.com/rust-lang/crates.io-index)" = "05410c1e4aff497bdea1ccb274ac35536fda0ee858600df36966502d4f7acbe3" -"checksum lalrpop-snap 0.13.1 (registry+https://github.com/rust-lang/crates.io-index)" = "3f866ece35287f5223a1a022c5d86417c260cda2ca9c8a156af9959404ce5313" -"checksum lalrpop-util 0.13.1 (registry+https://github.com/rust-lang/crates.io-index)" = "7c7743f235fc17f5f50f3b1e64a8690ee154f17f86bd68cbb78787c5b37907f7" -"checksum lazy_static 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)" = "76f033c7ad61445c5b347c7382dd1237847eb1bce590fe50365dcb33d546be73" +"checksum itoa 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)" = "8324a32baf01e2ae060e9de58ed0bc2320c9a2833491ee36cd3b4c414de4db8c" "checksum lazy_static 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)" = "c8f31047daa365f19be14b47c29df4f7c3b581832407daabe6ae77397619237d" -"checksum libc 0.2.35 (registry+https://github.com/rust-lang/crates.io-index)" = "96264e9b293e95d25bfcbbf8a88ffd1aedc85b754eba8b7d78012f638ba220eb" +"checksum libc 0.2.36 (registry+https://github.com/rust-lang/crates.io-index)" = "1e5d97d6708edaa407429faa671b942dc0f2727222fb6b6539bf1db936e4b121" "checksum matches 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)" = "100aabe6b8ff4e4a7e32c1c13523379802df0772b82466207ac25b013f193376" "checksum memchr 2.0.1 (registry+https://github.com/rust-lang/crates.io-index)" = "796fba70e76612589ed2ce7f45282f5af869e0fdd7cc6199fa1aa1f1d591ba9d" -"checksum ordermap 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)" = "690f9a54b4ad4e529b50a72d63152266dade43f072042b9cbd4788b8656bef4a" "checksum pango 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "3e81c404ab81ea7ea2fc2431a0a7672507b80e4b8bf4b41eac3fc83cc665104e" "checksum pango-sys 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)" = "34f34a1be107fe16abb2744e0e206bee4b3b07460b5fddd3009a6aaf60bd69ab" -"checksum petgraph 0.4.11 (registry+https://github.com/rust-lang/crates.io-index)" = "7a7e5234c228fbfa874c86a77f685886127f82e0aef602ad1d48333fcac6ad61" "checksum phf 0.7.21 (registry+https://github.com/rust-lang/crates.io-index)" = "cb325642290f28ee14d8c6201159949a872f220c62af6e110a56ea914fbe42fc" "checksum phf_codegen 0.7.21 (registry+https://github.com/rust-lang/crates.io-index)" = "d62594c0bb54c464f633175d502038177e90309daf2e0158be42ed5f023ce88f" "checksum phf_generator 0.7.21 (registry+https://github.com/rust-lang/crates.io-index)" = "6b07ffcc532ccc85e3afc45865469bf5d9e4ef5bfcf9622e3cfe80c2d275ec03" @@ -551,16 +389,13 @@ source = "registry+https://github.com/rust-lang/crates.io-index" "checksum rand 0.3.20 (registry+https://github.com/rust-lang/crates.io-index)" = "512870020642bb8c221bf68baa1b2573da814f6ccfe5c9699b1c303047abe9b1" "checksum regex 0.2.5 (registry+https://github.com/rust-lang/crates.io-index)" = "744554e01ccbd98fff8c457c3b092cd67af62a555a43bfe97ae8a0451f7799fa" "checksum regex-syntax 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)" = "8e931c58b93d86f080c734bfd2bce7dd0079ae2331235818133c8be7f422e20e" -"checksum rustc-serialize 0.3.24 (registry+https://github.com/rust-lang/crates.io-index)" = "dcf128d1287d2ea9d80910b5f1120d0b8eede3fbf1abe91c40d39ea7d51e6fda" "checksum siphasher 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "0df90a788073e8d0235a67e50441d47db7c8ad9debd91cbf43736a2a92d36537" -"checksum strsim 0.6.0 (registry+https://github.com/rust-lang/crates.io-index)" = "b4d15c810519a91cf877e7e36e63fe068815c678181439f2f29e2562147c3694" +"checksum smallvec 0.4.4 (registry+https://github.com/rust-lang/crates.io-index)" = "ee4f357e8cd37bf8822e1b964e96fd39e2cb5a0424f8aaa284ccaccc2162411c" "checksum syn 0.11.11 (registry+https://github.com/rust-lang/crates.io-index)" = "d3b891b9015c88c576343b9b3e41c2c11a51c219ef067b264bd9c8aa9b441dad" "checksum synom 0.11.3 (registry+https://github.com/rust-lang/crates.io-index)" = "a393066ed9010ebaed60b9eafa373d4b1baac186dd7e008555b0f702b51945b6" -"checksum term 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)" = "fa63644f74ce96fbeb9b794f66aff2a52d601cbd5e80f4b97123e3899f4570f1" "checksum thread_local 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)" = "279ef31c19ededf577bfd12dfae728040a21f635b06a24cd670ff510edd38963" "checksum unicode-xid 0.0.4 (registry+https://github.com/rust-lang/crates.io-index)" = "8c1f860d7d29cf02cb2f3f359fd35991af3d30bac52c57d265a3c461074cb4dc" "checksum unreachable 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)" = "382810877fe448991dfc7f0dd6e3ae5d58088fd0ea5e35189655f84e6814fa56" "checksum utf8-ranges 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)" = "662fab6525a98beff2921d7f61a39e7d59e0b425ebc7d0d9e66d316e55124122" "checksum void 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)" = "6a02e4885ed3bc0f2de90ea6dd45ebcbb66dacffe03547fadbb0eeae2770887d" "checksum winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)" = "167dc9d6949a9b857f3451275e911c3f44255842c1f7a76f33c55103a909087a" -"checksum winapi-build 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "2d315eee3b34aca4797b2da6b13ed88266e6d612562a0c46390af8299fc699bc" diff --git a/rust/Cargo.toml b/rust/Cargo.toml index b6089834..9ae34a7b 100644 --- a/rust/Cargo.toml +++ b/rust/Cargo.toml @@ -2,17 +2,15 @@ name = "rsvg_internals" version = "0.0.1" authors = ["Federico Mena Quintero <federico@gnome.org>"] -build = "build.rs" [dependencies] libc = "0.2" downcast-rs = "^1.0.0" regex = "^0.2.1" -lalrpop-util = "0.13.1" -cssparser = "^0.18.2" itertools = "0.7.4" pango = "0.3.0" pango-sys = "0.5.0" +cssparser = "^0.22.1" [dependencies.cairo-sys-rs] version = "0.5.0" @@ -40,9 +38,6 @@ version = "0.5.0" #git = "https://github.com/gtk-rs/sys" #branch = "master" -[build-dependencies.lalrpop] -version = "0.13.1" - [lib] name = "rsvg_internals" crate-type = ["staticlib"] diff --git a/rust/build.rs b/rust/build.rs deleted file mode 100644 index 23c7d3f8..00000000 --- a/rust/build.rs +++ /dev/null @@ -1,5 +0,0 @@ -extern crate lalrpop; - -fn main() { - lalrpop::process_root().unwrap(); -} diff --git a/rust/src/error.rs b/rust/src/error.rs index 4abfdc87..615415c1 100644 --- a/rust/src/error.rs +++ b/rust/src/error.rs @@ -1,6 +1,8 @@ use std::fmt; use std::error; +use cssparser::{BasicParseError}; + use parsers::ParseError; #[derive(Debug, Clone, PartialEq)] @@ -72,6 +74,12 @@ impl From<ParseError> for AttributeError { } } +impl<'a> From<BasicParseError<'a>> for AttributeError { + fn from (e: BasicParseError) -> AttributeError { + AttributeError::from(ParseError::from(e)) + } +} + #[cfg(test)] pub fn is_parse_error<T> (r: &Result<T, AttributeError>) -> bool { match *r { diff --git a/rust/src/lib.rs b/rust/src/lib.rs index f18235b4..fd308b5b 100644 --- a/rust/src/lib.rs +++ b/rust/src/lib.rs @@ -177,8 +177,6 @@ mod mask; mod node; mod opacity; mod paint_server; -#[cfg_attr(feature = "cargo-clippy", allow(clippy))] -mod parse_transform; mod parsers; mod path_builder; mod path_parser; diff --git a/rust/src/parsers.rs b/rust/src/parsers.rs index 49e43a5e..61c6c119 100644 --- a/rust/src/parsers.rs +++ b/rust/src/parsers.rs @@ -71,7 +71,7 @@ pub fn angle_degrees (s: &str) -> Result <f64, ParseError> { Ok (angle) } -fn optional_comma (parser: &mut Parser) { +pub fn optional_comma (parser: &mut Parser) { let _ = parser.try (|p| p.expect_comma ()); } @@ -87,11 +87,11 @@ pub fn number_optional_number (s: &str) -> Result <(f64, f64), ParseError> { let x = f64::from(parser.expect_number ()?); if !parser.is_exhausted () { - let position = parser.position (); + let state = parser.state (); match *parser.next ()? { Token::Comma => {}, - _ => parser.reset (position) + _ => parser.reset (&state) }; let y = f64::from(parser.expect_number ()?); diff --git a/rust/src/transform.rs b/rust/src/transform.rs index 21da51ac..82038cee 100644 --- a/rust/src/transform.rs +++ b/rust/src/transform.rs @@ -3,16 +3,13 @@ use ::glib::translate::*; use ::glib_sys; use ::libc; -#[cfg(test)] use std::f64::consts::*; use cairo::MatrixTrait; - -use parse_transform::*; +use cssparser::{Parser, ParserInput, Token, ParseError as CssParseError}; use error::*; -use parsers::ParseError; -use parsers::Parse; +use parsers::{Parse, ParseError, optional_comma}; impl Parse for cairo::Matrix { type Data = (); @@ -23,19 +20,160 @@ impl Parse for cairo::Matrix { } } -pub fn parse_transform (s: &str) -> Result <cairo::Matrix, AttributeError> { - let r = parse_TransformList (s); +// This parser is for the "transform" attribute in SVG. +// Its operataion and grammar are described here: +// https://www.w3.org/TR/SVG/coords.html#TransformAttribute - match r { - Ok (m) => { - m.try_invert ().map (|_| m) - .map_err (|_| AttributeError::Value ("invalid transformation matrix".to_string ())) - }, +pub fn parse_transform(s: &str) -> Result<cairo::Matrix, AttributeError> { + let matrix = parse_transform_list(s)?; + + matrix.try_invert ().map (|_| matrix) + .map_err (|_| AttributeError::Value ("invalid transformation matrix".to_string ())) +} + +fn parse_transform_list(s: &str) -> Result<cairo::Matrix, AttributeError> { + let mut input = ParserInput::new(s); + let mut parser = Parser::new(&mut input); + + let mut matrix = cairo::Matrix::identity(); - Err (e) => { - Err (AttributeError::Parse (ParseError::new (format! ("{:?}", e)))) + loop { + let m = parse_transform_command(&mut parser)?; + matrix = cairo::Matrix::multiply(&m, &matrix); + + if parser.is_exhausted() { + break; } + + optional_comma(&mut parser); } + + Ok(matrix) +} + +fn make_expected_function_error() -> AttributeError { + AttributeError::from(ParseError::new("expected matrix|translate|scale|rotate|skewX|skewY")) +} + +fn parse_transform_command(parser: &mut Parser) -> Result<cairo::Matrix, AttributeError> { + match parser.next()?.clone() { + Token::Function(ref name) => parse_transform_function(name, parser), + + Token::Ident(ref name) => { + parser.expect_parenthesis_block()?; + parse_transform_function(name, parser) + }, + + _ => Err(make_expected_function_error()), + } +} + +fn parse_transform_function(name: &str, parser: &mut Parser) -> Result<cairo::Matrix, AttributeError> { + match name { + "matrix" => parse_matrix_args(parser), + "translate" => parse_translate_args(parser), + "scale" => parse_scale_args(parser), + "rotate" => parse_rotate_args(parser), + "skewX" => parse_skewx_args(parser), + "skewY" => parse_skewy_args(parser), + _ => Err(make_expected_function_error()), + } +} + +fn parse_matrix_args(parser: &mut Parser) -> Result<cairo::Matrix, AttributeError> { + parser.parse_nested_block(|p| { + let xx = p.expect_number()? as f64; + optional_comma(p); + + let yx = p.expect_number()? as f64; + optional_comma(p); + + let xy = p.expect_number()? as f64; + optional_comma(p); + + let yy = p.expect_number()? as f64; + optional_comma(p); + + let x0 = p.expect_number()? as f64; + optional_comma(p); + + let y0 = p.expect_number()? as f64; + + Ok(cairo::Matrix::new(xx, yx, xy, yy, x0, y0)) + }).map_err(CssParseError::<()>::basic) + .map_err(|e| AttributeError::from(e)) +} + +fn parse_translate_args(parser: &mut Parser) -> Result<cairo::Matrix, AttributeError> { + parser.parse_nested_block(|p| { + let tx = p.expect_number()?; + + let ty = p.try(|p| -> Result<f32, CssParseError<()>> { + optional_comma(p); + Ok(p.expect_number()?) + }).unwrap_or(0.0); + + Ok(cairo::Matrix::new(1.0, 0.0, 0.0, 1.0, tx as f64, ty as f64)) + }).map_err(CssParseError::<()>::basic) + .map_err(|e| AttributeError::from(e)) +} + +fn parse_scale_args(parser: &mut Parser) -> Result<cairo::Matrix, AttributeError> { + parser.parse_nested_block(|p| { + let x = p.expect_number()?; + + let y = p.try(|p| -> Result<f32, CssParseError<()>> { + optional_comma(p); + Ok(p.expect_number()?) + }).unwrap_or(x); + + Ok(cairo::Matrix::new(x as f64, 0.0, 0.0, y as f64, 0.0, 0.0)) + }).map_err(CssParseError::<()>::basic) + .map_err(|e| AttributeError::from(e)) +} + +fn parse_rotate_args(parser: &mut Parser) -> Result<cairo::Matrix, AttributeError> { + parser.parse_nested_block(|p| { + let angle = p.expect_number()? as f64 * PI / 180.0; + let (s, c) = angle.sin_cos(); + + let (tx, ty) = p.try(|p| -> Result<_, CssParseError<()>> { + optional_comma(p); + let tx = p.expect_number()? as f64; + + optional_comma(p); + let ty = p.expect_number()? as f64; + + Ok((tx, ty)) + }).unwrap_or((0.0, 0.0)); + + let mut m = cairo::Matrix::new (1.0, 0.0, 0.0, 1.0, tx, ty); + + m = cairo::Matrix::multiply (&cairo::Matrix::new (c, s, -s, c, 0.0, 0.0), &m); + m = cairo::Matrix::multiply (&cairo::Matrix::new (1.0, 0.0, 0.0, 1.0, -tx, -ty), &m); + Ok(m) + }).map_err(CssParseError::<()>::basic) + .map_err(|e| AttributeError::from(e)) +} + +fn parse_skewx_args(parser: &mut Parser) -> Result<cairo::Matrix, AttributeError> { + parser.parse_nested_block(|p| { + let a = p.expect_number()? as f64 * PI / 180.0; + Ok(cairo::Matrix::new (1.0, 0.0, + a.tan (), 1.0, + 0.0, 0.0)) + }).map_err(CssParseError::<()>::basic) + .map_err(|e| AttributeError::from(e)) +} + +fn parse_skewy_args(parser: &mut Parser) -> Result<cairo::Matrix, AttributeError> { + parser.parse_nested_block(|p| { + let a = p.expect_number()? as f64 * PI / 180.0; + Ok(cairo::Matrix::new (1.0, a.tan (), + 0.0, 1.0, + 0.0, 0.0)) + }).map_err(CssParseError::<()>::basic) + .map_err(|e| AttributeError::from(e)) } #[cfg(test)] @@ -88,17 +226,23 @@ mod test { cairo::Matrix::multiply (&r, &a)); } - #[test] - fn syntax_error_yields_parse_error () { - match parse_transform ("foo") { - Err (AttributeError::Parse (_)) => {}, - _ => { panic! (); } + fn assert_parse_error(s: &str) { + match parse_transform(s) { + Err(AttributeError::Parse(_)) => {}, + _ => { panic!(); } } + } - match parse_transform ("matrix (1 2 3 4 5)") { - Err (AttributeError::Parse (_)) => {}, - _ => { panic! (); } - } + #[test] + fn syntax_error_yields_parse_error () { + assert_parse_error("foo"); + assert_parse_error("matrix (1 2 3 4 5)"); + assert_parse_error("translate(1 2 3 4 5)"); + assert_parse_error("translate (1,)"); + assert_parse_error("scale (1,)"); + assert_parse_error("skewX (1,2)"); + assert_parse_error("skewY ()"); + assert_parse_error("skewY"); } #[test] @@ -129,7 +273,7 @@ mod parser_tests { assert_eq! (parse_transform ("matrix (1 2 3 4 5 6)").unwrap (), cairo::Matrix::new (1.0, 2.0, 3.0, 4.0, 5.0, 6.0)); - assert_eq! (parse_transform ("matrix (1,2,3,4 5 6)").unwrap (), + assert_eq! (parse_transform ("matrix(1,2,3,4 5 6)").unwrap (), cairo::Matrix::new (1.0, 2.0, 3.0, 4.0, 5.0, 6.0)); assert_eq! (parse_transform ("matrix (1,2.25,-3.25e2,4 5 6)").unwrap (), @@ -149,22 +293,22 @@ mod parser_tests { } #[test] - fn parses_scale () { + fn parses_scale() { + assert_eq! (parse_transform ("scale (-1)").unwrap (), + cairo::Matrix::new (-1.0, 0.0, 0.0, -1.0, 0.0, 0.0)); + assert_eq! (parse_transform ("scale(-1 -2)").unwrap (), cairo::Matrix::new (-1.0, 0.0, 0.0, -2.0, 0.0, 0.0)); assert_eq! (parse_transform ("scale(-1, -2)").unwrap (), cairo::Matrix::new (-1.0, 0.0, 0.0, -2.0, 0.0, 0.0)); - - assert_eq! (parse_transform ("scale(-1)").unwrap (), - cairo::Matrix::new (-1.0, 0.0, 0.0, -1.0, 0.0, 0.0)); } #[test] fn parses_rotate () { assert_eq! (parse_transform ("rotate (30)").unwrap (), make_rotation_matrix (30.0, 0.0, 0.0)); assert_eq! (parse_transform ("rotate (30,-1,-2)").unwrap (), make_rotation_matrix (30.0, -1.0, -2.0)); - assert_eq! (parse_transform ("rotate (30, -1, -2)").unwrap (), make_rotation_matrix (30.0, -1.0, -2.0)); + assert_eq! (parse_transform ("rotate(30, -1, -2)").unwrap (), make_rotation_matrix (30.0, -1.0, -2.0)); } fn make_skew_x_matrix (angle_degrees: f64) -> cairo::Matrix { |