This patch rewrites the rust-url-capi crate as the mozurl crate, which provides a threadsafe MozURL object which is compatible with the previous MozURL class. Creating a MozURL this way performs a single allocation, which contains only a rust-url Url object and an atomic refcnt, however it is fully compatible with the C++ RefPtr type. This patch also exposes methods for accessing dependent substrings of the serialized spec, meaning that string copies can be avoided in many situations when inspecting attributes of the MozURL.
90 lines
2.9 KiB
Rust
90 lines
2.9 KiB
Rust
// This Source Code Form is subject to the terms of the Mozilla Public
|
|
// License, v. 2.0. If a copy of the MPL was not distributed with this
|
|
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
|
|
|
#[cfg(feature="servo")]
|
|
extern crate geckoservo;
|
|
|
|
extern crate mp4parse_capi;
|
|
extern crate nsstring;
|
|
extern crate nserror;
|
|
extern crate xpcom;
|
|
extern crate netwerk_helper;
|
|
extern crate prefs_parser;
|
|
extern crate mozurl;
|
|
#[cfg(feature = "quantum_render")]
|
|
extern crate webrender_bindings;
|
|
#[cfg(feature = "cubeb_pulse_rust")]
|
|
extern crate cubeb_pulse;
|
|
extern crate encoding_c;
|
|
extern crate encoding_glue;
|
|
#[cfg(feature = "cubeb-remoting")]
|
|
extern crate audioipc_client;
|
|
#[cfg(feature = "cubeb-remoting")]
|
|
extern crate audioipc_server;
|
|
extern crate u2fhid;
|
|
extern crate log;
|
|
extern crate cosec;
|
|
extern crate rsdparsa_capi;
|
|
|
|
use std::boxed::Box;
|
|
use std::ffi::CStr;
|
|
use std::os::raw::c_char;
|
|
use std::panic;
|
|
|
|
|
|
|
|
/// Used to implement `nsIDebug2::RustPanic` for testing purposes.
|
|
#[no_mangle]
|
|
pub extern "C" fn intentional_panic(message: *const c_char) {
|
|
panic!("{}", unsafe { CStr::from_ptr(message) }.to_string_lossy());
|
|
}
|
|
|
|
/// Contains the panic message, if set.
|
|
static mut PANIC_REASON: Option<*const str> = None;
|
|
|
|
/// Configure a panic hook to capture panic messages for crash reports.
|
|
///
|
|
/// We don't store this in `gMozCrashReason` because:
|
|
/// a) Rust strings aren't null-terminated, so we'd have to allocate
|
|
/// memory to get a null-terminated string
|
|
/// b) The panic=abort handler is going to call `abort()` on non-Windows,
|
|
/// which is `mozalloc_abort` for us, which will use `MOZ_CRASH` and
|
|
/// overwrite `gMozCrashReason` with an unhelpful string.
|
|
#[no_mangle]
|
|
pub extern "C" fn install_rust_panic_hook() {
|
|
let default_hook = panic::take_hook();
|
|
panic::set_hook(Box::new(move |info| {
|
|
// Try to handle &str/String payloads, which should handle 99% of cases.
|
|
let payload = info.payload();
|
|
// We'll hold a raw *const str here, but it will be OK because
|
|
// Rust is going to abort the process before the payload could be
|
|
// deallocated.
|
|
if let Some(s) = payload.downcast_ref::<&str>() {
|
|
unsafe { PANIC_REASON = Some(*s as *const str); }
|
|
} else if let Some(s) = payload.downcast_ref::<String>() {
|
|
unsafe { PANIC_REASON = Some(s.as_str() as *const str); }
|
|
} else {
|
|
// Not the most helpful thing, but seems unlikely to happen
|
|
// in practice.
|
|
println!("Unhandled panic payload!");
|
|
}
|
|
// Fall through to the default hook so we still print the reason and
|
|
// backtrace to the console.
|
|
default_hook(info);
|
|
}));
|
|
}
|
|
|
|
#[no_mangle]
|
|
pub extern "C" fn get_rust_panic_reason(reason: *mut *const c_char, length: *mut usize) -> bool {
|
|
unsafe {
|
|
if let Some(s) = PANIC_REASON {
|
|
*reason = s as *const c_char;
|
|
*length = (*s).len();
|
|
true
|
|
} else {
|
|
false
|
|
}
|
|
}
|
|
}
|