rust工程

文章目录

  • Cargo
  • macOS配置rust环境
    • vscode配置
  • 目录结构
    • Cargo.toml
    • cargo命令
    • hello world
  • 跟web交互
    • WebAssembly
  • 跟Android交互
    • 配置Android环境
    • JNI例子
    • NDK例子

Rust 是一种现代的、系统级的编程语言,它强调并发安全、内存安全和高性能。Rust 的设计目标是提供一种有着良好抽象能力,同时又能够保证代码运行效率和安全性的语言。它将内存安全、并发安全和数据竞争检测等特性作为语言的一部分,通过所有权系统、借用检查器和生命周期等机制来防止常见的编程错误。

下面是一些与 Rust 相关的工具和库的介绍:

  1. Cargo
    Cargo 是 Rust 的包管理工具和构建系统。它能够自动管理 Rust 项目的依赖关系,并提供命令行工具来构建、测试和运行项目。Cargo 简化了 Rust 项目的创建和管理过程,使得开发者可以更专注于编写代码而不用过多关注构建细节。

  2. Clippy
    Clippy 是 Rust 的静态代码分析工具,它能够检测出一些潜在的代码问题和不良习惯,并给出相应的建议。Clippy 可以帮助开发者编写更规范、更高质量的 Rust 代码。

  3. Rust 文档(Rust Docs)
    Rust Docs 是 Rust 官方提供的文档工具,用于生成和浏览 Rust 标准库和第三方库的文档。它为 Rust 开发者提供了一个方便的方式来查阅和学习 Rust 相关的文档。

  4. Rust 标准库(Rust Standard Library)
    Rust 标准库是 Rust 语言的核心库,它提供了许多常用的数据结构、算法和系统调用等功能。开发者可以直接使用标准库中的类型和函数,以快速构建高效、安全的 Rust 程序。

  5. Rust 编译器(rustc)
    Rust 编译器是将 Rust 代码编译为可执行文件或库的工具。它负责解析、类型检查、代码生成等编译过程,并生成适应目标平台的机器码。Rust 编译器是 Rust 语言的核心组件之一,它实现了 Rust 语言规范,并负责将 Rust 代码转化为可执行的程序。

这些工具和库都是 Rust 生态系统中重要的组成部分,它们与 Rust 的设计理念和目标相辅相成,使得开发者能够更加高效地编写、测试和维护 Rust 项目。无论是初学者还是有经验的开发者,对于这些工具的了解和使用都能够提升开发效率和代码质量。

Cargo

Cargo 是 Rust 的官方构建工具和包管理器。它用于帮助开发者构建、测试和管理 Rust 项目,简化了项目的依赖管理、构建配置和发布流程。下面详细介绍一下 Cargo 的主要功能和用法:

  1. 创建项目: 使用 Cargo 可以快速创建一个新的 Rust 项目。通过运行 cargo new 命令,在当前目录下生成一个新的项目文件夹,并自动生成了一个简单的目录结构和必要的文件,包括 Cargo.tomlsrc/main.rs 等。

  2. 依赖管理: Cargo 管理 Rust 项目的依赖关系。在项目的 Cargo.toml 文件中,可以指定项目所需要的外部依赖库及其版本。当构建项目时,Cargo 会自动下载并编译这些依赖库,并将其集成到项目中。可以使用 cargo build 命令来构建项目并处理依赖关系。

  3. 构建项目: Cargo 提供了简洁的命令行接口,可以用于构建 Rust 项目。运行 cargo build 命令将会编译项目的源代码,并生成可执行文件或库文件。Cargo 会根据项目的依赖关系自动解析和编译相关的代码。

  4. 运行项目: 使用 cargo run 命令可以方便地运行 Rust 项目。Cargo 会自动编译项目并执行生成的可执行文件。如果项目是一个库,可以使用 cargo test 命令来运行项目中的测试用例。

  5. 测试项目: Cargo 提供了内置的测试框架和命令,用于编写和运行测试用例。在项目中的 src 目录下创建一个名为 tests 的子目录,并在其中编写测试用例。然后使用 cargo test 命令运行测试,并查看测试结果。

  6. 发布项目: 使用 Cargo 可以方便地发布 Rust 项目。通过运行 cargo build --release 命令,Cargo 会进行优化编译,生成一个发布版本的可执行文件。然后可以将生成的可执行文件部署到生产环境中。

  7. 文档生成: Cargo 提供了文档生成工具,可以生成项目的文档。在项目中的注释中添加文档注解,并使用 cargo doc 命令生成文档。生成的文档会包含项目的结构、函数、模块等信息,并可以通过浏览器进行查看。

  8. 更新依赖: 当项目依赖的库有新的版本发布时,可以使用 Cargo 更新依赖关系。运行 cargo update 命令,Cargo 会检查项目的依赖关系,并下载最新的版本。

