[librsvg/librsvg-2.44] Register enums and flags against GType in Rust
- From: Federico Mena Quintero <federico src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [librsvg/librsvg-2.44] Register enums and flags against GType in Rust
- Date: Fri, 15 Feb 2019 16:41:02 +0000 (UTC)
commit 2555ff5d3c65ae19ae83b1fe1f41315401f5447a
Author: Federico Mena Quintero <federico gnome org>
Date: Fri Feb 15 09:51:40 2019 -0600
Register enums and flags against GType in Rust
This is a backport of the relevant code from the "subclass" branch.
The C code generated by glib-mkenums and its templates did not use
GOnce, so registration of enums/flags across threads would have been
buggy.
Cargo.lock | 3 ++
Makefile.am | 46 ++----------------------
librsvg/rsvg-handle.c | 16 +++++++++
librsvg/rsvg.h | 7 +++-
rsvg_internals/Cargo.toml | 3 ++
rsvg_internals/src/c_api.rs | 88 +++++++++++++++++++++++++++++++++++++++++++++
rsvg_internals/src/error.rs | 3 ++
rsvg_internals/src/lib.rs | 7 ++++
8 files changed, 129 insertions(+), 44 deletions(-)
---
diff --git a/Cargo.lock b/Cargo.lock
index 635e4e7b..b0024ae7 100644
--- a/Cargo.lock
+++ b/Cargo.lock
@@ -1,3 +1,5 @@
+# This file is automatically @generated by Cargo.
+# It is not intended for manual editing.
[[package]]
name = "aho-corasick"
version = "0.6.8"
@@ -886,6 +888,7 @@ dependencies = [
"gdk-pixbuf 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)",
"glib 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)",
"glib-sys 0.6.0 (registry+https://github.com/rust-lang/crates.io-index)",
+ "gobject-sys 0.6.0 (registry+https://github.com/rust-lang/crates.io-index)",
"itertools 0.7.8 (registry+https://github.com/rust-lang/crates.io-index)",
"language-tags 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)",
"lazy_static 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
diff --git a/Makefile.am b/Makefile.am
index acf51182..9f608543 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -14,14 +14,7 @@ headers = \
librsvg/rsvg.h \
librsvg/rsvg-cairo.h
-enum_sources = \
- librsvg/librsvg-enum-types.h \
- librsvg/librsvg-enum-types.c
-BUILT_SOURCES += $(enum_sources)
-
librsvg_@RSVG_API_MAJOR_VERSION@_la_SOURCES = \
- librsvg/librsvg-enum-types.c \
- librsvg/librsvg-enum-types.h \
librsvg/librsvg-features.c \
librsvg/librsvg-features.h \
librsvg/rsvg-attributes.h \
@@ -47,6 +40,7 @@ RUST_SRC = \
rsvg_internals/src/aspect_ratio.rs \
rsvg_internals/src/attributes.rs \
rsvg_internals/src/bbox.rs \
+ rsvg_internals/src/c_api.rs \
rsvg_internals/src/clip_path.rs \
rsvg_internals/src/color.rs \
rsvg_internals/src/cond.rs \
@@ -205,8 +199,7 @@ librsvg_@RSVG_API_MAJOR_VERSION@_la_LIBADD = \
librsvgincdir = $(includedir)/librsvg-$(RSVG_API_VERSION)/librsvg
librsvginc_HEADERS = \
$(headers) \
- librsvg/librsvg-features.h \
- librsvg/librsvg-enum-types.h
+ librsvg/librsvg-features.h
dist_man_MANS = rsvg-convert.1
@@ -286,45 +279,12 @@ EXTRA_DIST = \
tap-driver.sh \
tap-test
-CLEANFILES = \
- $(enum_sources) \
- librsvg/s-enum-types-h librsvg/s-enum-types-c
-
## Put `exec' in the name because this should be installed by
## `install-exec', not `install-data'.
pkgconfigdir = $(libdir)/pkgconfig
pkgconfig_DATA = librsvg-$(RSVG_API_VERSION).pc
-librsvg/librsvg-enum-types.h: librsvg/s-enum-types-h
- @true
-
-librsvg/s-enum-types-h: $(headers) Makefile
- $(AM_V_GEN) ( cd $(srcdir) && $(GLIB_MKENUMS) \
- --fhead "#if !defined (__RSVG_RSVG_H_INSIDE__) && !defined
(RSVG_COMPILATION)\n#warning \"Including <librsvg/librsvg-enum-types.h> directly is
deprecated.\"\n#endif\n\n#ifndef __LIBRSVG_ENUM_TYPES_H__\n#define __LIBRSVG_ENUM_TYPES_H__\n\n#include
<glib-object.h>\n\nG_BEGIN_DECLS\n" \
- --fprod "/* enumerations from \"@filename@\" */\n" \
- --vhead "GType @enum_name@_get_type (void);\n#define RSVG_TYPE_@ENUMSHORT@
(@enum_name@_get_type())\n" \
- --ftail "G_END_DECLS\n\n#endif /* __LIBRSVG_ENUM_TYPES_H__ */" \
- $(headers) ) > librsvg/tmp-librsvg-enum-types.h \
- && (cmp -s librsvg/tmp-librsvg-enum-types.h librsvg/librsvg-enum-types.h || cp
librsvg/tmp-librsvg-enum-types.h librsvg/librsvg-enum-types.h ) \
- && rm -f librsvg/tmp-librsvg-enum-types.h \
- && echo timestamp > $@
-
-librsvg/librsvg-enum-types.c: librsvg/s-enum-types-c librsvg/librsvg-enum-types.h
- @true
-
-librsvg/s-enum-types-c: $(headers) Makefile
- $(AM_V_GEN) ( cd $(srcdir) && $(GLIB_MKENUMS) \
- --fhead "#include \"librsvg/rsvg.h\"" \
- --fprod "\n/* enumerations from \"@filename@\" */" \
- --vhead "GType\n@enum_name@_get_type (void)\n{\n static GType etype = 0;\n if
(etype == 0) {\n static const G@Type@Value values[] = {" \
- --vprod " { @VALUENAME@, \"@VALUENAME@\", \"@valuenick@\" }," \
- --vtail " { 0, NULL, NULL }\n };\n etype = g_@type@_register_static
(\"@EnumName@\", values);\n }\n return etype;\n}\n" \
- $(headers) ) > librsvg/tmp-librsvg-enum-types.c \
- && (cmp -s librsvg/tmp-librsvg-enum-types.c librsvg/librsvg-enum-types.c || cp
librsvg/tmp-librsvg-enum-types.c librsvg/librsvg-enum-types.c ) \
- && rm -f librsvg/tmp-librsvg-enum-types.c \
- && echo timestamp > $@
-
DISTCHECK_CONFIGURE_FLAGS = --enable-gtk-doc
if HAVE_INTROSPECTION
@@ -363,7 +323,7 @@ nodist_gir_DATA = $(INTROSPECTION_GIRS)
typelibsdir = $(libdir)/girepository-1.0
nodist_typelibs_DATA = $(INTROSPECTION_GIRS:.gir=.typelib)
-CLEANFILES += $(nodist_gir_DATA) $(nodist_typelibs_DATA)
+CLEANFILES = $(nodist_gir_DATA) $(nodist_typelibs_DATA)
if ENABLE_VAPIGEN
include $(VAPIGEN_MAKEFILE)
diff --git a/librsvg/rsvg-handle.c b/librsvg/rsvg-handle.c
index af66b5e8..72bcacbf 100644
--- a/librsvg/rsvg-handle.c
+++ b/librsvg/rsvg-handle.c
@@ -128,6 +128,10 @@
#include "rsvg-load.h"
#include "rsvg-private.h"
+/* Implemented in rsvg_internals/src/c_api.rs */
+extern GType rsvg_rust_error_get_type (void);
+extern GType rsvg_rust_handle_flags_get_type (void);
+
enum {
PROP_0,
PROP_FLAGS,
@@ -1876,3 +1880,15 @@ rsvg_handle_internal_set_testing (RsvgHandle *handle, gboolean testing)
rsvg_handle_update_font_map_for_testing (handle);
}
+
+GType
+rsvg_error_get_type(void)
+{
+ return rsvg_rust_error_get_type();
+}
+
+GType
+rsvg_handle_flags_get_type(void)
+{
+ return rsvg_rust_handle_flags_get_type();
+}
diff --git a/librsvg/rsvg.h b/librsvg/rsvg.h
index 2e73dbf9..623a4d37 100644
--- a/librsvg/rsvg.h
+++ b/librsvg/rsvg.h
@@ -65,6 +65,9 @@ typedef enum {
#define RSVG_ERROR (rsvg_error_quark ())
GQuark rsvg_error_quark (void) G_GNUC_CONST;
+GType rsvg_error_get_type (void);
+#define RSVG_TYPE_ERROR (rsvg_error_get_type())
+
typedef struct _RsvgHandle RsvgHandle;
typedef struct RsvgHandlePrivate RsvgHandlePrivate;
typedef struct _RsvgHandleClass RsvgHandleClass;
@@ -174,6 +177,9 @@ typedef enum /*< flags >*/
RSVG_HANDLE_FLAG_KEEP_IMAGE_DATA = 1 << 1
} RsvgHandleFlags;
+GType rsvg_handle_flags_get_type (void);
+#define RSVG_TYPE_HANDLE_FLAGS (rsvg_handle_flags_get_type())
+
RsvgHandle *rsvg_handle_new_with_flags (RsvgHandleFlags flags);
void rsvg_handle_set_base_gfile (RsvgHandle *handle,
@@ -262,7 +268,6 @@ const char *rsvg_handle_get_metadata (RsvgHandle * handle);
G_END_DECLS
-#include "librsvg-enum-types.h"
#include "librsvg-features.h"
#include "rsvg-cairo.h"
diff --git a/rsvg_internals/Cargo.toml b/rsvg_internals/Cargo.toml
index 32f6eae6..61b1ffd2 100644
--- a/rsvg_internals/Cargo.toml
+++ b/rsvg_internals/Cargo.toml
@@ -65,6 +65,9 @@ version = "0.6"
#git = "https://github.com/gtk-rs/sys"
#branch = "master"
+[dependencies.gobject-sys]
+version = "0.6"
+
[dependencies.gdk-pixbuf]
version = "0.4"
diff --git a/rsvg_internals/src/c_api.rs b/rsvg_internals/src/c_api.rs
new file mode 100644
index 00000000..83314050
--- /dev/null
+++ b/rsvg_internals/src/c_api.rs
@@ -0,0 +1,88 @@
+use std::sync::Once;
+
+use glib_sys;
+use gobject_sys::{self, GEnumValue, GFlagsValue};
+
+use error::RSVG_ERROR_FAILED;
+
+#[no_mangle]
+pub unsafe extern "C" fn rsvg_rust_error_get_type() -> glib_sys::GType {
+ static ONCE: Once = Once::new();
+ static mut ETYPE: glib_sys::GType = gobject_sys::G_TYPE_INVALID;
+
+ // We have to store the GEnumValue in a static variable but
+ // that requires it to be Sync. It is not Sync by default
+ // because it contains pointers, so we have define a custom
+ // wrapper type here on which we can implement Sync.
+ #[repr(transparent)]
+ struct GEnumValueWrapper(GEnumValue);
+ unsafe impl Sync for GEnumValueWrapper {}
+
+ static VALUES: [GEnumValueWrapper; 2] = [
+ GEnumValueWrapper(GEnumValue {
+ value: RSVG_ERROR_FAILED,
+ value_name: b"RSVG_ERROR_FAILED\0" as *const u8 as *const _,
+ value_nick: b"failed\0" as *const u8 as *const _,
+ }),
+ GEnumValueWrapper(GEnumValue {
+ value: 0,
+ value_name: 0 as *const _,
+ value_nick: 0 as *const _,
+ }),
+ ];
+
+ ONCE.call_once(|| {
+ ETYPE = gobject_sys::g_enum_register_static(
+ b"RsvgError\0" as *const u8 as *const _,
+ &VALUES as *const GEnumValueWrapper as *const GEnumValue,
+ );
+ });
+
+ ETYPE
+}
+
+#[no_mangle]
+pub unsafe extern "C" fn rsvg_rust_handle_flags_get_type() -> glib_sys::GType {
+ static ONCE: Once = Once::new();
+ static mut FTYPE: glib_sys::GType = gobject_sys::G_TYPE_INVALID;
+
+ // We have to store the GFlagsValue in a static variable but
+ // that requires it to be Sync. It is not Sync by default
+ // because it contains pointers, so we have define a custom
+ // wrapper type here on which we can implement Sync.
+ #[repr(transparent)]
+ struct GFlagsValueWrapper(GFlagsValue);
+ unsafe impl Sync for GFlagsValueWrapper {}
+
+ static VALUES: [GFlagsValueWrapper; 4] = [
+ GFlagsValueWrapper(GFlagsValue {
+ value: 0, // handle_flags::HandleFlags::NONE.bits(),
+ value_name: b"RSVG_HANDLE_FLAGS_NONE\0" as *const u8 as *const _,
+ value_nick: b"flags-none\0" as *const u8 as *const _,
+ }),
+ GFlagsValueWrapper(GFlagsValue {
+ value: 1 << 0, // HandleFlags::UNLIMITED.to_glib(),
+ value_name: b"RSVG_HANDLE_FLAG_UNLIMITED\0" as *const u8 as *const _,
+ value_nick: b"flag-unlimited\0" as *const u8 as *const _,
+ }),
+ GFlagsValueWrapper(GFlagsValue {
+ value: 1 << 1, // HandleFlags::KEEP_IMAGE_DATA.to_glib(),
+ value_name: b"RSVG_HANDLE_FLAG_KEEP_IMAGE_DATA\0" as *const u8 as *const _,
+ value_nick: b"flag-keep-image-data\0" as *const u8 as *const _,
+ }),
+ GFlagsValueWrapper(GFlagsValue {
+ value: 0,
+ value_name: 0 as *const _,
+ value_nick: 0 as *const _,
+ }),
+ ];
+
+ ONCE.call_once(|| {
+ FTYPE = gobject_sys::g_flags_register_static(
+ b"RsvgHandleFlags\0" as *const u8 as *const _,
+ &VALUES as *const GFlagsValueWrapper as *const GFlagsValue,
+ );
+ });
+
+ FTYPE
+}
diff --git a/rsvg_internals/src/error.rs b/rsvg_internals/src/error.rs
index 4ced1898..df0d9b9d 100644
--- a/rsvg_internals/src/error.rs
+++ b/rsvg_internals/src/error.rs
@@ -138,3 +138,6 @@ pub fn is_value_error<T>(r: &Result<T, ValueErrorKind>) -> bool {
_ => false,
}
}
+
+// Keep in sync with rsvg.h:RsvgError
+pub const RSVG_ERROR_FAILED: i32 = 0;
diff --git a/rsvg_internals/src/lib.rs b/rsvg_internals/src/lib.rs
index 3bd41a1c..1d36d394 100644
--- a/rsvg_internals/src/lib.rs
+++ b/rsvg_internals/src/lib.rs
@@ -9,6 +9,7 @@ extern crate float_cmp;
extern crate gdk_pixbuf;
extern crate glib;
extern crate glib_sys;
+extern crate gobject_sys;
extern crate itertools;
extern crate language_tags;
extern crate libc;
@@ -28,6 +29,11 @@ extern crate lazy_static;
extern crate downcast_rs;
+pub use c_api::{
+ rsvg_rust_error_get_type,
+ rsvg_rust_handle_flags_get_type,
+};
+
pub use color::{rsvg_css_parse_color, ColorKind, ColorSpec};
pub use css::{rsvg_css_parse_into_handle, rsvg_css_styles_free, rsvg_css_styles_new};
@@ -91,6 +97,7 @@ mod property_macros;
mod aspect_ratio;
mod attributes;
mod bbox;
+mod c_api;
mod clip_path;
mod color;
mod cond;
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]