fzyzcjy / flutter_rust_bridge

Flutter/Dart <-> Rust binding generator, feature-rich, but seamless and simple.
https://fzyzcjy.github.io/flutter_rust_bridge/
MIT License
4.17k stars 289 forks source link

Panic on codegen "Parse HIR" phase when defining private type #2170

Closed pixelshot91 closed 3 months ago

pixelshot91 commented 3 months ago

Describe the bug

The codegen panics when I execute the steps described below. What I find surprising is that:

  1. Neither the struct nor the 2 traits are pub.
  2. The file common.rs is not imported by pub mod but by mod
  3. The file rust/src/api/simple.rs is unchanged from the default greet function, and does not references in any way my struct or my traits

frb_codegen shouldn't even see my file common.rs , no ?

Tentatives

  1. If I add

    #[frb(ignore)]

    to every item in common.rs, codegen still fails

  2. If I add #[frb(ignore)] above mod common; codegen succeed, but Rust compilation fails with

    error[E0658]: non-inline modules in proc macro input are unstable

Working versions

  1. If I remove this line, codegen succeed

    impl MyTrait2 for MyStruct {}
  2. If I add this comment in rust/src/lib.rs, codegen succeed

    /// flutter_rust_bridge:ignore
    mod common;

Any help is appreciated, I thanks again for your work :+1:

Steps to reproduce

From the repo created by flutter_rust_bridge_codegen create, I add a file rust/src/common.rs

trait MyTrait {
    fn request(&self);
}

trait MyTrait2 {}

struct MyStruct {
    client: Box<dyn MyTrait>,
}

impl MyTrait2 for MyStruct {}

and add this file to the crate:

pub mod api;
mod frb_generated;

mod common;

Logs

Details