除了上述功能,Cargo 还提供了其他一些辅助功能,例如初始化 Git 仓库、自动下载编译工具链(Rustup)、发布到 Cargo 社区等。这些功能使得 Cargo 成为 Rust 开发中必不可少的工具,极大地简化了项目的管理和构建过程,提高了开发效率。

macOS配置rust环境

在 macOS 上配置 Rust 环境,可以按照以下步骤进行:

  1. 安装 Homebrew(如果未安装):
    打开终端,并执行以下命令来安装 Homebrew:

    /bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)"
    
  2. 安装 Rust 编程语言:
    在终端中执行以下命令来安装 Rust:

    curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh
    

    这将下载并运行 Rust 安装脚本。

  3. 配置环境变量:
    安装完成后,脚本会提示你将 Rust 相关的可执行文件路径添加到环境变量中。请按照提示选择「2」或输入「2」,然后按 Enter 键。

  4. 初始化 Rust 环境:
    执行以下命令初始化 Rust 环境:

    source $HOME/.cargo/env
    
  5. 验证安装:
    在终端中执行以下命令验证 Rust 是否成功安装:

    rustc --version
    cargo --version
    
  6. 安装 wasm-pack:
    这将下载并执行 wasm-pack 安装脚本。根据提示,可能需要输入管理员密码来完成安装。

    curl https://rustwasm.github.io/wasm-pack/installer/init.sh -sSf | sh
    wasm-pack --version
    

如果以上步骤没有出现任何错误,那么你的 macOS 系统上已成功配置了 Rust 环境。你可以开始使用 Rust 编程语言进行开发了。需要注意的是,Rust 包管理器 Cargo 也已经安装好了,它可以帮助你管理 Rust 项目的依赖和构建过程。

希望上述步骤能够帮助到你顺利配置 Rust 环境。如果在安装过程中遇到任何问题,你可以参考 Rust 官方文档 或 Rust 社区中的相关资源来获取更多帮助。

vscode配置

当在 VS Code 中配置 Rust 开发环境时,以下是几个常用的插件推荐:

  1. rust-analyzer:这是官方提供的 Rust 插件,是一个功能强大的 Rust 语言服务器,它提供了智能代码补全、重构建议、错误检查等高级功能。

  2. Crates by serayuzgur:这个插件提供了对 Cargo.toml 和 Cargo.lock 文件的支持,可以方便地查看和管理项目的依赖关系。

  3. CodeLLDB by Vadim Chugunov:如果你需要在 VS Code 中进行 Rust 代码的调试,这个插件可以与 LLDB 调试器集成,提供了强大的调试功能。

  4. Better TOML by bungcip:这个插件提供了对 TOML 文件的语法高亮和格式化支持,对于编辑 Cargo.toml 文件来说非常实用。

  5. Rusty Code by matklad:Rusty Code 插件提供了代码格式化、自动导入缺失的模块、错误检查等功能,帮助减少开发中的一些常见错误。

以上这些插件可以为你提供更好的 Rust 开发体验,使得在 VS Code 中编写、调试和管理 Rust 项目更加便捷和高效。可以通过在 VS Code 中搜索插件名称并安装来开始配置 Rust 开发环境。同时,也可以根据自己的需求和喜好,探索其他的 Rust 插件。

目录结构

Rust 项目通常遵循一种常见的目录结构,该结构有助于组织代码、资源文件和构建工具。以下是一个常见的 Rust 项目目录结构示例:

myproject/
  ├── src/
  │   └── main.rs
  ├── Cargo.toml
  └── Cargo.lock

