From 45d37e275d07e3f6d0f24b7a4875f8a44a1d16a6 Mon Sep 17 00:00:00 2001 From: Martin Stein Date: Thu, 17 Oct 2013 00:41:14 +0200 Subject: [PATCH] hw: send request size through UTCB ref #874 --- base-hw/include/kernel/syscalls.h | 7 +++---- base-hw/src/base/ipc.cc | 31 ++++++++++++++++++++++++++++--- base-hw/src/core/kernel/thread.cc | 15 ++++++++------- 3 files changed, 39 insertions(+), 14 deletions(-) diff --git a/base-hw/include/kernel/syscalls.h b/base-hw/include/kernel/syscalls.h index 0da577e241..2198dde0f4 100644 --- a/base-hw/include/kernel/syscalls.h +++ b/base-hw/include/kernel/syscalls.h @@ -335,8 +335,7 @@ namespace Kernel /** * Send IPC request and wait for reply * - * \param id kernel name of the server thread - * \param size size of request message located in the callers UTCB + * \param id kernel name of the server thread * * \retval 0 successful * \retval -1 failed @@ -344,9 +343,9 @@ namespace Kernel * If the call returns successful the callers UTCB provides * a valid reply message and its size. */ - inline int request_and_wait(unsigned const id, size_t const size) + inline int request_and_wait(unsigned const id) { - return (int)syscall(REQUEST_AND_WAIT, id, size); + return (int)syscall(REQUEST_AND_WAIT, id); } diff --git a/base-hw/src/base/ipc.cc b/base-hw/src/base/ipc.cc index 6d3f9d0e3e..7a8df59470 100644 --- a/base-hw/src/base/ipc.cc +++ b/base-hw/src/base/ipc.cc @@ -61,7 +61,7 @@ static void utcb_to_msgbuf(Msgbuf_base * const msgbuf, size_t size) } /** - * Copy message payload with integrated size toion message buffer + * Copy message payload with size header to message buffer * * This function pioneers IPC messages with headers and will * replace utcb_to_msgbuf sometime. @@ -92,6 +92,30 @@ static void msgbuf_to_utcb(Msgbuf_base * const msgbuf, size_t size, } +/** + * Copy message payload with size header to the UTCB + * + * This function pioneers IPC messages with headers and will + * replace msgbuf_to_utcb sometime. + */ +static void msgbuf_to_sized_utcb(Msgbuf_base * const msg_buf, size_t msg_size, + unsigned const local_name) +{ + Native_utcb * const utcb = Thread_base::myself()->utcb(); + enum { NAME_SIZE = sizeof(local_name) }; + size_t const ipc_msg_size = msg_size + NAME_SIZE; + if (ipc_msg_size > utcb->max_ipc_msg_size()) { + kernel_log() << "oversized IPC message\n"; + msg_size = utcb->max_ipc_msg_size() - NAME_SIZE; + } + *(unsigned *)utcb->ipc_msg_base() = local_name; + void * const utcb_msg = (void *)((addr_t)utcb->ipc_msg_base() + NAME_SIZE); + void * const buf_msg = (void *)((addr_t)msg_buf->buf + NAME_SIZE); + memcpy(utcb_msg, buf_msg, msg_size); + utcb->ipc_msg_size(ipc_msg_size); +} + + /***************** ** Ipc_ostream ** *****************/ @@ -136,8 +160,9 @@ void Ipc_client::_call() using namespace Kernel; /* send request and receive reply */ - msgbuf_to_utcb(_snd_msg, _write_offset, Ipc_ostream::_dst.local_name()); - int error = request_and_wait(Ipc_ostream::_dst.dst(), _write_offset); + unsigned const local_name = Ipc_ostream::_dst.local_name(); + msgbuf_to_sized_utcb(_snd_msg, _write_offset, local_name); + int error = request_and_wait(Ipc_ostream::_dst.dst()); if (error) { throw Blocking_canceled(); } sized_utcb_to_msgbuf(_rcv_msg); diff --git a/base-hw/src/core/kernel/thread.cc b/base-hw/src/core/kernel/thread.cc index 0c64e88908..2f5d544c9a 100644 --- a/base-hw/src/core/kernel/thread.cc +++ b/base-hw/src/core/kernel/thread.cc @@ -624,14 +624,15 @@ void Thread::_syscall_wait_for_request() */ void Thread::_syscall_request_and_wait() { - Thread * const dst = Thread::pool()->object(user_arg_1()); - size_t const msg_size = (size_t)user_arg_2(); - assert(dst); - + Thread * const dst = Thread::pool()->object(user_arg_1()); + if (!dst) { + PERR("unkonwn recipient"); + _await_ipc(); + return; + } Ipc_node::send_request_await_reply( - dst, _phys_utcb->base(), msg_size, - _phys_utcb->ipc_msg_base(), - _phys_utcb->max_ipc_msg_size()); + dst, _phys_utcb->ipc_msg_base(), _phys_utcb->ipc_msg_size(), + _phys_utcb->ipc_msg_base(), _phys_utcb->max_ipc_msg_size()); }