@@ -79,14 +79,14 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
7979
8080 tree match {
8181 case Assign (lhs @ DesugaredSelect (qual, _), rhs) =>
82- val savedStackHeight = stackHeight
82+ val savedStackSize = stack.recordSize()
8383 val isStatic = lhs.symbol.isStaticMember
8484 if (! isStatic) {
85- genLoadQualifier(lhs )
86- stackHeight += 1
85+ val qualTK = genLoad(qual )
86+ stack.push(qualTK)
8787 }
8888 genLoad(rhs, symInfoTK(lhs.symbol))
89- stackHeight = savedStackHeight
89+ stack.restoreSize(savedStackSize)
9090 lineNumber(tree)
9191 // receiverClass is used in the bytecode to access the field. using sym.owner may lead to IllegalAccessError
9292 val receiverClass = qual.tpe.typeSymbol
@@ -150,9 +150,9 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
150150 }
151151
152152 genLoad(larg, resKind)
153- stackHeight += resKind.size
153+ stack.push(resKind)
154154 genLoad(rarg, if (isShift) INT else resKind)
155- stackHeight -= resKind.size
155+ stack.pop()
156156
157157 (code : @ switch) match {
158158 case ADD => bc add resKind
@@ -189,19 +189,19 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
189189 if (isArrayGet(code)) {
190190 // load argument on stack
191191 assert(args.length == 1 , s " Too many arguments for array get operation: $tree" );
192- stackHeight += 1
192+ stack.push(k)
193193 genLoad(args.head, INT )
194- stackHeight -= 1
194+ stack.pop()
195195 generatedType = k.asArrayBType.componentType
196196 bc.aload(elementType)
197197 }
198198 else if (isArraySet(code)) {
199199 val List (a1, a2) = args
200- stackHeight += 1
200+ stack.push(k)
201201 genLoad(a1, INT )
202- stackHeight += 1
202+ stack.push( INT )
203203 genLoad(a2)
204- stackHeight -= 2
204+ stack.pop( 2 )
205205 generatedType = UNIT
206206 bc.astore(elementType)
207207 } else {
@@ -235,7 +235,7 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
235235 val resKind = if (hasUnitBranch) UNIT else tpeTK(tree)
236236
237237 val postIf = new asm.Label
238- genLoadTo(thenp, resKind, LoadDestination .Jump (postIf, stackHeight ))
238+ genLoadTo(thenp, resKind, LoadDestination .Jump (postIf, stack.recordSize() ))
239239 markProgramPoint(failure)
240240 genLoadTo(elsep, resKind, LoadDestination .FallThrough )
241241 markProgramPoint(postIf)
@@ -294,8 +294,10 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
294294 )
295295 }
296296
297- def genLoad (tree : Tree ): Unit = {
298- genLoad(tree, tpeTK(tree))
297+ def genLoad (tree : Tree ): BType = {
298+ val generatedType = tpeTK(tree)
299+ genLoad(tree, generatedType)
300+ generatedType
299301 }
300302
301303 /* Generate code for trees that produce values on the stack */
@@ -364,6 +366,7 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
364366 case t @ Ident (_) => (t, Nil )
365367 }
366368
369+ val savedStackSize = stack.recordSize()
367370 if (! fun.symbol.isStaticMember) {
368371 // load receiver of non-static implementation of lambda
369372
@@ -372,10 +375,12 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
372375 // AbstractValidatingLambdaMetafactory.validateMetafactoryArgs
373376
374377 val DesugaredSelect (prefix, _) = fun : @ unchecked
375- genLoad(prefix)
378+ val prefixTK = genLoad(prefix)
379+ stack.push(prefixTK)
376380 }
377381
378382 genLoadArguments(env, fun.symbol.info.firstParamTypes map toTypeKind)
383+ stack.restoreSize(savedStackSize)
379384 generatedType = genInvokeDynamicLambda(NoSymbol , fun.symbol, env.size, functionalInterface)
380385
381386 case app @ Apply (_, _) =>
@@ -494,9 +499,9 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
494499 dest match
495500 case LoadDestination .FallThrough =>
496501 ()
497- case LoadDestination .Jump (label, targetStackHeight ) =>
498- if targetStackHeight < stackHeight then
499- val stackDiff = stackHeight - targetStackHeight
502+ case LoadDestination .Jump (label, targetStackSize ) =>
503+ val stackDiff = stack.heightDiffWrt(targetStackSize)
504+ if stackDiff != 0 then
500505 if expectedType == UNIT then
501506 bc dropMany stackDiff
502507 else
@@ -599,7 +604,7 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
599604 if dest == LoadDestination .FallThrough then
600605 val resKind = tpeTK(tree)
601606 val jumpTarget = new asm.Label
602- registerJumpDest(labelSym, resKind, LoadDestination .Jump (jumpTarget, stackHeight ))
607+ registerJumpDest(labelSym, resKind, LoadDestination .Jump (jumpTarget, stack.recordSize() ))
603608 genLoad(expr, resKind)
604609 markProgramPoint(jumpTarget)
605610 resKind
@@ -657,7 +662,7 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
657662 markProgramPoint(loop)
658663
659664 if isInfinite then
660- val dest = LoadDestination .Jump (loop, stackHeight )
665+ val dest = LoadDestination .Jump (loop, stack.recordSize() )
661666 genLoadTo(body, UNIT , dest)
662667 dest
663668 else
@@ -672,7 +677,7 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
672677 val failure = new asm.Label
673678 genCond(cond, success, failure, targetIfNoJump = success)
674679 markProgramPoint(success)
675- genLoadTo(body, UNIT , LoadDestination .Jump (loop, stackHeight ))
680+ genLoadTo(body, UNIT , LoadDestination .Jump (loop, stack.recordSize() ))
676681 markProgramPoint(failure)
677682 end match
678683 LoadDestination .FallThrough
@@ -765,10 +770,10 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
765770 // on the stack (contrary to what the type in the AST says).
766771
767772 // scala/bug#10290: qual can be `this.$outer()` (not just `this`), so we call genLoad (not just ALOAD_0)
768- genLoad(superQual)
769- stackHeight += 1
773+ val superQualTK = genLoad(superQual)
774+ stack.push(superQualTK)
770775 genLoadArguments(args, paramTKs(app))
771- stackHeight -= 1
776+ stack.pop()
772777 generatedType = genCallMethod(fun.symbol, InvokeStyle .Super , app.span)
773778
774779 // 'new' constructor call: Note: since constructors are
@@ -790,9 +795,10 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
790795 assert(classBTypeFromSymbol(ctor.owner) == rt, s " Symbol ${ctor.owner.showFullName} is different from $rt" )
791796 mnode.visitTypeInsn(asm.Opcodes .NEW , rt.internalName)
792797 bc dup generatedType
793- stackHeight += 2
798+ stack.push(rt)
799+ stack.push(rt)
794800 genLoadArguments(args, paramTKs(app))
795- stackHeight -= 2
801+ stack.pop( 2 )
796802 genCallMethod(ctor, InvokeStyle .Special , app.span)
797803
798804 case _ =>
@@ -825,12 +831,11 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
825831 else if (app.hasAttachment(BCodeHelpers .UseInvokeSpecial )) InvokeStyle .Special
826832 else InvokeStyle .Virtual
827833
828- val savedStackHeight = stackHeight
834+ val savedStackSize = stack.recordSize()
829835 if invokeStyle.hasInstance then
830- genLoadQualifier(fun)
831- stackHeight += 1
836+ stack.push(genLoadQualifier(fun))
832837 genLoadArguments(args, paramTKs(app))
833- stackHeight = savedStackHeight
838+ stack.restoreSize(savedStackSize)
834839
835840 val DesugaredSelect (qual, name) = fun : @ unchecked // fun is a Select, also checked in genLoadQualifier
836841 val isArrayClone = name == nme.clone_ && qual.tpe.widen.isInstanceOf [JavaArrayType ]
@@ -888,7 +893,10 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
888893 bc iconst elems.length
889894 bc newarray elmKind
890895
891- stackHeight += 3 // during the genLoad below, there is the result, its dup, and the index
896+ // during the genLoad below, there is the result, its dup, and the index
897+ stack.push(generatedType)
898+ stack.push(generatedType)
899+ stack.push(INT )
892900
893901 var i = 0
894902 var rest = elems
@@ -901,7 +909,7 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
901909 i = i + 1
902910 }
903911
904- stackHeight -= 3
912+ stack.pop( 3 )
905913
906914 generatedType
907915 }
@@ -917,7 +925,7 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
917925 val (generatedType, postMatch, postMatchDest) =
918926 if dest == LoadDestination .FallThrough then
919927 val postMatch = new asm.Label
920- (tpeTK(tree), postMatch, LoadDestination .Jump (postMatch, stackHeight ))
928+ (tpeTK(tree), postMatch, LoadDestination .Jump (postMatch, stack.recordSize() ))
921929 else
922930 (expectedType, null , dest)
923931
@@ -1179,7 +1187,7 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
11791187 }
11801188
11811189 /* Emit code to Load the qualifier of `tree` on top of the stack. */
1182- def genLoadQualifier (tree : Tree ): Unit = {
1190+ def genLoadQualifier (tree : Tree ): BType = {
11831191 lineNumber(tree)
11841192 tree match {
11851193 case DesugaredSelect (qualifier, _) => genLoad(qualifier)
@@ -1188,6 +1196,7 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
11881196 case Some (sel) => genLoadQualifier(sel)
11891197 case None =>
11901198 assert(t.symbol.owner == this .claszSymbol)
1199+ UNIT
11911200 }
11921201 case _ => abort(s " Unknown qualifier $tree" )
11931202 }
@@ -1200,14 +1209,14 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
12001209 btpes match
12011210 case btpe :: btpes1 =>
12021211 genLoad(arg, btpe)
1203- stackHeight += btpe.size
1212+ stack.push(btpe)
12041213 loop(args1, btpes1)
12051214 case _ =>
12061215 case _ =>
12071216
1208- val savedStackHeight = stackHeight
1217+ val savedStackSize = stack.recordSize()
12091218 loop(args, btpes)
1210- stackHeight = savedStackHeight
1219+ stack.restoreSize(savedStackSize)
12111220 end genLoadArguments
12121221
12131222 def genLoadModule (tree : Tree ): BType = {
@@ -1307,13 +1316,13 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
13071316 }.sum
13081317 bc.genNewStringBuilder(approxBuilderSize)
13091318
1310- stackHeight += 1 // during the genLoad below, there is a reference to the StringBuilder on the stack
1319+ stack.push(jlStringBuilderRef) // during the genLoad below, there is a reference to the StringBuilder on the stack
13111320 for (elem <- concatArguments) {
13121321 val elemType = tpeTK(elem)
13131322 genLoad(elem, elemType)
13141323 bc.genStringBuilderAppend(elemType)
13151324 }
1316- stackHeight -= 1
1325+ stack.pop()
13171326
13181327 bc.genStringBuilderEnd
13191328 } else {
@@ -1331,15 +1340,17 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
13311340 var totalArgSlots = 0
13321341 var countConcats = 1 // ie. 1 + how many times we spilled
13331342
1334- val savedStackHeight = stackHeight
1343+ val savedStackSize = stack.recordSize()
13351344
13361345 for (elem <- concatArguments) {
13371346 val tpe = tpeTK(elem)
13381347 val elemSlots = tpe.size
13391348
13401349 // Unlikely spill case
13411350 if (totalArgSlots + elemSlots >= MaxIndySlots ) {
1342- stackHeight = savedStackHeight + countConcats
1351+ stack.restoreSize(savedStackSize)
1352+ for _ <- 0 until countConcats do
1353+ stack.push(StringRef )
13431354 bc.genIndyStringConcat(recipe.toString, argTypes.result(), constVals.result())
13441355 countConcats += 1
13451356 totalArgSlots = 0
@@ -1364,10 +1375,10 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
13641375 val tpe = tpeTK(elem)
13651376 argTypes += tpe.toASMType
13661377 genLoad(elem, tpe)
1367- stackHeight += 1
1378+ stack.push(tpe)
13681379 }
13691380 }
1370- stackHeight = savedStackHeight
1381+ stack.restoreSize(savedStackSize)
13711382 bc.genIndyStringConcat(recipe.toString, argTypes.result(), constVals.result())
13721383
13731384 // If we spilled, generate one final concat
@@ -1562,9 +1573,9 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
15621573 } else {
15631574 val tk = tpeTK(l).maxType(tpeTK(r))
15641575 genLoad(l, tk)
1565- stackHeight += tk.size
1576+ stack.push(tk)
15661577 genLoad(r, tk)
1567- stackHeight -= tk.size
1578+ stack.pop()
15681579 genCJUMP(success, failure, op, tk, targetIfNoJump)
15691580 }
15701581 }
@@ -1679,9 +1690,9 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
16791690 }
16801691
16811692 genLoad(l, ObjectRef )
1682- stackHeight += 1
1693+ stack.push( ObjectRef )
16831694 genLoad(r, ObjectRef )
1684- stackHeight -= 1
1695+ stack.pop()
16851696 genCallMethod(equalsMethod, InvokeStyle .Static )
16861697 genCZJUMP(success, failure, Primitives .NE , BOOL , targetIfNoJump)
16871698 }
@@ -1697,9 +1708,9 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
16971708 } else if (isNonNullExpr(l)) {
16981709 // SI-7852 Avoid null check if L is statically non-null.
16991710 genLoad(l, ObjectRef )
1700- stackHeight += 1
1711+ stack.push( ObjectRef )
17011712 genLoad(r, ObjectRef )
1702- stackHeight -= 1
1713+ stack.pop()
17031714 genCallMethod(defn.Any_equals , InvokeStyle .Virtual )
17041715 genCZJUMP(success, failure, Primitives .NE , BOOL , targetIfNoJump)
17051716 } else {
@@ -1709,9 +1720,9 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
17091720 val lNonNull = new asm.Label
17101721
17111722 genLoad(l, ObjectRef )
1712- stackHeight += 1
1723+ stack.push( ObjectRef )
17131724 genLoad(r, ObjectRef )
1714- stackHeight -= 1
1725+ stack.pop()
17151726 locals.store(eqEqTempLocal)
17161727 bc dup ObjectRef
17171728 genCZJUMP(lNull, lNonNull, Primitives .EQ , ObjectRef , targetIfNoJump = lNull)
0 commit comments