让我们逐个解释每个目录和文件的作用:

  • src/:这是存放 Rust 源代码的目录。你可以在此目录下创建多个 .rs 文件来组织你的代码。通常,你会在 src/ 目录下创建一个 main.rs 文件,其中包含项目的入口点。

  • main.rs:这是包含项目入口点(例如 main 函数)的 Rust 源代码文件。它是 Rust 程序的起点,负责启动应用程序的执行流程。

  • Cargo.toml:这是 Rust 项目的配置文件,使用 Toml 格式来描述项目的依赖项、构建选项和其他元数据。你可以在 Cargo.toml 中指定项目名称、版本号、作者信息等。

  • Cargo.lock:这是由 Cargo 自动生成的锁定文件。它记录了实际使用的依赖项及其确切版本,以确保在后续构建中使用相同的依赖项版本。

除了上述基本结构之外,Rust 项目通常还包括其他目录和文件:

  • tests/:如果你的项目包含测试代码,通常会在此目录下创建测试文件。测试代码用于验证项目中各个部分的正确性。

  • examples/:如果你想提供一些示例用法或演示代码,可以将其放置在此目录下。

  • target/:这是 Cargo 自动生成的目录,在构建过程中存储目标文件和编译生成的二进制可执行文件。

  • build.rs:这是一个可选的构建脚本文件,使用 Rust 代码编写。它允许你在构建过程中自定义一些操作,例如生成代码、配置构建选项等。

  • 其他自定义目录:根据项目的需要,你可能还会创建其他自定义的目录,用于存放静态资源文件、模板文件、配置文件等。

请注意,Rust 的目录结构没有强制要求,你可以根据项目的需求进行调整和扩展。上述目录结构只是一个常见的约定,大多数 Rust 项目都遵循类似的结构来提供一致性和易于理解的代码组织方式。

Cargo.toml

Cargo.toml 是 Rust 项目的配置文件,用于指定项目的元数据、依赖项和构建选项。它使用 Toml 格式(Tom’s Obvious, Minimal Language)编写,是一种易于理解和编辑的简单配置语言。要详细了解Cargo请阅读manifest。

下面是一个典型的 Cargo.toml 示例:

[package]
name = "myproject"
version = "0.1.0"
edition = "2021"

[dependencies]
crate1 = "1.0"
crate2 = { version = "2.0", features = ["feature1", "feature2"] }

[build-dependencies]
build_crate = "1.0"

让我们逐个解释每个部分的含义:

  • [package] 这个部分用于指定项目的元数据信息。

    • name:指定项目的名称。
    • version:指定项目的版本号。
    • edition:指定 Rust 的版本。支持的选项有 "2015""2018""2021"
  • [dependencies] 这个部分用于指定项目的依赖项。你可以列出项目所依赖的外部库或 crate,并指定它们的版本信息。

    • crate1 = "1.0":这表示项目依赖名为 crate1 的 crate,并指定其版本为 1.0
    • crate2 = { version = "2.0", features = ["feature1", "feature2"] }:这表示项目依赖名为 crate2 的 crate,并指定其版本为 2.0,同时启用其中的一些特性。
  • [build-dependencies] 这个部分用于指定项目构建过程中所需要的依赖项。这些依赖项只在构建过程中使用,而不会包含在最终的二进制可执行文件中。

除了上述常见的部分之外,Cargo.toml 文件还支持其他配置选项,如:

  • workspace:用于同时管理多个相关的 Rust 项目。
  • features:用于定义和启用 crate 的不同功能特性。
  • target:用于指定特定的目标平台和相关设置。
  • patch:用于修复或替换依赖项的特定版本。

你可以根据项目的需求自定义 Cargo.toml 文件,添加适当的依赖项、配置选项和元数据信息。Rust 的构建工具 Cargo 将根据 Cargo.toml 中的配置来下载和管理依赖项,并执行相应的构建操作。

希望这个介绍对你有所帮助!如果还有其他问题,请随时提问。

cargo命令

