Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

High level Lua 5.4/5.3/5.2/5.1 (including LuaJIT) and Luau bindings to Rust with async/await support

License

NotificationsYou must be signed in to change notification settings

mlua-rs/mlua

Repository files navigation

Build StatusLatest VersionAPI DocumentationCoverage StatusMSRV

Guided Tour |Benchmarks |FAQ

mlua is a set of bindings to theLua programming language for Rust with a goal to provide asafe (as much as possible), high level, easy to use, practical and flexible API.

Started as anrlua fork,mlua supports Lua 5.4, 5.3, 5.2, 5.1 (including LuaJIT) andLuau and allows writing native Lua modules in Rust as well as using Lua in a standalone mode.

mlua is tested on Windows/macOS/Linux including module mode inGitHub Actions onx86_64 platforms and cross-compilation toaarch64 (other targets are also supported).

WebAssembly (WASM) is supported throughwasm32-unknown-emscripten target for all Lua/Luau versions excluding JIT.

Usage

Feature flags

mlua uses feature flags to reduce the amount of dependencies and compiled code, and allow to choose only required set of features.Below is a list of the available feature flags. By defaultmlua does not enable any features.

  • lua54: enable Lua5.4 support
  • lua53: enable Lua5.3 support
  • lua52: enable Lua5.2 support
  • lua51: enable Lua5.1 support
  • luajit: enableLuaJIT support
  • luajit52: enableLuaJIT support with partial compatibility with Lua 5.2
  • luau: enableLuau support (auto vendored mode)
  • luau-jit: enableLuau support with JIT backend.
  • luau-vector4: enableLuau support with 4-dimensional vector.
  • vendored: build static Lua(JIT) libraries from sources duringmlua compilation usinglua-src orluajit-src
  • module: enable module mode (building loadablecdylib library for Lua)
  • async: enable async/await support (any executor can be used, eg.tokio orasync-std)
  • send: makemlua::Lua: Send + Sync (addsSend requirement tomlua::Function andmlua::UserData)
  • error-send: makemlua:Error: Send + Sync
  • serde: add serialization and deserialization support tomlua types usingserde
  • macros: enable procedural macros (such aschunk!)
  • anyhow: enableanyhow::Error conversion into Lua
  • userdata-wrappers: opt intoimpl UserData forRc<T>/Arc<T>/Rc<RefCell<T>>/Arc<Mutex<T>> whereT: UserData

Async/await support

mlua supports async/await for all Lua versions including Luau.

This works using Luacoroutines and requires runningThread along with enablingfeature = "async" inCargo.toml.

Examples:

shell command examples:

# async http client (hyper)cargo run --example async_http_client --features=lua54,async,macros# async http client (reqwest)cargo run --example async_http_reqwest --features=lua54,async,macros,serde# async http servercargo run --example async_http_server --features=lua54,async,macros,sendcurl -v http://localhost:3000

Serde support

With theserde feature flag enabled,mlua allows you to serialize/deserialize any type that implementsserde::Serialize andserde::Deserialize into/frommlua::Value. In addition,mlua provides theserde::Serialize trait implementation formlua::Value (includingUserData support).

Example

Compiling

You have to enable one of the features:lua54,lua53,lua52,lua51,luajit(52) orluau, according to the chosen Lua version.

By defaultmlua usespkg-config to find Lua includes and libraries for the chosen Lua version.In most cases it works as desired, although sometimes it may be preferable to use a custom Lua library.To achieve this, mlua supports theLUA_LIB,LUA_LIB_NAME andLUA_LINK environment variables.LUA_LINK is optional and may bedylib (a dynamic library) orstatic (a static library,.a archive).

An example of how to use them:

my_project $ LUA_LIB=$HOME/tmp/lua-5.2.4/src LUA_LIB_NAME=lua LUA_LINK=static cargo build

mlua also supports vendored Lua/LuaJIT using the auxiliary crateslua-src andluajit-src.Just enable thevendored feature and cargo will automatically build and link the specified Lua/LuaJIT version. This is the easiest way to get started withmlua.

Standalone mode

In standalone mode,mlua allows adding scripting support to your application with a gently configured Lua runtime to ensure safety and soundness.

Add toCargo.toml:

[dependencies]mlua = {version ="0.11",features = ["lua54","vendored"] }

main.rs

use mlua::prelude::*;fnmain() ->LuaResult<()>{let lua =Lua::new();let map_table = lua.create_table()?;    map_table.set(1,"one")?;    map_table.set("two",2)?;    lua.globals().set("map_table", map_table)?;    lua.load("for k,v in pairs(map_table) do print(k,v) end").exec()?;Ok(())}

Module mode