```shell [2024-06-30T20:55:39.360Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/main.rs:24] cli=Cli { verbose: false, command: Generate(GenerateCommandArgs { watch: false, primary: GenerateCommandArgsPrimary { config_file: None, rust_input: None, dart_output: None, c_output: None, duplicated_c_output: None, rust_root: None, rust_output: None, dart_entrypoint_class_name: None, dart_format_line_length: None, dart_preamble: None, rust_preamble: None, no_dart_enums_style: false, no_add_mod_to_lib: false, llvm_path: None, llvm_compiler_opts: None, dart_root: None, no_build_runner: false, extra_headers: None, no_web: false, no_deps_check: false, default_external_library_loader_web_prefix: None, no_dart3: false, full_dep: false, local: false, enable_lifetime: false, type_64bit_int: false, stop_on_error: false, dump: None, dump_all: false } }) } [2024-06-30T20:55:39.360Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/codegen/config/config_parser.rs:51] Found config file flutter_rust_bridge.yaml [2024-06-30T20:55:39.360Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/codegen/mod.rs:23] config=Config { base_dir: Some(""), rust_input: Some("crate::api"), dart_output: Some("lib/src/rust"), c_output: None, duplicated_c_output: None, rust_root: Some("rust/"), rust_output: None, dart_entrypoint_class_name: None, dart_format_line_length: None, dart_preamble: None, rust_preamble: None, dart_enums_style: None, add_mod_to_lib: None, llvm_path: None, llvm_compiler_opts: None, dart_root: None, build_runner: None, extra_headers: None, web: None, deps_check: None, dart3: None, full_dep: None, local: None, default_external_library_loader_web_prefix: None, dart_type_rename: None, enable_lifetime: None, type_64bit_int: None, stop_on_error: None, dump: None, dump_all: None } meta_config=MetaConfig { watch: false } [2024-06-30T20:55:39.360Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/codegen/config/internal_config_parser/mod.rs:33] InternalConfig.parse base_dir="/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug" [2024-06-30T20:55:39.452Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/codegen/mod.rs:26] internal_config=InternalConfig { controller: ControllerInternalConfig { watch: false, watching_paths: ["/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust/src"], exclude_paths: ["/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust/src/frb_generated.rs", "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust/src/frb_generated.io.rs", "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust/src/frb_generated.web.rs"], max_count: None }, preparer: PreparerInternalConfig { dart_root: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug", deps_check: true, needs_ffigen: false }, parser: ParserInternalConfig { hir: ParserHirInternalConfig { rust_input_namespace_pack: RustInputNamespacePack { rust_input_namespace_prefixes: [Namespace { joined_path: "crate::api" }], rust_output_path_namespace: Namespace { joined_path: "crate::frb_generated" } }, rust_crate_dir: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust", third_party_crate_names: [] }, mir: ParserMirInternalConfig { rust_input_namespace_pack: RustInputNamespacePack { rust_input_namespace_prefixes: [Namespace { joined_path: "crate::api" }], rust_output_path_namespace: Namespace { joined_path: "crate::frb_generated" } }, force_codec_mode_pack: Some(CodecModePack { dart2rust: Pde, rust2dart: Pde }), default_stream_sink_codec: Sse, default_rust_opaque_codec: Moi, stop_on_error: false, enable_lifetime: false, type_64bit_int: false } }, generator: GeneratorInternalConfig { api_dart: GeneratorApiDartInternalConfig { dart_enums_style: true, dart3: true, dart_decl_base_output_path: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/lib/src/rust", dart_impl_output_path: TargetOrCommonMap { common: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/lib/src/rust/frb_generated.dart", io: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/lib/src/rust/frb_generated.io.dart", web: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/lib/src/rust/frb_generated.web.dart" }, dart_entrypoint_class_name: "RustLib", dart_preamble: "", dart_type_rename: {} }, wire: GeneratorWireInternalConfig { dart: GeneratorWireDartInternalConfig { has_ffigen: false, web_enabled: true, llvm_path: ["/opt/homebrew/opt/llvm", "/usr/local/opt/llvm", "/usr/lib/llvm-9", "/usr/lib/llvm-10", "/usr/lib/llvm-11", "/usr/lib/llvm-12", "/usr/lib/llvm-13", "/usr/lib/llvm-14", "/usr/lib/", "/usr/lib64/", "C:/Program Files/llvm", "C:/msys64/mingw64"], llvm_compiler_opts: "", dart_root: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug", extra_headers: "", dart_impl_output_path: TargetOrCommonMap { common: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/lib/src/rust/frb_generated.dart", io: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/lib/src/rust/frb_generated.io.dart", web: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/lib/src/rust/frb_generated.web.dart" }, dart_output_class_name_pack: DartOutputClassNamePack { entrypoint_class_name: "RustLib", api_class_name: "RustLibApi", api_impl_class_name: "RustLibApiImpl", api_impl_platform_class_name: "RustLibApiImplPlatform", wire_class_name: "RustLibWire", wasm_module_name: "RustLibWasmModule" }, default_external_library_loader: GeneratorWireDartDefaultExternalLibraryLoaderInternalConfig { stem: "rust_lib_booky_minimal_frb_unwrap_bug", io_directory: "rust/target/release/", web_prefix: "pkg/" }, c_symbol_prefix: "frbgen_booky_minimal_frb_unwrap_bug_" }, rust: GeneratorWireRustInternalConfig { rust_crate_dir: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust", web_enabled: true, rust_output_path: TargetOrCommonMap { common: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust/src/frb_generated.rs", io: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust/src/frb_generated.io.rs", web: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust/src/frb_generated.web.rs" }, c_symbol_prefix: "frbgen_booky_minimal_frb_unwrap_bug_", has_ffigen: false, default_stream_sink_codec: Sse, default_rust_opaque_codec: Moi, rust_preamble: "" }, c: GeneratorWireCInternalConfig { enable: false, rust_crate_dir: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust", rust_output_path: TargetOrCommonMap { common: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust/src/frb_generated.rs", io: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust/src/frb_generated.io.rs", web: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust/src/frb_generated.web.rs" }, c_output_path: None, c_symbol_prefix: "frbgen_booky_minimal_frb_unwrap_bug_" } } }, polisher: PolisherInternalConfig { duplicated_c_output_path: [], dart_format_line_length: 80, add_mod_to_lib: true, build_runner: true, web_enabled: true, dart_root: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug", rust_crate_dir: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust", rust_output_path: TargetOrCommonMap { common: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust/src/frb_generated.rs", io: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust/src/frb_generated.io.rs", web: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust/src/frb_generated.web.rs" }, c_output_path: None, enable_auto_upgrade: true }, dumper: DumperInternalConfig { dump_contents: [], dump_directory: "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust/target/frb_dump" } } [2024-06-30T20:55:39.452Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/utils/dart_repository/dart_repo.rs:22] Guessing toolchain the runner is run into [2024-06-30T20:55:39.452Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/commands/command_runner.rs:129] execute command: bin=sh args="-c \"flutter\" \"--version\"" current_dir=None cmd="sh" "-c" "\"flutter\" \"--version\"" [2024-06-30T20:55:39.717Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/commands/command_runner.rs:140] command="sh" "-c" "\"flutter\" \"--version\"" stdout=Flutter 3.22.2 • channel stable • https://github.com/flutter/flutter.git Framework • revision 761747bfc5 (4 weeks ago) • 2024-06-05 22:15:13 +0200 Engine • revision edd8546116 Tools • Dart 3.4.3 • DevTools 2.34.3 stderr= [2024-06-30T20:55:39.717Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/commands/cargo_expand/mod.rs:26] run_cargo_expand manifest_dir= rust_crate_dir="/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust" [2024-06-30T20:55:39.717Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/commands/cargo_expand/real.rs:60] Running cargo expand in '"/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust"' [2024-06-30T20:55:39.717Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/commands/command_runner.rs:129] execute command: bin=cargo args="expand --lib --theme=none --ugly" current_dir=Some("/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust") cmd=cd "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust" && RUSTFLAGS="--cfg frb_expand" "cargo" "expand" "--lib" "--theme=none" "--ugly" [2024-06-30T20:55:39.843Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/commands/command_runner.rs:140] command=cd "/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust" && RUSTFLAGS="--cfg frb_expand" "cargo" "expand" "--lib" "--theme=none" "--ugly" stdout=#![feature(prelude_import)] #[prelude_import] use std::prelude::rust_2021::*; #[macro_use] extern crate std; use flutter_rust_bridge::frb; pub mod api { pub mod simple { #[doc = "frb_encoded(235b6672622873796e63295d)"] pub fn gredfdset(name: String) -> String { { let res = ::alloc::fmt::format(format_args!("Hello, {0}!", name)); res } } #[doc = "frb_encoded(235b66726228696e6974295d)"] pub fn init_app() { flutter_rust_bridge::setup_default_user_utils(); } trait MyTrait { fn request(&self); } trait MyTrait2 {} struct MyStruct { client: Box, } impl MyTrait2 for MyStruct {} } } mod frb_generated { #![allow(non_camel_case_types, unused, non_snake_case, clippy::needless_return, clippy::redundant_closure_call, clippy::redundant_closure, clippy::useless_conversion, clippy::unit_arg, clippy::unused_unit, clippy::double_parens, clippy::let_and_return, clippy::too_many_arguments, clippy::match_single_binding, clippy::clone_on_copy, clippy::let_unit_value, clippy::deref_addrof, clippy::explicit_auto_deref, clippy::borrow_deref_ref, clippy::needless_borrow)] use flutter_rust_bridge::for_generated::byteorder::{ NativeEndian, ReadBytesExt, WriteBytesExt, }; use flutter_rust_bridge::for_generated::{ transform_result_dco, Lifetimeable, Lockable, }; use flutter_rust_bridge::{Handler, IntoIntoDart}; #[doc(hidden)] pub(crate) struct FrbWrapper(T); impl Clone for FrbWrapper { fn clone(&self) -> Self { FrbWrapper(self.0.clone()) } } impl PartialEq for FrbWrapper { fn eq(&self, other: &Self) -> bool { self.0.eq(&other.0) } } impl Eq for FrbWrapper {} impl std::hash::Hash for FrbWrapper { fn hash(&self, state: &mut H) { self.0.hash(state) } } impl From for FrbWrapper { fn from(t: T) -> Self { FrbWrapper(t) } } use std::collections::HashMap; use std::marker::PhantomData; use std::sync::Arc; pub struct MoiArc { object_id: Option, value: Option>, _phantom: PhantomData, } #[automatically_derived] impl ::core::fmt::Debug for MoiArc { #[inline] fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result { ::core::fmt::Formatter::debug_struct_field3_finish(f, "MoiArc", "object_id", &self.object_id, "value", &self.value, "_phantom", &&self._phantom) } } impl Drop for MoiArc { fn drop(&mut self) { if let Some(object_id) = self.object_id { Self::decrement_strong_count(object_id); } } } impl AsRef for MoiArc { fn as_ref(&self) -> &T { self.value.as_ref().unwrap().as_ref() } } impl ::flutter_rust_bridge::for_generated::BaseArc for MoiArc { fn new(value: T) -> Self where T: Sized { let mut pool = T::get_pool().write().unwrap(); let object_id = pool.id_generator.next_id(); let value = Arc::new(value); let old_value = pool.map.insert(object_id, MoiArcPoolValue { ref_count: 1, value: value.clone() }); if !old_value.is_none() { ::core::panicking::panic("assertion failed: old_value.is_none()") }; Self { object_id: Some(object_id), value: Some(value), _phantom: PhantomData, } } fn try_unwrap(mut self) -> Result where T: Sized { let pool = &mut T::get_pool().write().unwrap(); if pool.map.get(&self.object_id.unwrap()).unwrap().ref_count == 1 { Self::decrement_strong_count_raw(self.object_id.unwrap(), pool); self.object_id.take().unwrap(); Ok(Arc::into_inner(self.value.take().unwrap()).unwrap()) } else { Err(self) } } fn into_inner(self) -> Option where T: Sized { self.try_unwrap().ok() } fn into_raw(mut self) -> usize { self.object_id.take().unwrap() } } impl Clone for MoiArc { fn clone(&self) -> Self { Self::increment_strong_count(self.object_id.unwrap()); Self { object_id: self.object_id, value: self.value.clone(), _phantom: PhantomData, } } } impl MoiArc { pub(crate) fn from_raw(raw: usize) -> Self where T: Sized { let map = &T::get_pool().read().unwrap().map; Self { object_id: Some(raw), value: Some(map.get(&raw).unwrap().value.clone()), _phantom: PhantomData, } } pub fn increment_strong_count(raw: usize) { let map = &mut T::get_pool().write().unwrap().map; map.get_mut(&raw).unwrap().ref_count += 1; } pub fn decrement_strong_count(raw: usize) { let mut pool = T::get_pool().write().unwrap(); let object = Self::decrement_strong_count_raw(raw, &mut pool); drop(pool); drop(object); } fn decrement_strong_count_raw(raw: usize, pool: &mut MoiArcPoolInner) -> Option> { let value = pool.map.get_mut(&raw).unwrap(); value.ref_count -= 1; if value.ref_count == 0 { pool.map.remove(&raw) } else { None } } } pub trait MoiArcValue: 'static { fn get_pool() -> &'static MoiArcPool; } type ObjectId = usize; pub type MoiArcPool = std::sync::RwLock>; pub struct MoiArcPoolInner { map: HashMap>, id_generator: IdGenerator, } impl Default for MoiArcPoolInner { fn default() -> Self { Self { map: HashMap::new(), id_generator: Default::default() } } } struct IdGenerator { next_id: ObjectId, } impl Default for IdGenerator { fn default() -> Self { Self { next_id: Self::MIN_ID } } } impl IdGenerator { const MIN_ID: ObjectId = 1; const MAX_ID: ObjectId = 2147483600; fn next_id(&mut self) -> ObjectId { let ans = self.next_id; self.next_id = if self.next_id >= Self::MAX_ID { Self::MIN_ID } else { self.next_id + 1 }; ans } } impl MoiArcPoolInner {} struct MoiArcPoolValue { ref_count: i32, value: Arc, } use ::flutter_rust_bridge::for_generated::decode_rust_opaque_nom; fn decode_rust_opaque_moi(ptr: usize) -> RustOpaqueMoi { RustOpaqueMoi::from_arc(MoiArc::::from_raw(ptr)) } use ::flutter_rust_bridge::for_generated::StdArc; use ::flutter_rust_bridge::RustOpaqueNom; /// Please refer to `RustOpaque` for doc. pub type RustOpaqueMoi = ::flutter_rust_bridge::for_generated::RustOpaqueBase>; /// A wrapper to support [arbitrary Rust types](https://cjycode.com/flutter_rust_bridge/guides/types/arbitrary). pub type RustOpaque = RustOpaqueMoi; use ::flutter_rust_bridge::RustAutoOpaqueNom; /// Please refer to `RustAutoOpaque` for doc. pub type RustAutoOpaqueMoi = ::flutter_rust_bridge::for_generated::RustAutoOpaqueBase>>; /// Usually this is unneeded, and just write down arbitrary types. /// However, when you need arbitrary types at places that are not supported yet, /// use `RustOpaqueOpaque`. pub type RustAutoOpaque = RustAutoOpaqueMoi; pub trait CstDecode { fn cst_decode(self) -> T; } impl CstDecode> for *mut S where *mut S: CstDecode { fn cst_decode(self) -> Option { (!self.is_null()).then(|| self.cst_decode()) } } pub trait SseDecode { fn sse_decode(deserializer: &mut ::flutter_rust_bridge::for_generated::SseDeserializer) -> Self; } pub trait SseEncode { fn sse_encode(self, serializer: &mut ::flutter_rust_bridge::for_generated::SseSerializer); } fn transform_result_sse(raw: Result) -> Result<::flutter_rust_bridge::for_generated::Rust2DartMessageSse, ::flutter_rust_bridge::for_generated::Rust2DartMessageSse> where T: SseEncode, E: SseEncode { use ::flutter_rust_bridge::for_generated::{Rust2DartAction, SseCodec}; match raw { Ok(raw) => Ok(SseCodec::encode(Rust2DartAction::Success, |serializer| { raw.sse_encode(serializer) })), Err(raw) => Err(SseCodec::encode(Rust2DartAction::Error, |serializer| { raw.sse_encode(serializer) })), } } pub struct StreamSink { base: ::flutter_rust_bridge::for_generated::StreamSinkBase, } #[automatically_derived] impl ::core::clone::Clone for StreamSink { #[inline] fn clone(&self) -> StreamSink { StreamSink { base: ::core::clone::Clone::clone(&self.base) } } } impl StreamSink { pub fn deserialize(raw: String) -> Self { Self { base: ::flutter_rust_bridge::for_generated::StreamSinkBase::deserialize(raw), } } } impl StreamSink { pub fn add(&self, value: T) -> Result<(), ::flutter_rust_bridge::Rust2DartSendError> where T: ::flutter_rust_bridge::IntoIntoDart, T2: ::flutter_rust_bridge::IntoDart { self.add_raw(::flutter_rust_bridge::for_generated::Rust2DartAction::Success, value) } pub fn add_error(&self, value: TR) -> Result<(), ::flutter_rust_bridge::Rust2DartSendError> where TR: ::flutter_rust_bridge::IntoIntoDart, T2: ::flutter_rust_bridge::IntoDart { self.add_raw(::flutter_rust_bridge::for_generated::Rust2DartAction::Error, value) } fn add_raw(&self, action: ::flutter_rust_bridge::for_generated::Rust2DartAction, value: TR) -> Result<(), ::flutter_rust_bridge::Rust2DartSendError> where TR: ::flutter_rust_bridge::IntoIntoDart, T2: ::flutter_rust_bridge::IntoDart { self.base.add_raw(::flutter_rust_bridge::for_generated::DcoCodec::encode(action, value.into_into_dart())) } } impl StreamSink where T: SseEncode { pub fn add(&self, value: T) -> Result<(), ::flutter_rust_bridge::Rust2DartSendError> { self.add_raw(::flutter_rust_bridge::for_generated::Rust2DartAction::Success, value) } pub fn add_error(&self, value: TR) -> Result<(), ::flutter_rust_bridge::Rust2DartSendError> { self.add_raw(::flutter_rust_bridge::for_generated::Rust2DartAction::Error, value) } pub fn add_raw(&self, action: ::flutter_rust_bridge::for_generated::Rust2DartAction, value: TR) -> Result<(), ::flutter_rust_bridge::Rust2DartSendError> { self.base.add_raw(::flutter_rust_bridge::for_generated::SseCodec::encode(action, |serializer| value.sse_encode(serializer))) } } impl ::flutter_rust_bridge::IntoIntoDart> for StreamSink { fn into_into_dart(self) -> StreamSink { ::core::panicking::panic("internal error: entered unreachable code") } } impl ::flutter_rust_bridge::IntoDart for StreamSink { fn into_dart(self) -> ::flutter_rust_bridge::for_generated::DartAbi { ::core::panicking::panic("internal error: entered unreachable code") } } pub(crate) const FLUTTER_RUST_BRIDGE_CODEGEN_VERSION: &str = "2.0.0"; pub(crate) const FLUTTER_RUST_BRIDGE_CODEGEN_CONTENT_HASH: i32 = -890726528; #[allow(missing_copy_implementations)] #[allow(non_camel_case_types)] #[allow(dead_code)] pub struct FLUTTER_RUST_BRIDGE_HANDLER { __private_field: (), } #[doc(hidden)] pub static FLUTTER_RUST_BRIDGE_HANDLER: FLUTTER_RUST_BRIDGE_HANDLER = FLUTTER_RUST_BRIDGE_HANDLER { __private_field: () }; impl ::lazy_static::__Deref for FLUTTER_RUST_BRIDGE_HANDLER { type Target = ::flutter_rust_bridge::DefaultHandler<::flutter_rust_bridge::for_generated::SimpleThreadPool>; fn deref(&self) -> &::flutter_rust_bridge::DefaultHandler<::flutter_rust_bridge::for_generated::SimpleThreadPool> { #[inline(always)] fn __static_ref_initialize() -> ::flutter_rust_bridge::DefaultHandler<::flutter_rust_bridge::for_generated::SimpleThreadPool> { { match (&FLUTTER_RUST_BRIDGE_CODEGEN_VERSION, &flutter_rust_bridge::for_generated::FLUTTER_RUST_BRIDGE_RUNTIME_VERSION) { (left_val, right_val) => { if !(*left_val == *right_val) { let kind = ::core::panicking::AssertKind::Eq; ::core::panicking::assert_failed(kind, &*left_val, &*right_val, ::core::option::Option::Some(format_args!("Please ensure flutter_rust_bridge\'s codegen ({0}) and runtime ({1}) versions are the same", FLUTTER_RUST_BRIDGE_CODEGEN_VERSION, flutter_rust_bridge::for_generated::FLUTTER_RUST_BRIDGE_RUNTIME_VERSION))); } } }; ::flutter_rust_bridge::DefaultHandler::new_simple(Default::default()) } } #[inline(always)] fn __stability() -> &'static ::flutter_rust_bridge::DefaultHandler<::flutter_rust_bridge::for_generated::SimpleThreadPool> { static LAZY: ::lazy_static::lazy::Lazy<::flutter_rust_bridge::DefaultHandler<::flutter_rust_bridge::for_generated::SimpleThreadPool>> = ::lazy_static::lazy::Lazy::INIT; LAZY.get(__static_ref_initialize) } __stability() } } impl ::lazy_static::LazyStatic for FLUTTER_RUST_BRIDGE_HANDLER { fn initialize(lazy: &Self) { let _ = &**lazy; } } fn wire__crate__api__simple__gredfdset_impl(ptr_: flutter_rust_bridge::for_generated::PlatformGeneralizedUint8ListPtr, rust_vec_len_: i32, data_len_: i32) -> flutter_rust_bridge::for_generated::WireSyncRust2DartSse { FLUTTER_RUST_BRIDGE_HANDLER.wrap_sync::(flutter_rust_bridge::for_generated::TaskInfo { debug_name: "gredfdset", port: None, mode: flutter_rust_bridge::for_generated::FfiCallMode::Sync, }, move || { let message = unsafe { flutter_rust_bridge::for_generated::Dart2RustMessageSse::from_wire(ptr_, rust_vec_len_, data_len_) }; let mut deserializer = flutter_rust_bridge::for_generated::SseDeserializer::new(message); let api_name = ::sse_decode(&mut deserializer); deserializer.end(); transform_result_sse::<_, ()>((move || { let output_ok = Result::<_, ()>::Ok(crate::api::simple::gredfdset(api_name))?; Ok(output_ok) })()) }) } fn wire__crate__api__simple__init_app_impl(port_: flutter_rust_bridge::for_generated::MessagePort, ptr_: flutter_rust_bridge::for_generated::PlatformGeneralizedUint8ListPtr, rust_vec_len_: i32, data_len_: i32) { FLUTTER_RUST_BRIDGE_HANDLER.wrap_normal::(flutter_rust_bridge::for_generated::TaskInfo { debug_name: "init_app", port: Some(port_), mode: flutter_rust_bridge::for_generated::FfiCallMode::Normal, }, move || { let message = unsafe { flutter_rust_bridge::for_generated::Dart2RustMessageSse::from_wire(ptr_, rust_vec_len_, data_len_) }; let mut deserializer = flutter_rust_bridge::for_generated::SseDeserializer::new(message); deserializer.end(); move |context| { transform_result_sse::<_, ()>((move || { let output_ok = Result::<_, ()>::Ok({ crate::api::simple::init_app(); })?; Ok(output_ok) })()) } }) } impl SseDecode for String { fn sse_decode(deserializer: &mut flutter_rust_bridge::for_generated::SseDeserializer) -> Self { let mut inner = >::sse_decode(deserializer); return String::from_utf8(inner).unwrap(); } } impl SseDecode for Vec { fn sse_decode(deserializer: &mut flutter_rust_bridge::for_generated::SseDeserializer) -> Self { let mut len_ = ::sse_decode(deserializer); let mut ans_ = ::alloc::vec::Vec::new(); for idx_ in 0..len_ { ans_.push(::sse_decode(deserializer)); } return ans_; } } impl SseDecode for u8 { fn sse_decode(deserializer: &mut flutter_rust_bridge::for_generated::SseDeserializer) -> Self { deserializer.cursor.read_u8().unwrap() } } impl SseDecode for () { fn sse_decode(deserializer: &mut flutter_rust_bridge::for_generated::SseDeserializer) -> Self {} } impl SseDecode for i32 { fn sse_decode(deserializer: &mut flutter_rust_bridge::for_generated::SseDeserializer) -> Self { deserializer.cursor.read_i32::().unwrap() } } impl SseDecode for bool { fn sse_decode(deserializer: &mut flutter_rust_bridge::for_generated::SseDeserializer) -> Self { deserializer.cursor.read_u8().unwrap() != 0 } } fn pde_ffi_dispatcher_primary_impl(func_id: i32, port: flutter_rust_bridge::for_generated::MessagePort, ptr: flutter_rust_bridge::for_generated::PlatformGeneralizedUint8ListPtr, rust_vec_len: i32, data_len: i32) { match func_id { 2 => wire__crate__api__simple__init_app_impl(port, ptr, rust_vec_len, data_len), _ => ::core::panicking::panic("internal error: entered unreachable code"), } } fn pde_ffi_dispatcher_sync_impl(func_id: i32, ptr: flutter_rust_bridge::for_generated::PlatformGeneralizedUint8ListPtr, rust_vec_len: i32, data_len: i32) -> flutter_rust_bridge::for_generated::WireSyncRust2DartSse { match func_id { 1 => wire__crate__api__simple__gredfdset_impl(ptr, rust_vec_len, data_len), _ => ::core::panicking::panic("internal error: entered unreachable code"), } } impl SseEncode for String { fn sse_encode(self, serializer: &mut flutter_rust_bridge::for_generated::SseSerializer) { >::sse_encode(self.into_bytes(), serializer); } } impl SseEncode for Vec { fn sse_encode(self, serializer: &mut flutter_rust_bridge::for_generated::SseSerializer) { ::sse_encode(self.len() as _, serializer); for item in self { ::sse_encode(item, serializer); } } } impl SseEncode for u8 { fn sse_encode(self, serializer: &mut flutter_rust_bridge::for_generated::SseSerializer) { serializer.cursor.write_u8(self).unwrap(); } } impl SseEncode for () { fn sse_encode(self, serializer: &mut flutter_rust_bridge::for_generated::SseSerializer) {} } impl SseEncode for i32 { fn sse_encode(self, serializer: &mut flutter_rust_bridge::for_generated::SseSerializer) { serializer.cursor.write_i32::(self).unwrap(); } } impl SseEncode for bool { fn sse_encode(self, serializer: &mut flutter_rust_bridge::for_generated::SseSerializer) { serializer.cursor.write_u8(self as _).unwrap(); } } #[cfg(not(target_family = "wasm"))] #[path = "frb_generated.io.rs"] mod io { use super::*; use flutter_rust_bridge::for_generated::byteorder::{ NativeEndian, ReadBytesExt, WriteBytesExt, }; use flutter_rust_bridge::for_generated::{ transform_result_dco, Lifetimeable, Lockable, }; use flutter_rust_bridge::{Handler, IntoIntoDart}; pub trait NewWithNullPtr { fn new_with_null_ptr() -> Self; } impl NewWithNullPtr for *mut T { fn new_with_null_ptr() -> Self { std::ptr::null_mut() } } #[no_mangle] pub extern "C" fn frb_get_rust_content_hash() -> i32 { FLUTTER_RUST_BRIDGE_CODEGEN_CONTENT_HASH } #[no_mangle] pub extern "C" fn frb_pde_ffi_dispatcher_primary(func_id: i32, port_: i64, ptr_: *mut u8, rust_vec_len_: i32, data_len_: i32) { pde_ffi_dispatcher_primary_impl(func_id, port_, ptr_, rust_vec_len_, data_len_) } #[no_mangle] pub extern "C" fn frb_pde_ffi_dispatcher_sync(func_id: i32, ptr_: *mut u8, rust_vec_len_: i32, data_len_: i32) -> ::flutter_rust_bridge::for_generated::WireSyncRust2DartSse { pde_ffi_dispatcher_sync_impl(func_id, ptr_, rust_vec_len_, data_len_) } #[no_mangle] pub extern "C" fn dart_fn_deliver_output(call_id: i32, ptr_: *mut u8, rust_vec_len_: i32, data_len_: i32) { let message = unsafe { ::flutter_rust_bridge::for_generated::Dart2RustMessageSse::from_wire(ptr_, rust_vec_len_, data_len_) }; FLUTTER_RUST_BRIDGE_HANDLER.dart_fn_handle_output(call_id, message) } } #[cfg(not(target_family = "wasm"))] pub use io::*; } /// flutter_rust_bridge:ignore mod common { trait MyTrait { fn request(&self); } trait MyTrait2 {} struct MyStruct { client: Box, } impl MyTrait2 for MyStruct {} } stderr= Checking rust_lib_booky_minimal_frb_unwrap_bug v0.1.0 (/home/julien/Perso/LeBonCoin/chain_automatisation/booky_minimal_frb_unwrap_bug/rust) warning: unused import: `flutter_rust_bridge::frb` --> src/lib.rs:1:5 | 1 | use flutter_rust_bridge::frb; | ^^^^^^^^^^^^^^^^^^^^^^^^ | = note: `#[warn(unused_imports)]` on by default Finished `dev` profile [unoptimized + debuginfo] target(s) in 0.07s [2024-06-30T20:55:39.848Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/codegen/parser/hir/flat/parser/syn_item/item_struct_or_enum.rs:36] parse_syn_item_struct_or_enum item_ident=Ident { sym: MyStruct, span: bytes(588..596) } [2024-06-30T20:55:39.848Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/codegen/parser/mir/parser/ty/ty.rs:12] TypeParserWithContext.parse_type ty=dyn MyTrait ans=Delegate(DynTrait(MirTypeDelegateDynTrait { trait_def_name: NamespacedName { namespace: Namespace { joined_path: "crate::api::simple" }, name: "MyTrait" }, data: None })) [2024-06-30T20:55:39.848Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/codegen/parser/mir/parser/ty/ty.rs:12] TypeParserWithContext.parse_type ty=Box < dyn MyTrait > ans=Boxed(MirTypeBoxed { exist_in_real_api: true, inner: Delegate(DynTrait(MirTypeDelegateDynTrait { trait_def_name: NamespacedName { namespace: Namespace { joined_path: "crate::api::simple" }, name: "MyTrait" }, data: None })) }) [2024-06-30T20:55:39.848Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/codegen/parser/mir/parser/ty/ty.rs:12] TypeParserWithContext.parse_type ty=MyStruct ans=StructRef(MirTypeStructRef { ident: MirStructIdent(NamespacedName { namespace: Namespace { joined_path: "crate::api::simple" }, name: "MyStruct" }), is_exception: false }) [2024-06-30T20:55:39.848Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/codegen/parser/mir/parser/function/real/mod.rs:134] parse_function function name: "request" [2024-06-30T20:55:39.848Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/codegen/parser/mir/parser/function/real/lifetime.rs:36] parse_function_lifetime name=request inputs_lifetimes=[[]] output_lifetimes=[] ans=ParseFunctionLifetimeOutput { needs_extend_lifetime_per_arg: [false] } [2024-06-30T20:55:39.848Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/codegen/parser/mir/parser/ty/ty.rs:12] TypeParserWithContext.parse_type ty=MyTrait ans=TraitDef(MirTypeTraitDef { name: NamespacedName { namespace: Namespace { joined_path: "crate::api::simple" }, name: "MyTrait" } }) [2024-06-30T20:55:39.848Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/codegen/parser/mir/parser/function/real/mod.rs:134] parse_function function name: "gredfdset" [2024-06-30T20:55:39.848Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/codegen/parser/mir/parser/function/real/lifetime.rs:36] parse_function_lifetime name=gredfdset inputs_lifetimes=[[]] output_lifetimes=[] ans=ParseFunctionLifetimeOutput { needs_extend_lifetime_per_arg: [false] } [2024-06-30T20:55:39.848Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/codegen/parser/mir/parser/ty/ty.rs:12] TypeParserWithContext.parse_type ty=String ans=Delegate(String) [2024-06-30T20:55:39.848Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/codegen/parser/mir/parser/ty/ty.rs:12] TypeParserWithContext.parse_type ty=String ans=Delegate(String) [2024-06-30T20:55:39.848Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/codegen/parser/mir/parser/function/real/mod.rs:134] parse_function function name: "init_app" [2024-06-30T20:55:39.848Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/codegen/parser/mir/parser/function/real/lifetime.rs:36] parse_function_lifetime name=init_app inputs_lifetimes=[] output_lifetimes=[] ans=ParseFunctionLifetimeOutput { needs_extend_lifetime_per_arg: [] } [2024-06-30T20:55:39.848Z DEBUG /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/codegen/parser/mir/parser/ty/ty.rs:12] TypeParserWithContext.parse_type ty=MyStruct ans=StructRef(MirTypeStructRef { ident: MirStructIdent(NamespacedName { namespace: Namespace { joined_path: "crate::api::simple" }, name: "MyStruct" }), is_exception: false }) [2024-06-30T20:55:39.848Z ERROR /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/utils/logs.rs:55] panicked at /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/codegen/parser/mir/parser/ty/trait_object.rs:48:38: called `Option::unwrap()` on a `None` value thread 'main' panicked at /home/julien/.cargo/registry/src/index.crates.io-6f17d22bba15001f/flutter_rust_bridge_codegen-2.0.0/src/library/codegen/parser/mir/parser/ty/trait_object.rs:48:38: called `Option::unwrap()` on a `None` value note: run with `RUST_BACKTRACE=1` environment variable to display a backtrace ```

