@@ -78,7 +78,41 @@ trait AstForFunctionsCreator(implicit withSchemaValidation: ValidationMode) exte
7878 val fullName = nameRenderer.combineFunctionFullName(descFullName, signature)
7979
8080 val _methodNode = methodNode(ktFn, ktFn.getName, fullName, signature, relativizedPath)
81- scope.pushNewScope(_methodNode)
81+ val closureBindingEntriesForCaptured =
82+ if (ktFn.getName == " main" ) {
83+ scope
84+ .pushClosureScope(_methodNode)
85+ .collect { case node : NewLocal => NodeContext (node, node.name, node.typeFullName) }
86+ .map { capturedNodeContext =>
87+ val closureBindingId = s " ${_methodNode.fullName}: ${capturedNodeContext.name}"
88+ val closureBinding = closureBindingNode(closureBindingId, EvaluationStrategies .BY_REFERENCE )
89+ (closureBinding, capturedNodeContext)
90+ }
91+ } else {
92+ scope.pushNewScope(_methodNode)
93+ List .empty
94+ }
95+ val methodRefForCapture =
96+ if (closureBindingEntriesForCaptured.nonEmpty) {
97+ val methodTypeDeclFullName = fullName.split(" :" ).head
98+ Some (methodRefNode(ktFn, ktFn.getName, fullName, methodTypeDeclFullName))
99+ } else {
100+ None
101+ }
102+
103+ val localsForCaptured = closureBindingEntriesForCaptured.map { case (closureBinding, capturedNodeContext) =>
104+ val node =
105+ localNode(
106+ ktFn,
107+ capturedNodeContext.name,
108+ capturedNodeContext.name,
109+ capturedNodeContext.typeFullName,
110+ closureBinding.closureBindingId
111+ )
112+ scope.addToScope(capturedNodeContext.name, node)
113+ node
114+ }
115+
82116 methodAstParentStack.push(_methodNode)
83117
84118 val isExtensionMethod = funcDesc.getExtensionReceiverParameter != null
@@ -128,7 +162,8 @@ trait AstForFunctionsCreator(implicit withSchemaValidation: ValidationMode) exte
128162 astForParameter(p, valueParamStartIndex + idx - 1 )
129163 }
130164 val bodyAst = Option (ktFn.getBodyBlockExpression) match {
131- case Some (bodyBlockExpression) => astForBlock(bodyBlockExpression, None , None )
165+ case Some (bodyBlockExpression) =>
166+ astForBlock(bodyBlockExpression, None , None , localsForCaptures = localsForCaptured)
132167 case None =>
133168 Option (ktFn.getBodyExpression)
134169 .map { expr =>
@@ -141,16 +176,21 @@ trait AstForFunctionsCreator(implicit withSchemaValidation: ValidationMode) exte
141176 val returnAst_ = returnAst(returnNode(expr, Constants .RetCode ), Seq (lastStatementAst))
142177 (allStatementsButLast ++ Seq (returnAst_)).toList
143178 } else List ()
144- blockAst(bodyBlock, blockChildAsts)
179+ blockAst(bodyBlock, localsForCaptured.map( Ast (_)) ++ blockChildAsts)
145180 }
146181 .getOrElse {
147182 val bodyBlock = blockNode(ktFn, " <empty>" , TypeConstants .Any )
148- blockAst(bodyBlock, List [ Ast ]( ))
183+ blockAst(bodyBlock, localsForCaptured.map( Ast (_) ))
149184 }
150185 }
151186 methodAstParentStack.pop()
152187 scope.popScope()
153188
189+ val closureBindingDefs = closureBindingEntriesForCaptured.map { case (closureBinding, node) =>
190+ ClosureBindingDef (closureBinding, methodRefForCapture, node.node)
191+ }
192+ closureBindingDefs.foreach(closureBindingDefQueue.prepend)
193+
154194 val explicitTypeName = Option (ktFn.getTypeReference).map(_.getText).getOrElse(TypeConstants .Any )
155195 val typeFullName = registerType(nameRenderer.typeFullName(funcDesc.getReturnType).getOrElse(explicitTypeName))
156196 val _methodReturnNode = methodReturnNode(ktFn, typeFullName)
@@ -183,6 +223,7 @@ trait AstForFunctionsCreator(implicit withSchemaValidation: ValidationMode) exte
183223 val annotationEntries = ktFn.getAnnotationEntries.asScala.map(astForAnnotationEntry).toSeq
184224 methodAst(_methodNode, thisParameterAsts ++ methodParametersAsts, bodyAst, _methodReturnNode, modifiers)
185225 .withChildren(annotationEntries)
226+ .withChildren(methodRefForCapture.map(Ast (_)).toSeq)
186227 }
187228
188229 private def astsForDestructuring (param : KtParameter , backingParamName : Option [String ] = None ): Seq [Ast ] = {
@@ -485,7 +526,7 @@ trait AstForFunctionsCreator(implicit withSchemaValidation: ValidationMode) exte
485526
486527 scope.popScope()
487528 val closureBindingDefs = closureBindingEntriesForCaptured.collect { case (closureBinding, node) =>
488- ClosureBindingDef (closureBinding, _methodRefNode, node.node)
529+ ClosureBindingDef (closureBinding, Some ( _methodRefNode) , node.node)
489530 }
490531 closureBindingDefs.foreach(closureBindingDefQueue.prepend)
491532 lambdaAstQueue.prepend(lambdaMethodAst)
@@ -656,7 +697,7 @@ trait AstForFunctionsCreator(implicit withSchemaValidation: ValidationMode) exte
656697
657698 scope.popScope()
658699 val closureBindingDefs = closureBindingEntriesForCaptured.collect { case (closureBinding, node) =>
659- ClosureBindingDef (closureBinding, _methodRefNode, node.node)
700+ ClosureBindingDef (closureBinding, Some ( _methodRefNode) , node.node)
660701 }
661702 closureBindingDefs.foreach(closureBindingDefQueue.prepend)
662703 lambdaAstQueue.prepend(lambdaMethodAst)
0 commit comments