diff options
author | Björn Gustavsson <[email protected]> | 2017-11-16 13:11:35 +0100 |
---|---|---|
committer | GitHub <[email protected]> | 2017-11-16 13:11:35 +0100 |
commit | 68dd05500dcad280417a2479f32fb6f7894ae712 (patch) | |
tree | e4bda059dea8ee0d3c3d94b635dae8423518a63a /erts/emulator/beam/msg_instrs.tab | |
parent | f1bee5747a39adde2e8bab666d19c99a0069f5a9 (diff) | |
parent | 3679444fb654e9cba1252c6df0be5170e5388639 (diff) | |
download | otp-68dd05500dcad280417a2479f32fb6f7894ae712.tar.gz otp-68dd05500dcad280417a2479f32fb6f7894ae712.tar.bz2 otp-68dd05500dcad280417a2479f32fb6f7894ae712.zip |
Merge pull request #1626 from bjorng/bjorn/erts/fix-receive-opt/ERL-511
Fix broken receive mark after an exception
OTP-14782
Diffstat (limited to 'erts/emulator/beam/msg_instrs.tab')
-rw-r--r-- | erts/emulator/beam/msg_instrs.tab | 21 |
1 files changed, 9 insertions, 12 deletions
diff --git a/erts/emulator/beam/msg_instrs.tab b/erts/emulator/beam/msg_instrs.tab index 8055a8616f..d6d4d2fb49 100644 --- a/erts/emulator/beam/msg_instrs.tab +++ b/erts/emulator/beam/msg_instrs.tab @@ -43,27 +43,23 @@ // * // */ -recv_mark(Dest) { +i_recv_mark() { /* - * Save the current position in message buffer and the - * the label for the loop_rec/2 instruction for the - * the receive statement. + * Save the current position in message buffer. */ - $SET_REL_I(c_p->msg.mark, $Dest); c_p->msg.saved_last = c_p->msg.last; } i_recv_set() { /* - * If the mark is valid (points to the loop_rec/2 - * instruction that follows), we know that the saved - * position points to the first message that could - * possibly be matched out. + * If c_p->msg.saved_last is non-zero, it points to the first + * message that could possibly be matched out. * - * If the mark is invalid, we do nothing, meaning that - * we will look through all messages in the message queue. + * If c_p->msg.saved_last is zero, it means that it was invalidated + * because another receive was executed before this i_recv_set() + * instruction was reached. */ - if (c_p->msg.mark == (BeamInstr *) ($NEXT_INSTRUCTION)) { + if (c_p->msg.saved_last) { c_p->msg.save = c_p->msg.saved_last; } SET_I($NEXT_INSTRUCTION); @@ -131,6 +127,7 @@ i_loop_rec(Dest) { ASSERT(HTOP == c_p->htop && E == c_p->stop); /* TODO: Add DTrace probe for this bad message situation? */ UNLINK_MESSAGE(c_p, msgp); + c_p->msg.saved_last = 0; /* Better safe than sorry. */ msgp->next = NULL; erts_cleanup_messages(msgp); goto loop_rec__; |