Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

El módulo puente (Bridge)

CXX se basa en una descripción de las firmas de la función que se mostrarán de un lenguaje a otro. Proporcionas esta descripción mediante bloques externos en un módulo de Rust anotado con la macro de atributo #[cxx::bridge].

#[allow(unsafe_op_in_unsafe_fn)]
#[cxx::bridge(namespace = "org::blobstore")]
mod ffi {
    // Estructuras compartidas con campos visibles para ambos lenguajes.
    struct BlobMetadata {
        size: usize,
        tags: Vec<String>,
    }

    // Tipos y firmas de Rust expuestos a C++.
    extern "Rust" {
        type MultiBuf;

        fn next_chunk(buf: &mut MultiBuf) -> &[u8];
    }

    // Tipos y firmas de C++ y expuestos a Rust.
    unsafe extern "C++" {
        include!("include/blobstore.h");

        type BlobstoreClient;

        fn new_blobstore_client() -> UniquePtr<BlobstoreClient>;
        fn put(self: Pin<&mut BlobstoreClient>, parts: &mut MultiBuf) -> u64;
        fn tag(self: Pin<&mut BlobstoreClient>, blobid: u64, tag: &str);
        fn metadata(&self, blobid: u64) -> BlobMetadata;
    }
}
  • Bridge se declara generalmente en un módulo ffi dentro del crate.
  • A partir de las declaraciones que se han hecho en el módulo bridge, CXX generará definiciones de funciones o tipos de Rust y C++ que coincidan para exponer esos elementos a ambos lenguajes.
  • Para ver el código de Rust generado, usa cargo-expand para ver la macro de procedimiento desplegada. En la mayoría de los ejemplos, se utilizaría cargo expand ::ffi para desplegar únicamente el módulo ffi (aunque esta acción no se aplica a los proyectos de Android).
  • Para ver el código C++ generado, consulta target/cxxbridge.