Skip to content

Commit aaf4555

Browse files
committed
Teach backend to emit iinc instructions
The backend is now able to turn `x += 42` into an `iinc 42` instruction. The optimization only applies to `+=` and `-=`, provided the the net increment fits inside a signed 16-bit value (the ASM library handles choosing `iinc` or `wide iinc` as is appropriate). Ported from scala/scala#9713
1 parent 461b30f commit aaf4555

File tree

2 files changed

+18
-3
lines changed

2 files changed

+18
-3
lines changed

compiler/src/dotty/tools/backend/jvm/BCodeBodyBuilder.scala

Lines changed: 17 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -88,9 +88,23 @@ trait BCodeBodyBuilder extends BCodeSkelBuilder {
8888
case Assign(lhs, rhs) =>
8989
val s = lhs.symbol
9090
val Local(tk, _, idx, _) = locals.getOrMakeLocal(s)
91-
genLoad(rhs, tk)
92-
lineNumber(tree)
93-
bc.store(idx, tk)
91+
92+
rhs match {
93+
case Apply(Select(larg: Ident, nme.ADD), Literal(x) :: Nil)
94+
if larg.symbol == s && tk.isIntSizedType && x.isShortRange =>
95+
lineNumber(tree)
96+
bc.iinc(idx, x.intValue)
97+
98+
case Apply(Select(larg: Ident, nme.SUB), Literal(x) :: Nil)
99+
if larg.symbol == s && tk.isIntSizedType && Constant(-x.intValue).isShortRange =>
100+
lineNumber(tree)
101+
bc.iinc(idx, -x.intValue)
102+
103+
case _ =>
104+
genLoad(rhs, tk)
105+
lineNumber(tree)
106+
bc.store(idx, tk)
107+
}
94108

95109
case _ =>
96110
genLoad(tree, UNIT)

compiler/src/dotty/tools/backend/jvm/BCodeIdiomatic.scala

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -433,6 +433,7 @@ trait BCodeIdiomatic {
433433

434434
final def load( idx: Int, tk: BType): Unit = { emitVarInsn(Opcodes.ILOAD, idx, tk) } // can-multi-thread
435435
final def store(idx: Int, tk: BType): Unit = { emitVarInsn(Opcodes.ISTORE, idx, tk) } // can-multi-thread
436+
final def iinc( idx: Int, increment: Int): Unit = jmethod.visitIincInsn(idx, increment) // can-multi-thread
436437

437438
final def aload( tk: BType): Unit = { emitTypeBased(JCodeMethodN.aloadOpcodes, tk) } // can-multi-thread
438439
final def astore(tk: BType): Unit = { emitTypeBased(JCodeMethodN.astoreOpcodes, tk) } // can-multi-thread

0 commit comments

Comments
 (0)