Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

const { ... } blocks cannot be written outside of function #128338

Open
StackOverflowExcept1on opened this issue Jul 29, 2024 · 4 comments · May be fixed by #128374
Open

const { ... } blocks cannot be written outside of function #128338

StackOverflowExcept1on opened this issue Jul 29, 2024 · 4 comments · May be fixed by #128374
Labels
A-diagnostics Area: Messages for errors, warnings, and lints C-bug Category: This is a bug. D-papercut Diagnostics: An error or lint that needs small tweaks. D-terse Diagnostics: An error or lint that doesn't give enough information about the problem at hand.

Comments

@StackOverflowExcept1on
Copy link
Contributor

I tried this code:

// error
const { assert!(size_of::<u32>() <= size_of::<usize>()) };

fn main() {
    //ok
    const { assert!(size_of::<u32>() <= size_of::<usize>()) };
}

I expected to see this happen: it compiles

Instead, this happened: it doesn't compile

error: expected item, found keyword `const`
 --> src/main.rs:2:1
  |
2 | const { assert!(size_of::<u32>() <= size_of::<usize>()) };
  | ^^^^^ expected item
  |
  = note: for a full list of items that can appear in modules, see <https://doc.rust-lang.org/reference/items.html>

error: could not compile `app` (bin "app") due to 1 previous error

Meta

rustc --version --verbose:

rustc 1.82.0-nightly (2cbbe8b8b 2024-07-28)
binary: rustc
commit-hash: 2cbbe8b8bb2be672b14cf741a2f0ec24a49f3f0b
commit-date: 2024-07-28
host: x86_64-unknown-linux-gnu
release: 1.82.0-nightly
LLVM version: 18.1.7
@StackOverflowExcept1on StackOverflowExcept1on added the C-bug Category: This is a bug. label Jul 29, 2024
@rustbot rustbot added the needs-triage This issue may need triage. Remove it if it has been sufficiently triaged. label Jul 29, 2024
@RalfJung
Copy link
Member

RalfJung commented Jul 29, 2024

Thanks for the report! However, there is no bug here. This is expected. const { ... } is an expression, and you can't write expressions outside of functions.

If you want to just declare a constant outside a function for the purpose of checking an assertion, you can declare an anonymous const item as follows:

const _: () = assert!(size_of::<u32>() <= size_of::<usize>());

@saethlin saethlin added C-discussion Category: Discussion or questions that doesn't represent real issues. and removed C-bug Category: This is a bug. needs-triage This issue may need triage. Remove it if it has been sufficiently triaged. labels Jul 29, 2024
@workingjubilee
Copy link
Member

workingjubilee commented Jul 29, 2024

The diagnostic should say that, then.

@rustbot label: -C-discussion +C-bug +A-diagnostics +D-papercut +D-terse

@rustbot rustbot added A-diagnostics Area: Messages for errors, warnings, and lints C-bug Category: This is a bug. D-papercut Diagnostics: An error or lint that needs small tweaks. D-terse Diagnostics: An error or lint that doesn't give enough information about the problem at hand. and removed C-discussion Category: Discussion or questions that doesn't represent real issues. labels Jul 29, 2024
@maia-s
Copy link

maia-s commented Jul 29, 2024

It would be nice if this was allowed if the const block evaluates to (), like in this example. The _: () = syntax feels more like a workaround for missing functionality than something that's supposed to still be required now that we have const blocks.

@workingjubilee
Copy link
Member

while a nice wishlist idea, given that we don't even have a finished story for const {} in patterns, where we already know we want to be able to write it (as normally we can put a NAME there, and notionally using const NAME: T = {}; then NAME should "always" be possible to replace by const {}), I don't think it's in anyone's interest to special-case item generation here yet. maybe later.

note that it also would be somewhat unusual for us to start accepting any expression in item context, as normally Rust is quite the hardass about misplacing expressions. for instance, not only is const {} supposed to be equal to this, in an expression context:

{
    const NAME: T = expr;
    NAME
}

but this is rejected in item context, because blocks are expressions, not items:

{
}

and part of the reason rustc is persnickety about this sort of thing is that it allows us to be really certain what is supposed to go where, and from there easily infer what was likely intended, and then issue diagnostics.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-diagnostics Area: Messages for errors, warnings, and lints C-bug Category: This is a bug. D-papercut Diagnostics: An error or lint that needs small tweaks. D-terse Diagnostics: An error or lint that doesn't give enough information about the problem at hand.
Projects
None yet
Development

Successfully merging a pull request may close this issue.

6 participants