In module mode,mlua allows creating a compiled Lua module that can be loaded from Lua code usingrequire. In this casemlua uses an external Lua runtime which could lead to potential unsafety due to the unpredictability of the Lua environment and usage of libraries such asdebug.

Example

Add toCargo.toml:

[lib]crate-type = ["cdylib"][dependencies]mlua = {version ="0.11",features = ["lua54","module"] }

lib.rs:

use mlua::prelude::*;fnhello(_:&Lua,name:String) ->LuaResult<()>{println!("hello, {}!", name);Ok(())}#[mlua::lua_module]fnmy_module(lua:&Lua) ->LuaResult<LuaTable>{let exports = lua.create_table()?;    exports.set("hello", lua.create_function(hello)?)?;Ok(exports)}

And then (macOS example):

$ cargo rustc -- -C link-arg=-undefined -C link-arg=dynamic_lookup$ ln -s ./target/debug/libmy_module.dylib ./my_module.so$ lua5.4 -e'require("my_module").hello("world")'hello, world!

On macOS, you need to set additional linker arguments. One option is to compile withcargo rustc --release -- -C link-arg=-undefined -C link-arg=dynamic_lookup, the other is to create a.cargo/config.toml with the following content:

[target.x86_64-apple-darwin]rustflags = ["-C","link-arg=-undefined","-C","link-arg=dynamic_lookup",][target.aarch64-apple-darwin]rustflags = ["-C","link-arg=-undefined","-C","link-arg=dynamic_lookup",]

On Linux you can build modules normally withcargo build --release.

On Windows the target module will be linked with thelua5x.dll library (depending on your feature flags).Your main application should provide this library.

Module builds don't require Lua binaries or headers to be installed on the system.

Publishing to luarocks.org

There is a LuaRocks build backend for mlua modules:luarocks-build-rust-mlua.

Modules written in Rust and published to luarocks:

Safety

One ofmlua's goals is to provide asafe API between Rust and Lua.Every place where the Lua C API may trigger an error longjmp is protected bylua_pcall,and the user of the library is protected from directly interacting with unsafe things like the Lua stack.There is overhead associated with this safety.

Unfortunately,mlua does not provide absolute safety even without usingunsafe .This library contains a huge amount of unsafe code. There are almost certainly bugs still lurking in this library!It is surprisingly, fiendishly difficult to use the Lua C API without the potential for unsafety.

Panic handling

mlua wraps panics that are generated inside Rust callbacks in a regular Lua error. Panics can then beresumed by returning or propagating the Lua error to Rust code.

For example:

let lua =Lua::new();let f = lua.create_function(|_,()| ->LuaResult<()>{panic!("test panic");})?;lua.globals().set("rust_func", f)?;let _ = lua.load(r#"    local status, err = pcall(rust_func)    print(err) -- prints: test panic    error(err) -- propagate panic"#).exec();unreachable!()

Optionally,mlua can disable Rust panic catching in Lua viapcall/xpcall and automatically resumethem across the Lua API boundary. This is controlled viaLuaOptions and done by wrapping the Luapcall/xpcallfunctions to prevent catching errors that are wrapped Rust panics.

mlua should also be panic safe in another way as well, which is that anyLua instances or handlesremain usable after a user generated panic, and such panics should not break internal invariants orleak Lua stack space. This is mostly important to safely usemlua types in Drop impls, as you should not beusing panics for general error handling.

Below is a list ofmlua behaviors that should be considered a bug.If you encounter them, a bug report would be very welcome:

  • If you can cause UB withmlua without typing the word "unsafe", this is a bug.

  • If your program panics with a message that contains the string "mlua internal error", this is a bug.

  • Lua C API errors are handled by longjmp. All instances where the Lua C API would otherwise longjmp over calling stack frames should be guarded against, except in internal callbacks where this is intentional. If you detect thatmlua is triggering a longjmp over your Rust stack frames, this is a bug!

  • If you detect that, after catching a panic or during a Drop triggered from a panic, aLua or handle method is triggering other bugs or there is a Lua stack space leak, this is a bug.mlua instances are supposed to remain fully usable in the face of user generated panics. This guarantee does not extend to panics marked with "mlua internal error" simply because that is already indicative of a separate bug.

Sandboxing

Please check theLuau Sandboxing page if you are interested in running untrusted Lua scripts in a controlled environment.

mlua provides theLua::sandbox method for enabling sandbox mode (Luau only).

License

This project is licensed under theMIT license.

About

High level Lua 5.4/5.3/5.2/5.1 (including LuaJIT) and Luau bindings to Rust with async/await support

Topics

Resources

License

Stars

Watchers

Forks

Sponsor this project

 

Languages


[8]ページ先頭

©2009-2025 Movatter.jp