Giter Club home page Giter Club logo

nvim-oxi's People

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

nvim-oxi's Issues

What's next?

Since 0.1 release is out, there is a very simple question mentioned inside the issue's title. Is the project being put at the bug-maintenance mode? Or some features are still planned?

LuaPushable does not impl for Vec<T>

The custom completion list function require a type Function<(String, String, usize), Vec<String>>: https://docs.rs/nvim-oxi/latest/nvim_oxi/types/enum.CommandComplete.html#variant.CustomList. However the trait LuaPushable doesn't implemented for Vec, so I can't create a new function that have return type Result<Vec<T>>.

121 |     let completion = Function::from_fn(generate_completion);
    |                      ^^^^^^^^^^^^^^^^^ the trait `LuaPushable` is not implemented for `Vec<std::string::String>`

My function signature: fn generate_completion(arguments: (String, String, usize)) -> Result<Vec<String>>

Build with rev=e5c34c7, which is currently the HEAD of the git repo.

With `set_hl` `.underline()` doesn't seem to be working

Hi, currently just messing around with nvim-oxi. Thanks for the awesome project!

image

As you can see the matched parenthesis should have a small underline underneath it, but it doesn't.

If it helps, .bold() and .italic() both seem to work fine

`LuaFun::from_fn_mut` and `LuaFun::from_fn_once` are unsound

  • use after move in from_fn_once: if called twice, on second call, we call Box::from_raw is called on a value is that already moved in previous call.

