Skip to content

Commit fe8289c

Browse files
authored
Merge pull request #74479 from hamishknight/no-completion-usr-for-local
[Completion] Don’t generate USRs for local decls
2 parents d4c1a3a + ddd1bde commit fe8289c

File tree

3 files changed

+38
-2
lines changed

3 files changed

+38
-2
lines changed

lib/AST/ASTMangler.cpp

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3766,8 +3766,9 @@ void ASTMangler::appendClosureEntity(const AbstractClosureExpr *closure) {
37663766

37673767
auto type = closure->getType();
37683768

3769-
// FIXME: CodeCompletionResultBuilder calls printValueDeclUSR() but the
3770-
// closure hasn't been type checked yet.
3769+
// FIXME: We can end up with a null type here in the presence of invalid
3770+
// code; the type-checker currently isn't strict about producing typed
3771+
// expression nodes when it fails. Once we enforce that, we can remove this.
37713772
if (!type)
37723773
type = ErrorType::get(closure->getASTContext());
37733774

lib/IDE/CodeCompletionResultBuilder.cpp

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,11 @@ static bool shouldCopyAssociatedUSRForDecl(const ValueDecl *VD) {
3636
if (VD->hasClangNode() && !VD->getClangDecl())
3737
return false;
3838

39+
// Avoid generating USRs for decls in local contexts, we cannot guarantee
40+
// any parent closures will be type-checked, which is needed for mangling.
41+
if (VD->getDeclContext()->getLocalContext())
42+
return false;
43+
3944
return true;
4045
}
4146

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
// rdar://128294522 - Make sure we don't generate USRs for decls in local contexts.
2+
3+
func test1() {
4+
let loclVar = 0 // This typo is intentional; otherwise mangling applies a substitution for 'local'.
5+
// RUN: %sourcekitd-test -req=complete -pos=%(line):3 %s -- %s | %FileCheck %s --check-prefix LOCAL_VAR
6+
// LOCAL_VAR-NOT: key.associated_usrs: "s:{{.*}}loclVar{{.*}}"
7+
// LOCAL_VAR: key.name: "loclVar"
8+
// LOCAL_VAR-NOT: key.associated_usrs: "s:{{.*}}loclVar{{.*}}"
9+
}
10+
11+
func test2() {
12+
let _ = {
13+
struct S {
14+
func nestedMethod() {
15+
// RUN: %sourcekitd-test -req=complete -pos=%(line):3 %s -- %s | %FileCheck %s --check-prefix LOCAL_METHOD
16+
// RUN: %sourcekitd-test -req=complete -pos=%(line+1):14 %s -- %s | %FileCheck %s --check-prefix LOCAL_METHOD
17+
self.
18+
// LOCAL_METHOD-NOT: key.associated_usrs: "s:{{.*}}nestedMethod{{.*}}"
19+
// LOCAL_METHOD: key.name: "nestedMethod()"
20+
// LOCAL_METHOD-NOT: key.associated_usrs: "s:{{.*}}nestedMethod{{.*}}"
21+
}
22+
}
23+
}
24+
}
25+
26+
// Just to make sure 'key.associated_usrs' is produced for a non-local decl
27+
// so the above CHECK-NOT's are working. If this fails, make sure to update the
28+
// above checks too.
29+
// RUN: %sourcekitd-test -req=complete -pos=%(line):1 %s -- %s | %FileCheck %s --check-prefix NON_LOCAL
30+
// NON_LOCAL: key.associated_usrs: "s:{{.*}}test2{{.*}}"

0 commit comments

Comments
 (0)