Skip to content

Lex lifetimes as identifiers, recover from emoji and emit appropriate error - #153893

Merged
rust-bors[bot] merged 1 commit into
rust-lang:mainfrom
estebank:emoji-lifetime
Oct 27, 2026
Merged

rust-bors[bot] merged 1 commit into
rust-lang:mainfrom
estebank:emoji-lifetime

Conversation

@estebank

@estebank estebank commented Mar 15, 2026 •

Copy link
Copy Markdown
Contributor

View all comments

Lex and parse emoji in lifetimes by using the identifier logic, and disallow them in the parser with a hard error. Allow emoji to start a lifetime name even if they are not XID_Start.

error: identifiers cannot contain emoji: `'🐛🐛🐛family👨👩👧👦`
  --> $DIR/emoji-in-lifetime.rs:1:22
   |
LL | fn bad_lifetime_name<'🐛🐛🐛family👨👩👧👦>(
   |                      ^^^^^^^^^^^^^^^^^^^^^

Address #141081 (but we could provide more information in the diagnostic, pointing at the specific chars, providing a link to the reference on identifiers and/or some other extra information).

@rustbot

rustbot commented Mar 15, 2026

Copy link
Copy Markdown
Collaborator

The parser was modified, potentially altering the grammar of (stable) Rust
which would be a breaking change.

cc @fmease

@rustbot rustbot added S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue. labels Mar 15, 2026
@rustbot

rustbot commented Mar 15, 2026

Copy link
Copy Markdown
Collaborator

r? @jdonszelmann

rustbot has assigned @jdonszelmann.
They will have a look at your PR within the next two weeks and either review your PR or reassign to another reviewer.

Use r? to explicitly pick a reviewer

Why was this reviewer chosen?

The reviewer was selected based on:

  • Owners of files modified in this PR: compiler
  • compiler expanded to 69 candidates
  • Random selection from 15 candidates

@rust-log-analyzer

This comment has been minimized.

@rust-log-analyzer

This comment has been minimized.

