[librsvg: 1/4] systemLanguage: parse the env only once



commit 7cfd08c88a6b5d18cda920d5eced1010d64e1100
Author: Paolo Borelli <pborelli gnome org>
Date:   Sat Feb 23 19:24:52 2019 +0100

    systemLanguage: parse the env only once
    
    Parse the locale related env var just once and pass the current
    locale as a reference while parsing all the nodes.

 rsvg_internals/src/cond.rs   | 22 ----------------------
 rsvg_internals/src/handle.rs | 40 ++++++++++++++++++++++++++++++++++++----
 rsvg_internals/src/node.rs   | 11 ++++++-----
 rsvg_internals/src/xml.rs    |  2 +-
 4 files changed, 43 insertions(+), 32 deletions(-)
---
diff --git a/rsvg_internals/src/cond.rs b/rsvg_internals/src/cond.rs
index e3dface3..24f5380c 100644
--- a/rsvg_internals/src/cond.rs
+++ b/rsvg_internals/src/cond.rs
@@ -3,7 +3,6 @@ use std::ascii::AsciiExt;
 
 use std::str::FromStr;
 
-use glib;
 use language_tags::LanguageTag;
 use locale_config::{LanguageRange, Locale};
 
@@ -110,27 +109,6 @@ impl SystemLanguage {
     }
 }
 