Expected behavior

frb_codegen should never panic. Some restriction may apply on the type and traits that I expose to Dart, but Rust code that stay private should not have any impact on codegen

Generated binding code

No response

OS

Debian GNU/Linux 12 (bookworm)

Version of flutter_rust_bridge_codegen

v2.0.0

Flutter info

Details

```shell [✓] Flutter (Channel stable, 3.22.2, on Debian GNU/Linux 12 (bookworm) 6.1.0-18-amd64, locale en) • Flutter version 3.22.2 on channel stable at /home/julien/fvm/versions/stable • Upstream repository https://github.com/flutter/flutter.git • Framework revision 761747bfc5 (4 weeks ago), 2024-06-05 22:15:13 +0200 • Engine revision edd8546116 • Dart version 3.4.3 • DevTools version 2.34.3 [!] Android toolchain - develop for Android devices (Android SDK version 34.0.0) • Android SDK at /home/julien/Android/Sdk • Platform android-34, build-tools 34.0.0 • Java binary at: /home/julien/.local/share/JetBrains/Toolbox/apps/android-studio-2/jbr/bin/java • Java version OpenJDK Runtime Environment (build 17.0.9+0-17.0.9b1087.9-11255266) ! Some Android licenses not accepted. To resolve this, run: flutter doctor --android-licenses [✗] Chrome - develop for the web (Cannot find Chrome executable at google-chrome) ! Cannot find Chrome. Try setting CHROME_EXECUTABLE to a Chrome executable. [✓] Linux toolchain - develop for Linux desktop • Debian clang version 16.0.6 (19) • cmake version 3.25.1 • ninja version 1.11.1 • pkg-config version 1.8.1 [✓] Android Studio (version 2023.3) • Android Studio at /home/julien/.local/share/JetBrains/Toolbox/apps/android-studio-2 • Flutter plugin can be installed from: 🔨 https://plugins.jetbrains.com/plugin/9212-flutter • Dart plugin can be installed from: 🔨 https://plugins.jetbrains.com/plugin/6351-dart • Java version OpenJDK Runtime Environment (build 17.0.9+0-17.0.9b1087.9-11255266) [✓] Android Studio (version 2023.1) • Android Studio at /home/julien/.local/share/JetBrains/Toolbox/apps/android-studio • Flutter plugin version 78.2.1 • Dart plugin can be installed from: 🔨 https://plugins.jetbrains.com/plugin/6351-dart • Java version OpenJDK Runtime Environment (build 17.0.7+0-17.0.7b1000.6-10550314) [✓] Android Studio (version 2022.3) • Android Studio at /home/julien/android-studios/android-studio-2022.3.1.19 • Flutter plugin version 75.1.2 • Dart plugin can be installed from: 🔨 https://plugins.jetbrains.com/plugin/6351-dart • Java version OpenJDK Runtime Environment (build 17.0.6+0-17.0.6b829.9-10027231) [✓] IntelliJ IDEA Community Edition (version 2019.2) • IntelliJ at /home/julien/idea • Flutter plugin can be installed from: 🔨 https://plugins.jetbrains.com/plugin/9212-flutter • Dart plugin can be installed from: 🔨 https://plugins.jetbrains.com/plugin/6351-dart [✓] VS Code (version 1.87.0) • VS Code at /usr/share/code • Flutter extension can be installed from: 🔨 https://marketplace.visualstudio.com/items?itemName=Dart-Code.flutter [✓] Connected device (1 available) • Linux (desktop) • linux • linux-x64 • Debian GNU/Linux 12 (bookworm) 6.1.0-18-amd64 [✓] Network resources • All expected network resources are available. ! Doctor found issues in 2 categories. ```