unsafe extern "C" fn c_fun(lstate: *mut lua_State) -> c_int {
let fun = {
let idx = lua_upvalueindex(1);
let upv = lua_touserdata(lstate, idx) as *mut CbOnce;
Box::from_raw(&mut **upv)
};
fun(lstate).unwrap_or_else(|err| handle_error(lstate, err))


  • mutable aliasing in from_fn_mut: if called recursively, we create two mutable references to same closure.

unsafe extern "C" fn c_fun(lstate: *mut lua_State) -> c_int {
let fun = {
let idx = lua_upvalueindex(1);
let upv = lua_touserdata(lstate, idx) as *mut CbMut;
&mut **upv
};
fun(lstate).unwrap_or_else(|err| handle_error(lstate, err))

SIGSEGV with nightly when deserializing object

Hey @noib3,

I've ran into an issue where a get a SIGSEGV when calling an exposed function from Nvim nightly that involves deserializing an Object. This worked fine on Nvim stable.

Here's a simple module that reproduces the error:

use nvim_oxi::{self as oxi, object, Dictionary, Function, Object, ObjectKind, Result};
use serde::Deserialize;

#[derive(Default, Deserialize, Debug)]
#[serde(deny_unknown_fields)]
pub struct Config {
    #[serde(default)]
    pub dir: String,
}

fn setup(preferences: Object) -> Result<()> {
    // This works fine as long as preferences is Nil
    let config = match preferences.kind() {
        ObjectKind::Nil => Config::default(),
        _ => {
            // This will cause SIGSEGV
            let deserializer = object::Deserializer::new(preferences);
            Config::deserialize(deserializer)?
        }
    };

    oxi::print!("All good! {config:?}");

    Ok(())
}

#[oxi::module]
fn foobar() -> oxi::Result<Dictionary> {
    Ok(Dictionary::from_iter([(
        "setup",
        Object::from(Function::from_fn(setup)),
    )]))
}

From Nvim, calling :lua require("foobar").setup() works fine, but :lua require("foobar").setup({ dir: "./" }) results in

'nvim $argv' terminated by signal SIGSEGV (Address boundary error)

Again, this worked fine on the latest stable Nvim. Any ideas?

Reason for not using mlua

For most neovim plugin, interop with Lua is crucial. mlua seems to pretty good at that. What is rationale behind reinvented the wheel here?

nightly: SIGSEGV on `api::get_runtime_file` only somewhat reproducible with test

When calling api::get_runtime_file I get a SIGSEV from neovim. (though calling it from lua is fine).

This is only somewhat reproducible, I added a test like this:

#[oxi::test]
fn get_runtime_file() {
    api::get_runtime_file("test", true).unwrap();
    panic!();
}

And it did not reach the panic, showing as "successful".

On stable neovim it worked fine.

The underlying issue might be on the neovim side and outside this repo, but the test should fail IMO.

Leaks

Currently, once a Object(string, array, ...) is created it is never freed. Object, String Collection don't implement drop. We need to be more systematic about it.

the mlua example is broken

# build in `nvim-oxi/examples/mlua`
cargo b -r && mkdir lua -p && mv target/release/liblua.so lua/lua.so -fn
# nvim
set_rtp=":set rtp+=$PWD"
cmd=":lua require'lua'.greetings()"
nvim -u NONE --headless +"$set_rtp" +"$cmd" +quit

And I got

Hello from Rust..
Hello from Rust.. function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18 function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18
Hello from Rust.. function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18 function: builtin#18
...

If :lua require'lua'.greetings() is run in nvim cmd, nvim just always prints them without stop.

The mlua features I use is this:
mlua = { version = "0.8", features = ["luajit", "vendored"] }
because Lua is not installed locally.

Publish to crates.io

Hey @noib3, I'm in the middle of refactoring out neovim logic from Xmas core, and I thought I might give nvim-oxi a try. Though unfortunately it isn't publish yet to crate io and current version is at 0.0.0 which a bit odd don't you think? or is it saying don't used me 🤣. Anyways I'm browse through the codebase right now, amazing progress so far, congrats

The calc example is broken

Copy the calc example and build it, then copy the .so file to lua directory, and then setup the rtp path and call the add or multiply function, got totally wrong result:

Example test script:

execute ':set rtp+=' . expand("%:p:h")
" I am testing in a crate named playground, it doesn't matter
lua =require("playground").add(1, 1)
lua =require("playground").multiply(1, 1)

Got:

1
0

Cargo.toml

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

# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html

[dependencies]
nvim-oxi = { git = "https://github.com/noib3/nvim-oxi", features = ["nightly"] }

[lib]
crate-type = ["cdylib"]

Async support

Just to give a little bit of context, Rust's async functions return Futures that need an executor to drive them to completion. The usual way to achieve this is to let the async runtime, e.g. tokio, control the "main" thread. This is not a viable option in our case since it would block the UI thread, i.e. the one Neovim runs in, defeating the whole point of concurrent code.

However it should be possible (emphasis on the should) to use libuv, which Neovim uses for the event loop, as the executor. We could expose something like a Task object that wraps an async {} block and drives it to completion by scheduling it via libuv.

NvimError("\'ctermbg\' must be string or integer")',

when i try to compile the plugin with nyoom

thread '<unnamed>' panicked at 'called `Result::unwrap()` on an `Err` value: NvimError("\'ctermbg\' must be string or integer")', /Users/luxus/.cargo/git/checkouts/nvim-oxi-68d2fdc1d1cdbe82/15fb30d/nvim-oxi/src/lua/lua.rs:41:12
stack backtrace:
   0:        0x103ecf8a0 - <std::sys_common::backtrace::_print::DisplayBacktrace as core::fmt::Display>::fmt::he13a97dfe3ba6dc4
   1:        0x103ef73e4 - core::fmt::write::hd751207b60c12d4c
   2:        0x103ed9954 - std::io::Write::write_fmt::h08841cca3656c74a
   3:        0x103ee4404 - std::panicking::default_hook::{{closure}}::h8d96478a0c41fbb8
   4:        0x103ee40c8 - std::panicking::default_hook::haca5b586a55289c5
   5:        0x103ee4918 - std::panicking::rust_panic_with_hook::h419d889b0a87beff
   6:        0x103ecfcfc - std::panicking::begin_panic_handler::{{closure}}::hf9a5ae5699838d81
   7:        0x103ecf9b4 - std::sys_common::backtrace::__rust_end_short_backtrace::h6248404e1e92c641
   8:        0x103ee4518 - _rust_begin_unwind
   9:        0x103efb92c - core::panicking::panic_fmt::ha964b6658f104372
  10:        0x103efb988 - core::result::unwrap_failed::hf92687bbd06849b8
  11:        0x103ec9334 - _luaopen_oxocarbon
  12:        0x101246258 - <unknown>
  13:        0x1012be51c - _luaL_openlibs
  14:        0x101246258 - <unknown>
  15:        0x10125995c - _lua_pcall
  16:        0x100cdbdc4 - _nlua_require
  17:        0x101246258 - <unknown>
  18:        0x10125995c - _lua_pcall
  19:        0x100cd94bc - _nlua_pcall
  20:        0x100cda3a8 - _nlua_exec_file
  21:        0x100db0fa0 - _do_source
  22:        0x100dadbbc - _do_in_cached_path
  23:        0x100dad140 - _source_runtime
  24:        0x100cbc97c - _load_colors
  25:        0x100c81ba4 - _ex_colorscheme
  26:        0x100c7d33c - _execute_cmd0
  27:        0x100c7d050 - _execute_cmd
  28:        0x100bce964 - _nvim_cmd
  29:        0x100bbc2f0 - _nlua_api_nvim_cmd
  30:        0x101246258 - <unknown>
  31:        0x1012be51c - _luaL_openlibs
  32:        0x101246258 - <unknown>
  33:        0x10125995c - _lua_pcall
  34:        0x100cdbdc4 - _nlua_require
  35:        0x101246258 - <unknown>
  36:        0x1012be51c - _luaL_openlibs
  37:        0x101246258 - <unknown>
  38:        0x10125995c - _lua_pcall
  39:        0x100cdbdc4 - _nlua_require
  40:        0x101246258 - <unknown>
  41:        0x10125995c - _lua_pcall
  42:        0x100cd94bc - _nlua_pcall
  43:        0x100cda3a8 - _nlua_exec_file
  44:        0x100db0fa0 - _do_source
  45:        0x100ce3344 - _main
fatal runtime error: Rust panics must be rethrown
fish: Job 1, 'RUST_BACKTRACE=full bin/nyoom...' terminated by signal SIGABRT (Abort)
rustc --version
rustc 1.62.1

cargo --version
cargo 1.62.0

Segfaults during creation of user-defined commands in macOS (aarch64)

Hi all!

Firstly, thank you for the awesome work y'all are doing to make Rust accessible for neovim plugin writers!

I'm using nvim-oxi to write a plugin and have run into what appears to be a macos-specific issue. I only have access to an M1 mac, so I don't know for sure if this happens on intel macs or not. I do have access to a linux box, and I have confirmed the issue does not show up on linux (arch linux x86).

I'm seeing segfaults any time I try to execute a user-defined command. Here's my reproducible code snippet:

use nvim_oxi as oxi;
use nvim_oxi::types::{CommandArgs, CommandNArgs, CommandRange};
use nvim_oxi::opts::CreateCommandOpts;
use nvim_oxi::api;

#[oxi::module]
fn vim_plugin_test() -> oxi::Result<u32> {
    let opts = CreateCommandOpts::builder().build();

    let greetings = move |args: CommandArgs| {
        api::out_write("Test");
        Ok(())
    };

    api::create_user_command("Greetings", greetings, Some(&opts))?;

    Ok(42)
}

I also have the linker arguments for macos as described in your examples directory:

# .cargo/config
[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",
]

My project builds with no issues, and I can confirm the user-defined command is accessible from neovim-- it shows up in tab completion. However, when I actually run :Greetings<CR>, neovim dies with Segmentation fault: 11.

I don't think this is an issue with code signing-- I got a different error (Killed: 9) when that was the case. I am now running codesign on the produced libraries and that seems to work just fine.

Any advice you have on next investigation steps would be much appreciated. Unfortunately GDB does not work on M1 architectures, but I have run neovim through lldb and got the following stack trace on the error:

:GreetingsProcess 44524 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = EXC_BAD_ACCESS (code=1, address=0xa)
    frame #0: 0x0000000196c53274 libsystem_platform.dylib`_platform_memmove + 420
libsystem_platform.dylib`_platform_memmove:
->  0x196c53274 <+420>: ldr    x6, [x1], #0x8
    0x196c53278 <+424>: str    x6, [x3], #0x8
    0x196c5327c <+428>: subs   x2, x2, #0x8              ; =0x8
    0x196c53280 <+432>: b.hs   0x196c53274               ; <+420>
Target 0: (nvim) stopped.
(lldb) bt
error: need to add support for DW_TAG_base_type '()' encoded with DW_ATE = 0x7, bit_size = 0
* thread #1, queue = 'com.apple.main-thread', stop reason = EXC_BAD_ACCESS (code=1, address=0xa)
  * frame #0: 0x0000000196c53274 libsystem_platform.dylib`_platform_memmove + 420
    frame #1: 0x0000000103d31eec vim_plugin_test.so`core::ptr::read::h9e01436829227460(src=0x000000000000000a) at mod.rs:1115:9
    frame #2: 0x0000000103d3843c vim_plugin_test.so`_$LT$nvim_types..dictionary..DictIterator$u20$as$u20$core..iter..traits..iterator..Iterator$GT$::next::hc4c389472e824fba(self=0x000000016fdfc560) at dictionary.rs:128:52
    frame #3: 0x0000000103d2e550 vim_plugin_test.so`_$LT$nvim_oxi..object..de..MapDeserializer$u20$as$u20$serde..de..MapAccess$GT$::next_key_seed::h36af9d336687008b(self=0x000000016fdfc560, seed=PhantomData<nvim_oxi::api::types::command_args::_::{impl#0}::deserialize::__Field> @ 0x000000016fdfb15f) at de.rs:242:39
    frame #4: 0x0000000103d28ed0 vim_plugin_test.so`serde::de::MapAccess::next_key::ha2ac654861086e10(self=0x000000016fdfc560) at mod.rs:1854:9
    frame #5: 0x0000000103d28a70 vim_plugin_test.so`_$LT$$RF$mut$u20$A$u20$as$u20$serde..de..MapAccess$GT$::next_key::hf70525b52654ea59(self=0x000000016fdfb3a8) at mod.rs:1944:9
    frame #6: 0x0000000103d38d78 vim_plugin_test.so`_$LT$nvim_oxi..api..types..command_args.._..$LT$impl$u20$serde..de..Deserialize$u20$for$u20$nvim_oxi..api..types..command_args..CommandArgs$GT$..deserialize..__Visitor$u20$as$u20$serde..de..Visitor$GT$::visit_map::h778579db4598e380(self=(marker = core::marker::PhantomData<nvim_oxi::api::types::command_args::CommandArgs> @ 0x000000016fdfc43e, lifetime = core::marker::PhantomData<void *> @ 0x000000016fdfc43e), __map=0x000000016fdfc560) at command_args.rs:12:45
    frame #7: 0x0000000103d2e1b4 vim_plugin_test.so`_$LT$nvim_oxi..object..de..Deserializer$u20$as$u20$serde..de..Deserializer$GT$::deserialize_map::hbb41dd910ef1931e(self=Deserializer @ 0x000000016fdfc730, visitor=(marker = core::marker::PhantomData<nvim_oxi::api::types::command_args::CommandArgs> @ 0x000000016fdfc67f, lifetime = core::marker::PhantomData<void *> @ 0x000000016fdfc67f)) at de.rs:171:17
    frame #8: 0x0000000103d2e270 vim_plugin_test.so`_$LT$nvim_oxi..object..de..Deserializer$u20$as$u20$serde..de..Deserializer$GT$::deserialize_struct::h1c7c2cd4a8b36d84(self=<unavailable>, _name=(data_ptr = "CommandArgsreg", length = 11), _fields=&[&str] @ 0x000000016fdfc768, visitor=(marker = core::marker::PhantomData<nvim_oxi::api::types::command_args::CommandArgs> @ 0x000000016fdfc77f, lifetime = core::marker::PhantomData<void *> @ 0x000000016fdfc77f)) at de.rs:191:9
    frame #9: 0x0000000103d3853c vim_plugin_test.so`nvim_oxi::api::types::command_args::_::_$LT$impl$u20$serde..de..Deserialize$u20$for$u20$nvim_oxi..api..types..command_args..CommandArgs$GT$::deserialize::ha3ed7f8afb11d764(__deserializer=<unavailable>) at command_args.rs:12:45
    frame #10: 0x0000000103d384e0 vim_plugin_test.so`_$LT$nvim_oxi..api..types..command_args..CommandArgs$u20$as$u20$nvim_oxi..object..from_object..FromObject$GT$::from_obj::h8776a94f554c1fc3(obj=<unavailable>) at command_args.rs:53:9
    frame #11: 0x0000000103d265c4 vim_plugin_test.so`_$LT$A$u20$as$u20$nvim_oxi..lua..poppable..LuaPoppable$GT$::pop::ha691d818a34416d5(lstate=0x000000010070c380) at poppable.rs:46:9
    frame #12: 0x0000000103d27f94 vim_plugin_test.so`nvim_oxi::lua::fun::Function$LT$A$C$R$GT$::from_fn::_$u7b$$u7b$closure$u7d$$u7d$::_$u7b$$u7b$closure$u7d$$u7d$::h1f0421eb4ed04d2f(l=0x000000010070c380) at fun.rs:104:45
    frame #13: 0x0000000103d30fbc vim_plugin_test.so`nvim_oxi::lua::fun::Function$LT$A$C$R$GT$::from_fn::c_fun::hdd04c61c9bcb723d(lstate=0x000000010070c380) at fun.rs:100:13
    frame #14: 0x0000000100734238 libluajit-5.1.2.dylib`___lldb_unnamed_symbol96$$libluajit-5.1.2.dylib + 44
    frame #15: 0x0000000100740d80 libluajit-5.1.2.dylib`lua_pcall + 148
    frame #16: 0x000000010012c368 nvim`nlua_pcall + 120
    frame #17: 0x000000010012decc nvim`nlua_do_ucmd + 1368
    frame #18: 0x000000010024109c nvim`do_ucmd + 208
    frame #19: 0x00000001000d578c nvim`execute_cmd0 + 140
    frame #20: 0x00000001000d261c nvim`do_cmdline + 12264
    frame #21: 0x00000001001761c0 nvim`nv_colon + 416
    frame #22: 0x0000000100173be8 nvim`normal_execute + 4172
    frame #23: 0x000000010020ad44 nvim`state_enter + 360
    frame #24: 0x0000000100137b60 nvim`main + 10716
    frame #25: 0x000000010039508c dyld`start + 520
(lldb)

My best parse of this is that it's related to argument parsing or handling during the processing of the user-defined command. Perhaps relatedly, I noticed that using CommandNArgs::One in the creation of the command caused an immediate crash of neovim on launch with the following error:

thread '<unnamed>' panicked at 'called `Result::unwrap()` on an `Err` value: NvimError("Invalid value for \'nargs\'")', /Users/reecestevens/.cargo/registry/src/github.com-1ecc6299db9ec823/nvim-oxi-0.1.3/src/lua/lua.rs:42:12
stack backtrace:
   0: rust_begin_unwind
             at /rustc/a55dd71d5fb0ec5a6a3a9e8c27b2127ba491ce52/library/std/src/panicking.rs:584:5
   1: core::panicking::panic_fmt
             at /rustc/a55dd71d5fb0ec5a6a3a9e8c27b2127ba491ce52/library/core/src/panicking.rs:142:14
   2: core::result::unwrap_failed
             at /rustc/a55dd71d5fb0ec5a6a3a9e8c27b2127ba491ce52/library/core/src/result.rs:1814:5
   3: core::result::Result<T,E>::unwrap
             at /rustc/a55dd71d5fb0ec5a6a3a9e8c27b2127ba491ce52/library/core/src/result.rs:1107:23
   4: nvim_oxi::lua::lua::module_entrypoint
             at /Users/reecestevens/.cargo/registry/src/github.com-1ecc6299db9ec823/nvim-oxi-0.1.3/src/lua/lua.rs:42:5
   5: luaopen_vim_plugin_test
             at ./src/lib.rs:6:1
   6: <unknown>
   7: _luaL_openlibs
   8: <unknown>
   9: _lua_pcall
  10: _nlua_pcall
  11: _nlua_typval_exec
  12: _ex_lua
  13: _execute_cmd0
  14: _do_cmdline
  15: _do_source
  16: _cmd_source
  17: _execute_cmd0
  18: _do_cmdline
  19: _source_using_linegetter
  20: _nvim_exec
  21: _nlua_api_nvim_exec
  22: <unknown>
  23: _lua_pcall
  24: _nlua_pcall
  25: _nlua_typval_exec
  26: _ex_lua
  27: _execute_cmd0
  28: _do_cmdline
  29: _do_source
  30: _main
note: Some details are omitted, run with `RUST_BACKTRACE=full` for a verbose backtrace.
fatal runtime error: Rust panics must be rethrown

If you have any bandwidth to review these stack traces and let me know what you think, I would really appreciate it. Thanks again!

can i get the diagnostic table?

image

hey im trying to figure out how can i get the diagnostic table, can it be done in the way above with some changes?
or is there other way to do so, it there are.
thanks

error in compiling part of `api` example

good day to you!

im trying to compile some part of api example, but keep receiveing errors in build

image

lib.rs:

use nvim_oxi::api::{self, opts::*, types::*, Window};
use nvim_oxi::{self as oxi, print, Dictionary, Function};

#[oxi::module]
fn api() -> oxi::Result<i32> {
    api::set_keymap(Mode::Insert, "hi", "hello", Default::default())?;
    Ok(42)
}

Use well known TryFrom instead of custom FromObject / ToObjet tratis

Maybe it's just me overlooking something but both traits in nvim_types::conversion are just a specialized version of TryFrom/TryInto.
Is there a technical reason?
Else I suggest to rewrite conversion.rs to use TryFrom instead or delete it all together.

I'm currently exploring nvim-oxi and while toying around with it I wrote a bunch of TryFrom<Object> implementations before I realized FromObject is a thing, if it's down to development time needed I could do the conversion and create a PR.

Support for nightly neovim

Is it possible to support nightly neovim as well, or is that something that can just break very easily due to the ffi interface?

I got an error for nvim_get/set_option_value with invalid value for key: scope on neovim nightly.

I looked at the API and don't really see the reason why it would break, as they only removed win and buf, but kept scope the same:

nvim_get_option_value({name}, {*opts})               *nvim_get_option_value()*
                Gets the value of an option. The behavior of this function
                matches that of |:set|: the local value of an option is
                returned if it exists; otherwise, the global value is
                returned. Local values always correspond to the current buffer
                or window. To get a buffer-local or window-local option for a
                specific buffer or window, use |nvim_buf_get_option()| or
                |nvim_win_get_option()|.

                Parameters: ~
                    {name}  Option name
                    {opts}  Optional parameters
                            • scope: One of 'global' or 'local'. Analogous to
                              |:setglobal| and |:setlocal|, respectively.

                Return: ~
                    Option value

Is this a cause of a change in memory layout, so to say?

Support for `vim.lsp` and `vim.diagnostic`

Hey 👋🏾

First of all, thank you very much for all the effort and time you put into this project. I really appreciate it and it gave the necessary motivation to start working on NeoVim plugins again.

I'm now in need to make some calls to functions that are globally defined in Lua by NeoVim. Means I want to access vim.lsp, vim.diagnostic, ... Unfortunately I don't see how this should be possible right now. But maybe I'm blind. 🙈
I took a look into your noib3/nvim-compleet project to checkout how you do it there. But it seems like this includes a huge amount of boilerplate code with a bridge etc. pp. completely independent of this library here. I'm not sure if there is any better way to do it, because I honestly have no clue about this topic. But in any case, do you plan to integrate this feature into nvim-oxi too? It looks like you did already all the work for it in the other project, so it would be just a matter of putting it here too and wrap it nicely. Am I wrong?

Looking forward to hear what you think. 🙃

Add roadmap of the project

Some people like me would like to contribute, but sadly, I dont know what to start with. Having somekind of a todo/gh project/roadmap would be great, so more people would contribute.

[Neovim 0.8.0] `list_bufs` and `list_wins` not working as expected

Hello! Looking for a bit of help (or advice). I'm not sure if this is a bug or just me not understanding how API bindings in Rust works. I'm trying to use list_bufs and list_wins, but neither appear to be demonstrating the same behaviour as vim.api.nvim_list_bufs or vim.api.nvim_list_wins. For list_bufs, no buffers are ever found. For list_wins, I keep hitting a segfault.

Please let me know if I'm doing anything wrong. This is on Neovim 0.8.0 and I've made sure to point to master with the neovim-0-8 feature flag.

Thanks!

Expected

List buffers

:lua =vim.api.nvim_list_bufs()                                                                                                                                             
{ 1, 2, 3 }

List windows

:lua =vim.api.nvim_list_wins()                                                                                                                                             
{ 1000 }

Found

List buffers

:lua =require("nvim_open").buffers()
"[]"

List windows

:lua =require("nvim_open").windows()
fish: Job 1, 'nvim' terminated by signal SIGSEGV (Address boundary error))

Code

lib.rs

use std::convert::Infallible;

use nvim_oxi as oxi;
use oxi::{
    api::{list_bufs, Buffer, Window, list_wins},
    Function, Dictionary, Object
};


#[oxi::module]
fn nvim_open() -> oxi::Result<oxi::Dictionary> {
    let buffers = Function::from_fn(|()| {
        let open_buffers: Vec<Buffer> = list_bufs().collect();
        Ok::<_, Infallible>(oxi::String::from(format!("{:?}", open_buffers)))
    });

    let windows = Function::from_fn(|()| {
        let open_windows: Vec<Window> = list_wins().collect();
        Ok::<_, Infallible>(oxi::String::from(format!("{:?}", open_windows)))
    });

    Ok(Dictionary::from_iter([
        ("buffers", Object::from(buffers)),
        ("windows", Object::from(windows)),
    ]))
}

Cargo.toml

[dependencies.nvim-oxi]
git = "https://github.com/noib3/nvim-oxi"
branch = "master"
features = [ "neovim-0-8" ]

Implement FromObject for Object

This allows to get back a "dynamic" object from functions that return <T: FromObject>.

My workaround is to do:

#[derive(Deref)]
struct Object(oxi::Object);

impl FromObject for Object {
    fn from_object(object: oxi::Object) -> Result<Self, conversion::Error> {
        Ok(Self(object))
    }
}

but this would be nice to have in the library, especially as it would be a 4 line implementation

Better integration with mlua

It would be nice to allow returning mlua objects from the lua module, for example userdata or coroutines. I think you could either make the mlua value pushable or use the mlua module macro

Pass Rust closures where the Lua api expects functions

It should be possible to pass a Rust closure everywhere one would pass a Lua function when using the Lua API.

Just as an example, something like

local print_current_modified = function()
  local buf = vim.api.nvim_get_current_buf()

  local is_modified = vim.api.nvim_buf_call(buf, function()
    return vim.api.nvim_buf_get_option(0, "modified")
  end)

  print(is_modified)
end

should become

use nvim_oxi as nvim;

fn print_current_modified() -> nvim::Result<()> {
    let buf = nvim::api::get_current_buf();

    let is_modified = buf.call(|| {
        nvim::Buffer::from(0).get_option::<bool>("modified")
    })?;

    nvim::print!("{is_modified}");

    Ok(())
}

Functions should accept FnOnce or FnMut closures on a case-by-case basis, but always with a 'static bound.

Support for Lua API's opt manipulation

I'm not sure whether it is possible to implement this in here as it is only part of the lua API if I understand correctly, but they have a really convenient way to interact with option values using e.g. append, prepend...

I want to migrate from my own nvim plugin library, which was purely based on the lua api, which had these features therefor, to nvim-oxi as it seems to provide way better ergonomics.

But I would be glad if I could somehow get access to the vim.opts that is available from lua: example in my API.

How to get return from an async function

Inspired by your crate, I want to use Rust to provide completion list for the cargo add command so that user can easily get available version when they type @ and get available features when they input -F through the neovim command line.

I have wrote some simple code to get crate information from crates.io, but now I stuck at not knowing how to return result from async function.

Here is my current implementation: https://github.com/Avimitin/cargo-add-cmp.nvim/blob/master/src/lib.rs#L99. I don't know how to await it and return the list of result as Lua api.

Move oxi-tests to root tests dir

Currently CI does not show us the fact that tests are failing because oxi-tests is excluded from cargo workspace. I will create a PR that fixes this behavior by cding into oxi-tests dir, although the better approach would be extracting tests from a crate and moving to actual tests dir.

more info about tests/

Can't build this repository on Windows.

Rustc: rustc 1.59.0 (9d1b2106e 2022-02-23)
Cargo: cargo 1.59.0 (49d8809dc 2022-02-10)
NeoVim: NVIM v0.8.0-dev+296-g307c5c63e
Error:
изображение

Translation of some parts of error message:
ссылка на неразрешённый внешний символ -> link to forbidden external symbol
в функции -> in function
неразрешенных внешних элементов -> forbidden external elements
создается библиотека -> creating a library

Double free on Array

Im trying to handle the complete function in the nvim-cmp, in mlua i made it works with the same signature, here i have a double free error. maybe i create Array incorrectly or i do something weird in the func?
Im trying to create something like that
arr = { { "label" = "Jan"} } where it is in index 0.

the same in mlua:
image

image

image

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.