-/// Gets the user's preferred locale from the environment and
-/// translates it to a `Locale` with `LanguageRange` fallbacks.
-///
-/// The `Locale::current()` call only contemplates a single language,
-/// but glib is smarter, and `g_get_langauge_names()` can provide
-/// fallbacks, for example, when LC_MESSAGES="en_US.UTF-8:de" (USA
-/// English and German).  This function converts the output of
-/// `g_get_language_names()` into a `Locale` with appropriate
-/// fallbacks.
-pub fn locale_from_environment() -> Locale {
-    let mut locale = Locale::invariant();
-
-    for name in glib::get_language_names() {
-        if let Ok(range) = LanguageRange::from_unix(&name) {
-            locale.add(&range);
-        }
-    }
-
-    locale
-}
-
 fn locale_accepts_language_tag(
     locale: &Locale,
     language_tag: &LanguageTag,
diff --git a/rsvg_internals/src/handle.rs b/rsvg_internals/src/handle.rs
index 34e4e414..d24450f5 100644
--- a/rsvg_internals/src/handle.rs
+++ b/rsvg_internals/src/handle.rs
@@ -19,7 +19,7 @@ use glib::{self, Bytes, Cast};
 use glib_sys;
 use gobject_sys;
 use libc;
-use url::Url;
+use locale_config::{LanguageRange, Locale};
 
 use allowed_url::{AllowedUrl, Href};
 use c_api::{get_rust_handle, HandleFlags, RsvgHandle, RsvgHandleFlags};
@@ -32,6 +32,7 @@ use pixbuf_utils::pixbuf_from_surface;
 use structure::{IntrinsicDimensions, NodeSvg};
 use surface_utils::{shared_surface::SharedImageSurface, shared_surface::SurfaceType};
 use svg::Svg;
+use url::Url;
 use util::rsvg_g_warning;
 use xml::XmlState;
 use xml2_load::xml_state_load_from_possibly_compressed_stream;
@@ -75,17 +76,23 @@ pub struct LoadFlags {
 pub struct LoadOptions {
     pub flags: LoadFlags,
     pub base_url: Option<Url>,
+    pub locale: Locale,
 }
 
 impl LoadOptions {
-    fn new(flags: LoadFlags, base_url: Option<Url>) -> LoadOptions {
-        LoadOptions { flags, base_url }
+    fn new(flags: LoadFlags, base_url: Option<Url>, locale: Locale) -> LoadOptions {
+        LoadOptions {
+            flags,
+            base_url,
+            locale,
+        }
     }
 
     pub fn copy_with_base_url(&self, base_url: &AllowedUrl) -> LoadOptions {
         LoadOptions {
             flags: self.flags,
             base_url: Some((*base_url).clone()),
+            locale: self.locale.clone(),
         }
     }
 }
@@ -257,7 +264,11 @@ impl Handle {
     }
 
     fn load_options(&self) -> LoadOptions {
-        LoadOptions::new(self.load_flags.get(), self.base_url.borrow().clone())
+        LoadOptions::new(
+            self.load_flags.get(),
+            self.base_url.borrow().clone(),
+            locale_from_environment(),
+        )
     }
 
     pub fn write(&self, buf: &[u8]) {
@@ -730,6 +741,27 @@ impl LoadFlags {
     }
 }
 
+/// Gets the user's preferred locale from the environment and
+/// translates it to a `Locale` with `LanguageRange` fallbacks.
+///
+/// The `Locale::current()` call only contemplates a single language,
+/// but glib is smarter, and `g_get_langauge_names()` can provide
+/// fallbacks, for example, when LC_MESSAGES="en_US.UTF-8:de" (USA
+/// English and German).  This function converts the output of
+/// `g_get_language_names()` into a `Locale` with appropriate
+/// fallbacks.
+fn locale_from_environment() -> Locale {
+    let mut locale = Locale::invariant();
+
+    for name in glib::get_language_names() {
+        if let Ok(range) = LanguageRange::from_unix(&name) {
+            locale.add(&range);
+        }
+    }
+
+    locale
+}
+
 #[no_mangle]
 pub unsafe extern "C" fn rsvg_handle_rust_new() -> *mut Handle {
     Box::into_raw(Box::new(Handle::new()))
diff --git a/rsvg_internals/src/node.rs b/rsvg_internals/src/node.rs
index 3e6be9fc..6188c59c 100644
--- a/rsvg_internals/src/node.rs
+++ b/rsvg_internals/src/node.rs
@@ -5,10 +5,11 @@ use std::collections::HashSet;
 use std::rc::{Rc, Weak};
 
 use attributes::Attribute;
-use cond::{locale_from_environment, RequiredExtensions, RequiredFeatures, SystemLanguage};
+use cond::{RequiredExtensions, RequiredFeatures, SystemLanguage};
 use css::CssStyles;
 use drawing_ctx::DrawingCtx;
 use error::*;
+use locale_config::Locale;
 use parsers::Parse;
 use properties::{ComputedValues, Overflow, SpecifiedValue, SpecifiedValues};
 use property_bag::PropertyBag;
@@ -349,7 +350,7 @@ impl Node {
         self.data.cond.get()
     }
 
-    pub fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) {
+    pub fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>, locale: &Locale) {
         for (attr, value) in pbag.iter() {
             match attr {
                 Attribute::Transform => match Matrix::parse_str(value) {
@@ -364,7 +365,7 @@ impl Node {
             }
         }
 
-        match self.parse_conditional_processing_attributes(pbag) {
+        match self.parse_conditional_processing_attributes(pbag, locale) {
             Ok(_) => (),
             Err(e) => {
                 self.set_error(e);
@@ -384,6 +385,7 @@ impl Node {
     fn parse_conditional_processing_attributes(
         &self,
         pbag: &PropertyBag<'_>,
+        locale: &Locale,
     ) -> Result<(), NodeError> {
         let mut cond = self.get_cond();
 
@@ -402,8 +404,7 @@ impl Node {
                     }
 
                     Attribute::SystemLanguage if cond => {
-                        let locale = locale_from_environment();
-                        cond = SystemLanguage::from_attribute(value, &locale)
+                        cond = SystemLanguage::from_attribute(value, locale)
                             .map(|SystemLanguage(res)| res)?;
                     }
 
diff --git a/rsvg_internals/src/xml.rs b/rsvg_internals/src/xml.rs
index 3b3d4b17..ab238758 100644
--- a/rsvg_internals/src/xml.rs
+++ b/rsvg_internals/src/xml.rs
@@ -320,7 +320,7 @@ impl XmlState {
             parent.add_child(&new_node);
         }
 
-        new_node.set_atts(&new_node, pbag);
+        new_node.set_atts(&new_node, pbag, &self.load_options.locale);
 
         // The "svg" node is special; it will parse its style attributes
         // until the end, in standard_element_end().


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]