slint-ui / slint

Slint is a declarative GUI toolkit to build native user interfaces for Rust, C++, or JavaScript apps.
https://slint.dev
Other
17.71k stars 614 forks source link

slint does not compile due to "lifetime parameters or bounds on type `Target` do not match the trait declaration" #5702

Closed SirMangler closed 4 months ago

SirMangler commented 4 months ago

Steps to recreate:

Tested on slint release/1.7 and on master https://github.com/slint-ui/slint/commit/e0f3fd4168fa6ad5ed17a50910111ed72d1ae95e Tested with both rust version 1.78 and 1.80

Output log

slint on ξ‚  master is πŸ“¦ v1.7.1 via β–³ v3.28.2 via πŸ¦€ v1.78.0 
❯ rustc --version
rustc 1.78.0 (9b00956e5 2024-04-29)

slint on ξ‚  master is πŸ“¦ v1.7.1 via β–³ v3.28.2 via πŸ¦€ v1.78.0 
❯ cargo version
cargo 1.78.0 (54d8815d0 2024-03-26)

slint on ξ‚  master is πŸ“¦ v1.7.1 via β–³ v3.28.2 via πŸ¦€ v1.78.0 
❯ cargo build
warning: /home/user/Downloads/slint/internal/core/Cargo.toml: unused manifest key: lints.rust.unexpected_cfgs.check-cfg
   Compiling thiserror-impl v1.0.63
   Compiling derive_more v0.99.18
   Compiling serde_derive v1.0.204
   Compiling strum_macros v0.26.4
   Compiling tracing-attributes v0.1.27
   Compiling num_enum_derive v0.7.2
   Compiling bytemuck_derive v1.7.0
   Compiling jpeg-decoder v0.3.1
   Compiling resvg v0.42.0
   Compiling css-color-parser2 v1.0.1
   Compiling wayland-sys v0.31.4
   Compiling hashbrown v0.14.5
   Compiling futures-macro v0.3.30
   Compiling strict-num v0.1.1
   Compiling spin v0.9.8
   Compiling concurrent-queue v2.5.0
   Compiling crossbeam-epoch v0.9.18
error[E0195]: lifetime parameters or bounds on type `Target` do not match the trait declaration
   --> /home/user/.cargo/registry/src/index.crates.io-6f17d22bba15001f/css-color-parser2-1.0.1/src/color/named_colors.rs:28:1
    |
28  | / lazy_static::lazy_static! {
29  | |     /// List of CSS3 named colors from http://www.w3.org/TR/css3-color.
30  | |     pub static ref NAMED_COLORS: HashMap<&'static str, Color> = {
31  | |         let mut m = HashMap::new();
...   |
181 | |     };
182 | | }
    | |_^ lifetimes do not match type in trait
    |
    = note: this error originates in the macro `__lazy_static_internal` which comes from the expansion of the macro `lazy_static::lazy_static` (in Nightly builds, run with -Z macro-backtrace for more info)

error[E0599]: no method named `get` found for struct `NAMED_COLORS` in the current scope
   --> /home/user/.cargo/registry/src/index.crates.io-6f17d22bba15001f/css-color-parser2-1.0.1/src/color/color.rs:109:44
    |
109 |           if let Some(&color) = NAMED_COLORS.get(&*string) {
    |                                              ^^^ method not found in `NAMED_COLORS`
    |
   ::: /home/user/.cargo/registry/src/index.crates.io-6f17d22bba15001f/css-color-parser2-1.0.1/src/color/named_colors.rs:28:1
    |
28  | / lazy_static::lazy_static! {
29  | |     /// List of CSS3 named colors from http://www.w3.org/TR/css3-color.
30  | |     pub static ref NAMED_COLORS: HashMap<&'static str, Color> = {
31  | |         let mut m = HashMap::new();
...   |
181 | |     };
182 | | }
    | |_- method `get` not found for this struct
    |
    = help: items from traits can only be used if the trait is implemented and in scope
    = note: the following trait defines an item `get`, perhaps you need to implement it:
            candidate #1: `SliceIndex`

Some errors have detailed explanations: E0195, E0599.
For more information about an error, try `rustc --explain E0195`.
error: could not compile `css-color-parser2` (lib) due to 2 previous errors
warning: build failed, waiting for other jobs to finish...

Thanks for your help!

tronical commented 4 months ago

