Skip to content

Commit

Permalink
stylo: Remove usage of ServoComputedValues from binding functions
Browse files Browse the repository at this point in the history
  • Loading branch information
Manishearth committed Jul 21, 2017
1 parent 9776d07 commit 3c3e439
Show file tree
Hide file tree
Showing 7 changed files with 71 additions and 46 deletions.
6 changes: 6 additions & 0 deletions components/servo_arc/lib.rs
Expand Up @@ -889,6 +889,12 @@ impl<'a, T> ArcBorrow<'a, T> {
arc
}

/// For constructing from a reference known to be Arc-backed,
/// e.g. if we obtain such a reference over FFI
pub unsafe fn from_ref(r: &'a T) -> Self {
ArcBorrow(r)
}

pub fn with_arc<F, U>(&self, f: F) -> U where F: FnOnce(&Arc<T>) -> U, T: 'static {
// Synthesize transient Arc, which never touches the refcount.
let transient = unsafe { NoDrop::new(Arc::from_raw(self.0)) };
Expand Down
35 changes: 29 additions & 6 deletions components/style/gecko/arc_types.rs
Expand Up @@ -13,13 +13,14 @@ use gecko_bindings::bindings::{RawServoKeyframe, RawServoKeyframesRule};
use gecko_bindings::bindings::{RawServoMediaRule, RawServoNamespaceRule, RawServoPageRule};
use gecko_bindings::bindings::{RawServoRuleNode, RawServoRuleNodeStrong, RawServoDocumentRule};
use gecko_bindings::bindings::ServoCssRules;
use gecko_bindings::structs::{RawServoAnimationValue, RawServoDeclarationBlock, RawServoStyleRule, RawServoMediaList};
use gecko_bindings::structs::{RawServoStyleSheetContents, ServoStyleContext};
use gecko_bindings::sugar::ownership::{HasArcFFI, HasFFI};
use gecko_bindings::structs::{RawServoAnimationValue, RawServoDeclarationBlock, RawServoStyleRule};
use gecko_bindings::structs::{RawServoMediaList, RawServoStyleSheetContents};
use gecko_bindings::sugar::ownership::{HasArcFFI, HasFFI, Strong};
use media_queries::MediaList;
use properties::{ComputedValues, PropertyDeclarationBlock};
use properties::animated_properties::AnimationValue;
use rule_tree::StrongRuleNode;
use servo_arc::{Arc, ArcBorrow};
use shared_lock::Locked;
use std::{mem, ptr};
use stylesheets::{CssRules, StylesheetContents, StyleRule, ImportRule, KeyframesRule, MediaRule};
Expand Down Expand Up @@ -51,9 +52,6 @@ impl_arc_ffi!(Locked<CssRules> => ServoCssRules
impl_arc_ffi!(StylesheetContents => RawServoStyleSheetContents
[Servo_StyleSheetContents_AddRef, Servo_StyleSheetContents_Release]);

impl_arc_ffi!(ComputedValues => ServoStyleContext
[Servo_StyleContext_AddRef, Servo_StyleContext_Release]);

impl_arc_ffi!(Locked<PropertyDeclarationBlock> => RawServoDeclarationBlock
[Servo_DeclarationBlock_AddRef, Servo_DeclarationBlock_Release]);

Expand Down Expand Up @@ -114,3 +112,28 @@ pub unsafe extern "C" fn Servo_RuleNode_Release(obj: &RawServoRuleNode) {
let ptr = StrongRuleNode::from_ffi(&obj);
ptr::read(ptr as *const StrongRuleNode);
}

// ServoStyleContext is not an opaque type on any side of FFI.
// This means that doing the HasArcFFI type trick is actually unsound,
// since it gives us a way to construct an Arc<ServoStyleContext> from
// an &ServoStyleContext, which in general is not allowed. So we
// implement the restricted set of arc type functionality we need.

#[no_mangle]
pub unsafe extern "C" fn Servo_StyleContext_AddRef(obj: &ComputedValues) {
mem::forget(ArcBorrow::from_ref(obj).clone_arc());
}

#[no_mangle]
pub unsafe extern "C" fn Servo_StyleContext_Release(obj: &ComputedValues) {
ArcBorrow::from_ref(obj).with_arc(|a: &Arc<ComputedValues>| {
let _: Arc<ComputedValues> = ptr::read(a);
});
}


impl From<Arc<ComputedValues>> for Strong<ComputedValues> {
fn from(arc: Arc<ComputedValues>) -> Self {
unsafe { mem::transmute(Arc::into_raw_offset(arc)) }
}
}
14 changes: 7 additions & 7 deletions components/style/gecko/generated/bindings.rs
Expand Up @@ -5,7 +5,7 @@ use gecko_bindings::structs::nsStyleTransformMatrix;
use gecko_bindings::structs::nsTArray;
type nsACString_internal = nsACString;
type nsAString_internal = nsAString;
pub type ServoStyleContextBorrowed<'a> = &'a ServoStyleContext;
pub type ServoStyleContextBorrowed<'a> = &'a ::properties::ComputedValues;
pub type ServoStyleContextBorrowedOrNull<'a> = Option<&'a ::properties::ComputedValues>;
pub type ServoComputedValuesBorrowed<'a> = &'a ServoComputedValues;
pub type ServoComputedValuesBorrowedOrNull<'a> = Option<&'a ServoComputedValues>;
Expand Down Expand Up @@ -2322,7 +2322,7 @@ extern "C" {
}
extern "C" {
pub fn Servo_ComputedValues_SpecifiesAnimationsOrTransitions(computed_values:
ServoComputedValuesBorrowed)
ServoStyleContextBorrowed)
-> bool;
}
extern "C" {
Expand Down Expand Up @@ -2705,7 +2705,7 @@ extern "C" {
}
extern "C" {
pub fn Servo_ComputedValues_GetStyleBits(values:
ServoComputedValuesBorrowed)
ServoStyleContextBorrowed)
-> u64;
}
extern "C" {
Expand All @@ -2717,7 +2717,7 @@ extern "C" {
}
extern "C" {
pub fn Servo_ComputedValues_GetStyleRuleList(values:
ServoComputedValuesBorrowed,
ServoStyleContextBorrowed,
rules:
RawGeckoServoStyleRuleListBorrowedMut);
}
Expand Down Expand Up @@ -2804,17 +2804,17 @@ extern "C" {
}
extern "C" {
pub fn Servo_GetCustomPropertyValue(computed_values:
ServoComputedValuesBorrowed,
ServoStyleContextBorrowed,
name: *const nsAString,
value: *mut nsAString) -> bool;
}
extern "C" {
pub fn Servo_GetCustomPropertiesCount(computed_values:
ServoComputedValuesBorrowed)
ServoStyleContextBorrowed)
-> u32;
}
extern "C" {
pub fn Servo_GetCustomPropertyNameAt(arg1: ServoComputedValuesBorrowed,
pub fn Servo_GetCustomPropertyNameAt(arg1: ServoStyleContextBorrowed,
index: u32, name: *mut nsAString)
-> bool;
}
Expand Down
2 changes: 1 addition & 1 deletion components/style/gecko/generated/structs_debug.rs
Expand Up @@ -16,7 +16,7 @@ pub type ServoRuleNode = Option<::rule_tree::StrongRuleNode>;
pub type ServoVisitedStyle = Option<::servo_arc::RawOffsetArc<::properties::ComputedValues>>;
pub type ServoComputedValueFlags = ::properties::computed_value_flags::ComputedValueFlags;
pub type ServoRawOffsetArc<T> = ::servo_arc::RawOffsetArc<T>;
pub type ServoStyleContextStrong = ::gecko_bindings::sugar::ownership::Strong<ServoStyleContext>;
pub type ServoStyleContextStrong = ::gecko_bindings::sugar::ownership::Strong<::properties::ComputedValues>;

#[allow(non_snake_case, non_camel_case_types, non_upper_case_globals)]
pub mod root {
Expand Down
2 changes: 1 addition & 1 deletion components/style/gecko/generated/structs_release.rs
Expand Up @@ -16,7 +16,7 @@ pub type ServoRuleNode = Option<::rule_tree::StrongRuleNode>;
pub type ServoVisitedStyle = Option<::servo_arc::RawOffsetArc<::properties::ComputedValues>>;
pub type ServoComputedValueFlags = ::properties::computed_value_flags::ComputedValueFlags;
pub type ServoRawOffsetArc<T> = ::servo_arc::RawOffsetArc<T>;
pub type ServoStyleContextStrong = ::gecko_bindings::sugar::ownership::Strong<ServoStyleContext>;
pub type ServoStyleContextStrong = ::gecko_bindings::sugar::ownership::Strong<::properties::ComputedValues>;

#[allow(non_snake_case, non_camel_case_types, non_upper_case_globals)]
pub mod root {
Expand Down
3 changes: 2 additions & 1 deletion components/style/properties/gecko.mako.rs
Expand Up @@ -227,7 +227,8 @@ impl ComputedValuesInner {
) -> Arc<ComputedValues> {
let arc = unsafe {
let arc: Arc<ComputedValues> = Arc::new(uninitialized());
bindings::Gecko_ServoStyleContext_Init(&arc.0 as *const _ as *mut _, parent, pres_context,
bindings::Gecko_ServoStyleContext_Init(&arc.0 as *const _ as *mut _,
parent, pres_context,
&self, pseudo_ty, pseudo_tag);
// We're simulating a move by having C++ do a memcpy and then forgetting
// it on this end.
Expand Down

0 comments on commit 3c3e439

Please sign in to comment.