diff options
author | Erlang/OTP <otp@erlang.org> | 2023-04-25 17:08:53 +0200 |
---|---|---|
committer | Erlang/OTP <otp@erlang.org> | 2023-04-25 17:08:53 +0200 |
commit | fe3fd7144dd4ff6925088249a7cda7d299e6adf6 (patch) | |
tree | 477fea5458e2537e90e5d58568a3b40bf2e48a60 /erts | |
parent | ec59a080681865a8a32003ec527b6802e8aefdc5 (diff) | |
parent | 7b74c04ded2172a286a38063dad1f5e9f2431bf0 (diff) | |
download | erlang-fe3fd7144dd4ff6925088249a7cda7d299e6adf6.tar.gz |
Merge branch 'rickard/driver-call-callback-fix/24.3.4/OTP-18525' into maint-25
* rickard/driver-call-callback-fix/24.3.4/OTP-18525:
[erts] Fix error case for driver call callback
Diffstat (limited to 'erts')
-rw-r--r-- | erts/emulator/beam/io.c | 44 |
1 files changed, 28 insertions, 16 deletions
diff --git a/erts/emulator/beam/io.c b/erts/emulator/beam/io.c index dfdbe475b3..2ef5bc4d01 100644 --- a/erts/emulator/beam/io.c +++ b/erts/emulator/beam/io.c @@ -4659,6 +4659,7 @@ erts_port_call(Process* c_p, unsigned ret_flags = 0U; Eterm term; Eterm* hp; + ErtsPortOpResult result; res = call_driver_call(c_p->common.id, prt, @@ -4672,25 +4673,36 @@ erts_port_call(Process* c_p, finalize_imm_drv_call(&try_call_state); if (bufp != &input_buf[0]) erts_free(ERTS_ALC_T_TMP, bufp); - if (res == ERTS_PORT_OP_BADARG) - return ERTS_PORT_OP_BADARG; - hsz = erts_decode_ext_size((byte *) resp_bufp, resp_size); - if (hsz < 0) - return ERTS_PORT_OP_BADARG; - hsz += 3; - erts_factory_proc_prealloc_init(&factory, c_p, hsz); - endp = (byte *) resp_bufp; - term = erts_decode_ext(&factory, (const byte**)&endp, 0); - if (term == THE_NON_VALUE) - return ERTS_PORT_OP_BADARG; - hp = erts_produce_heap(&factory,3,0); - *retvalp = TUPLE2(hp, am_ok, term); - erts_factory_close(&factory); + if (res == ERTS_PORT_OP_BADARG) { + result = ERTS_PORT_OP_BADARG; + } + else { + hsz = erts_decode_ext_size((byte *) resp_bufp, resp_size); + if (hsz < 0) { + result = ERTS_PORT_OP_BADARG; + } + else { + hsz += 3; + erts_factory_proc_prealloc_init(&factory, c_p, hsz); + endp = (byte *) resp_bufp; + term = erts_decode_ext(&factory, (const byte**)&endp, 0); + if (term == THE_NON_VALUE) { + result = ERTS_PORT_OP_BADARG; + } + else { + hp = erts_produce_heap(&factory,3,0); + *retvalp = TUPLE2(hp, am_ok, term); + result = ERTS_PORT_OP_DONE; + } + erts_factory_close(&factory); + } + } if (resp_bufp != &resp_buf[0] - && !(ret_flags & DRIVER_CALL_KEEP_BUFFER)) + && !(ret_flags & DRIVER_CALL_KEEP_BUFFER)) { driver_free(resp_bufp); + } BUMP_REDS(c_p, ERTS_PORT_REDS_CALL); - return ERTS_PORT_OP_DONE; + return result; } case ERTS_TRY_IMM_DRV_CALL_INVALID_PORT: if (bufp != &input_buf[0]) |