summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/main/kotlin/org/rust/ide/hints/parameter/RsInlayParameterHints.kt30
-rw-r--r--src/main/kotlin/org/rust/ide/hints/type/RsInlayTypeHintsProvider.kt25
-rw-r--r--src/main/resources/compiler-info/compiler-features.json2
-rw-r--r--src/test/kotlin/org/rust/ide/hints/parameter/RsInlayParameterHintsProviderTest.kt16
-rw-r--r--src/test/kotlin/org/rust/ide/hints/type/RsChainMethodTypeHintsProviderTest.kt1
5 files changed, 49 insertions, 25 deletions
diff --git a/src/main/kotlin/org/rust/ide/hints/parameter/RsInlayParameterHints.kt b/src/main/kotlin/org/rust/ide/hints/parameter/RsInlayParameterHints.kt
index 1bee223d2..637109b24 100644
--- a/src/main/kotlin/org/rust/ide/hints/parameter/RsInlayParameterHints.kt
+++ b/src/main/kotlin/org/rust/ide/hints/parameter/RsInlayParameterHints.kt
@@ -9,9 +9,11 @@ import com.intellij.codeInsight.hints.InlayInfo
import com.intellij.codeInsight.hints.Option
import com.intellij.psi.PsiElement
import org.rust.RsBundle
+import org.rust.ide.hints.type.findExpandedByLeaf
import org.rust.ide.utils.CallInfo
import org.rust.lang.core.psi.*
-import org.rust.lang.core.psi.ext.existsAfterExpansion
+import org.rust.lang.core.psi.ext.childOfType
+import org.rust.lang.core.psi.ext.elementType
import org.rust.lang.core.psi.ext.startOffset
import org.rust.lang.core.types.emptySubstitution
import org.rust.stdext.buildList
@@ -22,14 +24,14 @@ object RsInlayParameterHints {
val smart: Boolean get() = smartOption.get()
fun provideHints(elem: PsiElement): List<InlayInfo> {
- val (callInfo, valueArgumentList) = when (elem) {
- is RsCallExpr -> (CallInfo.resolve(elem) to elem.valueArgumentList)
- is RsMethodCall -> (CallInfo.resolve(elem) to elem.valueArgumentList)
- else -> return emptyList()
- }
- if (!elem.existsAfterExpansion) return emptyList()
- if (callInfo == null) return emptyList()
+ val elementExpanded = findExpandedElement(elem) ?: return emptyList()
+ val callInfo = when (elementExpanded) {
+ is RsCallExpr -> CallInfo.resolve(elementExpanded)
+ is RsMethodCall -> CallInfo.resolve(elementExpanded)
+ else -> null
+ } ?: return emptyList()
+ val valueArgumentList = elem.childOfType<RsValueArgumentList>() ?: return emptyList()
val hints = buildList {
if (callInfo.selfParameter != null && elem is RsCallExpr) {
add(callInfo.selfParameter)
@@ -61,6 +63,18 @@ object RsInlayParameterHints {
return hints.map { (hint, arg) -> InlayInfo("$hint:", arg.startOffset) }
}
+ private fun findExpandedElement(element: PsiElement): PsiElement? {
+ val valueArgumentList = when (element) {
+ is RsCallExpr -> element.valueArgumentList
+ is RsMethodCall -> element.valueArgumentList
+ else -> return null
+ }
+ val valueArgumentListExpanded = valueArgumentList.findExpandedByLeaf { it.lparen } ?: return null
+ if (valueArgumentListExpanded == valueArgumentList) return element
+ if (valueArgumentListExpanded.exprList.size != valueArgumentList.exprList.size) return null
+ return valueArgumentListExpanded.parent.takeIf { it.elementType == element.elementType }
+ }
+
private fun onlyOneParam(hints: List<Pair<String, RsExpr>>, callInfo: CallInfo, elem: PsiElement): Boolean {
if (callInfo.selfParameter != null && elem is RsCallExpr && hints.size == 2) {
return true
diff --git a/src/main/kotlin/org/rust/ide/hints/type/RsInlayTypeHintsProvider.kt b/src/main/kotlin/org/rust/ide/hints/type/RsInlayTypeHintsProvider.kt
index 78f9d06fe..5402e1136 100644
--- a/src/main/kotlin/org/rust/ide/hints/type/RsInlayTypeHintsProvider.kt
+++ b/src/main/kotlin/org/rust/ide/hints/type/RsInlayTypeHintsProvider.kt
@@ -21,6 +21,7 @@ import com.intellij.psi.impl.source.tree.LeafPsiElement
import com.intellij.psi.util.parentOfTypes
import org.rust.RsBundle
import org.rust.lang.RsLanguage
+import org.rust.lang.core.crate.Crate
import org.rust.lang.core.macros.*
import org.rust.lang.core.psi.*
import org.rust.lang.core.psi.ext.*
@@ -171,7 +172,7 @@ class RsInlayTypeHintsProvider : InlayHintsProvider<RsInlayTypeHintsProvider.Set
if (typeReference.descendantOfTypeOrSelf<RsInferType>() == null) return
}
- val expandedDeclaration = declaration.getExpanded { it.let } ?: return
+ val expandedDeclaration = declaration.findExpandedByLeaf(crate) { it.let } ?: return
if (isExpanded) testAssert { declaration == expandedDeclaration }
val inferredType = expandedDeclaration.pat?.type ?: return
val formalType = expandedDeclaration.typeReference?.rawType ?: return
@@ -231,7 +232,7 @@ class RsInlayTypeHintsProvider : InlayHintsProvider<RsInlayTypeHintsProvider.Set
}
private fun presentTypeForBinding(binding: RsPatBinding, isExpanded: Boolean) {
- val bindingExpanded = binding.getExpanded { it.identifier } ?: return
+ val bindingExpanded = binding.findExpandedByLeaf(crate) { it.identifier } ?: return
if (bindingExpanded.reference.resolve()?.isConstantLike == true) return
if (bindingExpanded.type is TyUnknown) return
@@ -245,16 +246,6 @@ class RsInlayTypeHintsProvider : InlayHintsProvider<RsInlayTypeHintsProvider.Set
val finalPresentation = presentation.withDisableAction(project)
sink.addInlineElement(offset, false, finalPresentation, false)
}
-
- private inline fun <reified T : PsiElement> T.getExpanded(getLeaf: (T) -> PsiElement): T? =
- when (getCodeStatus(crate)) {
- RsCodeStatus.CFG_DISABLED -> null
- RsCodeStatus.ATTR_PROC_MACRO_CALL -> {
- val leafExpanded = getLeaf(this).findExpansionElements()?.singleOrNull()
- leafExpanded?.parent as? T
- }
- else -> this
- }
}
}
@@ -325,3 +316,13 @@ private fun findOriginalOffset(anchor: PsiElement, originalFile: PsiFile): Int?
if (originalFile.findElementAt(offset1)?.findExpansionElements()?.size != 1) return null
return offset1
}
+
+inline fun <reified T : PsiElement> T.findExpandedByLeaf(explicitCrate: Crate? = null, getLeaf: (T) -> PsiElement): T? =
+ when (getCodeStatus(explicitCrate)) {
+ RsCodeStatus.CFG_DISABLED -> null
+ RsCodeStatus.ATTR_PROC_MACRO_CALL -> {
+ val leafExpanded = getLeaf(this).findExpansionElements()?.singleOrNull()
+ leafExpanded?.parent as? T
+ }
+ else -> this
+ }
diff --git a/src/main/resources/compiler-info/compiler-features.json b/src/main/resources/compiler-info/compiler-features.json
index 42f2dd907..ba5277b0a 100644
--- a/src/main/resources/compiler-info/compiler-features.json
+++ b/src/main/resources/compiler-info/compiler-features.json
@@ -93,6 +93,7 @@
{"name":"min_const_generics","state":"accepted","since":"1.51.0"},
{"name":"min_const_unsafe_fn","state":"accepted","since":"1.33.0"},
{"name":"more_struct_aliases","state":"accepted","since":"1.16.0"},
+ {"name":"movbe_target_feature","state":"accepted","since":"1.70.0"},
{"name":"move_ref_pattern","state":"accepted","since":"1.49.0"},
{"name":"native_link_modifiers","state":"accepted","since":"1.61.0"},
{"name":"native_link_modifiers_bundle","state":"accepted","since":"1.63.0"},
@@ -197,7 +198,6 @@
{"name":"ermsb_target_feature","state":"active","since":"1.49.0"},
{"name":"hexagon_target_feature","state":"active","since":"1.27.0"},
{"name":"mips_target_feature","state":"active","since":"1.27.0"},
- {"name":"movbe_target_feature","state":"active","since":"1.34.0"},
{"name":"powerpc_target_feature","state":"active","since":"1.27.0"},
{"name":"riscv_target_feature","state":"active","since":"1.45.0"},
{"name":"rtm_target_feature","state":"active","since":"1.35.0"},
diff --git a/src/test/kotlin/org/rust/ide/hints/parameter/RsInlayParameterHintsProviderTest.kt b/src/test/kotlin/org/rust/ide/hints/parameter/RsInlayParameterHintsProviderTest.kt
index 40346d4eb..4b38937b0 100644
--- a/src/test/kotlin/org/rust/ide/hints/parameter/RsInlayParameterHintsProviderTest.kt
+++ b/src/test/kotlin/org/rust/ide/hints/parameter/RsInlayParameterHintsProviderTest.kt
@@ -8,11 +8,12 @@ package org.rust.ide.hints.parameter
import com.intellij.codeInsight.daemon.impl.HintRenderer
import com.intellij.openapi.vfs.VirtualFileFilter
import org.intellij.lang.annotations.Language
-import org.rust.MockAdditionalCfgOptions
-import org.rust.RsTestBase
-import org.rust.fileTreeFromText
+import org.rust.*
+import org.rust.ide.experiments.RsExperiments.PROC_MACROS
import org.rust.lang.core.psi.RsMethodCall
+@WithExperimentalFeatures(PROC_MACROS)
+@ProjectDescriptor(WithProcMacroRustProjectDescriptor::class)
class RsInlayParameterHintsProviderTest : RsTestBase() {
fun `test fn args`() = checkByText("""
fn foo(arg: u32, arg2: u32) {}
@@ -230,8 +231,15 @@ class RsInlayParameterHintsProviderTest : RsTestBase() {
check(inlays.size == 1)
}
- @Suppress("UnstableApiUsage")
private fun checkByText(@Language("Rust") code: String, smart: Boolean = true) {
+ check("fn main() {" in code) { "Please use hints inside `fn main` function - needed for testing with attr macros" }
+
+ doTest(code, smart)
+ doTest(code.replace("fn main() {", "#[test_proc_macros::attr_as_is] fn main() {"), smart)
+ }
+
+ @Suppress("UnstableApiUsage")
+ private fun doTest(@Language("Rust") code: String, smart: Boolean) {
InlineFile(code.replace(HINT_COMMENT_PATTERN, "<$1/>"))
RsInlayParameterHints.smartOption.set(smart)
diff --git a/src/test/kotlin/org/rust/ide/hints/type/RsChainMethodTypeHintsProviderTest.kt b/src/test/kotlin/org/rust/ide/hints/type/RsChainMethodTypeHintsProviderTest.kt
index 7e8958d1a..355136530 100644
--- a/src/test/kotlin/org/rust/ide/hints/type/RsChainMethodTypeHintsProviderTest.kt
+++ b/src/test/kotlin/org/rust/ide/hints/type/RsChainMethodTypeHintsProviderTest.kt
@@ -157,6 +157,7 @@ class RsChainMethodTypeHintsProviderTest : RsInlayTypeHintsTestBase(RsChainMetho
fun `test inside attribute macro call body`() = doTest("""
$types
+ #[test_proc_macros::attr_as_is]
fn main() {
let foo = A;
foo