Bug 1888683 - Upgrade UniFFI to 0.27.1. r=markh,janerik,glandium,supply-chain-reviewers,mach-reviewers,android-reviewers,kaya

Update:
  - UniFFI to 0.27.1
  - Glean to 59.0.0
  - App-services to a recent version

This removes the need for the goblin build hack, although we still have
duplicate versions of goblin since UniFFI is ahead of the moz-central
version.  I think that should be easy to resolve as a follow-up.

Updating uniffi-bindget-gecko-js based on upstream changes:
  - Clone objects before lowering them
    (https://github.com/mozilla/uniffi-rs/pull/1880)
  - Use u64 for the RustBuffer length and capacity field
    (https://github.com/mozilla/uniffi-rs/pull/1978)

I didn't implement the new callback interface VTable code.  Instead I
simply disabled the one fixture that tests it.  I'd rather implement
https://bugzilla.mozilla.org/show_bug.cgi?id=1888668 first, since that
will simplify the process a bunch. The only real-world use-case for
callbacks that I know of is Mark's logging changes, but that will
require implementing trait interfaces anyways so I'd rather wait than
write a bunch of C++ code that we then throw away.

Differential Revision: https://phabricator.services.mozilla.com/D206130
This commit is contained in:
Ben Dean-Kawamura 2024-04-09 20:15:16 +00:00
Родитель 259ecaefdf
Коммит 3c47b31e06
38 изменённых файлов: 292 добавлений и 88 удалений

8
Cargo.lock сгенерированный
Просмотреть файл

@ -2330,6 +2330,7 @@ dependencies = [
"uniffi-example-todolist",
"uniffi-fixture-callbacks",
"uniffi-fixture-external-types",
"uniffi-fixture-refcounts",
"url",
"viaduct",
"webext_storage_bridge",
@ -6107,6 +6108,13 @@ dependencies = [
"uniffi-example-geometry",
]
[[package]]
name = "uniffi-fixture-refcounts"
version = "0.21.0"
dependencies = [
"uniffi",
]
[[package]]
name = "uniffi_bindgen"
version = "0.25.3"

Просмотреть файл

@ -53,7 +53,8 @@ resolver = "2"
[workspace.dependencies]
# Shared across multiple UniFFI consumers.
uniffi = "0.25.3"
uniffi = "0.27.1"
uniffi_bindgen = "0.27.1"
# Shared across multiple application-services consumers.
rusqlite = "0.30.0"
@ -164,10 +165,12 @@ derive_more = { path = "build/rust/derive_more" }
# Patch autocfg to hide rustc output. Workaround for https://github.com/cuviper/autocfg/issues/30
autocfg = { path = "third_party/rust/autocfg" }
# Patch goblin 0.6.0 to 0.7.0 because uniffi crates still use the older version
# and we want to avoid duplications
# Patch goblin 0.7.0 to 0.8
goblin = { path = "build/rust/goblin" }
# Patch scroll 0.11 to 0.12
scroll = { path = "build/rust/scroll" }
# Patch memoffset from 0.8.0 to 0.9.0 since it's compatible and it avoids duplication
memoffset = { path = "build/rust/memoffset" }
@ -209,14 +212,14 @@ warp = { git = "https://github.com/seanmonstar/warp", rev = "9d081461ae1167eb321
malloc_size_of_derive = { path = "xpcom/rust/malloc_size_of_derive" }
# application-services overrides to make updating them all simpler.
interrupt-support = { git = "https://github.com/mozilla/application-services", rev = "9054db4bb5031881550ceab3448665ef6499a706" }
relevancy = { git = "https://github.com/mozilla/application-services", rev = "9054db4bb5031881550ceab3448665ef6499a706" }
sql-support = { git = "https://github.com/mozilla/application-services", rev = "9054db4bb5031881550ceab3448665ef6499a706" }
suggest = { git = "https://github.com/mozilla/application-services", rev = "9054db4bb5031881550ceab3448665ef6499a706" }
sync15 = { git = "https://github.com/mozilla/application-services", rev = "9054db4bb5031881550ceab3448665ef6499a706" }
tabs = { git = "https://github.com/mozilla/application-services", rev = "9054db4bb5031881550ceab3448665ef6499a706" }
viaduct = { git = "https://github.com/mozilla/application-services", rev = "9054db4bb5031881550ceab3448665ef6499a706" }
webext-storage = { git = "https://github.com/mozilla/application-services", rev = "9054db4bb5031881550ceab3448665ef6499a706" }
interrupt-support = { git = "https://github.com/mozilla/application-services", rev = "e6ccfed09ebe663f464a33968f42e656c152e584" }
relevancy = { git = "https://github.com/mozilla/application-services", rev = "e6ccfed09ebe663f464a33968f42e656c152e584" }
sql-support = { git = "https://github.com/mozilla/application-services", rev = "e6ccfed09ebe663f464a33968f42e656c152e584" }
suggest = { git = "https://github.com/mozilla/application-services", rev = "e6ccfed09ebe663f464a33968f42e656c152e584" }
sync15 = { git = "https://github.com/mozilla/application-services", rev = "e6ccfed09ebe663f464a33968f42e656c152e584" }
tabs = { git = "https://github.com/mozilla/application-services", rev = "e6ccfed09ebe663f464a33968f42e656c152e584" }
viaduct = { git = "https://github.com/mozilla/application-services", rev = "e6ccfed09ebe663f464a33968f42e656c152e584" }
webext-storage = { git = "https://github.com/mozilla/application-services", rev = "e6ccfed09ebe663f464a33968f42e656c152e584" }
# Patch mio 0.8.8 to use windows-sys 0.52 (backport https://github.com/tokio-rs/mio/commit/eea9e3e0c469480e5c59c01e6c3c7e5fd88f0848)
mio_0_8 = { package = "mio", git = "https://github.com/glandium/mio", rev = "9a2ef335c366044ffe73b1c4acabe50a1daefe05" }
@ -227,8 +230,8 @@ mio_0_8 = { package = "mio", git = "https://github.com/glandium/mio", rev = "9a2
path = "third_party/rust/mio-0.6.23"
[patch."https://github.com/mozilla/uniffi-rs.git"]
uniffi = "=0.25.3"
uniffi_bindgen = "=0.25.3"
uniffi_build = "=0.25.3"
uniffi_macros = "=0.25.3"
weedle2 = "=4.0.0"
uniffi = "0.27.1"
uniffi_bindgen = "0.27.1"
uniffi_build = "0.27.1"
uniffi_macros = "0.27.1"
weedle2 = "=5.0.0"

Просмотреть файл

@ -1,6 +1,6 @@
[package]
name = "goblin"
version = "0.6.999"
version = "0.7.999"
edition = "2018"
license = "MIT/Apache-2.0"
@ -8,4 +8,19 @@ license = "MIT/Apache-2.0"
path = "lib.rs"
[dependencies.goblin]
version = "0.7.0"
version = "0.8.0"
default-features = false
[features]
alloc = ["goblin/alloc"]
archive = ["goblin/archive"]
default = ["goblin/default"]
elf32 = ["goblin/elf32"]
elf64 = ["goblin/elf64"]
endian_fd = ["goblin/endian_fd"]
mach32 = ["goblin/mach32"]
mach64 = ["goblin/mach64"]
pe32 = ["goblin/pe32"]
pe64 = ["goblin/pe64"]
std = ["goblin/std"]

Просмотреть файл

@ -0,0 +1,17 @@
[package]
name = "scroll"
version = "0.11.999"
edition = "2018"
license = "MIT/Apache-2.0"
[lib]
path = "lib.rs"
[dependencies.scroll]
version = "0.12.0"
default-features = false
[features]
default = ["scroll/default"]
derive = ["scroll/derive"]
std = ["scroll/std"]

11
build/rust/scroll/lib.rs Normal file
Просмотреть файл

@ -0,0 +1,11 @@
// Copyright 2014 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
pub use scroll::*;

Просмотреть файл

@ -35,7 +35,7 @@ typedef unsigned long long UniFFICallbackObjectHandle;
// Opaque type used to represent a pointer from Rust
[ChromeOnly, Exposed=Window]
interface UniFFIPointer {};
interface UniFFIPointer { };
// Types that can be passed or returned from scaffolding functions
//

Просмотреть файл

@ -32,6 +32,8 @@ packages = [
# transition to syn 2 is underway.
"syn",
"synstructure",
# Requires an update to clap v4
"textwrap",
# Can be fixed by removing time dependency - see bug 1765324
"wasi",
]

Просмотреть файл

@ -52,7 +52,7 @@ svg_fmt = "0.4"
tracy-rs = "0.1.2"
derive_more = { version = "0.99", default-features = false, features = ["add_assign"] }
etagere = "0.2.6"
glean = { version = "58.1.0", optional = true }
glean = { version = "59.0.0", optional = true }
firefox-on-glean = { version = "0.1.0", optional = true }
swgl = { path = "../swgl", optional = true }
topological-sort = "0.1"

Просмотреть файл

@ -25,7 +25,7 @@ tracy-rs = "0.1.2"
log = "0.4"
lazy_static = "1"
fxhash = "0.2.1"
glean = { version = "58.1.0", optional = true }
glean = { version = "59.0.0", optional = true }
firefox-on-glean = { version = "0.1.0", optional = true }
serde = { optional = true, version = "1.0", features = ["serde_derive"] }

Просмотреть файл

@ -19,7 +19,7 @@ object Versions {
const val serialization = "1.6.3"
const val python_envs_plugin = "0.0.31"
const val mozilla_glean = "58.1.0"
const val mozilla_glean = "59.0.0"
const val junit = "4.13.2"
const val robolectric = "4.11.1"

Просмотреть файл

@ -93,7 +93,7 @@ vendored:third_party/python/wheel
vendored:third_party/python/zipp
# glean-sdk may not be installable if a wheel isn't available
# and it has to be built from source.
pypi-optional:glean-sdk==58.1.0:telemetry will not be collected
pypi-optional:glean-sdk==59.0.0:telemetry will not be collected
# Mach gracefully handles the case where `psutil` is unavailable.
# We aren't (yet) able to pin packages in automation, so we have to
# support down to the oldest locally-installed version (5.4.2).

Просмотреть файл

@ -3750,6 +3750,11 @@ who = "Mike Hommey <mh+mozilla@glandium.org>"
criteria = "safe-to-deploy"
delta = "0.15.2 -> 0.16.0"
[[audits.textwrap]]
who = "Jan-Erik Rediger <jrediger@mozilla.com>"
criteria = "safe-to-deploy"
delta = "0.16.0 -> 0.16.1"
[[audits.thin-vec]]
who = "Aria Beingessner <a.beingessner@gmail.com>"
criteria = "safe-to-deploy"

Просмотреть файл

@ -6,7 +6,7 @@ edition = "2018"
license = "MPL-2.0"
[dependencies]
glean = "58.1.0"
glean = "59.0.0"
log = "0.4"
nserror = { path = "../../../xpcom/rust/nserror" }
nsstring = { path = "../../../xpcom/rust/nsstring" }

Просмотреть файл

@ -9,7 +9,7 @@ license = "MPL-2.0"
[dependencies]
bincode = "1.0"
chrono = "0.4.10"
glean = "58.1.0"
glean = "59.0.0"
inherent = "1.0.0"
log = "0.4"
nsstring = { path = "../../../../xpcom/rust/nsstring", optional = true }

Просмотреть файл

@ -43,6 +43,7 @@ fn setup_glean(tempdir: Option<tempfile::TempDir>) -> tempfile::TempDir {
rate_limit: None,
enable_event_timestamps: false,
experimentation_id: None,
enable_internal_pings: true
};
let client_info = glean::ClientInfoMetrics {

Просмотреть файл

@ -184,6 +184,7 @@ fn build_configuration(
rate_limit,
enable_event_timestamps,
experimentation_id: None,
enable_internal_pings: true,
};
Ok((configuration, client_info))

Просмотреть файл

@ -15,7 +15,7 @@ clap = { version = "4", default-features = false, features = ["std", "derive", "
extend = "1.1"
heck = "0.4"
uniffi = { workspace = true }
uniffi_bindgen = "0.25"
uniffi_bindgen = { workspace = true }
serde = "1"
toml = "0.5"
camino = "1.0.8"

Просмотреть файл

@ -72,16 +72,27 @@ crate_name = "uniffi_todolist"
udl_file = "third_party/rust/uniffi-example-todolist/src/todolist.udl"
fixture = true
[fixture_callbacks]
crate_name = "uniffi_fixture_callbacks"
udl_file = "toolkit/components/uniffi-fixture-callbacks/src/callbacks.udl"
[fixture_refcounts]
crate_name = "uniffi_fixture_refcounts"
udl_file = "toolkit/components/uniffi-fixture-refcounts/src/refcounts.udl"
fixture = true
[fixture_callbacks.receiver_thread]
default = "worker"
main = [
"log_even_numbers_main_thread",
]
[fixture_refcounts.receiver_thread]
default = "main"
# Temporarily disabled until we can re-enable callback support
#
# I think this can be done when we implement https://bugzilla.mozilla.org/show_bug.cgi?id=1888668
# [fixture_callbacks]
# crate_name = "uniffi_fixture_callbacks"
# udl_file = "toolkit/components/uniffi-fixture-callbacks/src/callbacks.udl"
# fixture = true
#
# [fixture_callbacks.receiver_thread]
# default = "worker"
# main = [
# "log_even_numbers_main_thread",
# ]
[custom_types]
crate_name = "uniffi_custom_types"

Просмотреть файл

@ -12,6 +12,7 @@ components = [
"ExternalTypes",
"FixtureCallbacks",
"Geometry",
"Refcounts",
"Rondpoint",
"Sprites",
"Todolist",

Просмотреть файл

@ -0,0 +1,57 @@
/* Any copyright is dedicated to the Public Domain.
http://creativecommons.org/publicdomain/zero/1.0/ */
const { getSingleton, getJsRefcount } = ChromeUtils.importESModule(
"resource://gre/modules/RustRefcounts.sys.mjs"
);
// Test refcounts when we call methods.
//
// Each method call requires that we clone the Arc pointer on the JS side, then pass it to Rust
// which will consumer the reference. Make sure we get this right
function createObjectAndCallMethods() {
const obj = getSingleton();
obj.method();
}
add_test(() => {
// Create an object that we'll keep around. If the ref count ends up being low, we don't want
// to reduce it below 0, since the Rust code may catch that and clamp it
const obj = getSingleton();
createObjectAndCallMethods();
Cu.forceGC();
Cu.forceCC();
do_test_pending();
do_timeout(500, () => {
Assert.equal(getJsRefcount(), 1);
// Use `obj` to avoid unused warnings and try to ensure that JS doesn't destroy it early
obj.method();
do_test_finished();
run_next_test();
});
});
// Test refcounts when creating/destroying objects
function createAndDeleteObjects() {
[getSingleton(), getSingleton(), getSingleton()];
}
add_test(() => {
const obj = getSingleton();
createAndDeleteObjects();
Cu.forceGC();
Cu.forceCC();
do_timeout(500, () => {
Assert.equal(getJsRefcount(), 1);
obj.method();
do_test_finished();
run_next_test();
});
});
// As we implement more UniFFI features we should probably add refcount tests for it.
// Some features that should probably have tests:
// - Async methods
// - UniFFI builtin trait methods like 'to_string'
// - Rust trait objects

Просмотреть файл

@ -2,18 +2,33 @@
["test_arithmetic.js"]
# I think this can be re-enabled when we implement https://bugzilla.mozilla.org/show_bug.cgi?id=1888668
lineno = "3"
["test_callbacks.js"]
disabled = "Temporarily disabled until we can re-enable callback support"
lineno = "8"
["test_custom_types.js"]
lineno = "12"
["test_external_types.js"]
lineno = "15"
["test_geometry.js"]
lineno = "18"
["test_refcounts.js"]
lineno = "21"
["test_rondpoint.js"]
lineno = "24"
["test_sprites.js"]
lineno = "27"
["test_todolist.js"]
lineno = "30"
["test_type_checking.js"]
lineno = "33"

Просмотреть файл

@ -136,31 +136,25 @@ pub impl FfiType {
// Type for the Rust scaffolding code
fn rust_type(&self) -> String {
match self {
FfiType::UInt8 => "uint8_t",
FfiType::Int8 => "int8_t",
FfiType::UInt16 => "uint16_t",
FfiType::Int16 => "int16_t",
FfiType::UInt32 => "uint32_t",
FfiType::Int32 => "int32_t",
FfiType::UInt64 => "uint64_t",
FfiType::Int64 => "int64_t",
FfiType::Float32 => "float",
FfiType::Float64 => "double",
FfiType::RustBuffer(_) => "RustBuffer",
FfiType::RustArcPtr(_) => "void *",
FfiType::ForeignCallback => "ForeignCallback",
FfiType::UInt8 => "uint8_t".to_owned(),
FfiType::Int8 => "int8_t".to_owned(),
FfiType::UInt16 => "uint16_t".to_owned(),
FfiType::Int16 => "int16_t".to_owned(),
FfiType::UInt32 => "uint32_t".to_owned(),
FfiType::Int32 => "int32_t".to_owned(),
FfiType::UInt64 => "uint64_t".to_owned(),
FfiType::Int64 => "int64_t".to_owned(),
FfiType::Float32 => "float".to_owned(),
FfiType::Float64 => "double".to_owned(),
FfiType::RustBuffer(_) => "RustBuffer".to_owned(),
FfiType::RustArcPtr(_) => "void *".to_owned(),
FfiType::ForeignBytes => unimplemented!("ForeignBytes not supported"),
FfiType::ForeignExecutorHandle => unimplemented!("ForeignExecutorHandle not supported"),
FfiType::ForeignExecutorCallback => {
unimplemented!("ForeignExecutorCallback not supported")
}
FfiType::RustFutureHandle
| FfiType::RustFutureContinuationCallback
| FfiType::RustFutureContinuationData => {
unimplemented!("Rust async functions not supported")
}
FfiType::Handle => "uint64_t".to_owned(),
FfiType::RustCallStatus => "RustCallStatus".to_owned(),
FfiType::Callback(name) | FfiType::Struct(name) => name.to_owned(),
FfiType::VoidPointer => "void *".to_owned(),
FfiType::Reference(_) => unimplemented!("References not supported"),
}
.to_owned()
}
}

Просмотреть файл

@ -92,7 +92,8 @@ pub impl Literal {
Literal::Enum(name, typ) => render_enum_literal(typ, name),
Literal::EmptyMap => "{}".to_string(),
Literal::EmptySequence => "[]".to_string(),
Literal::Null => "null".to_string(),
Literal::Some { inner } => inner.render(),
Literal::None => "null".to_string(),
}
}
}
@ -258,7 +259,6 @@ pub impl Type {
| Type::CallbackInterface { name, .. } => format!("Type{name}"),
Type::Timestamp => "Timestamp".into(),
Type::Duration => "Duration".into(),
Type::ForeignExecutor => "ForeignExecutor".into(),
Type::Optional { inner_type } => format!("Optional{}", inner_type.canonical_name()),
Type::Sequence { inner_type } => format!("Sequence{}", inner_type.canonical_name()),
Type::Map {

Просмотреть файл

@ -37,7 +37,8 @@ extern "C" {
{%- let pointer_type = ci.pointer_type(object) %}
const static mozilla::uniffi::UniFFIPointerType {{ pointer_type }} {
"{{ "{}::{}"|format(ci.namespace(), object.name()) }}"_ns,
{{ object.ffi_object_free().rust_name() }}
{{ object.ffi_object_clone().rust_name() }},
{{ object.ffi_object_free().rust_name() }},
};
{%- endfor %}
{%- endfor %}

Просмотреть файл

@ -7,7 +7,7 @@ license = "MPL-2.0"
publish = false
[dependencies]
uniffi-example-geometry = { git = "https://github.com/mozilla/uniffi-rs.git", rev = "afb29ebdc1d9edf15021b1c5332fc9f285bbe13b" }
uniffi-example-geometry = { git = "https://github.com/mozilla/uniffi-rs.git", rev = "d52c5460ae42ecad1e73a5b394ac96d48f4769de" }
uniffi = { workspace = true }
thiserror = "1.0"

Просмотреть файл

@ -0,0 +1,12 @@
[package]
name = "uniffi-fixture-refcounts"
edition = "2021"
version = "0.21.0"
license = "MPL-2.0"
publish = false
[dependencies]
uniffi = { workspace = true }
[build-dependencies]
uniffi = { workspace = true, features = ["build"] }

Просмотреть файл

@ -0,0 +1,7 @@
/* 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/. */
fn main() {
uniffi::generate_scaffolding("./src/refcounts.udl").unwrap();
}

Просмотреть файл

@ -0,0 +1,28 @@
/* 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/. */
/// This crate exists to test managing the Rust Arc strong counts as JS objects are
/// created/destroyed. See `test_refcounts.js` for how it's used.
use std::sync::{Arc, Mutex};
pub struct SingletonObject;
impl SingletonObject {
pub fn method(&self) { }
}
static SINGLETON: Mutex<Option<Arc<SingletonObject>>> = Mutex::new(None);
pub fn get_singleton() -> Arc<SingletonObject> {
Arc::clone(SINGLETON.lock().unwrap().get_or_insert_with(|| Arc::new(SingletonObject)))
}
pub fn get_js_refcount() -> i32 {
// Subtract 2: one for the reference in the Mutex and one for the temporary reference that
// we're calling Arc::strong_count on.
(Arc::strong_count(&get_singleton()) as i32) - 2
}
include!(concat!(env!("OUT_DIR"), "/refcounts.uniffi.rs"));

Просмотреть файл

@ -0,0 +1,8 @@
namespace refcounts {
SingletonObject get_singleton();
i32 get_js_refcount();
};
interface SingletonObject {
void method();
};

Просмотреть файл

@ -27,7 +27,7 @@ Result<OwnedRustBuffer, nsCString> OwnedRustBuffer::FromArrayBuffer(
RustCallStatus status{};
RustBuffer buf = uniffi_rustbuffer_alloc(
static_cast<int32_t>(aData.Length()), &status);
static_cast<uint64_t>(aData.Length()), &status);
buf.len = aData.Length();
if (status.code != 0) {
if (status.error_buf.data) {
@ -84,7 +84,7 @@ RustBuffer OwnedRustBuffer::IntoRustBuffer() {
JSObject* OwnedRustBuffer::IntoArrayBuffer(JSContext* cx) {
JS::Rooted<JSObject*> obj(cx);
{
int32_t len = mBuf.len;
auto len = mBuf.len;
void* data = mBuf.data;
auto userData = MakeUnique<OwnedRustBuffer>(std::move(*this));
UniquePtr<void, JS::BufferContentsDeleter> dataPtr{

Просмотреть файл

@ -173,7 +173,7 @@ class ScaffoldingObjectConverter {
if (!value.IsSamePtrType(PointerType)) {
return Err("Bad pointer type"_ns);
}
return value.GetPtr();
return value.ClonePtr();
}
static void* IntoRust(void* aValue) { return aValue; }

Просмотреть файл

@ -82,7 +82,7 @@ void UniFFIPointer::Write(const ArrayBuffer& aArrayBuff, uint32_t aPosition,
// a pointer we do the reverse here
const auto& data_ptr = aData.Subspan(aPosition, 8);
mozilla::BigEndian::writeUint64(data_ptr.Elements(),
(uint64_t)GetPtr());
(uint64_t)ClonePtr());
return true;
})) {
aError.ThrowRangeError("position is out of range");
@ -100,10 +100,14 @@ JSObject* UniFFIPointer::WrapObject(JSContext* aCx,
return dom::UniFFIPointer_Binding::Wrap(aCx, this, aGivenProto);
}
void* UniFFIPointer::GetPtr() const {
void* UniFFIPointer::ClonePtr() const {
MOZ_LOG(sUniFFIPointerLogger, LogLevel::Info,
("[UniFFI] Getting raw pointer"));
return this->mPtr;
("[UniFFI] Cloning raw pointer"));
RustCallStatus status{};
auto cloned = this->mType->clone(this->mPtr, &status);
MOZ_DIAGNOSTIC_ASSERT(status.code == RUST_CALL_SUCCESS,
"UniFFI clone call returned a non-success result");
return cloned;
}
bool UniFFIPointer::IsSamePtrType(const UniFFIPointerType* aType) const {

Просмотреть файл

@ -36,15 +36,13 @@ class UniFFIPointer final : public nsISupports, public nsWrapperCache {
nsISupports* GetParentObject() { return nullptr; }
/**
* returns the raw pointer `UniFFIPointer` holds
* This is safe because:
* - The pointer was allocated in Rust as a reference counted `Arc<T>`
* - Rust cloned the pointer without destructing it when passed into C++
* - Eventually, when the destructor of `UniFFIPointer` runs, we return
* ownership to Rust, which then decrements the count and deallocates the
* memory the pointer points to.
* Clone the raw pointer that `UniFFIPointer` holds
*
* Use this when lowering the pointer to pass it across the FFI, for example:
* - When calling a method
* - When passing the object as an argument to a function
*/
void* GetPtr() const;
void* ClonePtr() const;
/**
* Returns true if the pointer type `this` holds is the same as the argument

Просмотреть файл

@ -21,7 +21,9 @@ namespace mozilla::uniffi {
**/
struct UniFFIPointerType {
nsLiteralCString typeName;
// The Rust destructor for the pointer, this gives back ownership to Rust
// Rust FFI function to clone for the pointer
void* (*clone)(void*, RustCallStatus*);
// Rust FFI function to destroy for the pointer
void (*destructor)(void*, RustCallStatus*);
};
} // namespace mozilla::uniffi

Просмотреть файл

@ -28,8 +28,8 @@ constexpr int8_t CALLBACK_INTERFACE_UNEXPECTED_ERROR = 2;
// structs/functions from UniFFI
extern "C" {
struct RustBuffer {
int32_t capacity;
int32_t len;
uint64_t capacity;
uint64_t len;
uint8_t* data;
};
@ -42,7 +42,7 @@ typedef int (*ForeignCallback)(uint64_t handle, uint32_t method,
const uint8_t* argsData, int32_t argsLen,
RustBuffer* buf_ptr);
RustBuffer uniffi_rustbuffer_alloc(int32_t size, RustCallStatus* call_status);
RustBuffer uniffi_rustbuffer_alloc(uint64_t size, RustCallStatus* call_status);
void uniffi_rustbuffer_free(RustBuffer buf, RustCallStatus* call_status);
}

Просмотреть файл

@ -72,18 +72,19 @@ origin-trials-ffi = { path = "../../../../dom/origin-trials/ffi" }
jog = { path = "../../../components/glean/bindings/jog" }
dap_ffi = { path = "../../../components/telemetry/dap/ffi" }
data-encoding-ffi = { path = "../../../../dom/fs/parent/rust/data-encoding-ffi" }
uniffi-example-arithmetic = { git = "https://github.com/mozilla/uniffi-rs.git", rev = "afb29ebdc1d9edf15021b1c5332fc9f285bbe13b", optional = true }
uniffi-example-geometry = { git = "https://github.com/mozilla/uniffi-rs.git", rev = "afb29ebdc1d9edf15021b1c5332fc9f285bbe13b", optional = true }
uniffi-example-rondpoint = { git = "https://github.com/mozilla/uniffi-rs.git", rev = "afb29ebdc1d9edf15021b1c5332fc9f285bbe13b", optional = true }
uniffi-example-sprites = { git = "https://github.com/mozilla/uniffi-rs.git", rev = "afb29ebdc1d9edf15021b1c5332fc9f285bbe13b", optional = true }
uniffi-example-todolist = { git = "https://github.com/mozilla/uniffi-rs.git", rev = "afb29ebdc1d9edf15021b1c5332fc9f285bbe13b", optional = true }
uniffi-example-arithmetic = { git = "https://github.com/mozilla/uniffi-rs.git", rev = "d52c5460ae42ecad1e73a5b394ac96d48f4769de", optional = true }
uniffi-example-geometry = { git = "https://github.com/mozilla/uniffi-rs.git", rev = "d52c5460ae42ecad1e73a5b394ac96d48f4769de", optional = true }
uniffi-example-rondpoint = { git = "https://github.com/mozilla/uniffi-rs.git", rev = "d52c5460ae42ecad1e73a5b394ac96d48f4769de", optional = true }
uniffi-example-sprites = { git = "https://github.com/mozilla/uniffi-rs.git", rev = "d52c5460ae42ecad1e73a5b394ac96d48f4769de", optional = true }
uniffi-example-todolist = { git = "https://github.com/mozilla/uniffi-rs.git", rev = "d52c5460ae42ecad1e73a5b394ac96d48f4769de", optional = true }
uniffi-example-custom-types = { path = "../../../components/uniffi-example-custom-types/", optional = true }
uniffi-fixture-callbacks = { path = "../../../components/uniffi-fixture-callbacks/", optional = true }
uniffi-fixture-external-types = { path = "../../../components/uniffi-fixture-external-types/", optional = true }
uniffi-fixture-refcounts = { path = "../../../components/uniffi-fixture-refcounts/", optional = true }
binary_http = { path = "../../../../netwerk/protocol/http/binary_http" }
oblivious_http = { path = "../../../../netwerk/protocol/http/oblivious_http" }
mime-guess-ffi = { path = "../../../../dom/fs/parent/rust/mime-guess-ffi" }
uniffi = { version = "0.25.2" }
uniffi = { workspace = true }
# Note: `modern_sqlite` means rusqlite's bindings file be for a sqlite with
# version less than or equal to what we link to. This isn't a problem because we
@ -145,7 +146,7 @@ thread_sanitizer = ["xpcom/thread_sanitizer"]
uniffi_fixtures = [
"uniffi-example-arithmetic", "uniffi-example-geometry", "uniffi-example-rondpoint", "uniffi-example-sprites",
"uniffi-example-todolist", "uniffi-example-custom-types", "uniffi-fixture-callbacks",
"uniffi-fixture-external-types",
"uniffi-fixture-external-types", "uniffi-fixture-refcounts",
]
webmidi_midir_impl = ["midir_impl"]
icu4x = ["jsrust_shared/icu4x"]

Просмотреть файл

@ -136,6 +136,7 @@ mod uniffi_fixtures {
uniffi_fixture_callbacks::uniffi_reexport_scaffolding!();
uniffi_custom_types::uniffi_reexport_scaffolding!();
uniffi_fixture_external_types::uniffi_reexport_scaffolding!();
uniffi_fixture_refcounts::uniffi_reexport_scaffolding!();
uniffi_geometry::uniffi_reexport_scaffolding!();
uniffi_rondpoint::uniffi_reexport_scaffolding!();
uniffi_sprites::uniffi_reexport_scaffolding!();
@ -174,7 +175,7 @@ pub unsafe extern "C" fn debug_log(target: *const c_char, message: *const c_char
// Define extern "C" versions of these UniFFI functions, so that they can be called from C++
#[no_mangle]
pub extern "C" fn uniffi_rustbuffer_alloc(
size: i32,
size: u64,
call_status: &mut uniffi::RustCallStatus,
) -> uniffi::RustBuffer {
uniffi::uniffi_rustbuffer_alloc(size, call_status)

Просмотреть файл

@ -14,6 +14,7 @@ trojan-source:
- third_party/python/arrow/arrow/locales.py
- third_party/rust/chardetng/src/data.rs
- third_party/rust/clap_builder/src/output/textwrap/core.rs
- third_party/rust/textwrap/src/core.rs
- third_party/rust/icu_provider/src/hello_world.rs
- third_party/rust/uniffi-example-rondpoint/tests/bindings/test_rondpoint.py
- third_party/rust/error-chain/tests/tests.rs