Cargo 是 Rust 的官方构建工具和包管理器,提供了许多命令用于构建、测试、管理和发布 Rust 项目。以下是 Cargo 的常用命令列表:

  1. cargo new:创建一个新的 Rust 项目。

  2. cargo build:构建项目,编译源代码并处理依赖关系。

  3. cargo run:运行项目,编译并执行生成的可执行文件。

  4. cargo test:运行测试用例。

  5. cargo bench:运行基准测试。

  6. cargo doc:生成项目文档。

  7. cargo clean:清理项目构建产生的临时文件和目录。

  8. cargo update:更新项目的依赖库。

  9. cargo init:初始化当前目录为一个 Rust 项目。

  10. cargo check:检查代码是否可以成功编译,但不生成可执行文件。

  11. cargo fix:自动修复一些编译警告和错误。

  12. cargo publish:发布项目到 crates.io,Rust 社区的包管理平台。

  13. cargo install:安装一个二进制包程序到系统路径。

  14. cargo uninstall:卸载一个已安装的二进制包程序。

  15. cargo package:生成一个用于发布的压缩包。

  16. cargo metadata:显示项目的元数据信息,依赖关系等。

  17. cargo fmt:格式化源代码。

  18. cargo clippy:运行 Clippy(Rust 的 lint 工具)对代码进行静态分析。

  19. cargo doc --open:生成文档并在浏览器中打开。

  20. cargo build --release:生成发布版本的可执行文件。

  21. cargo build --target :指定目标平台进行构建。

  22. cargo build --features :启用指定的特性进行构建。

  23. cargo build --no-default-features:禁用默认特性进行构建。

  24. cargo build --all:构建项目及其所有依赖。

  25. cargo build --workspace:在工作区中构建所有子项目。

  26. cargo build --lib:只构建项目中的库文件。

  27. cargo build --bin :只构建指定名称的可执行文件。

  28. cargo build --example :只构建指定名称的示例程序。

  29. cargo build --tests:只构建项目中的测试目标。

  30. cargo build --benches:只构建项目中的基准测试目标。

  31. cargo build --target-dir

    :指定构建输出的目录。

  32. cargo build --all-features:启用所有特性进行构建。

  33. cargo build --no-default-runtime:禁用默认运行时(仅适用于编写运行时的 Crate)。

  34. cargo test -- --test-threads=:设置并发运行测试的线程数。

  35. cargo test -- :只运行与指定模式匹配的测试。

  36. cargo test -- --ignored:运行被标记为 #[ignore] 的测试。

  37. cargo test --release:以发布模式运行所有测试。

  38. cargo doc --no-deps:生成项目文档,但不包含依赖库的文档。

  39. cargo run -- :在编译并运行项目时传递参数。

  40. cargo check --all-targets:检查项目及其所有目标的代码是否可以成功编译。

  41. cargo fix --edition:自动升级代码到指定的 Rust 版本。

  42. cargo fix --allow-dirty:允许在 Git 工作目录中运行 cargo fix

  43. cargo publish --dry-run:发布前进行 dry-run,检查是否有错误。

  44. cargo publish --allow-dirty:允许在 Git 工作目录中运行 cargo publish

  45. cargo install :安装指定的 Crate。

  46. cargo install-update :更新指定的 Crate。

  47. cargo uninstall :卸载指定的 Crate。

  48. cargo search :在 crates.io 中搜索包。

  49. cargo clean --package :清理指定的 Package。

  50. cargo metadata --format-version :指定元数据格式的版本。

这些是常用的 Cargo 命令,可以帮助你管理 Rust 项目的构建、测试、文档生成、依赖管理和发布等任务。你可以通过在命令行中输入 cargo --help 来查看更多命令以及它们的详细使用说明。

hello world

要开始你的第一个 Rust “Hello, World!” 项目,按照以下步骤进行:

  1. 安装 Rust 编程语言:首先,确保您已在计算机上安装了 Rust。可以访问 Rust 官方网站,按照指示下载并安装 Rust。

  2. 创建新项目:打开终端或命令提示符,导航到要创建项目的目录,并运行以下命令来创建一个新的 Rust 项目:

    cargo new hello_world
    

    这将在当前目录下创建一个名为 “hello_world” 的新目录,并自动生成一些初始代码。

  3. 进入项目目录:运行以下命令以进入新创建的项目目录:

    cd hello_world
    
  4. 编辑代码:使用你喜欢的文本编辑器打开 src/main.rs 文件,并将以下代码复制粘贴到文件中:

    fn main() {
        println!("Hello, World!");
    }
    
  5. 构建和运行项目:返回终端或命令提示符,运行以下命令来构建和运行你的项目:

    cargo run
    

    Rust 的构建系统 Cargo 将编译项目并运行生成的可执行文件。你应该会在终端上看到输出 “Hello, World!”。