Version of clang++

16.0.6 (19)

Additional context

rustc 1.79.0 (129f3b996 2024-06-10)

fzyzcjy commented 3 months ago

Firstly, yes it should never panic. (e.g. it can return a Result::Err, and later that err is ignored). Feel free to PR for this by e.g. converting a panic into a Result::Err! Alternatively, I will work on it in the next batch.

Secondly, as for why it sees it: I have not implemented full-featured module parsing logic, since the rule of "what module is visible" is not very trivial. But feel free to PR for this as well. The non-api folder is scanned because there can be definitions in non-api folders and is used in api folders, so in this phase we just parse it.

Thirdly, the current workaround, as you pointed out, is to /// flutter_rust_bridge:ignore that mod.

AlexV525 commented 3 months ago

Running into the same issue, how do I determine which mod I should write?

```console  flutter_rust_bridge_codegen generate [2024-07-01T02:23:49.548Z INFO frb_codegen\src\library\codegen\parser\mir\parser\ty\enum_or_struct.rs:73] Skip parsing enum_or_struct `NamespacedName { namespace: Namespace { joined_path: "crate::bls::bls12381::big" }, name: "BIG" }` because of error (e=Cannot parse array length Stack backtrace: 0: 1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25: 26: BaseThreadInitThunk 27: RtlUserThreadStart) [2024-07-01T02:23:49.550Z INFO frb_codegen\src\library\codegen\parser\mir\parser\ty\enum_or_struct.rs:73] Skip parsing enum_or_struct `NamespacedName { namespace: Namespace { joined_path: "crate::bls::bls12381::dbig" }, name: "DBIG" }` because of error (e=Cannot parse array length Stack backtrace: 0: 1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25: 26: BaseThreadInitThunk 27: RtlUserThreadStart) [1.2s] Parse ⢀ └── [1.2s] Cargo expand & syn parse └── [0.0s] Parse HIR └── [0.0s] Parse MIR ⠂ [2024-07-01T02:23:49.552Z ERROR frb_codegen\src\library\utils\logs.rs:55] panicked at frb_codegen\src\library\codegen\parser\mir\parser\ty\trait_object.rs:48:38: called `Option::unwrap()` on a `None` value thread 'main' panicked at frb_codegen\src\library\codegen\parser\mir\parser\ty\trait_object.rs:48:38: called `Option::unwrap()` on a `None` value stack backtrace: 0: 0x7ff74f6751da - 1: 0x7ff74f6931cb - 2: 0x7ff74f66fec1 - 3: 0x7ff74f674f5a - 4: 0x7ff74f677dea - 5: 0x7ff74f677a58 - 6: 0x7ff74f57d3a7 - 7: 0x7ff74f678629 - 8: 0x7ff74f678332 - 9: 0x7ff74f675e99 - 10: 0x7ff74f678090 - 11: 0x7ff75005e887 - 12: 0x7ff75005e942 - 13: 0x7ff74f8251c3 - 14: 0x7ff74f81d42f - 15: 0x7ff74f82401e - 16: 0x7ff74f822d19 - 17: 0x7ff74f72cad8 - 18: 0x7ff74f88d9d5 - 19: 0x7ff74f82224f - 20: 0x7ff74f5c24db - 21: 0x7ff74f81e16a - 22: 0x7ff74f82401e - 23: 0x7ff74f7bd9b3 - 24: 0x7ff74f733d93 - 25: 0x7ff74f8aa796 - 26: 0x7ff74f82709d - 27: 0x7ff74f5ed0ca - 28: 0x7ff74f5f0711 - 29: 0x7ff74f566149 - 30: 0x7ff74f5eeb8c - 31: 0x7ff74f50c78e - 32: 0x7ff74f50b8c6 - 33: 0x7ff74f510eda - 34: 0x7ff74f667428 - 35: 0x7ff74f50cd8c - 36: 0x7ff750059e9c - 37: 0x7ffaeb3d257d - BaseThreadInitThunk 38: 0x7ffaebe4af28 - RtlUserThreadStart ```
fzyzcjy commented 3 months ago

