diff options
author | Björn Gustavsson <[email protected]> | 2018-09-05 13:25:28 +0200 |
---|---|---|
committer | GitHub <[email protected]> | 2018-09-05 13:25:28 +0200 |
commit | 66b797b4aeca486f515d96c1677cc633ce12a5d3 (patch) | |
tree | 1d5d55a26a42a97b1f052fa87cfe772e212b6775 /erts | |
parent | 092f4847f489cba0381676a6a389ddbfc2af4f1e (diff) | |
parent | 47a2ff39ac75c69b41f90f05a63fd9a2e6c0b36a (diff) | |
download | otp-66b797b4aeca486f515d96c1677cc633ce12a5d3.tar.gz otp-66b797b4aeca486f515d96c1677cc633ce12a5d3.tar.bz2 otp-66b797b4aeca486f515d96c1677cc633ce12a5d3.zip |
Merge pull request #1947 from bjorng/bjorn/opt-put-tuple
Introduce a put_tuple2 instruction
Diffstat (limited to 'erts')
-rw-r--r-- | erts/emulator/beam/beam_debug.c | 4 | ||||
-rw-r--r-- | erts/emulator/beam/instrs.tab | 17 | ||||
-rw-r--r-- | erts/emulator/beam/ops.tab | 15 |
3 files changed, 24 insertions, 12 deletions
diff --git a/erts/emulator/beam/beam_debug.c b/erts/emulator/beam/beam_debug.c index 9633de2021..b33aab7eee 100644 --- a/erts/emulator/beam/beam_debug.c +++ b/erts/emulator/beam/beam_debug.c @@ -786,8 +786,8 @@ print_op(fmtfn_t to, void *to_arg, int op, int size, BeamInstr* addr) } } break; - case op_i_put_tuple_xI: - case op_i_put_tuple_yI: + case op_put_tuple2_xI: + case op_put_tuple2_yI: case op_new_map_dtI: case op_update_map_assoc_sdtI: case op_update_map_exact_jsdtI: diff --git a/erts/emulator/beam/instrs.tab b/erts/emulator/beam/instrs.tab index 42c1168f85..da1dd3dc45 100644 --- a/erts/emulator/beam/instrs.tab +++ b/erts/emulator/beam/instrs.tab @@ -559,17 +559,19 @@ update_list(Hd, Dst) { HTOP += 2; } -i_put_tuple := i_put_tuple.make.fill; - -i_put_tuple.make(Dst) { - $Dst = make_tuple(HTOP); -} - -i_put_tuple.fill(Arity) { +put_tuple2(Dst, Arity) { Eterm* hp = HTOP; Eterm arity = $Arity; + /* + * If operands are not packed (in the 32-bit VM), + * is is not safe to use $Dst directly after I + * has been updated. + */ + Eterm* dst_ptr = &($Dst); + //| -no_next + ASSERT(arity != 0); *hp++ = make_arityval(arity); I = $NEXT_INSTRUCTION; do { @@ -586,6 +588,7 @@ i_put_tuple.fill(Arity) { break; } } while (--arity != 0); + *dst_ptr = make_tuple(HTOP); HTOP = hp; ASSERT(VALID_INSTR(* (Eterm *)I)); Goto(*I); diff --git a/erts/emulator/beam/ops.tab b/erts/emulator/beam/ops.tab index d71594235e..d859c4bb24 100644 --- a/erts/emulator/beam/ops.tab +++ b/erts/emulator/beam/ops.tab @@ -483,9 +483,16 @@ is_eq f? s s is_ne f? s s # -# Putting things. +# Putting tuples. +# +# Code compiled with OTP 22 and later uses put_tuple2 to +# to construct a tuple. +# +# Code compiled before OTP 22 uses put_tuple + one put instruction +# per element. Translate to put_tuple2. # +i_put_tuple/2 put_tuple Arity Dst => i_put_tuple Dst u i_put_tuple Dst Arity Puts=* | put S1 | put S2 | \ @@ -495,11 +502,13 @@ i_put_tuple Dst Arity Puts=* | put S1 | put S2 | \ i_put_tuple Dst Arity Puts=* | put S => \ tuple_append_put(Arity, Dst, Puts, S) -i_put_tuple/2 +i_put_tuple Dst Arity Puts=* => put_tuple2 Dst Arity Puts -i_put_tuple xy I +put_tuple2 xy I # +# Putting lists. +# # The instruction "put_list Const [] Dst" were generated in rare # circumstances up to and including OTP 18. Starting with OTP 19, # AFAIK, it should never be generated. |