恭喜!你已经成功创建并运行了你的第一个 Rust “Hello, World!” 项目。从这个简单的示例开始,你可以继续学习和探索 Rust 编程语言的更多方面。

跟web交互

Rust 可以与 Web 进行交互,使你能够构建 Web 应用程序、API 和后端服务。下面是一些可以帮助你在 Rust 中进行 Web 交互的常见方法:

  1. Web 框架:使用 Rust 的 Web 框架可以简化 Web 开发过程,并提供路由、请求处理、中间件等功能。一些流行的 Rust Web 框架包括 Rocket、Actix-web 和 Warp。

  2. HTTP 客户端和服务器:Rust 提供了多个库用于构建 HTTP 客户端和服务器。例如,reqwest 是一个常用的 HTTP 客户端库,hyper 是一个强大的 HTTP 服务器库。

  3. 数据库访问:与 Web 相关的应用程序通常需要与数据库进行交互。Rust 提供了各种数据库连接库和 ORM(对象关系映射)工具,例如 Diesel、sqlx 和 rusqlite。

  4. 模板引擎:用于生成动态 HTML 页面的模板引擎在 Web 开发中非常有用。Rust 中一些流行的模板引擎包括 Tera 和 Handlebars。

  5. WebAssembly(Wasm):Rust 具备编写 WebAssembly 模块的能力,这使得你可以在 Web 浏览器中运行原生速度的 Rust 代码。你可以使用 wasm-bindgen 和 wasm-pack 工具来构建和集成 Rust 和 JavaScript 之间的接口。

  6. WebSocket:Rust 提供了用于 WebSocket 通信的库,如 tokio-tungstenite 和 actix-web 的 WebSocket 功能。

以上只是一些在 Rust 中进行 Web 交互的方法示例,你可以根据具体需求选择合适的库和工具。Rust 社区拥有丰富的资源和文档,可以帮助你深入了解和学习 Rust 的 Web 开发。

WebAssembly

以下是一个使用 Rust 和 WebAssembly(Wasm)进行交互的示例:

首先,确保你已经安装了 Rust 和 wasm-pack 工具。

  1. 创建新的 Rust 项目:
    打开终端或命令提示符,导航到要创建项目的目录,并运行以下命令来创建一个新的 Rust 项目:

    cargo new wasm_example
    cd wasm_example
    
  2. 添加依赖:
    在项目的根目录中,打开 Cargo.toml 文件,并添加以下代码来添加 wasm-bindgen 和 js-sys 的依赖:

    [lib]
    crate-type = ["cdylib"]
    
    [dependencies]
    wasm-bindgen = "0.2"
    js-sys = "0.3"
    
  3. 编写 Rust 代码:
    打开 src/lib.rs 文件,并使用以下代码替换其中的内容:

    use wasm_bindgen::prelude::*;
    
    #[wasm_bindgen]
    extern "C" {
        #[wasm_bindgen(js_namespace = console)]
        fn log(s: &str);
    }
    
    #[wasm_bindgen]
    pub fn greet(name: &str) {
        let message = format!("FromRust, {}!", name);
        log(&message);
    }
    

    上述代码定义了一个 greet 函数,它接受一个字符串参数,并在控制台输出问候消息。

  4. 生成 Wasm 模块:
    在终端中运行以下命令来生成 Wasm 模块:

    wasm-pack build --target web
    

    这将使用 wasm-pack 工具将 Rust 代码编译为 WebAssembly 模块,并生成与 JavaScript 交互的必要代码。

  5. 创建 HTML 文件:
    在项目的根目录中,创建一个名为 index.html 的文件,并使用以下代码填充它:

    DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>WebAssembly Exampletitle>
        <script type="module">
            import init, { greet } from './pkg/wasm_example.js';
            async function run() {
                await init();
                greet("Alice");
            }
            run();
        script>
    head>
    <body>
    body>
    html>
    

    上述代码导入了生成的 wasm_example.js 文件,并在页面加载完成后调用 greet 函数。

  6. 启动本地服务器:
    在终端中运行以下命令来启动一个简单的本地服务器:

    python -m http.server
    
  7. 运行示例:
    打开浏览器并访问 http://localhost:8000,然后打开浏览器的控制台。你应该会看到控制台输出了 “Hello, Alice!”。