Interesting, I've never seen this before. How did you install Rust/Cargo?

Is there any chance this goes away if you wipe the target folder?

SirMangler commented 4 months ago

Interesting, I've never seen this before. How did you install Rust/Cargo?

Rustup. I'm using the stable channel. It shouldn't make a difference but I'm on Fedora 40.

Is there any chance this goes away if you wipe the target folder?

It does not unfortunately. It's a fresh clone but I cleared my target folder just to be sure.

SirMangler commented 4 months ago

This definitely strange. I went into an existing rust project of mine and added css_color_parser2 and some test code at the top, it compiled without problem. So I then created a new project with cargo, and added css-color-parser2, then compiled the same test code on its own:

fn main() {
    let str = "some string";

    let _abc = str 
    .parse::<css_color_parser2::Color>().unwrap();

    for (name, c) in css_color_parser2::NAMED_COLORS.iter() {
          println!("color: {}", name);  
    }
}

And it failed, with the same error as above. I deleted the Cargo.lock file on that existing project, and now it no longer compiles and has the same error. Restoring the Cargo.lock then fixes it again. Introducing the Cargo.lock file from the existing unrelated project, to the new test project allows it to build, and also allows slint to build. I also tried copying just the css-color-parser2 and lazy_static entries from the lock first but this did nothing as they were identical. So in other words, the ""fix"" is to add this crate to an existing Cargo.lock, then use that Cargo.lock in whatever project you want to use the css crate in.

I noticed that css-color-parser2 uses a wildcard to specify the version for lazy_static ("0.1.*"). It seems as though the version of lazy_static being used is broken with these newer versions of Rust. It may be worth slint forking this crate and updating what version of lazy_static is used, or since this css crate is now over 7 years old, it may be worth simply updating the few places that this crate is used to use a newer crate.

tronical commented 4 months ago

Thanks for the analysis - I think you're right. We should eliminate the dependency to css-color-parser2.

tronical commented 4 months ago

We have multiple uses of the parser. One in the compiler, where all we're interested in are the named colors from the CSS standard. This is the one you're running into and it's easy to fix - I'll do that right away. The other uses are in the Node.js and Python bindings, where we aim to support parsing rgb(...) style strings.

tronical commented 4 months ago

I noticed that css-color-parser2 uses a wildcard to specify the version for lazy_static ("0.1.*"). It seems as though the version of lazy_static being used is broken with these newer versions of Rust.

I tried to verify this, but I'm not successful here. The upload to crates.io seems to have "1", not "0.1" for the dependency: https://docs.rs/crate/css-color-parser2/latest/source/Cargo.toml https://crates.io/crates/css-color-parser2/1.0.1/dependencies

In fact, my local build (with latest Rust, etc.) shows with cargo tree a dependency to lazy_static 1.5, and that compiles.

Would you be able to run cargo update and check with cargo tree what's causing the dependency to 0.1 for you?

tronical commented 4 months ago

@SirMangler I have one more question: The issue description refers to an attempt to build Slint from the git repo from what looks like the v1.7.1 tag. That tag does have a Cargo.lock file, but in that lock file I see lazy_static in version 1.5.0. Are you sure you're using an older version of lazy_static when the build is failing?

SirMangler commented 4 months ago

I noticed that css-color-parser2 uses a wildcard to specify the version for lazy_static ("0.1.*"). It seems as though the version of lazy_static being used is broken with these newer versions of Rust.

I tried to verify this, but I'm not successful here. The upload to crates.io seems to have "1", not "0.1" for the dependency: https://docs.rs/crate/css-color-parser2/latest/source/Cargo.toml https://crates.io/crates/css-color-parser2/1.0.1/dependencies

In fact, my local build (with latest Rust, etc.) shows with cargo tree a dependency to lazy_static 1.5, and that compiles.

Would you be able to run cargo update and check with cargo tree what's causing the dependency to 0.1 for you?

Oddly, the css-color-parser2 crate page links to a github which appears to not contain any of the latest changes on the crate (ie lazy_static v1.5 as you have noted). I got that version number from the linked github's latest version of the Cargo.toml, you're correct that the actual version is 1.0.1.

The issue description refers to an attempt to build Slint from the git repo from what looks like the v1.7.1 tag. That tag does have a Cargo.lock file, but in that lock file I see lazy_static in version 1.5.0.