how do I determine which mod I should write?

Currently, the workaround maybe just bisect the modules (ignore half mods, see whether it works, etc)... But after it is fixed, there is no need to do so (since it will not error).

Feel free to PR for this (possibly simple change)! Alternatively I will work on it in the next batch.

fzyzcjy commented 3 months ago

Given the error is related to trait_object in codegen, I would also guess it is related to code like dyn WhateverTrait.

AlexV525 commented 3 months ago

Bisected the minimal struct that can reproduce this issue:

use std::fmt;
use std::fmt::Debug;

/// Trait that logs at level INFO every update received (if any).
pub trait Progress: Send + Sync + 'static {
    /// Send a new progress update. The progress value should be in the range 0.0 - 100.0, and the message value is an
    /// optional text message that can be displayed to the user.
    fn update(&self, progress: f32, message: Option<String>);
}

pub struct ProgressHolder {
    pub progress: Box<dyn Progress>,
}
impl Debug for ProgressHolder {
    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
        f.debug_struct("ProgressHolder").finish_non_exhaustive()
    }
}
fzyzcjy commented 3 months ago

Looks like dyn TraitName causes the problem

github-actions[bot] commented 2 months ago

This thread has been automatically locked since there has not been any recent activity after it was closed. If you are still experiencing a similar issue, please open a new issue.