通过上述步骤,你可以在 Rust 中创建一个简单的 WebAssembly 模块,并与 JavaScript 进行交互。你可以根据需要扩展这个示例,并使用更多的 Rust 函数与 JavaScript 进行交互。

跟Android交互

当你想要在 Android 平台上使用 Rust 与 Java 进行交互时,下面是一些具体的步骤和工具可以帮助你实现这一目标:

  1. 使用 JNI(Java Native Interface):JNI 提供了一种方式,使得 Java 和本地代码能够进行交互。你可以使用 Rust 编写本地代码,并通过 JNI 接口与 Android 的 Java 代码进行通信。为了在 Rust 中与 JNI 交互,你可以使用 jnirust-jni 等库来编写相应的绑定代码。

    需要完成的步骤:

    • 编写 Rust 的绑定代码,将 Rust 函数暴露给 JNI。
    • 生成动态链接库(.so 文件)。
    • 在 Android 项目中使用 JNI 接口调用 Rust 函数。
  2. 使用 NDK(Native Development Kit):NDK 允许你使用 C、C++ 或其他本地语言来开发 Android 应用程序。你可以使用 Rust 作为 C 或 C++ 的替代语言,并在 NDK 中构建包含 Rust 代码的本地库。然后,你可以使用 Java 代码通过 JNI 调用这些本地库。

    需要完成的步骤:

    • 创建 Android NDK 项目,并配置好 Rust 的构建环境。
    • 编写 Rust 代码并构建共享库(.so 文件)。
    • 使用 JNI 接口在 Java 代码中调用本地库中的函数。
  3. 使用 FFI(Foreign Function Interface):FFI 允许不同语言之间进行函数调用和数据传递。你可以使用 Rust 的 FFI 功能,将 Rust 函数暴露给其他语言,比如 Java。通过这种方式,你可以在 Android 的 Java 代码中直接调用 Rust 函数。

    需要完成的步骤:

    • 使用 Rust 的 #[no_mangle]extern 关键字将函数标记为可供外部调用。
    • 根据 FFI 规范编写 Java 代码来调用 Rust 函数。
    • 在 Android 项目中将 Rust 代码和 Java 代码一起编译和构建。
  4. 使用 rust-android-gradle 插件:rust-android-gradle 是一个方便的工具,可用于将 Rust 代码集成到 Android 项目中。它可以自动处理 Rust 代码的构建和链接,并与 Gradle 构建系统集成。

    需要完成的步骤:

    • 在 Android 项目的 Gradle 文件中添加 rust-android-gradle 插件的依赖。
    • 创建 Rust 模块并设置构建配置。
    • 在 Android 项目中使用预生成的 Rust 库。

请注意,在实施任何方法之前,你需要确保已经按照相应工具和库的文档进行了正确的配置和设置。每种方法都有其优势和适用场景,因此根据需求选择最适合你的方法。

希望这些详细的步骤能够帮助你更好地理解 Rust 与 Android 的交互,并实现你的项目需求。

配置Android环境

