16
16
17
17
package org.jetbrains.kotlin.idea.decompiler.stubBuilder
18
18
19
- import com.google.protobuf.MessageLite
20
19
import com.intellij.psi.PsiElement
21
20
import com.intellij.psi.stubs.StubElement
22
21
import org.jetbrains.kotlin.idea.decompiler.stubBuilder.FlagsToModifiers.*
@@ -42,12 +41,12 @@ fun createCallableStubs(
42
41
) {
43
42
for (propertyProto in propertyProtos) {
44
43
if (! shouldSkip(propertyProto.flags, outerContext.nameResolver.getName(propertyProto.name))) {
45
- CallableClsStubBuilder (parentStub, propertyProto, outerContext, protoContainer).build()
44
+ PropertyClsStubBuilder (parentStub, outerContext, protoContainer, propertyProto ).build()
46
45
}
47
46
}
48
47
for (functionProto in functionProtos) {
49
48
if (! shouldSkip(functionProto.flags, outerContext.nameResolver.getName(functionProto.name))) {
50
- CallableClsStubBuilder (parentStub, functionProto, outerContext, protoContainer).build()
49
+ FunctionClsStubBuilder (parentStub, outerContext, protoContainer, functionProto ).build()
51
50
}
52
51
}
53
52
}
@@ -58,7 +57,7 @@ fun createConstructorStub(
58
57
outerContext : ClsStubBuilderContext ,
59
58
protoContainer : ProtoContainer
60
59
) {
61
- ConstructorClsStubBuilder (parentStub, constructorProto, outerContext, protoContainer).build()
60
+ ConstructorClsStubBuilder (parentStub, outerContext, protoContainer, constructorProto ).build()
62
61
}
63
62
64
63
private fun shouldSkip (flags : Int , name : Name ): Boolean {
@@ -70,155 +69,160 @@ private fun shouldSkip(flags: Int, name: Name): Boolean {
70
69
}
71
70
}
72
71
73
- private class CallableClsStubBuilder private constructor(
74
- private val parent : StubElement <out PsiElement >,
75
- private val callableProto : MessageLite ,
72
+ abstract class CallableClsStubBuilder (
73
+ parent : StubElement <out PsiElement >,
76
74
outerContext : ClsStubBuilderContext ,
77
- private val protoContainer : ProtoContainer ,
78
- private val callableKind : CallableClsStubBuilder .CallableKind ,
79
- private val nameIndex : Int ,
80
- private val typeParameterList : List <ProtoBuf .TypeParameter >,
81
- private val valueParameterList : List <ProtoBuf .ValueParameter >,
82
- private val receiverType : ProtoBuf .Type ? ,
83
- private val returnType : ProtoBuf .Type ? ,
84
- private val flags : Int
75
+ protected val protoContainer : ProtoContainer ,
76
+ private val typeParameters : List <ProtoBuf .TypeParameter >
85
77
) {
86
- private val c = outerContext.child(typeParameterList)
87
- private val typeStubBuilder = TypeClsStubBuilder (c)
88
- private val isTopLevel: Boolean get() = protoContainer.packageFqName != null
89
- private val callableStub = doCreateCallableStub()
90
-
91
- enum class CallableKind {
92
- FUN , VAL , VAR
93
- }
94
-
95
- constructor (
96
- parent: StubElement <out PsiElement >,
97
- functionProto: ProtoBuf .Function ,
98
- outerContext: ClsStubBuilderContext ,
99
- protoContainer: ProtoContainer
100
- ) : this (
101
- parent, functionProto, outerContext, protoContainer, CallableKind .FUN ,
102
- functionProto.name, functionProto.typeParameterList, functionProto.valueParameterList,
103
- if (functionProto.hasReceiverType()) functionProto.receiverType else null ,
104
- if (functionProto.hasReturnType()) functionProto.returnType else null ,
105
- functionProto.flags
106
- )
107
-
108
- constructor (
109
- parent: StubElement <out PsiElement >,
110
- propertyProto: ProtoBuf .Property ,
111
- outerContext: ClsStubBuilderContext ,
112
- protoContainer: ProtoContainer
113
- ) : this (
114
- parent, propertyProto, outerContext, protoContainer,
115
- if (Flags .IS_VAR .get(propertyProto.flags)) CallableKind .VAR else CallableKind .VAL ,
116
- propertyProto.name, propertyProto.typeParameterList, emptyList(),
117
- if (propertyProto.hasReceiverType()) propertyProto.receiverType else null ,
118
- if (propertyProto.hasReturnType()) propertyProto.returnType else null ,
119
- propertyProto.flags
120
- )
78
+ protected val c = outerContext.child(typeParameters)
79
+ protected val typeStubBuilder = TypeClsStubBuilder (c)
80
+ protected val isTopLevel: Boolean get() = protoContainer.packageFqName != null
81
+ protected val callableStub: StubElement <out PsiElement > by lazy(LazyThreadSafetyMode .NONE ) { doCreateCallableStub(parent) }
121
82
122
83
fun build () {
123
84
createModifierListStub()
124
- val typeConstraintListData = typeStubBuilder.createTypeParameterListStub(callableStub, typeParameterList )
85
+ val typeConstraintListData = typeStubBuilder.createTypeParameterListStub(callableStub, typeParameters )
125
86
createReceiverTypeReferenceStub()
126
87
createValueParameterList()
127
88
createReturnTypeStub()
128
89
typeStubBuilder.createTypeConstraintListStub(callableStub, typeConstraintListData)
129
90
}
130
91
131
- private fun createValueParameterList () {
132
- if (callableKind == CallableKind .FUN ) {
133
- typeStubBuilder.createValueParameterListStub(callableStub, callableProto, valueParameterList, protoContainer)
134
- }
135
- }
92
+ abstract val receiverType: ProtoBuf .Type ?
93
+ abstract val returnType: ProtoBuf .Type ?
136
94
137
95
private fun createReceiverTypeReferenceStub () {
138
- if ( receiverType != null ) {
139
- typeStubBuilder.createTypeReferenceStub(callableStub, receiverType )
96
+ receiverType?. let {
97
+ typeStubBuilder.createTypeReferenceStub(callableStub, it )
140
98
}
141
99
}
142
100
143
101
private fun createReturnTypeStub () {
144
- if ( returnType != null ) {
145
- typeStubBuilder.createTypeReferenceStub(callableStub, returnType )
102
+ returnType?. let {
103
+ typeStubBuilder.createTypeReferenceStub(callableStub, it )
146
104
}
147
105
}
148
106
149
- private fun createModifierListStub () {
150
- val modalityModifiers = if (isTopLevel) listOf () else listOf (MODALITY )
151
- val constModifiers = if (callableKind == CallableKind .VAL ) listOf (CONST ) else listOf ()
107
+ abstract fun createModifierListStub ()
152
108
153
- val additionalModifiers = when (callableKind) {
154
- CallableKind .FUN -> arrayOf(OPERATOR , INFIX )
155
- CallableKind .VAL , CallableKind .VAR -> arrayOf(LATEINIT )
156
- else -> emptyArray<FlagsToModifiers >()
157
- }
109
+ abstract fun createValueParameterList ()
110
+
111
+ abstract fun doCreateCallableStub (parent : StubElement <out PsiElement >): StubElement <out PsiElement >
112
+ }
113
+
114
+ private class FunctionClsStubBuilder (
115
+ parent : StubElement <out PsiElement >,
116
+ outerContext : ClsStubBuilderContext ,
117
+ protoContainer : ProtoContainer ,
118
+ private val functionProto : ProtoBuf .Function
119
+ ) : CallableClsStubBuilder(parent, outerContext, protoContainer, functionProto.typeParameterList) {
120
+ override val receiverType: ProtoBuf .Type ?
121
+ get() = if (functionProto.hasReceiverType()) functionProto.receiverType else null
158
122
159
- val relevantModifiers = listOf ( VISIBILITY ) + constModifiers + modalityModifiers + additionalModifiers
160
- val modifierListStubImpl = createModifierListStubForDeclaration(callableStub, flags, relevantModifiers)
123
+ override val returnType : ProtoBuf . Type ?
124
+ get() = if (functionProto.hasReturnType()) functionProto.returnType else null
161
125
162
- val kind = callableProto.annotatedCallableKind
163
- val annotationIds = c.components.annotationLoader.loadCallableAnnotations(protoContainer, callableProto, kind)
126
+ override fun createValueParameterList () {
127
+ typeStubBuilder.createValueParameterListStub(callableStub, functionProto, functionProto.valueParameterList, protoContainer)
128
+ }
129
+
130
+ override fun createModifierListStub () {
131
+ val modalityModifier = if (isTopLevel) listOf () else listOf (MODALITY )
132
+ val modifierListStubImpl = createModifierListStubForDeclaration(
133
+ callableStub, functionProto.flags,
134
+ listOf (VISIBILITY , OPERATOR , INFIX ) + modalityModifier
135
+ )
136
+
137
+ val annotationIds = c.components.annotationLoader.loadCallableAnnotations(
138
+ protoContainer, functionProto, AnnotatedCallableKind .FUNCTION
139
+ )
164
140
createTargetedAnnotationStubs(annotationIds, modifierListStubImpl)
165
141
}
166
142
167
- private fun doCreateCallableStub (): StubElement <out PsiElement > {
168
- val callableName = c.nameResolver.getName(nameIndex)
169
-
170
- return when (callableKind) {
171
- CallableKind .FUN -> {
172
- KotlinFunctionStubImpl (
173
- parent,
174
- callableName.ref(),
175
- isTopLevel,
176
- c.containerFqName.child(callableName),
177
- isExtension = receiverType != null ,
178
- hasBlockBody = true ,
179
- hasBody = Flags .MODALITY .get(flags) != Modality .ABSTRACT ,
180
- hasTypeParameterListBeforeFunctionName = typeParameterList.isNotEmpty()
181
- )
182
- }
183
- CallableKind .VAL , CallableKind .VAR -> {
184
- KotlinPropertyStubImpl (
185
- parent,
186
- callableName.ref(),
187
- isVar = callableKind == CallableKind .VAR ,
188
- isTopLevel = isTopLevel,
189
- hasDelegate = false ,
190
- hasDelegateExpression = false ,
191
- hasInitializer = false ,
192
- isExtension = receiverType != null ,
193
- hasReturnTypeRef = true ,
194
- fqName = c.containerFqName.child(callableName)
195
- )
196
- }
197
- else -> throw IllegalStateException (" Unknown callable kind $callableKind " )
198
- }
143
+ override fun doCreateCallableStub (parent : StubElement <out PsiElement >): StubElement <out PsiElement > {
144
+ val callableName = c.nameResolver.getName(functionProto.name)
145
+
146
+ return KotlinFunctionStubImpl (
147
+ parent,
148
+ callableName.ref(),
149
+ isTopLevel,
150
+ c.containerFqName.child(callableName),
151
+ isExtension = functionProto.hasReceiverType(),
152
+ hasBlockBody = true ,
153
+ hasBody = Flags .MODALITY .get(functionProto.flags) != Modality .ABSTRACT ,
154
+ hasTypeParameterListBeforeFunctionName = functionProto.typeParameterList.isNotEmpty()
155
+ )
199
156
}
200
157
}
201
158
202
- private class ConstructorClsStubBuilder (
203
- private val parent : StubElement <out PsiElement >,
204
- private val constructorProto : ProtoBuf .Constructor ,
159
+ private class PropertyClsStubBuilder (
160
+ parent : StubElement <out PsiElement >,
205
161
outerContext : ClsStubBuilderContext ,
206
- private val protoContainer : ProtoContainer
207
- ) {
208
- private val c = outerContext.child(emptyList())
209
- private val typeStubBuilder = TypeClsStubBuilder (c)
210
- private val callableStub = doCreateCallableStub()
162
+ protoContainer : ProtoContainer ,
163
+ private val propertyProto : ProtoBuf .Property
164
+ ) : CallableClsStubBuilder(parent, outerContext, protoContainer, propertyProto.typeParameterList) {
165
+ private val isVar = Flags .IS_VAR .get(propertyProto.flags)
211
166
212
- fun build () {
213
- createModifierListStub()
214
- createValueParameterList()
167
+ override val receiverType: ProtoBuf .Type ?
168
+ get() = if (propertyProto.hasReceiverType()) propertyProto.receiverType else null
169
+
170
+ override val returnType: ProtoBuf .Type ?
171
+ get() = if (propertyProto.hasReturnType()) propertyProto.returnType else null
172
+
173
+ override fun createValueParameterList () {
174
+ }
175
+
176
+ override fun createModifierListStub () {
177
+ val constModifier = if (isVar) listOf () else listOf (CONST )
178
+ val modalityModifier = if (isTopLevel) listOf () else listOf (MODALITY )
179
+
180
+ val modifierListStubImpl = createModifierListStubForDeclaration(
181
+ callableStub, propertyProto.flags,
182
+ listOf (VISIBILITY , LATEINIT ) + constModifier + modalityModifier
183
+ )
184
+
185
+ val annotationIds = c.components.annotationLoader.loadCallableAnnotations(
186
+ protoContainer, propertyProto, AnnotatedCallableKind .PROPERTY
187
+ )
188
+ createTargetedAnnotationStubs(annotationIds, modifierListStubImpl)
189
+ }
190
+
191
+ override fun doCreateCallableStub (parent : StubElement <out PsiElement >): StubElement <out PsiElement > {
192
+ val callableName = c.nameResolver.getName(propertyProto.name)
193
+
194
+ return KotlinPropertyStubImpl (
195
+ parent,
196
+ callableName.ref(),
197
+ isVar,
198
+ isTopLevel,
199
+ hasDelegate = false ,
200
+ hasDelegateExpression = false ,
201
+ hasInitializer = false ,
202
+ isExtension = propertyProto.hasReceiverType(),
203
+ hasReturnTypeRef = true ,
204
+ fqName = c.containerFqName.child(callableName)
205
+ )
215
206
}
207
+ }
208
+
209
+ private class ConstructorClsStubBuilder (
210
+ parent : StubElement <out PsiElement >,
211
+ outerContext : ClsStubBuilderContext ,
212
+ protoContainer : ProtoContainer ,
213
+ private val constructorProto : ProtoBuf .Constructor
214
+ ) : CallableClsStubBuilder(parent, outerContext, protoContainer, emptyList()) {
215
+ override val receiverType: ProtoBuf .Type ?
216
+ get() = null
217
+
218
+ override val returnType: ProtoBuf .Type ?
219
+ get() = null
216
220
217
- private fun createValueParameterList () {
221
+ override fun createValueParameterList () {
218
222
typeStubBuilder.createValueParameterListStub(callableStub, constructorProto, constructorProto.valueParameterList, protoContainer)
219
223
}
220
224
221
- private fun createModifierListStub () {
225
+ override fun createModifierListStub () {
222
226
val modifierListStubImpl = createModifierListStubForDeclaration(callableStub, constructorProto.flags, listOf (VISIBILITY ))
223
227
224
228
val annotationIds = c.components.annotationLoader.loadCallableAnnotations(
@@ -227,7 +231,7 @@ private class ConstructorClsStubBuilder(
227
231
createTargetedAnnotationStubs(annotationIds, modifierListStubImpl)
228
232
}
229
233
230
- private fun doCreateCallableStub (): StubElement <out PsiElement > {
234
+ override fun doCreateCallableStub (parent : StubElement < out PsiElement > ): StubElement <out PsiElement > {
231
235
return if (Flags .IS_SECONDARY .get(constructorProto.flags))
232
236
KotlinPlaceHolderStubImpl (parent, JetStubElementTypes .SECONDARY_CONSTRUCTOR )
233
237
else
0 commit comments