Repository: servo/servo
File: components/servo/lib.rs (Rust)

Code before:
    }
}

#[cfg(not(feature = "media-gstreamer"))]
mod media_platform {
    use super::ServoMedia;
    pub fn init() {
        ServoMedia::init::<servo_media_dummy::DummyBackend>();
    }
}

/// The in-process interface to Servo.
///
/// It does everything necessary to render the web, primarily
/// orchestrating the interaction between JavaScript, CSS layout,
/// rendering, and the client window.
///
// Clients create an event loop to pump messages between the embedding
// application and various browser components.
pub struct Servo {
    delegate: RefCell<Rc<dyn ServoDelegate>>,
    compositor: Rc<RefCell<IOCompositor>>,
    constellation_proxy: ConstellationProxy,
    embedder_receiver: Receiver<EmbedderMsg>,
    /// A Crossbeam Sender to asynchronusly notify WebDriver server that shutdown has completed.
    webdriver_shutdown_status_sender: Cell<Option<Sender<()>>>,
    /// A struct that tracks ongoing JavaScript evaluations and is responsible for
    /// calling the callback when the evaluation is complete.
    javascript_evaluator: Rc<RefCell<JavaScriptEvaluator>>,
    /// Tracks whether we are in the process of shutting down, or have shut down.
    /// This is shared with `WebView`s and the `ServoRenderer`.
    shutdown_state: Rc<Cell<ShutdownState>>,
    /// A map  [`WebView`]s that are managed by this [`Servo`] instance. These are stored
    /// as `Weak` references so that the embedding application can control their lifetime.
    /// When accessed, `Servo` will be reponsible for cleaning up the invalid `Weak`
    /// references.
    webviews: RefCell<FxHashMap<WebViewId, Weak<RefCell<WebViewInner>>>>,
    servo_errors: ServoErrorChannel,
    /// For single-process Servo instances, this field controls the initialization
    /// and deinitialization of the JS Engine. Multiprocess Servo instances have their
    /// own instance that exists in the content process instead.
    _js_engine_setup: Option<JSEngineSetup>,
    /// Whether or not any WebView in this instance is animating or WebXR is enabled.
    animating: Cell<bool>,
}

impl Servo {
    #[servo_tracing::instrument(skip(builder))]
    fn new(builder: ServoBuilder) -> Self {
        // Global configuration options, parsed from the command line.
        let opts = builder.opts.map(|opts| *opts);

Review comment (suggestion):
I think we can avoid pushing details of WebDriver into the API here. Instead of storing this channel in `Servo`, please store it somewhere in servoshell. Once `servo().spin_event_loop()` returns `false` in servoshell, you know that shutdown has finished and can message the channel that you've stored.

Code after:
    }
}

#[cfg(not(feature = "media-gstreamer"))]
mod media_platform {
    use super::ServoMedia;
    pub fn init() {
        ServoMedia::init::<servo_media_dummy::DummyBackend>();
    }
}

/// The in-process interface to Servo.
///
/// It does everything necessary to render the web, primarily
/// orchestrating the interaction between JavaScript, CSS layout,
/// rendering, and the client window.
///
// Clients create an event loop to pump messages between the embedding
// application and various browser components.
pub struct Servo {
    delegate: RefCell<Rc<dyn ServoDelegate>>,
    compositor: Rc<RefCell<IOCompositor>>,
    constellation_proxy: ConstellationProxy,
    embedder_receiver: Receiver<EmbedderMsg>,
    /// A struct that tracks ongoing JavaScript evaluations and is responsible for
    /// calling the callback when the evaluation is complete.
    javascript_evaluator: Rc<RefCell<JavaScriptEvaluator>>,
    /// Tracks whether we are in the process of shutting down, or have shut down.
    /// This is shared with `WebView`s and the `ServoRenderer`.
    shutdown_state: Rc<Cell<ShutdownState>>,
    /// A map  [`WebView`]s that are managed by this [`Servo`] instance. These are stored
    /// as `Weak` references so that the embedding application can control their lifetime.
    /// When accessed, `Servo` will be reponsible for cleaning up the invalid `Weak`
    /// references.
    webviews: RefCell<FxHashMap<WebViewId, Weak<RefCell<WebViewInner>>>>,
    servo_errors: ServoErrorChannel,
    /// For single-process Servo instances, this field controls the initialization
    /// and deinitialization of the JS Engine. Multiprocess Servo instances have their
    /// own instance that exists in the content process instead.
    _js_engine_setup: Option<JSEngineSetup>,
    /// Whether or not any WebView in this instance is animating or WebXR is enabled.
    animating: Cell<bool>,
}

impl Servo {
    #[servo_tracing::instrument(skip(builder))]
    fn new(builder: ServoBuilder) -> Self {
        // Global configuration options, parsed from the command line.
        let opts = builder.opts.map(|opts| *opts);
        opts::initialize_options(opts.unwrap_or_default());
        let opts = opts::get();