Skip to content

Backport "improvement: use heuristic to figure out nameSpan if pointDelta too big" to 3.3 LTS #237

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

Merged
merged 2 commits into from
Apr 22, 2025
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Next Next commit
improvement: use heuristic to figure out nameSpan if pointDelta t…
…o big

[Cherry-picked 9ef5579]
  • Loading branch information
kasiaMarek authored and tgodzik committed Apr 22, 2025
commit db194a8f3fc3ba653f8b21fb8edcc8ffa9490617
7 changes: 5 additions & 2 deletions compiler/src/dotty/tools/dotc/ast/Trees.scala
Original file line number Diff line number Diff line change
Expand Up @@ -460,8 +460,11 @@ object Trees {
else if qualifier.span.exists && qualifier.span.start > span.point then // right associative
val realName = name.stripModuleClassSuffix.lastPart
Span(span.start, span.start + realName.length, point)
else
Span(point, span.end, point)
else if span.pointMayBeIncorrect then
val realName = name.stripModuleClassSuffix.lastPart
val probablyPoint = span.end - realName.length
Span(probablyPoint, span.end, probablyPoint)
else Span(point, span.end, point)
else span
}

Expand Down
3 changes: 3 additions & 0 deletions compiler/src/dotty/tools/dotc/util/Spans.scala
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,9 @@ object Spans {
if (poff == SyntheticPointDelta) start else start + poff
}

def pointMayBeIncorrect =
pointDelta == 0 && end - start >= SyntheticPointDelta

/** The difference between point and start in this span */
def pointDelta: Int =
(coords >>> (StartEndBits * 2)).toInt
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1462,5 +1462,106 @@ class DocumentHighlightSuite extends BaseDocumentHighlightSuite:
|""".stripMargin
)

@Test def i3053 =
check(
"""import Aaaa.*
|
|def classDef2(cdef: List[Int]): Int = {
| def aaa(ddef: Thicket2): List[Int] = ddef match {
| case Thicket2(_) => ???
| }
|
| /** Does `tree' look like a reference to AnyVal? Temporary test before we have
| * inline classes
| */
| // The original type and value parameters in the constructor already have the flags
| // needed to be type members (i.e. param, and possibly also private and local unless
| // prefixed by type or val). `tparams` and `vparamss` are the type parameters that
| // go in `constr`, the constructor after desugaring.
|
| /** Does `tree' look like a reference to AnyVal? Temporary test before we have
| * inline classes
| */
| // The original type and value parameters in the constructor already have the flags
| // needed to be type members (i.e. param, and possibly also private and local unless
| // prefixed by type or val). `tparams` and `vparamss` are the type parameters that
| // go in `constr`, the constructor after desugaring.
|
| /** Does `tree' look like a reference to AnyVal? Temporary test before we have
| * inline classes
| */
| // Annotations on class _type_ parameters are set on the derived parameters
| // but not on the constructor parameters. The reverse is true for
| // annotations on class _value_ parameters.
| // The original type and value parameters in the constructor already have the flags
| // needed to be type members (i.e. param, and possibly also private and local unless
| // prefixed by type or val). `tparams` and `vparamss` are the type parameters that
| // go in `constr`, the constructor after desugaring.
| // The original type and value parameters in the constructor already have the flags
| // needed to be type members (i.e. param, and possibly also private and local unless
| // prefixed by type or val). `tparams` and `vparamss` are the type parameters that
| // go in `constr`, the constructor after desugaring.
|
| /** Does `tree' look like a reference to AnyVal? Temporary test before we have
| * inline classes
| */
| // The original type and value parameters in the constructor already have the flags
| // needed to be type members (i.e. param, and possibly also private and local unless
| // prefixed by type or val). `tparams` and `vparamss` are the type parameters that
| // go in `constr`, the constructor after desugaring.
|
| /** Does `tree' look like a reference to AnyVal? Temporary test before we have
| * inline classes
| */
|
| // Annotations on class _type_ parameters are set on the derived parameters
| // but not on the constructor parameters. The reverse is true for
| // annotations on class _value_ parameters.
| // The original type and value parameters in the constructor already have the flags
| // needed to be type members (i.e. param, and possibly also private and local unless
| // prefixed by type or val). `tparams` and `vparamss` are the type parameters that
| // go in `constr`, the constructor after desugaring.
| // The original type and value parameters in the constructor already have the flags
| // needed to be type members (i.e. param, and possibly also private and local unless
| // prefixed by type or val). `tparams` and `vparamss` are the type parameters that
| // go in `constr`, the constructor after desugaring.
|
| /** Does `tree' look like a reference to AnyVal? Temporary test before we have
| * inline classes
| */
| // The original type and value parameters in the constructor already have the flags
| // needed to be type members (i.e. param, and possibly also private and local unless
| // prefixed by type or val). `tparams` and `vparamss` are the type parameters that
| // go in `constr`, the constructor after desugaring.
|
| /** Does `tree' look like a reference to AnyVal? Temporary test before we have
| * inline classes
| */
| // Annotations on class _type_ parameters are set on the derived parameters
| // but not on the constructor parameters. The reverse is true for
| // annotations on class _value_ parameters.
| // The original type and value parameters in the constructor already have the flags
| // needed to be type members (i.e. param, and possibly also private and local unless
| // prefixed by type or val). `tparams` and `vparamss` are the type parameters that
| // go in `constr`, the constructor after desugaring.
| // The original type and value parameters in the constructor already have the flags
| // needed to be type members (i.e. param, and possibly also private and local unless
| // prefixed by type or val). `tparams` and `vparamss` are the type parameters that
| // go in `constr`, the constructor after desugaring.
| 1
|}.<<showing2>>("aaa")
|
|case class Thicket2(trees: List[Int]) {}
|
|object Aaaa {
| extension [T](x: T)
| def <<show@@ing2>>[U](aaa: String): T = {
| x
| }
|}
|
|""".stripMargin
)


end DocumentHighlightSuite