要正确安装和配置 Android NDK,请按照以下步骤进行操作:

  1. 下载 Android NDK:访问 Android NDK 的官方网站下载适合你操作系统的最新版本。

  2. 解压缩文件:将下载的 NDK 压缩文件解压到你选择的位置。例如,你可以将其解压到 ~/android-ndk 目录下。

  3. 配置环境变量:打开终端并编辑你的 shell 配置文件(例如 ~/.bashrc~/.zshrc)。在文件末尾添加以下行(假设你将 NDK 解压缩到了 ~/android-ndk 目录):

    export ANDROID_NDK_HOME=~/android-ndk
    export PATH=$PATH:$ANDROID_NDK_HOME
    

    保存文件后执行以下命令使配置立即生效:

    source ~/.bashrc
    

    或者你也可以重新启动终端。

  4. 测试安装:在终端中运行以下命令验证是否正确安装和配置了 Android NDK:

    ndk-build --version
    

    如果成功安装并配置,将显示 NDK 版本信息。

  5. 安装交叉编译目标:运行以下命令来安装 aarch64-linux-android 目标:

    rustup target add aarch64-linux-android
    rustup target add arm-linux-androideabi
    rustup target add armv7-linux-androideabi
    rustup target add i686-linux-android
    rustup target add thumbv7neon-linux-androideabi
    rustup target add x86_64-linux-android
    
  6. 配置链接器和编译参数:创建一个名为 $HOME/.cargo 的文件夹,并在其中创建一个名为 config 的文件。在 config 文件中添加以下内容:

    [target.arm-linux-androideabi]
    ar = "llvm-ar"
    linker = "armv7a-linux-androideabi29-clang"
    
    [target.armv7-linux-androideabi]
    ar = "llvm-ar"
    linker = "armv7a-linux-androideabi29-clang"
    
    [target.thumbv7neon-linux-androideabi]
    ar = "llvm-ar"
    linker = "armv7a-linux-androideabi29-clang"
    
    [target.aarch64-linux-android]
    ar = "llvm-ar"
    linker = "aarch64-linux-android29-clang"
    
    [target.i686-linux-android]
    ar = "llvm-ar"
    linker = "i686-linux-android29-clang"
    
    [target.x86_64-linux-android]
    ar = "llvm-ar"
    linker = "x86_64-linux-android29-clang"
    
  7. 测试编译:现在,你可以尝试使用 Cargo 构建你的项目,并将目标设置为 Android 平台,例如:

    cargo build --target aarch64-linux-android
    

通过按照以上步骤配置 Rust 的交叉编译环境,你应该能够开始在 Android 平台上使用 Rust 进行交叉编译了。

JNI例子

当使用 JNI 实现 Rust 与 Android 的交互时,可以使用以下示例来说明具体步骤。假设你希望在 Android 应用程序中调用一个计算两个整数和的 Rust 函数。

  1. 创建一个名为 rust_lib 的 Rust 项目cargo new rust_lib --lib,并添加以下内容到 lib.rs 文件中:

    #[no_mangle]
    pub extern "C" fn rust_greet(name: *const c_char) -> *mut c_char {
        let c_str = unsafe {
            assert!(!name.is_null());
    
            CStr::from_ptr(name)
        };
    
        let name = c_str.to_str().unwrap();
        let greeting = format!("FromRust, {}!", name);
    
        CString::new(greeting).unwrap().into_raw()
    }
    
  2. Cargo.toml 文件中添加以下内容:

    [lib]
    crate-type = ["cdylib"]
    
  3. 使用以下命令在 Rust 中构建共享库文件:

    cargo build --target aarch64-linux-android
    

    上述命令将在 target/aarch64-linux-android/debug/librust_lib.so 中生成共享库文件。

  4. 在 Android 项目中的 app 模块下的 src/main 目录中创建一个名为 jni 的文件夹,并在其中创建一个 native-lib.cpp 文件。

  5. native-lib.cpp 文件中添加以下内容:

    #include 
    #include 
    #include 
    
    extern "C" JNIEXPORT jstring JNICALL
    Java_com_example_androidapp_MainActivity_stringFromJNI(
            JNIEnv* env,
            jobject /* this */,
            jstring name) {
        const char* nativeString = env->GetStringUTFChars(name, nullptr);
    
        void* handle = dlopen("librust_lib.so", RTLD_LAZY);
        if (!handle) {
            return env->NewStringUTF("Failed to load Rust library");
        }
    
        typedef char* (*rust_greet_func)(const char*);
        rust_greet_func greet = (rust_greet_func)dlsym(handle, "rust_greet");
        if (!greet) {
            return env->NewStringUTF("Failed to find Rust function");
        }
    
        char* result = greet(nativeString);
    
        env->ReleaseStringUTFChars(name, nativeString);
    
        jstring output = env->NewStringUTF(result);
        free(result);
    
        dlclose(handle);
    
        return output;
    }
    

    要把librust_lib.so复制到jniLibs对应的目录中。

  6. 配置cmake

    app build.gradle

    android {
        // ...
        defaultConfig {
            // ...
            externalNativeBuild {
                cmake {
                    cppFlags '-std=c++17'
                }
            }
    
            ndk {
                abiFilters "arm64-v8a"
            }
        }
    
        sourceSets {
            main {
                // 配置 jniLibs 文件目录
                jniLibs.srcDirs = ['libs']
            }
        }
    
        externalNativeBuild {
            cmake {
                path file('src/main/cpp/CMakeLists.txt')
                version '3.22.1'
            }
        }
    }
    

    CMakeLists.txt

    cmake_minimum_required(VERSION 3.22.1)
    project("rust_jni")
    add_library(${CMAKE_PROJECT_NAME} SHARED native-lib.cpp)
    target_link_libraries(${CMAKE_PROJECT_NAME} android log)
    
  7. 在 Android 项目的 Java 类中,添加以下方法:

    public class MainActivity extends AppCompatActivity {
        static {
            System.loadLibrary("native-lib");
        }
    
        public native String stringFromJNI(String name);
    
        // ...
    }
    
  8. MainActivity.java 中的任何适当的方法中调用 stringFromJNI() 方法,并向其传递一个字符串参数:

    String greeting = stringFromJNI("Stone " + new Date().toString());
    Log.d("MainActivity", greeting);
    