Comment thread compiler/rustc_lexer/src/lib.rs Outdated
self.bump();
self.eat_while(is_id_continue);
self.eat_while(|c| {
let is_emoji = !c.is_ascii() && c.is_emoji_char();

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

can we possibly create a function or a method for this, i see this logic is using in two places, maybe something like self.is_emoji() would be better approach?

Comment thread compiler/rustc_parse/src/lexer/mod.rs Outdated
Comment on lines +332 to +334
if has_emoji {
self.dcx().struct_span_err(span, "lifetimes cannot contain emoji").emit();
}

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why not make use of the preexisting ParseSess.bad_unicode_identifiers & rustc_interface::passes infrastructure?

@fmease fmease Mar 15, 2026 •

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

("lifetime"1 tokens are a kind of identifier)

Footnotes

  1. Strictly speaking "ticked identifiers" because they don't just represent lifetimes but also labels which have a distinct grammar (e.g., 'static is not a syntactically valid label but it is a lexically valid "lifetime" ticked identifier) ↩

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The main reason to not do that is to still leverage the 'blah' recovery machinery. Here we are in a situation where we have to either choose one case to have nicer output than the other, or find a good way to unify both checks.

@rustbot

This comment has been minimized.

@rust-log-analyzer

This comment has been minimized.

@rustbot

rustbot commented Mar 18, 2026

Copy link
Copy Markdown
Collaborator

rust-analyzer is developed in its own repository. If possible, consider making this change to rust-lang/rust-analyzer instead.

cc @rust-lang/rust-analyzer

@rustbot rustbot added the T-rust-analyzer Relevant to the rust-analyzer team, which will review and decide on the PR/issue. label Mar 18, 2026
@rust-log-analyzer

This comment has been minimized.

@estebank estebank changed the title Lex lifetimes using emoji and emit appropriate error Lex lifetimes as identifiers, recover from emoji and emit appropriate error Mar 19, 2026

@Veykril Veykril left a comment •

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

rust-analyzer side

View changes since this review

@jdonszelmann

Copy link
Copy Markdown
Contributor

I agree with esteban for the nicer suggestions here, that's probably worth it. Sorry it took me a while, but lgtm.

@bors r=me,veykril rollup

@rust-bors

rust-bors Bot commented Mar 30, 2026

Copy link
Copy Markdown
Contributor

📌 Commit 4f1676d has been approved by me,veykril

It is now in the queue for this repository.

⚠️ The following reviewer(s) could not be found: me

@rust-bors rust-bors Bot added S-waiting-on-bors Status: Waiting on bors to run and complete tests. Bors will change the label on completion. and removed S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. labels Mar 30, 2026
@fmease

fmease commented Mar 30, 2026

Copy link
Copy Markdown
Member

@bors r=jdonszelmann,Veykril

@rust-bors

rust-bors Bot commented Mar 30, 2026

Copy link
Copy Markdown
Contributor

📌 Commit 4f1676d has been approved by jdonszelmann,Veykril

It is now in the queue for this repository.

tgross35 added a commit to tgross35/rust that referenced this pull request Mar 30, 2026
…lmann,Veykril

Lex lifetimes as identifiers, recover from emoji and emit appropriate error

Lex and parse emoji in lifetimes by using the identifier logic, and disallow them in the parser with a hard error. Allow emoji to start a lifetime name even if they are not XID_Start.

```
error: identifiers cannot contain emoji: `'🐛🐛🐛family👨👩👧👦`
  --> $DIR/emoji-in-lifetime.rs:1:22
   |
LL | fn bad_lifetime_name<'🐛🐛🐛family👨👩👧👦>(
   |                      ^^^^^^^^^^^^^^^^^^^^^
```

Address rust-lang#141081 (but we could provide more information in the diagnostic, pointing at the specific chars, providing a link to the reference on identifiers and/or some other extra information).
rust-bors Bot pushed a commit that referenced this pull request Mar 31, 2026
Rollup of 7 pull requests

Successful merges:

 - #142659 (compiler-builtins: Clean up features)
 - #153574 (Avoid ICE when param-env normalization leaves unresolved inference variables)
 - #153648 (Fix EII function aliases eliminated by LTO)
 - #153790 (Fix regression when dealing with generics/values with unresolved inference)
 - #153893 (Lex lifetimes as identifiers, recover from emoji and emit appropriate error)
 - #153980 (refactor: move doc(rust_logo) check to parser)
 - #154551 (Skip suggestions pointing to macro def for assert_eq)
rust-bors Bot pushed a commit that referenced this pull request Mar 31, 2026
Rollup of 7 pull requests

Successful merges:

 - #142659 (compiler-builtins: Clean up features)
 - #153574 (Avoid ICE when param-env normalization leaves unresolved inference variables)
 - #153648 (Fix EII function aliases eliminated by LTO)
 - #153790 (Fix regression when dealing with generics/values with unresolved inference)
 - #153893 (Lex lifetimes as identifiers, recover from emoji and emit appropriate error)
 - #153980 (refactor: move doc(rust_logo) check to parser)
 - #154551 (Skip suggestions pointing to macro def for assert_eq)
@rustbot

rustbot commented Oct 26, 2026

Copy link
Copy Markdown
Collaborator

This PR was rebased onto a different main commit. Here's a range-diff highlighting what actually changed.

Rebasing is a normal part of keeping PRs up to date, so no action is needed—this note is just to help reviewers.

@estebank

Copy link
Copy Markdown
Contributor Author

I've only made one change: reverted the field name change from invalid back to starts_with_number. The meaning of the field has changed to include emoji, but we need to introduce that name change in tandem between rust-analyzer and rustc for rustc_lexer. This PR adjusts ra to also consider it with the same meaning (emitting an appropriate message), and we should have a subsequent PR to adjust the name of the field once we figure out what the right cross-repo dance is to do that.

@estebank estebank added S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. and removed S-waiting-on-author Status: This is awaiting some action (such as code changes or more information) from the author. S-blocked Status: Blocked on something else such as an RFC or other implementation work. labels Oct 26, 2026
@rust-log-analyzer

This comment has been minimized.

Lex and parse emoji in lifetimes, and disallow them in the parser with a hard error. Allow emoji to start a lifetime name even if they are not XID_Start.

```
error: lifetimes cannot contain emoji
  --> $DIR/emoji-in-lifetime.rs:1:22
   |
LL | fn bad_lifetime_name<'🐛🐛🐛family👨👩👧👦>(
   |                      ^^^^^^^^^^^^^^^^^^^^^
```

Unify lifetime and identifier parsing. Use `bad_unicode_identifiers` for lifetimes.
@estebank
estebank force-pushed the emoji-lifetime branch 2 times, most recently from fc29b70 to a1c55e3 Compare October 26, 2026 19:18
@estebank

Copy link
Copy Markdown
Contributor Author

Approving as per #153893 (comment)

@bors r=jdonszelmann,Veykril

@rust-bors

rust-bors Bot commented Oct 26, 2026

Copy link
Copy Markdown
Contributor

📌 Commit 21f918c has been approved by jdonszelmann,Veykril

It is now in the queue for this repository.

@rust-bors rust-bors Bot added S-waiting-on-bors Status: Waiting on bors to run and complete tests. Bors will change the label on completion. and removed S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. labels Oct 26, 2026
tgross35 added a commit to tgross35/rust that referenced this pull request Oct 27, 2026
…lmann,Veykril

Lex lifetimes as identifiers, recover from emoji and emit appropriate error

Lex and parse emoji in lifetimes by using the identifier logic, and disallow them in the parser with a hard error. Allow emoji to start a lifetime name even if they are not XID_Start.

```
error: identifiers cannot contain emoji: `'🐛🐛🐛family👨👩👧👦`
  --> $DIR/emoji-in-lifetime.rs:1:22
   |
LL | fn bad_lifetime_name<'🐛🐛🐛family👨👩👧👦>(
   |                      ^^^^^^^^^^^^^^^^^^^^^
```

Address rust-lang#141081 (but we could provide more information in the diagnostic, pointing at the specific chars, providing a link to the reference on identifiers and/or some other extra information).
rust-bors Bot pushed a commit that referenced this pull request Oct 27, 2026
Rollup of 8 pull requests

Successful merges:

 - #159540 (Enable statx on all Linux targets and short-circuit it for musl)
 - #164168 (Add tests for unsoundness involving alias liveness)
 - #164608 (core: Constify `resumable_breakpoint` and re-export it in `std`)
 - #164787 (cg_llvm: Use an invariant lifetime brand for LLVM contexts )
 - #164966 (x86-64-linux-gnu seems to have working f128 now)
 - #153893 (Lex lifetimes as identifiers, recover from emoji and emit appropriate error)
 - #164895 (Disable recovery when attribute parser shouldn't emit)
 - #165004 (docs: Nitpick change in `HashMap`'s `.insert_entry()` doc example)
tgross35 added a commit to tgross35/rust that referenced this pull request Oct 27, 2026
…lmann,Veykril

Lex lifetimes as identifiers, recover from emoji and emit appropriate error

Lex and parse emoji in lifetimes by using the identifier logic, and disallow them in the parser with a hard error. Allow emoji to start a lifetime name even if they are not XID_Start.

```
error: identifiers cannot contain emoji: `'🐛🐛🐛family👨👩👧👦`
  --> $DIR/emoji-in-lifetime.rs:1:22
   |
LL | fn bad_lifetime_name<'🐛🐛🐛family👨👩👧👦>(
   |                      ^^^^^^^^^^^^^^^^^^^^^
```

Address rust-lang#141081 (but we could provide more information in the diagnostic, pointing at the specific chars, providing a link to the reference on identifiers and/or some other extra information).
rust-bors Bot pushed a commit that referenced this pull request Oct 27, 2026
Rollup of 8 pull requests

Successful merges:

 - #164168 (Add tests for unsoundness involving alias liveness)
 - #164608 (core: Constify `resumable_breakpoint` and re-export it in `std`)
 - #164787 (cg_llvm: Use an invariant lifetime brand for LLVM contexts )
 - #164851 (Add behavior tests for `Arc` and `Rc`)
 - #164966 (x86-64-linux-gnu seems to have working f128 now)
 - #153893 (Lex lifetimes as identifiers, recover from emoji and emit appropriate error)
 - #164895 (Disable recovery when attribute parser shouldn't emit)
 - #165004 (docs: Nitpick change in `HashMap`'s `.insert_entry()` doc example)
rust-bors Bot pushed a commit that referenced this pull request Oct 27, 2026
Rollup of 9 pull requests

Successful merges:

 - #164168 (Add tests for unsoundness involving alias liveness)
 - #164608 (core: Constify `resumable_breakpoint` and re-export it in `std`)
 - #164787 (cg_llvm: Use an invariant lifetime brand for LLVM contexts )
 - #164966 (x86-64-linux-gnu seems to have working f128 now)
 - #153893 (Lex lifetimes as identifiers, recover from emoji and emit appropriate error)
 - #164848 (Add `strict_` methods to `NonZero`)
 - #164895 (Disable recovery when attribute parser shouldn't emit)
 - #164963 (fd-views: enable test on Miri)
 - #165004 (docs: Nitpick change in `HashMap`'s `.insert_entry()` doc example)
rust-bors Bot pushed a commit that referenced this pull request Oct 27, 2026
Rollup of 9 pull requests

Successful merges:

 - #164168 (Add tests for unsoundness involving alias liveness)
 - #164608 (core: Constify `resumable_breakpoint` and re-export it in `std`)
 - #164787 (cg_llvm: Use an invariant lifetime brand for LLVM contexts )
 - #164966 (x86-64-linux-gnu seems to have working f128 now)
 - #153893 (Lex lifetimes as identifiers, recover from emoji and emit appropriate error)
 - #164848 (Add `strict_` methods to `NonZero`)
 - #164895 (Disable recovery when attribute parser shouldn't emit)
 - #164963 (fd-views: enable test on Miri)
 - #165004 (docs: Nitpick change in `HashMap`'s `.insert_entry()` doc example)
JonathanBrouwer added a commit to JonathanBrouwer/rust that referenced this pull request Oct 27, 2026
…lmann,Veykril

Lex lifetimes as identifiers, recover from emoji and emit appropriate error

Lex and parse emoji in lifetimes by using the identifier logic, and disallow them in the parser with a hard error. Allow emoji to start a lifetime name even if they are not XID_Start.

```
error: identifiers cannot contain emoji: `'🐛🐛🐛family👨👩👧👦`
  --> $DIR/emoji-in-lifetime.rs:1:22
   |
LL | fn bad_lifetime_name<'🐛🐛🐛family👨👩👧👦>(
   |                      ^^^^^^^^^^^^^^^^^^^^^
```

Address rust-lang#141081 (but we could provide more information in the diagnostic, pointing at the specific chars, providing a link to the reference on identifiers and/or some other extra information).
rust-bors Bot pushed a commit that referenced this pull request Oct 27, 2026
Rollup of 9 pull requests



Successful merges:

 - #164168 (Add tests for unsoundness involving alias liveness)
 - #164608 (core: Constify `resumable_breakpoint` and re-export it in `std`)
 - #164787 (cg_llvm: Use an invariant lifetime brand for LLVM contexts )
 - #164966 (x86-64-linux-gnu seems to have working f128 now)
 - #153893 (Lex lifetimes as identifiers, recover from emoji and emit appropriate error)
 - #164848 (Add `strict_` methods to `NonZero`)
 - #164895 (Disable recovery when attribute parser shouldn't emit)
 - #164963 (fd-views: enable test on Miri)
 - #165004 (docs: Nitpick change in `HashMap`'s `.insert_entry()` doc example)
@rust-bors
rust-bors Bot merged commit dc1aecd into rust-lang:main Oct 27, 2026
14 checks passed
@rustbot rustbot added this to the 1.101.0 milestone Oct 27, 2026
rust-bors Bot pushed a commit that referenced this pull request Oct 27, 2026
Rollup merge of #153893 - estebank:emoji-lifetime, r=jdonszelmann,Veykril

Lex lifetimes as identifiers, recover from emoji and emit appropriate error

Lex and parse emoji in lifetimes by using the identifier logic, and disallow them in the parser with a hard error. Allow emoji to start a lifetime name even if they are not XID_Start.

```
error: identifiers cannot contain emoji: `'🐛🐛🐛family👨👩👧👦`
  --> $DIR/emoji-in-lifetime.rs:1:22
   |
LL | fn bad_lifetime_name<'🐛🐛🐛family👨👩👧👦>(
   |                      ^^^^^^^^^^^^^^^^^^^^^
```

Address #141081 (but we could provide more information in the diagnostic, pointing at the specific chars, providing a link to the reference on identifiers and/or some other extra information).
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

S-waiting-on-bors Status: Waiting on bors to run and complete tests. Bors will change the label on completion. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue. T-rust-analyzer Relevant to the rust-analyzer team, which will review and decide on the PR/issue.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

8 participants