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

Provide a way for derives to know if they were invoked with #[derive_const] #118304

Open
jhpratt opened this issue Nov 26, 2023 · 2 comments
Open
Assignees
Labels
A-macros Area: All kinds of macros (custom derive, macro_rules!, proc macros, ..) A-trait-system Area: Trait system C-enhancement Category: An issue proposing an enhancement or a PR with one. F-const_trait_impl `#![feature(const_trait_impl)]` PG-const-traits Project group: Const traits S-blocked Status: Blocked on something else such as an RFC or other implementation work. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue. T-libs-api Relevant to the library API team, which will review and decide on the PR/issue. WG-macros Working group: Macros

Comments

@jhpratt
Copy link
Member

jhpratt commented Nov 26, 2023

As part of #67792, #[derive_const] is the current way to indicate that a derive should be impl const Trait rather than impl Trait. However, this only works for built-in macros. It should be possible for end-user proc macros to know if they were invoked with #[derive_const], permitting the derive to emit the appropriate code.

In my opinion, this could be an opaque type provided as an additional parameter to the derive implementation. That type would have methods to obtain constness and any other future extension (i.e. effects).

cc @fee1-dead per this Zulip comment.

@rustbot label +A-proc-macros +C-enhancement +F-const-trait-impl +T-libs-api

@rustbot rustbot added the needs-triage This issue may need triage. Remove it if it has been sufficiently triaged. label Nov 26, 2023
@fee1-dead fee1-dead added A-trait-system Area: Trait system A-macros Area: All kinds of macros (custom derive, macro_rules!, proc macros, ..) F-const_trait_impl `#![feature(const_trait_impl)]` C-enhancement Category: An issue proposing an enhancement or a PR with one. and removed needs-triage This issue may need triage. Remove it if it has been sufficiently triaged. labels Nov 26, 2023
@fmease fmease self-assigned this Dec 3, 2023
@fmease fmease added T-libs-api Relevant to the library API team, which will review and decide on the PR/issue. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue. labels Dec 4, 2023
@fmease
Copy link
Member

fmease commented Jul 1, 2024

PR #118580 extends support for #[derive_const] to user-defined derive proc-macros as outlined in the issue description. However, #[derive_const] itself is very ad-hoc and non-extensible as petrochenkov criticizes, justifiably so:

Both #[derive_const] itself, and this, are maximally ad hoc tools for addressing the issue.

How macros currently take their input - by a token stream, or two token streams if the macro has two inputs like #[attr(input1)] INPUT2.

This PR adds a third backdoor input tailored for a very specific use case.
The #[derive_const] added a whole new macro just to add one configuration bit to already existing #[derive] macro.

I would suggest keeping the current model and using already existing token-based methods for configuring macro behaviors.

  • Either helper attributes, like many derive macros, including derive_more, already do
  • Or giving derive macros the second input token stream - #[derive(Clone(input1))] INPUT2, that would also improve consistency with attributes.

Then the macros themselves can process the inputs as they want.
E.g. built-in macros could conventionally take a const token to produce a const impl - #[derive(Clone(const))] struct S;, others may accept more configuration.

If #[derive] needs some sugar to pass const to multiple derive macros that it applies at once, then it can grow such sugar itself, instead of delegating to a whole new special-purpose macro.
E.g. #[derive(const: Clone, PartialEq, PartialOrd)] struct S; or anything else, tokens inside the parentheses are an arbitrary token stream, I remind you, so #[derive] can create its own language for its input, like any other attribute macro.

Originally posted by @petrochenkov in #118580 (comment)

On a second thought, there's a third way to pass inputs - the "global data" in struct Rustc.

Proc macro methods without arguments like Span::call_site() take their return values from that global data. I also planned to add some more data there to be available to proc macros, like the kind of brackets used by the macro.

If "derive expansion options" are placed into struct Rustc, then there's no need to add a second parameter to #[proc_macro_derive] functions for passing them.

Originally posted by @petrochenkov in #118580 (comment)

What other similar configuration values we may need in the future?

Will we need to pass them to derive macros only, or for attribute possibly for attribute or fn-like macros too? With derive macros we have an intermediate layer, the #[derive] macro which has access to compiler magic to set such configuration values, but for attribute and fn-like macros we do not.

Originally posted by @petrochenkov in #118580 (comment)

@fmease fmease added the PG-const-traits Project group: Const traits label Jul 1, 2024
@fmease
Copy link
Member

fmease commented Jul 1, 2024

I will therefore close the aforementioned PR and block this issue on further design work to be done by PG-const-traits Project group: Const traits and likely also WG-macros Working group: Macros .

@fmease fmease added S-blocked Status: Blocked on something else such as an RFC or other implementation work. WG-macros Working group: Macros labels Jul 1, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-macros Area: All kinds of macros (custom derive, macro_rules!, proc macros, ..) A-trait-system Area: Trait system C-enhancement Category: An issue proposing an enhancement or a PR with one. F-const_trait_impl `#![feature(const_trait_impl)]` PG-const-traits Project group: Const traits S-blocked Status: Blocked on something else such as an RFC or other implementation work. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue. T-libs-api Relevant to the library API team, which will review and decide on the PR/issue. WG-macros Working group: Macros
Projects
None yet
Development

Successfully merging a pull request may close this issue.

4 participants