这样,在 Android 应用程序中运行时,将调用 Rust 函数并输出日志中的问候语。

NDK例子

当使用 Rust 和 Android NDK 进行开发时,以下是一个详细的示例,展示如何在 Android 项目中使用 Rust 编写并调用函数。

  1. 创建 Rust 项目:

    在终端中执行以下命令,创建一个名为 rust-ndk 的 Rust 项目:

    cargo new rust-ndk
    

    进入项目目录:

    cd rust-ndk
    
  2. 添加依赖项:

    打开项目中的 Cargo.toml 文件,并添加 ndkjnilibc 作为依赖项:

    [lib]
    crate-type = ["cdylib"]
    path = "src/jni.rs"
    
    [dependencies]
    jni = "0.21.1"
    
  3. 创建 JNI 接口:

    在项目的根目录下创建一个名为 jni.rs 的文件,并添加以下代码:

    use jni::JNIEnv;
    use jni::objects::{JClass, JString};
    use jni::sys::jstring;
    
    #[no_mangle]
    pub unsafe extern "C" fn Java_com_example_rustndk_MainActivity_stringFromRust<'local>(mut env: JNIEnv<'local>,
                                                        _: JClass<'local>,
                                                        input: JString<'local>)
                                                        -> jstring {
        let input: String = env.get_string(&input).expect("Couldn't get java string!").into();
        let output = env.new_string(format!("FromRust, {}!", input)).expect("Couldn't create java string!");
        output.into_raw()
    }
    

    这个例子中的 Java_com_example_rustndk_MainActivity_stringFromRust 函数是一个 JNI 方法,在字符串前面拼接一个FromRust字符串。

  4. 构建 Rust 项目:

    在终端中执行以下命令构建 Rust 项目:

    cargo build --target aarch64-linux-android --release
    
  5. 创建 Android 项目:

    使用 Android Studio 创建一个新的 Android 项目,并导航到 app/src/main 目录。

  6. 添加 Rust 动态链接库:

    将生成的 .so 文件复制到 app/src/main/jniLibs 目录下(如果没有该目录则自行创建)。例如,将 ../rust-ndk/target/release/librust_ndk.so 文件复制到 app/src/main/jniLibs/arm64-v8a/ 目录下。

  7. 创建 Java 类和 JNI 接口:

    app/src/main/java/com/example/rustndk 目录下创建一个名为 MainActivity.java 的类,并添加以下代码:

    package com.example.rustndk;
    
    public class MainActivity extends AppCompatActivity {
        static {
            System.loadLibrary("rust_ndk");
        }
    
        private ActivityMainBinding binding;
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
    
            binding = ActivityMainBinding.inflate(getLayoutInflater());
            setContentView(binding.getRoot());
    
            // Example of a call to a native method
            TextView tv = binding.sampleText;
            tv.setText(stringFromRust("Stone " + new Date().toString()));
        }
    
        public native String stringFromRust(String str);
    }
    

    这个类包含了一个静态代码块,用于加载名为 rust_ndk 的动态链接库。还有一个名为 stringFromRust 的方法,用于调用 Rust 函数。

这样,在 Android 应用程序中运行时,将调用 Rust 函数并输出日志中的问候语。

你可能感兴趣的:(前端,rust,开发语言,后端)