On a fresh clone, this is 1.5.0. However on my clone that I got to build with the various steps i took with the Cargo.lock file, the version of lazy_static that it builds successfully with is 1.4.0 (as reported by cargo tree). I'm not sure sure how this resulted from the steps I took, I wasn't manually editing any configs. Edit: Actually I just remembered, I did prototype some code with lazy_static a while ago, this might explain why this existed in the Cargo.lock. It was sheer coincidence that I had this project open and chose to test with it.

SirMangler commented 4 months ago

The commit to replace the css-color-parser dependency has allowed the build to continue further, however this has revealed that lazy_static is causing other areas (namely the use of the cpp_common crate) to fail to compile.

error[E0195]: lifetime parameters or bounds on type `Target` do not match the trait declaration
  --> /home/user/.cargo/registry/src/index.crates.io-6f17d22bba15001f/cpp_common-0.5.9/src/lib.rs:61:1
   |
61 | / lazy_static! {
62 | |     pub static ref OUT_DIR: PathBuf = PathBuf::from(env::var("OUT_DIR"...
63 | |         r#"
64 | | -- rust-cpp fatal error --
...  |
73 | |     };
74 | | }
   | |_^ lifetimes do not match type in trait
   |
   = note: this error originates in the macro `__lazy_static_internal` which comes from the expansion of the macro `lazy_static` (in Nightly builds, run with -Z macro-backtrace for more info)

error[E0599]: no method named `hash` found for struct `OUT_DIR` in the current scope
  --> /home/user/.cargo/registry/src/index.crates.io-6f17d22bba15001f/cpp_common-0.5.9/src/lib.rs:71:17
   |
61 | / lazy_static! {
62 | |     pub static ref OUT_DIR: PathBuf = PathBuf::from(env::var("OUT_DIR"...
63 | |         r#"
64 | | -- rust-cpp fatal error --
...  |
71 | |         OUT_DIR.hash(&mut hasher);
   | |                 ^^^^ method not found in `OUT_DIR`
72 | |         hasher.finish()
73 | |     };
74 | | }
   | |_- method `hash` not found for this struct
   |
   = help: items from traits can only be used if the trait is implemented and in scope
   = note: the following trait defines an item `hash`, perhaps you need to implement it:
           candidate #1: `Hash`
help: one of the expressions' fields has a method of the same name
   |
71 |         OUT_DIR.__private_field.hash(&mut hasher);
   |                 ++++++++++++++++

Some errors have detailed explanations: E0195, E0599.
For more information about an error, try `rustc --explain E0195`.
error: could not compile `cpp_common` (lib) due to 3 previous errors
warning: build failed, waiting for other jobs to finish...
tronical commented 4 months ago

The issue description refers to an attempt to build Slint from the git repo from what looks like the v1.7.1 tag. That tag does have a Cargo.lock file, but in that lock file I see lazy_static in version 1.5.0.

On a fresh clone, this is 1.5.0. However on my clone that I got to build with the various steps i took with the Cargo.lock file, the version of lazy_static that it builds successfully with is 1.4.0 (as reported by cargo tree). I'm not sure sure how this resulted from the steps I took, I wasn't manually editing any configs. Edit: Actually I just remembered, I did prototype some code with lazy_static a while ago, this might explain why this existed in the Cargo.lock. It was sheer coincidence that I had this project open and chose to test with it.

It sounds like to me then that your Cargo.lock has a version of lazy_static pinned that doesn't compile with a newer version of Rust, and that's probably fixable if you just run cargo update. If that fixes it, then I'd say this issue is not in scope for Slint :)

SirMangler commented 4 months ago

The issue description refers to an attempt to build Slint from the git repo from what looks like the v1.7.1 tag. That tag does have a Cargo.lock file, but in that lock file I see lazy_static in version 1.5.0.

On a fresh clone, this is 1.5.0. However on my clone that I got to build with the various steps i took with the Cargo.lock file, the version of lazy_static that it builds successfully with is 1.4.0 (as reported by cargo tree). I'm not sure sure how this resulted from the steps I took, I wasn't manually editing any configs. Edit: Actually I just remembered, I did prototype some code with lazy_static a while ago, this might explain why this existed in the Cargo.lock. It was sheer coincidence that I had this project open and chose to test with it.

It sounds like to me then that your Cargo.lock has a version of lazy_static pinned that doesn't compile with a newer version of Rust, and that's probably fixable if you just run cargo update. If that fixes it, then I'd say this issue is not in scope for Slint :)

If anything it's the reverse, it only compiled with the existing/old Cargo.lock because I had an older version of lazy_static pinned that does compile with the newer version of Rust, and as I said before it successfully builds with lazy_static 1.4.0, and does not build with 1.5.0. Unfortunately I already ran a cargo update followed by a cargo clean before submitting this issue and it did not solve anything.

tronical commented 4 months ago

Ahh, I see - sorry, I got it the wrong way around. I see that this is also tracked upstream with https://github.com/rust-lang-nursery/lazy-static.rs/issues/217

ogoffart commented 4 months ago

Note that lazy_static 1.5.0 was released on Jun 21st. Which is after people reported https://github.com/rust-lang-nursery/lazy-static.rs/issues/217 This seems to indicate that this can't be caused by the upgrade from 1.4 to 1.5.

SirMangler commented 4 months ago

Note that lazy_static 1.5.0 was released on Jun 21st. Which is after people reported rust-lang-nursery/lazy-static.rs#217 This seems to indicate that this can't be caused by the upgrade from 1.4 to 1.5.

That's interesting, my assumption is 1.5 did work at some point, but then was broken by a later rust update.

ogoffart commented 4 months ago

Another strange fact is that our CI test several versions of rust (MSRV, stable, beta, nightly) and always use the latest version of all crates (no .lock file). And the CI is not failing because of that. It would really be useful to figure out the combination of rust/lazy_static/... versions that causes the issue. Maybe it is platform specific. So far i haven't reproduced the problem. (but i did not try hard.)

ogoffart commented 4 months ago

This commennt https://github.com/hawkw/sharded-slab/issues/92#issuecomment-2108929034 seems to indicate that this might be dependent on some env variable.

SirMangler commented 4 months ago

It would really be useful to figure out the combination of rust/lazy_static/... versions that causes the issue. This commennt https://github.com/hawkw/sharded-slab/issues/92#issuecomment-2108929034 seems to indicate that this might be dependent on some env variable.

Personally I'm on rust 1.80.0, lazy_static 1.5.0 is broken but not 1.4.0, I haven't got these environment variables set and I have tried clearing my cargo registry.

ogoffart commented 4 months ago

With some other research: https://stackoverflow.com/questions/77710297/encountered-e0195-lifetime-parameters-or-bounds-on-type-target-do-not-match

Can you look at the file ~/.cargo/registry/src/index.crates.io-6f17d22bba15001f/lazy_static-1.5.0/src/lib.rs on your system and check the content of the line 127 (inside __lazy_static_internal), for me it is type Target = $T; and it doesn't have any lifetime.

Can you try to clear your cargo registry cache.

I have this crazy theory that maybe some tool (eg, a broken cargo fix or clippy fix) could have modified things its not supposed to modify.

SirMangler commented 4 months ago

With some other research: https://stackoverflow.com/questions/77710297/encountered-e0195-lifetime-parameters-or-bounds-on-type-target-do-not-match

Can you look at the file ~/.cargo/registry/src/index.crates.io-6f17d22bba15001f/lazy_static-1.5.0/src/lib.rs on your system and check the content of the line 127 (inside __lazy_static_internal), for me it is type Target = $T; and it doesn't have any lifetime.

Interesting, for me, it's type Target<'a> = $T;. Clearing the entire cache has made no effect.

Edit: Clearing it actually did update that line to type Target = $T;, but the compile error persists.

SirMangler commented 4 months ago

Following that stackoverflow post, I ran cargo add 'lazy_static@^1.5.0' in my test project, and it now builds!

ogoffart commented 4 months ago

Edit: Clearing it actually did update that line to type Target = $T;, but the compile error persists.

I think the error persists because cargo assumes that these directory are never changed and does not invalidate the cache in your target directory.


I'm going to close this issue as this is not a Slint issue. Thanks for your help with investigating this.

Would be interesting to know how this file was changed. As I said, it could be a bug in one of the tools that fixup things that did a fix in a macro where it shouldn't have. (If you ever figure out, let us know πŸ˜‰)

SirMangler commented 4 months ago

Thank you both for your help! I'm very glad that we have a fix documented here now for anyone else who runs into this!