From de69ee2e664a81993a950d82b168b607a3056d26 Mon Sep 17 00:00:00 2001 From: Norman Feske Date: Fri, 10 Aug 2012 16:35:57 +0200 Subject: [PATCH] Linux: cleanup system-call bindings This patch simplifies the system call bindings. The common syscall bindings in 'src/platform/' have been reduced to the syscalls needed by non-core programs. The additional syscalls that are needed solely by core have been moved to 'src/core/include/core_linux_syscalls.h'. Furthermore, the resource path is not used outside of core anymore. Hence, we could get rid of the rpath library. The resource-path code has been moved to 'src/core/include/resource_path.h'. The IPC-related parts of 'src/platform' have been moved to the IPC library. So there is now a clean separation between low-level syscall bindings (in 'src/platform') and higher-level code. The code for the socket-descriptor registry is now located in the 'src/base/ipc/socket_descriptor_registry.h' header. The interface is separated from 'ipc.cc' because core needs to access the registry from outside the ipc library. --- base-linux/lib/mk/ipc.mk | 3 +- base-linux/lib/mk/rpath.mk | 6 - base-linux/src/base/ipc/ipc.cc | 278 +++++++++- .../src/base/ipc/socket_descriptor_registry.h | 132 +++++ base-linux/src/base/process/process.cc | 2 +- base-linux/src/core/cpu_session_extension.cc | 2 +- .../src/core/include/core_linux_syscalls.h | 131 +++++ base-linux/src/core/include/resource_path.h | 44 ++ .../src/core/include/server_socket_pair.h | 107 ++++ base-linux/src/core/pd_session_component.cc | 2 +- base-linux/src/core/platform.cc | 10 +- base-linux/src/core/platform_thread.cc | 7 +- base-linux/src/core/ram_session_support.cc | 10 +- base-linux/src/core/rom_session_component.cc | 3 +- base-linux/src/core/target.mk | 5 +- base-linux/src/platform/linux_rpath.cc | 39 -- base-linux/src/platform/linux_rpath.h | 25 - base-linux/src/platform/linux_socket.h | 514 ------------------ base-linux/src/platform/linux_syscalls.h | 132 +---- 19 files changed, 738 insertions(+), 714 deletions(-) delete mode 100644 base-linux/lib/mk/rpath.mk create mode 100644 base-linux/src/base/ipc/socket_descriptor_registry.h create mode 100644 base-linux/src/core/include/core_linux_syscalls.h create mode 100644 base-linux/src/core/include/resource_path.h create mode 100644 base-linux/src/core/include/server_socket_pair.h delete mode 100644 base-linux/src/platform/linux_rpath.cc delete mode 100644 base-linux/src/platform/linux_rpath.h delete mode 100644 base-linux/src/platform/linux_socket.h diff --git a/base-linux/lib/mk/ipc.mk b/base-linux/lib/mk/ipc.mk index 8f972ae80..0664bedce 100644 --- a/base-linux/lib/mk/ipc.mk +++ b/base-linux/lib/mk/ipc.mk @@ -1,5 +1,6 @@ REQUIRES = linux SRC_CC = ipc.cc -LIBS = syscall rpath cap_copy +LIBS = syscall cap_copy +INC_DIR += $(REP_DIR)/src/base/ipc vpath ipc.cc $(REP_DIR)/src/base/ipc diff --git a/base-linux/lib/mk/rpath.mk b/base-linux/lib/mk/rpath.mk deleted file mode 100644 index fc42a899a..000000000 --- a/base-linux/lib/mk/rpath.mk +++ /dev/null @@ -1,6 +0,0 @@ -REQUIRES = linux -SRC_CC = linux_rpath.cc -LIBS = syscall - -vpath linux_rpath.cc $(REP_DIR)/src/platform - diff --git a/base-linux/src/base/ipc/ipc.cc b/base-linux/src/base/ipc/ipc.cc index ba1e01a0c..8ca8aea6c 100644 --- a/base-linux/src/base/ipc/ipc.cc +++ b/base-linux/src/base/ipc/ipc.cc @@ -34,14 +34,21 @@ #include #include +/* local includes */ +#include + /* Linux includes */ -#include #include +#include +#include using namespace Genode; +/****************************** + ** File-descriptor registry ** + ******************************/ Genode::Ep_socket_descriptor_registry *Genode::ep_sd_registry() { @@ -50,6 +57,275 @@ Genode::Ep_socket_descriptor_registry *Genode::ep_sd_registry() } +/******************************************** + ** Communication over Unix-domain sockets ** + ********************************************/ + +/** + * Utility: Return thread ID to which the given socket is directed to + * + * \return -1 if the socket is pointing to a valid entrypoint + */ +static int lookup_tid_by_client_socket(int sd) +{ + sockaddr_un name; + socklen_t name_len = sizeof(name); + int ret = lx_getpeername(sd, (sockaddr *)&name, &name_len); + if (ret < 0) + return -1; + + struct Prefix_len + { + size_t const len; + + static int _init_len(char const *s) + { + char const * const pattern = "/ep-"; + static size_t const pattern_len = Genode::strlen(pattern); + + for (size_t i = 0; Genode::strlen(s + i) >= pattern_len; i++) + if (Genode::strcmp(s + i, pattern, pattern_len) == 0) + return i + pattern_len; + + struct Unexpected_rpath_prefix { }; + throw Unexpected_rpath_prefix(); + } + + Prefix_len(char const *s) : len(_init_len(s)) { } + }; + + /* + * The name of the Unix-domain socket has the form -/ep-. + * We are only interested in the part. Hence, we determine the length + * of the -/ep- portion only once and keep it in a static + * variable. + */ + static Prefix_len prefix_len(name.sun_path); + + unsigned tid = 0; + if (Genode::ascii_to(name.sun_path + prefix_len.len, &tid) == 0) { + PRAW("Error: could not parse tid number"); + return -1; + } + return tid; +} + + +namespace { + + /** + * Message object encapsulating data for sendmsg/recvmsg + */ + struct Message + { + public: + + enum { MAX_SDS_PER_MSG = Genode::Msgbuf_base::MAX_CAPS_PER_MSG }; + + private: + + msghdr _msg; + sockaddr_un _addr; + iovec _iovec; + char _cmsg_buf[CMSG_SPACE(MAX_SDS_PER_MSG*sizeof(int))]; + + unsigned _num_sds; + + public: + + Message(void *buffer, size_t buffer_len) : _num_sds(0) + { + Genode::memset(&_msg, 0, sizeof(_msg)); + + /* initialize control message */ + struct cmsghdr *cmsg; + + _msg.msg_control = _cmsg_buf; + _msg.msg_controllen = sizeof(_cmsg_buf); /* buffer space available */ + _msg.msg_flags |= MSG_CMSG_CLOEXEC; + cmsg = CMSG_FIRSTHDR(&_msg); + cmsg->cmsg_len = CMSG_LEN(0); + cmsg->cmsg_level = SOL_SOCKET; + cmsg->cmsg_type = SCM_RIGHTS; + _msg.msg_controllen = cmsg->cmsg_len; /* actual cmsg length */ + + /* initialize iovec */ + _msg.msg_iov = &_iovec; + _msg.msg_iovlen = 1; + + _iovec.iov_base = buffer; + _iovec.iov_len = buffer_len; + } + + msghdr * msg() { return &_msg; } + + void marshal_socket(int sd) + { + *((int *)CMSG_DATA((cmsghdr *)_cmsg_buf) + _num_sds) = sd; + + _num_sds++; + + struct cmsghdr *cmsg = CMSG_FIRSTHDR(&_msg); + cmsg->cmsg_len = CMSG_LEN(_num_sds*sizeof(int)); + _msg.msg_controllen = cmsg->cmsg_len; /* actual cmsg length */ + } + + void accept_sockets(int num_sds) + { + struct cmsghdr *cmsg = CMSG_FIRSTHDR(&_msg); + cmsg->cmsg_len = CMSG_LEN(num_sds*sizeof(int)); + _msg.msg_controllen = cmsg->cmsg_len; /* actual cmsg length */ + } + + int socket_at_index(int index) const + { + return *((int *)CMSG_DATA((cmsghdr *)_cmsg_buf) + index); + } + + unsigned num_sockets() const + { + struct cmsghdr *cmsg = CMSG_FIRSTHDR(&_msg); + + if (!cmsg) + return 0; + + return (cmsg->cmsg_len - CMSG_ALIGN(sizeof(cmsghdr)))/sizeof(int); + } + }; + +} /* unnamed namespace */ + + +/** + * Utility: Extract socket desriptors from SCM message into 'Genode::Msgbuf' + */ +static void extract_sds_from_message(unsigned start_index, Message const &msg, + Genode::Msgbuf_base &buf) +{ + buf.reset_caps(); + + /* start at offset 1 to skip the reply channel */ + for (unsigned i = start_index; i < msg.num_sockets(); i++) { + + int const sd = msg.socket_at_index(i); + int const id = lookup_tid_by_client_socket(sd); + int const existing_sd = Genode::ep_sd_registry()->lookup_fd_by_global_id(id); + + if (existing_sd >= 0) { + lx_close(sd); + buf.append_cap(existing_sd); + } else { + Genode::ep_sd_registry()->associate(sd, id); + buf.append_cap(sd); + } + } +} + + +/** + * Send request to server and wait for reply + */ +static inline void lx_call(int dst_sd, + Genode::Msgbuf_base &send_msgbuf, size_t send_msg_len, + Genode::Msgbuf_base &recv_msgbuf) +{ + int ret; + Message send_msg(send_msgbuf.buf, send_msg_len); + + /* create reply channel */ + enum { LOCAL_SOCKET = 0, REMOTE_SOCKET = 1 }; + int reply_channel[2]; + + ret = lx_socketpair(AF_UNIX, SOCK_DGRAM | SOCK_CLOEXEC, 0, reply_channel); + if (ret < 0) { + PRAW("lx_socketpair failed with %d", ret); + throw Genode::Ipc_error(); + } + + /* assemble message */ + + /* marshal reply capability */ + send_msg.marshal_socket(reply_channel[REMOTE_SOCKET]); + + /* marshal capabilities contained in 'send_msgbuf' */ + for (unsigned i = 0; i < send_msgbuf.used_caps(); i++) + send_msg.marshal_socket(send_msgbuf.cap(i)); + + ret = lx_sendmsg(dst_sd, send_msg.msg(), 0); + if (ret < 0) { + PRAW("[%d] lx_sendmsg to sd %d failed with %d in lx_call()", + lx_getpid(), dst_sd, ret); + throw Genode::Ipc_error(); + } + + /* receive reply */ + + Message recv_msg(recv_msgbuf.buf, recv_msgbuf.size()); + recv_msg.accept_sockets(Message::MAX_SDS_PER_MSG); + + ret = lx_recvmsg(reply_channel[LOCAL_SOCKET], recv_msg.msg(), 0); + if (ret < 0) { + PRAW("[%d] lx_recvmsg failed with %d in lx_call()", lx_getpid(), ret); + throw Genode::Ipc_error(); + } + + extract_sds_from_message(0, recv_msg, recv_msgbuf); + + /* destroy reply channel */ + lx_close(reply_channel[LOCAL_SOCKET]); + lx_close(reply_channel[REMOTE_SOCKET]); +} + + +/** + * for request from client + * + * \return socket descriptor of reply capability + */ +static inline int lx_wait(Genode::Native_connection_state &cs, + Genode::Msgbuf_base &recv_msgbuf) +{ + Message msg(recv_msgbuf.buf, recv_msgbuf.size()); + + msg.accept_sockets(Message::MAX_SDS_PER_MSG); + + int ret = lx_recvmsg(cs.server_sd, msg.msg(), 0); + if (ret < 0) { + PRAW("lx_recvmsg failed with %d in lx_wait(), sd=%d", ret, cs.server_sd); + throw Genode::Ipc_error(); + } + + int const reply_socket = msg.socket_at_index(0); + + extract_sds_from_message(1, msg, recv_msgbuf); + + return reply_socket; +} + + +/** + * Send reply to client + */ +static inline void lx_reply(int reply_socket, + Genode::Msgbuf_base &send_msgbuf, + size_t msg_len) +{ + Message msg(send_msgbuf.buf, msg_len); + + /* + * Marshall capabilities to be transferred to the client + */ + for (unsigned i = 0; i < send_msgbuf.used_caps(); i++) + msg.marshal_socket(send_msgbuf.cap(i)); + + int ret = lx_sendmsg(reply_socket, msg.msg(), 0); + if (ret < 0) + PRAW("lx_sendmsg failed with %d in lx_reply()", ret); + + lx_close(reply_socket); +} + + /***************** ** Ipc_ostream ** *****************/ diff --git a/base-linux/src/base/ipc/socket_descriptor_registry.h b/base-linux/src/base/ipc/socket_descriptor_registry.h new file mode 100644 index 000000000..29e24a510 --- /dev/null +++ b/base-linux/src/base/ipc/socket_descriptor_registry.h @@ -0,0 +1,132 @@ +/* + * \brief Linux-specific socket-descriptor registry + * \author Norman Feske + * \date 2012-07-26 + * + * We use the names of Unix-domain sockets as keys to uniquely identify + * entrypoints. When receiving a socket descriptor as IPC payload, we first + * lookup the corresponding entrypoint ID. If we already possess a socket + * descriptor pointing to the same entrypoint, we close the received one and + * use the already known descriptor instead. + */ + +/* + * Copyright (C) 2012 Genode Labs GmbH + * + * This file is part of the Genode OS framework, which is distributed + * under the terms of the GNU General Public License version 2. + */ + +#ifndef _BASE__IPC__SOCKET_DESCRIPTOR_REGISTRY_H_ +#define _BASE__IPC__SOCKET_DESCRIPTOR_REGISTRY_H_ + +#include + + +namespace Genode +{ + template + class Socket_descriptor_registry; + + typedef Socket_descriptor_registry<100> Ep_socket_descriptor_registry; + + /** + * Return singleton instance of registry for tracking entrypoint sockets + */ + Ep_socket_descriptor_registry *ep_sd_registry(); +} + + +template +class Genode::Socket_descriptor_registry +{ + public: + + class Limit_reached { }; + class Aliased_global_id { }; + + private: + + struct Entry + { + int fd; + int global_id; + + /** + * Default constructor creates empty entry + */ + Entry() : fd(-1), global_id(-1) { } + + Entry(int fd, int global_id) : fd(fd), global_id(global_id) { } + + bool is_free() const { return fd == -1; } + }; + + Entry _entries[MAX_FDS]; + + Genode::Lock mutable _lock; + + Entry &_find_free_entry() + { + for (unsigned i = 0; i < MAX_FDS; i++) + if (_entries[i].is_free()) + return _entries[i]; + + throw Limit_reached(); + } + + bool _is_registered(int global_id) const + { + for (unsigned i = 0; i < MAX_FDS; i++) + if (_entries[i].global_id == global_id) + return true; + + return false; + } + + public: + + /** + * Register association of socket descriptor and its corresponding ID + * + * \throw Limit_reached + * \throw Aliased_global_id if global ID is already registered + */ + void associate(int sd, int global_id) + { + Genode::Lock::Guard guard(_lock); + + /* ignore invalid capabilities */ + if (sd == -1 || global_id == -1) + return; + + /* + * Check for potential aliasing + * + * We allow any global ID to be present in the registry only once. + */ + if (_is_registered(global_id)) + throw Aliased_global_id(); + + Entry &entry = _find_free_entry(); + entry = Entry(sd, global_id); + } + + /** + * Lookup file descriptor that belongs to specified global ID + * + * \return file descriptor or -1 if lookup failed + */ + int lookup_fd_by_global_id(int global_id) const + { + Genode::Lock::Guard guard(_lock); + + for (unsigned i = 0; i < MAX_FDS; i++) + if (_entries[i].global_id == global_id) + return _entries[i].fd; + + return -1; + } +}; + +#endif /* _BASE__IPC__SOCKET_DESCRIPTOR_REGISTRY_H_ */ diff --git a/base-linux/src/base/process/process.cc b/base-linux/src/base/process/process.cc index e6397936c..b30179153 100644 --- a/base-linux/src/base/process/process.cc +++ b/base-linux/src/base/process/process.cc @@ -63,7 +63,7 @@ extern char **lx_environ; */ static const char *get_env(const char *key) { - Genode::size_t key_len = strlen(key); + Genode::size_t key_len = Genode::strlen(key); for (char **curr = lx_environ; curr && *curr; curr++) if ((Genode::strcmp(*curr, key, key_len) == 0) && (*curr)[key_len] == '=') return (const char *)(*curr + key_len + 1); diff --git a/base-linux/src/core/cpu_session_extension.cc b/base-linux/src/core/cpu_session_extension.cc index 22f8d2155..ad4b22486 100644 --- a/base-linux/src/core/cpu_session_extension.cc +++ b/base-linux/src/core/cpu_session_extension.cc @@ -8,7 +8,7 @@ #include /* Linux includes */ -#include +#include using namespace Genode; diff --git a/base-linux/src/core/include/core_linux_syscalls.h b/base-linux/src/core/include/core_linux_syscalls.h new file mode 100644 index 000000000..2ca0c60d0 --- /dev/null +++ b/base-linux/src/core/include/core_linux_syscalls.h @@ -0,0 +1,131 @@ +/* + * \brief Linux system calls that are used in core only + * \author Norman Feske + * \date 2012-08-10 + */ + +/* + * Copyright (C) 2011-2012 Genode Labs GmbH + * + * This file is part of the Genode OS framework, which is distributed + * under the terms of the GNU General Public License version 2. + */ + +#ifndef _CORE__INCLUDE__CORE_LINUX_SYSCALLS_H_ +#define _CORE__INCLUDE__CORE_LINUX_SYSCALLS_H_ + +/* basic Linux syscall bindings */ +#include +#include + + +/******************************************************* + ** Functions used by core's ram-session support code ** + *******************************************************/ + +inline int lx_mkdir(char const *pathname, mode_t mode) +{ + return lx_syscall(SYS_mkdir, pathname, mode); +} + + +inline int lx_ftruncate(int fd, unsigned long length) +{ + return lx_syscall(SYS_ftruncate, fd, length); +} + + +inline int lx_unlink(const char *fname) +{ + return lx_syscall(SYS_unlink, fname); +} + + +/******************************************************* + ** Functions used by core's rom-session support code ** + *******************************************************/ + +inline int lx_open(const char *pathname, int flags, mode_t mode = 0) +{ + return lx_syscall(SYS_open, pathname, flags, mode); +} + + +inline int lx_stat(const char *path, struct stat64 *buf) +{ +#ifdef _LP64 + return lx_syscall(SYS_stat, path, buf); +#else + return lx_syscall(SYS_stat64, path, buf); +#endif +} + + +/************************************** + ** Process creation and destruction ** + **************************************/ + +/** + * Send signal to process + * + * This function is used by core to kill processes. + */ +inline int lx_kill(int pid, int signal) +{ + return lx_syscall(SYS_kill, pid, signal); +} + + +/******************************************** + ** Communication over Unix-domain sockets ** + ********************************************/ + +#ifdef SYS_socketcall + +inline int lx_socket(int domain, int type, int protocol) +{ + unsigned long args[3] = { domain, type, protocol }; + return lx_socketcall(SYS_SOCKET, args); +} + + +inline int lx_bind(int sockfd, const struct sockaddr *addr, + socklen_t addrlen) +{ + unsigned long args[3] = { sockfd, (unsigned long)addr, addrlen }; + return lx_socketcall(SYS_BIND, args); +} + + +inline int lx_connect(int sockfd, const struct sockaddr *serv_addr, + socklen_t addrlen) +{ + unsigned long args[3] = { sockfd, (unsigned long)serv_addr, addrlen }; + return lx_socketcall(SYS_CONNECT, args); +} + +#else + +inline int lx_socket(int domain, int type, int protocol) +{ + return lx_syscall(SYS_socket, domain, type, protocol); +} + + +inline int lx_bind(int sockfd, const struct sockaddr *addr, + socklen_t addrlen) +{ + return lx_syscall(SYS_bind, sockfd, addr, addrlen); +} + + +inline int lx_connect(int sockfd, const struct sockaddr *serv_addr, + socklen_t addrlen) +{ + return lx_syscall(SYS_connect, sockfd, serv_addr, addrlen); +} + +#endif /* SYS_socketcall */ + + +#endif /* _CORE__INCLUDE__CORE_LINUX_SYSCALLS_H_ */ diff --git a/base-linux/src/core/include/resource_path.h b/base-linux/src/core/include/resource_path.h new file mode 100644 index 000000000..f1bd597e4 --- /dev/null +++ b/base-linux/src/core/include/resource_path.h @@ -0,0 +1,44 @@ +/* + * \brief Genode resource path + * \author Norman Feske + * \date 2012-08-10 + */ + +/* + * Copyright (C) 2012 Genode Labs GmbH + * + * This file is part of the Genode OS framework, which is distributed + * under the terms of the GNU General Public License version 2. + */ + +#ifndef _CORE__INCLUDE__RPATH_H_ +#define _CORE__INCLUDE__RPATH_H_ + +/* Linux syscall bindings */ +#include + +/* Genode includes */ +#include + +/** + * Return resource path for Genode + * + * Genode creates files for dataspaces and endpoints under in this directory. + */ +static inline char const *resource_path() +{ + struct Resource_path + { + char string[32]; + + Resource_path() + { + Genode::snprintf(string, sizeof(string), "/tmp/genode-%d", lx_getuid()); + } + }; + + static Resource_path path; + return path.string; +} + +#endif /* _CORE__INCLUDE__RPATH_H_ */ diff --git a/base-linux/src/core/include/server_socket_pair.h b/base-linux/src/core/include/server_socket_pair.h new file mode 100644 index 000000000..69148a1d3 --- /dev/null +++ b/base-linux/src/core/include/server_socket_pair.h @@ -0,0 +1,107 @@ +/* + * \brief Support for communication over Unix domain sockets + * \author Norman Feske + * \date 2012-08-10 + */ + +/* + * Copyright (C) 2011-2012 Genode Labs GmbH + * + * This file is part of the Genode OS framework, which is distributed + * under the terms of the GNU General Public License version 2. + */ + +#ifndef _CORE__INCLUDE__SERVER_SOCKET_PAIR_H_ +#define _CORE__INCLUDE__SERVER_SOCKET_PAIR_H_ + +/* Linux syscall bindings */ +#include +#include +#include + +/* include from 'src/base/ipc' */ +#include + +/* core-local includes */ +#include + + +/** + * Utility: Create socket address for server entrypoint at thread ID + */ +struct Uds_addr : sockaddr_un +{ + Uds_addr(long thread_id) + { + sun_family = AF_UNIX; + Genode::snprintf(sun_path, sizeof(sun_path), "%s/ep-%ld", + resource_path(), thread_id); + } +}; + + +/** + * Utility: Create named socket pair for given unique ID + */ +static inline Genode::Native_connection_state create_server_socket_pair(long id) +{ + Genode::Native_connection_state ncs; + + /* + * Main thread uses 'Ipc_server' for 'sleep_forever()' only. No need for + * binding. + */ + if (id == -1) + return ncs; + + Uds_addr addr(id); + + /* + * Create server-side socket + */ + ncs.server_sd = lx_socket(AF_UNIX, SOCK_DGRAM | SOCK_CLOEXEC, 0); + if (ncs.server_sd < 0) { + PRAW("Error: Could not create server-side socket (ret=%d)", ncs.server_sd); + class Server_socket_failed { }; + throw Server_socket_failed(); + } + + /* make sure bind succeeds */ + lx_unlink(addr.sun_path); + + int const bind_ret = lx_bind(ncs.server_sd, (sockaddr *)&addr, sizeof(addr)); + if (bind_ret < 0) { + PRAW("Error: Could not bind server socket (ret=%d)", bind_ret); + class Bind_failed { }; + throw Bind_failed(); + } + + /* + * Create client-side socket + */ + ncs.client_sd = lx_socket(AF_UNIX, SOCK_DGRAM | SOCK_CLOEXEC, 0); + if (ncs.client_sd < 0) { + PRAW("Error: Could not create client-side socket (ret=%d)", ncs.client_sd); + class Client_socket_failed { }; + throw Client_socket_failed(); + } + + int const conn_ret = lx_connect(ncs.client_sd, (sockaddr *)&addr, sizeof(addr)); + if (conn_ret < 0) { + PRAW("Error: Could not connect client-side socket (ret=%d)", conn_ret); + class Connect_failed { }; + throw Connect_failed(); + } + + Genode::ep_sd_registry()->associate(ncs.client_sd, id); + + /* + * Wipe Unix domain socket from the file system. It will live as long as + * there exist references to it in the form of file descriptors. + */ + lx_unlink(addr.sun_path); + + return ncs; +} + +#endif /* _CORE__INCLUDE__SERVER_SOCKET_PAIR_H_ */ diff --git a/base-linux/src/core/pd_session_component.cc b/base-linux/src/core/pd_session_component.cc index e3c91e0a0..f9f93b2ba 100644 --- a/base-linux/src/core/pd_session_component.cc +++ b/base-linux/src/core/pd_session_component.cc @@ -20,7 +20,7 @@ #include /* Linux includes */ -#include +#include using namespace Genode; diff --git a/base-linux/src/core/platform.cc b/base-linux/src/core/platform.cc index cd4e7ff20..5b003c4ef 100644 --- a/base-linux/src/core/platform.cc +++ b/base-linux/src/core/platform.cc @@ -17,11 +17,10 @@ /* local includes */ #include "platform.h" #include "core_env.h" +#include "server_socket_pair.h" /* Linux includes */ -#include -#include -#include +#include using namespace Genode; @@ -44,7 +43,7 @@ Platform::Platform() lx_sigaction(2, signal_handler); /* create resource directory under /tmp */ - lx_mkdir(lx_rpath(), S_IRWXU); + lx_mkdir(resource_path(), S_IRWXU); _ram_alloc.add_range((addr_t)_some_mem, sizeof(_some_mem)); } @@ -57,6 +56,7 @@ void Platform::wait_for_exit() catch (Blocking_canceled) { }; } + void Core_parent::exit(int exit_value) { lx_exit_group(exit_value); @@ -71,7 +71,7 @@ namespace Genode { Native_connection_state server_socket_pair() { - return lx_server_socket_pair(Thread_base::myself()->tid().tid); + return create_server_socket_pair(Thread_base::myself()->tid().tid); } } diff --git a/base-linux/src/core/platform_thread.cc b/base-linux/src/core/platform_thread.cc index a4c61ecbb..8f595318a 100644 --- a/base-linux/src/core/platform_thread.cc +++ b/base-linux/src/core/platform_thread.cc @@ -18,10 +18,7 @@ /* local includes */ #include "platform_thread.h" - -/* Linux syscall helper */ -#include -#include +#include "server_socket_pair.h" using namespace Genode; @@ -59,7 +56,7 @@ int Platform_thread::client_sd() { /* construct socket pair on first call */ if (_ncs.client_sd == -1) - _ncs = lx_server_socket_pair(_tid); + _ncs = create_server_socket_pair(_tid); return _ncs.client_sd; } diff --git a/base-linux/src/core/ram_session_support.cc b/base-linux/src/core/ram_session_support.cc index fdc271002..a0e945178 100644 --- a/base-linux/src/core/ram_session_support.cc +++ b/base-linux/src/core/ram_session_support.cc @@ -18,11 +18,11 @@ #include /* local includes */ -#include "ram_session_component.h" +#include +#include /* Linux syscall bindings */ -#include -#include +#include using namespace Genode; @@ -34,8 +34,8 @@ void Ram_session_component::_export_ram_ds(Dataspace_component *ds) { char fname[Linux_dataspace::FNAME_LEN]; - /* create file using a unique file name in 'lx_rpath' */ - snprintf(fname, sizeof(fname), "%s/ds-%d", lx_rpath(), ram_ds_cnt++); + /* create file using a unique file name in the resource path */ + snprintf(fname, sizeof(fname), "%s/ds-%d", resource_path(), ram_ds_cnt++); lx_unlink(fname); int const fd = lx_open(fname, O_CREAT|O_RDWR|O_TRUNC|LX_O_CLOEXEC, S_IRWXU); lx_ftruncate(fd, ds->size()); diff --git a/base-linux/src/core/rom_session_component.cc b/base-linux/src/core/rom_session_component.cc index fde020d67..6473e5851 100644 --- a/base-linux/src/core/rom_session_component.cc +++ b/base-linux/src/core/rom_session_component.cc @@ -16,7 +16,8 @@ */ /* Linux includes */ -#include +#include +#include /* Genode includes */ #include diff --git a/base-linux/src/core/target.mk b/base-linux/src/core/target.mk index 9a972a311..98f54c823 100644 --- a/base-linux/src/core/target.mk +++ b/base-linux/src/core/target.mk @@ -1,6 +1,6 @@ TARGET = core REQUIRES = linux -LIBS = cxx ipc heap core_printf child lock raw_server syscall rpath +LIBS = cxx ipc heap core_printf child lock raw_server syscall GEN_CORE_DIR = $(BASE_DIR)/src/core @@ -25,7 +25,8 @@ SRC_CC = main.cc \ INC_DIR += $(REP_DIR)/src/core/include \ $(GEN_CORE_DIR)/include \ - $(REP_DIR)/src/platform + $(REP_DIR)/src/platform \ + $(REP_DIR)/src/base/ipc HOST_INC_DIR += /usr/include diff --git a/base-linux/src/platform/linux_rpath.cc b/base-linux/src/platform/linux_rpath.cc deleted file mode 100644 index 7f1519f33..000000000 --- a/base-linux/src/platform/linux_rpath.cc +++ /dev/null @@ -1,39 +0,0 @@ -/* - * \brief Linux resource path - * \author Christian Helmuth - * \date 2011-09-25 - */ - -/* - * Copyright (C) 2011-2012 Genode Labs GmbH - * - * This file is part of the Genode OS framework, which is distributed - * under the terms of the GNU General Public License version 2. - */ - -/* Genode includes */ -#include - -#include -#include - - -namespace { - struct Rpath - { - char string[32]; - - Rpath() - { - Genode::snprintf(string, sizeof(string), "/tmp/genode-%d", lx_getuid()); - } - }; -} - - -char const * lx_rpath() -{ - static Rpath rpath; - - return rpath.string; -} diff --git a/base-linux/src/platform/linux_rpath.h b/base-linux/src/platform/linux_rpath.h deleted file mode 100644 index 4f31c4e4b..000000000 --- a/base-linux/src/platform/linux_rpath.h +++ /dev/null @@ -1,25 +0,0 @@ -/* - * \brief Linux resource path - * \author Christian Helmuth - * \date 2011-09-25 - */ - -/* - * Copyright (C) 2011-2012 Genode Labs GmbH - * - * This file is part of the Genode OS framework, which is distributed - * under the terms of the GNU General Public License version 2. - */ - -#ifndef _PLATFORM__LINUX_RPATH_H_ -#define _PLATFORM__LINUX_RPATH_H_ - - -/** - * Return resource path for Genode - * - * Genode creates files for dataspaces and endpoints under in this directory. - */ -char const * lx_rpath(); - -#endif /* _PLATFORM__LINUX_RPATH_H_ */ diff --git a/base-linux/src/platform/linux_socket.h b/base-linux/src/platform/linux_socket.h deleted file mode 100644 index 99086cd1a..000000000 --- a/base-linux/src/platform/linux_socket.h +++ /dev/null @@ -1,514 +0,0 @@ -/* - * \brief Linux socket utilities - * \author Christian Helmuth - * \author Norman Feske - * \date 2012-01-17 - * - * We create one socket under lx_rpath() for each 'Ipc_server'. The naming is - * 'ep--'. - */ - -/* - * Copyright (C) 2011-2012 Genode Labs GmbH - * - * This file is part of the Genode OS framework, which is distributed - * under the terms of the GNU General Public License version 2. - */ - -#ifndef _PLATFORM__LINUX_SOCKET_H_ -#define _PLATFORM__LINUX_SOCKET_H_ - -/* Genode includes */ -#include -#include -#include -#include - -/* Linux includes */ -#include -#include -#include -#include - -/* Genode bindings to Linux kernel */ -#include -#include - - -extern "C" void wait_for_continue(void); -extern "C" int raw_write_str(const char *str); - -#define PRAW(fmt, ...) \ - do { \ - char str[128]; \ - Genode::snprintf(str, sizeof(str), \ - ESC_ERR fmt ESC_END "\n", ##__VA_ARGS__); \ - raw_write_str(str); \ - } while (0) - - -/****************************** - ** File-descriptor registry ** - ******************************/ - -/* - * We use the name of the Unix-domain socket as key to uniquely identify - * entrypoints. When receiving a socket descriptor as IPC payload, we first - * lookup the corresponding entrypoint ID. If we already possess a socket - * descriptor pointing to the same entrypoint, we close the received one and - * use the already known descriptor instead. - */ - -namespace Genode -{ - template - class Socket_descriptor_registry; - - typedef Socket_descriptor_registry<100> Ep_socket_descriptor_registry; - - /** - * Return singleton instance of registry for tracking entrypoint sockets - */ - Ep_socket_descriptor_registry *ep_sd_registry(); -} - - -template -class Genode::Socket_descriptor_registry -{ - public: - - class Limit_reached { }; - class Aliased_global_id { }; - - private: - - struct Entry - { - int fd; - int global_id; - - /** - * Default constructor creates empty entry - */ - Entry() : fd(-1), global_id(-1) { } - - Entry(int fd, int global_id) : fd(fd), global_id(global_id) { } - - bool is_free() const { return fd == -1; } - }; - - Entry _entries[MAX_FDS]; - - Genode::Lock mutable _lock; - - Entry &_find_free_entry() - { - for (unsigned i = 0; i < MAX_FDS; i++) - if (_entries[i].is_free()) - return _entries[i]; - - throw Limit_reached(); - } - - bool _is_registered(int global_id) const - { - for (unsigned i = 0; i < MAX_FDS; i++) - if (_entries[i].global_id == global_id) - return true; - - return false; - } - - public: - - /** - * Register association of socket descriptor and its corresponding ID - * - * \throw Limit_reached - * \throw Aliased_global_id if global ID is already registered - */ - void associate(int sd, int global_id) - { - Genode::Lock::Guard guard(_lock); - - /* ignore invalid capabilities */ - if (sd == -1 || global_id == -1) - return; - - /* - * Check for potential aliasing - * - * We allow any global ID to be present in the registry only once. - */ - if (_is_registered(global_id)) { - PRAW("attempted to register global ID %d twice", global_id); - throw Aliased_global_id(); - } - - Entry &entry = _find_free_entry(); - entry = Entry(sd, global_id); - } - - /** - * Lookup file descriptor that belongs to specified global ID - * - * \return file descriptor or -1 if lookup failed - */ - int lookup_fd_by_global_id(int global_id) const - { - Genode::Lock::Guard guard(_lock); - - for (unsigned i = 0; i < MAX_FDS; i++) - if (_entries[i].global_id == global_id) - return _entries[i].fd; - - return -1; - } -}; - - -/** - * Utility: Create socket address for server entrypoint at thread ID - */ -struct Uds_addr : sockaddr_un -{ - Uds_addr(long thread_id) - { - sun_family = AF_UNIX; - Genode::snprintf(sun_path, sizeof(sun_path), "%s/ep-%ld", - lx_rpath(), thread_id); - } -}; - - - -/** - * Utility: Return thread ID to which the given socket is directed to - * - * \return -1 if the socket is pointing to a valid entrypoint - */ -static int lookup_tid_by_client_socket(int sd) -{ - sockaddr_un name; - socklen_t name_len = sizeof(name); - int ret = lx_getpeername(sd, (sockaddr *)&name, &name_len); - if (ret < 0) - return -1; - - /* - * The socket name has the form '/ep-'. Hence, to determine the - * tid, we have to skip 'strlen(rpath)' and 'strlen("/ep-"). We use static - * variables to determine length of 'rpath' only once because it is not - * going to change at runtime. - */ - static size_t const rpath_len = Genode::strlen(lx_rpath()); - static size_t const ep_suffix = Genode::strlen("/ep-"); - - /* - * Reply capabilities do not have a name because they are created via - * 'socketpair'. Check if this function is called with such a socket - * descriptor as argument. - */ - if (rpath_len + ep_suffix >= name_len) { - PRAW("Error: unexpectedly short socket name"); - return -1; - } - - unsigned tid = 0; - if (Genode::ascii_to(name.sun_path + rpath_len + ep_suffix, &tid) == 0) { - PRAW("Error: could not parse tid number"); - return -1; - } - return tid; -} - - -namespace { - - /** - * Message object encapsulating data for sendmsg/recvmsg - */ - struct Message - { - public: - - enum { MAX_SDS_PER_MSG = Genode::Msgbuf_base::MAX_CAPS_PER_MSG }; - - private: - - msghdr _msg; - sockaddr_un _addr; - iovec _iovec; - char _cmsg_buf[CMSG_SPACE(MAX_SDS_PER_MSG*sizeof(int))]; - - unsigned _num_sds; - - public: - - Message(void *buffer, size_t buffer_len) : _num_sds(0) - { - memset(&_msg, 0, sizeof(_msg)); - - /* initialize control message */ - struct cmsghdr *cmsg; - - _msg.msg_control = _cmsg_buf; - _msg.msg_controllen = sizeof(_cmsg_buf); /* buffer space available */ - _msg.msg_flags |= MSG_CMSG_CLOEXEC; - cmsg = CMSG_FIRSTHDR(&_msg); - cmsg->cmsg_len = CMSG_LEN(0); - cmsg->cmsg_level = SOL_SOCKET; - cmsg->cmsg_type = SCM_RIGHTS; - _msg.msg_controllen = cmsg->cmsg_len; /* actual cmsg length */ - - /* initialize iovec */ - _msg.msg_iov = &_iovec; - _msg.msg_iovlen = 1; - - _iovec.iov_base = buffer; - _iovec.iov_len = buffer_len; - } - - msghdr * msg() { return &_msg; } - - void marshal_socket(int sd) - { - *((int *)CMSG_DATA((cmsghdr *)_cmsg_buf) + _num_sds) = sd; - - _num_sds++; - - struct cmsghdr *cmsg = CMSG_FIRSTHDR(&_msg); - cmsg->cmsg_len = CMSG_LEN(_num_sds*sizeof(int)); - _msg.msg_controllen = cmsg->cmsg_len; /* actual cmsg length */ - } - - void accept_sockets(int num_sds) - { - struct cmsghdr *cmsg = CMSG_FIRSTHDR(&_msg); - cmsg->cmsg_len = CMSG_LEN(num_sds*sizeof(int)); - _msg.msg_controllen = cmsg->cmsg_len; /* actual cmsg length */ - } - - int socket_at_index(int index) const - { - return *((int *)CMSG_DATA((cmsghdr *)_cmsg_buf) + index); - } - - unsigned num_sockets() const - { - struct cmsghdr *cmsg = CMSG_FIRSTHDR(&_msg); - - if (!cmsg) - return 0; - - return (cmsg->cmsg_len - CMSG_ALIGN(sizeof(cmsghdr)))/sizeof(int); - } - }; - -} /* unnamed namespace */ - - -/** - * Utility: Extract socket desriptors from SCM message into 'Genode::Msgbuf' - */ -static void extract_sds_from_message(unsigned start_index, Message const &msg, - Genode::Msgbuf_base &buf) -{ - buf.reset_caps(); - - /* start at offset 1 to skip the reply channel */ - for (unsigned i = start_index; i < msg.num_sockets(); i++) { - - int const sd = msg.socket_at_index(i); - int const id = lookup_tid_by_client_socket(sd); - int const existing_sd = Genode::ep_sd_registry()->lookup_fd_by_global_id(id); - - if (existing_sd >= 0) { - lx_close(sd); - buf.append_cap(existing_sd); - } else { - Genode::ep_sd_registry()->associate(sd, id); - buf.append_cap(sd); - } - } -} - - -class Server_socket_failed { }; -class Client_socket_failed { }; -class Bind_failed { }; -class Connect_failed { }; - - -/** - * Utility: Create named socket pair for given thread - * - * \throw Server_socket_failed - * \throw Client_socket_failed - * \throw Bind_failed - * \throw Connect_failed - */ -static inline Genode::Native_connection_state lx_server_socket_pair(long thread_id) -{ - Genode::Native_connection_state ncs; - - /* - * Main thread uses 'Ipc_server' for 'sleep_forever()' only. No need for - * binding. - */ - if (thread_id == -1) - return ncs; - - Uds_addr addr(thread_id); - - /* - * Create server-side socket - */ - ncs.server_sd = lx_socket(AF_UNIX, SOCK_DGRAM | SOCK_CLOEXEC, 0); - if (ncs.server_sd < 0) { - PRAW("Error: Could not create server-side socket (ret=%d)", ncs.server_sd); - throw Server_socket_failed(); - } - - /* make sure bind succeeds */ - lx_unlink(addr.sun_path); - - int const bind_ret = lx_bind(ncs.server_sd, (sockaddr *)&addr, sizeof(addr)); - if (bind_ret < 0) { - PRAW("Error: Could not bind server socket (ret=%d)", bind_ret); - throw Bind_failed(); - } - - /* - * Create client-side socket - */ - ncs.client_sd = lx_socket(AF_UNIX, SOCK_DGRAM | SOCK_CLOEXEC, 0); - if (ncs.client_sd < 0) { - PRAW("Error: Could not create client-side socket (ret=%d)", ncs.client_sd); - throw Client_socket_failed(); - } - - int const conn_ret = lx_connect(ncs.client_sd, (sockaddr *)&addr, sizeof(addr)); - if (conn_ret < 0) { - PRAW("Error: Could not connect client-side socket (ret=%d)", conn_ret); - throw Connect_failed(); - } - - int const tid = lookup_tid_by_client_socket(ncs.client_sd); - Genode::ep_sd_registry()->associate(ncs.client_sd, tid); - - /* - * Wipe Unix domain socket from the file system. It will live as long as - * there exist references to it in the form of file descriptors. - */ - lx_unlink(addr.sun_path); - - return ncs; -} - - -/** - * Utility: Send request to server and wait for reply - */ -static inline void lx_call(int dst_sd, - Genode::Msgbuf_base &send_msgbuf, size_t send_msg_len, - Genode::Msgbuf_base &recv_msgbuf) -{ - int ret; - Message send_msg(send_msgbuf.buf, send_msg_len); - - /* create reply channel */ - enum { LOCAL_SOCKET = 0, REMOTE_SOCKET = 1 }; - int reply_channel[2]; - - ret = lx_socketpair(AF_UNIX, SOCK_DGRAM | SOCK_CLOEXEC, 0, reply_channel); - if (ret < 0) { - PRAW("lx_socketpair failed with %d", ret); - throw Genode::Ipc_error(); - } - - /* assemble message */ - - /* marshal reply capability */ - send_msg.marshal_socket(reply_channel[REMOTE_SOCKET]); - - /* marshal capabilities contained in 'send_msgbuf' */ - for (unsigned i = 0; i < send_msgbuf.used_caps(); i++) - send_msg.marshal_socket(send_msgbuf.cap(i)); - - ret = lx_sendmsg(dst_sd, send_msg.msg(), 0); - if (ret < 0) { - PRAW("[%d] lx_sendmsg to sd %d failed with %d in lx_call()", - lx_getpid(), dst_sd, ret); - throw Genode::Ipc_error(); - } - - /* receive reply */ - - Message recv_msg(recv_msgbuf.buf, recv_msgbuf.size()); - recv_msg.accept_sockets(Message::MAX_SDS_PER_MSG); - - ret = lx_recvmsg(reply_channel[LOCAL_SOCKET], recv_msg.msg(), 0); - if (ret < 0) { - PRAW("[%d] lx_recvmsg failed with %d in lx_call()", lx_getpid(), ret); - throw Genode::Ipc_error(); - } - - extract_sds_from_message(0, recv_msg, recv_msgbuf); - - /* destroy reply channel */ - lx_close(reply_channel[LOCAL_SOCKET]); - lx_close(reply_channel[REMOTE_SOCKET]); -} - - -/** - * Utility: Wait for request from client - * - * \return socket descriptor of reply capability - */ -static inline int lx_wait(Genode::Native_connection_state &cs, - Genode::Msgbuf_base &recv_msgbuf) -{ - Message msg(recv_msgbuf.buf, recv_msgbuf.size()); - - msg.accept_sockets(Message::MAX_SDS_PER_MSG); - - int ret = lx_recvmsg(cs.server_sd, msg.msg(), 0); - if (ret < 0) { - PRAW("lx_recvmsg failed with %d in lx_wait(), sd=%d", ret, cs.server_sd); - throw Genode::Ipc_error(); - } - - int const reply_socket = msg.socket_at_index(0); - - extract_sds_from_message(1, msg, recv_msgbuf); - - return reply_socket; -} - - -/** - * Utility: Send reply to client - */ -static inline void lx_reply(int reply_socket, - Genode::Msgbuf_base &send_msgbuf, - size_t msg_len) -{ - Message msg(send_msgbuf.buf, msg_len); - - /* - * Marshall capabilities to be transferred to the client - */ - for (unsigned i = 0; i < send_msgbuf.used_caps(); i++) - msg.marshal_socket(send_msgbuf.cap(i)); - - int ret = lx_sendmsg(reply_socket, msg.msg(), 0); - if (ret < 0) - PRAW("lx_sendmsg failed with %d in lx_reply()", ret); - - lx_close(reply_socket); -} - -#endif /* _PLATFORM__LINUX_SOCKET_H_ */ diff --git a/base-linux/src/platform/linux_syscalls.h b/base-linux/src/platform/linux_syscalls.h index 844907db7..62b04d8de 100644 --- a/base-linux/src/platform/linux_syscalls.h +++ b/base-linux/src/platform/linux_syscalls.h @@ -1,5 +1,5 @@ /* - * \brief Linux system-call wrappers + * \brief Linux system-call bindings * \author Norman Feske * \date 2008-10-22 * @@ -7,8 +7,8 @@ * interface. * * From within the framework libraries, we have to use the Linux syscall - * interface directly rather than relying on convenient libC functions to be - * able to link this part of the framework to a custom libC. Otherwise, we + * interface directly rather than relying on convenient libc functions to be + * able to link this part of the framework to a custom libc. Otherwise, we * would end up with very nasty cyclic dependencies when using framework * functions such as IPC from the libC back end. * @@ -36,14 +36,33 @@ #include #include #include -#include #include -#include /* Genode includes */ #include +#include +/*********************************** + ** Low-level debugging utilities ** + ***********************************/ + +extern "C" void wait_for_continue(void); +extern "C" int raw_write_str(const char *str); + +#define PRAW(fmt, ...) \ + do { \ + char str[128]; \ + Genode::snprintf(str, sizeof(str), \ + ESC_ERR fmt ESC_END "\n", ##__VA_ARGS__); \ + raw_write_str(str); \ + } while (0) + + +/********************************************************* + ** System-call bindings implemented in syscall library ** + *********************************************************/ + extern "C" long lx_syscall(int number, ...); extern "C" int lx_clone(int (*fn)(void *), void *child_stack, int flags, void *arg); @@ -65,24 +84,12 @@ inline int lx_close(int fd) } -inline int lx_dup(int fd) -{ - return lx_syscall(SYS_dup, fd); -} - - inline int lx_dup2(int fd, int to) { return lx_syscall(SYS_dup2, fd, to); } -inline int lx_unlink(const char *fname) -{ - return lx_syscall(SYS_unlink, fname); -} - - /***************************************** ** Functions used by the IPC framework ** *****************************************/ @@ -97,14 +104,6 @@ inline int lx_socketcall(int call, unsigned long *args) return res; } - -inline int lx_socket(int domain, int type, int protocol) -{ - unsigned long args[3] = { domain, type, protocol }; - return lx_socketcall(SYS_SOCKET, args); -} - - inline int lx_socketpair(int domain, int type, int protocol, int sd[2]) { unsigned long args[4] = { domain, type, protocol, (unsigned long)sd }; @@ -112,22 +111,6 @@ inline int lx_socketpair(int domain, int type, int protocol, int sd[2]) } -inline int lx_bind(int sockfd, const struct sockaddr *addr, - socklen_t addrlen) -{ - unsigned long args[3] = { sockfd, (unsigned long)addr, addrlen }; - return lx_socketcall(SYS_BIND, args); -} - - -inline int lx_connect(int sockfd, const struct sockaddr *serv_addr, - socklen_t addrlen) -{ - unsigned long args[3] = { sockfd, (unsigned long)serv_addr, addrlen }; - return lx_socketcall(SYS_CONNECT, args); -} - - inline int lx_sendmsg(int sockfd, const struct msghdr *msg, int flags) { unsigned long args[3] = { sockfd, (unsigned long)msg, flags }; @@ -150,25 +133,6 @@ inline int lx_getpeername(int sockfd, struct sockaddr *name, socklen_t *namelen) #else -inline int lx_socket(int domain, int type, int protocol) -{ - return lx_syscall(SYS_socket, domain, type, protocol); -} - -inline int lx_bind(int sockfd, const struct sockaddr *addr, - socklen_t addrlen) -{ - return lx_syscall(SYS_bind, sockfd, addr, addrlen); -} - - -inline int lx_connect(int sockfd, const struct sockaddr *serv_addr, - socklen_t addrlen) -{ - return lx_syscall(SYS_connect, sockfd, serv_addr, addrlen); -} - - inline int lx_getpeername(int s, struct sockaddr *name, socklen_t *namelen) { return lx_syscall(SYS_getpeername, s, name, namelen); @@ -209,12 +173,6 @@ inline void lx_exit_group(int status) /* O_CLOEXEC is a GNU extension so we provide it here */ enum { LX_O_CLOEXEC = 02000000 }; -inline int lx_open(const char *pathname, int flags, mode_t mode = 0) -{ - return lx_syscall(SYS_open, pathname, flags, mode); -} - - inline void *lx_mmap(void *start, Genode::size_t length, int prot, int flags, int fd, off_t offset) { @@ -262,36 +220,6 @@ inline Genode::addr_t lx_vm_reserve(Genode::addr_t base, Genode::size_t size) } -/******************************************************* - ** Functions used by core's ram-session support code ** - *******************************************************/ - -inline int lx_mkdir(char const *pathname, mode_t mode) -{ - return lx_syscall(SYS_mkdir, pathname, mode); -} - - -inline int lx_ftruncate(int fd, unsigned long length) -{ - return lx_syscall(SYS_ftruncate, fd, length); -} - - -/******************************************************* - ** Functions used by core's rom-session support code ** - *******************************************************/ - -inline int lx_stat(const char *path, struct stat64 *buf) -{ -#ifdef _LP64 - return lx_syscall(SYS_stat, path, buf); -#else - return lx_syscall(SYS_stat64, path, buf); -#endif -} - - /*********************************************************************** ** Functions used by thread lib and core's cancel-blocking mechanism ** ***********************************************************************/ @@ -354,17 +282,6 @@ inline int lx_sigaction(int signum, void (*handler)(int)) } -/** - * Send signal to process - * - * This function is used by core to kill processes. - */ -inline int lx_kill(int pid, int signal) -{ - return lx_syscall(SYS_kill, pid, signal); -} - - /** * Send signal to thread * @@ -483,4 +400,5 @@ inline bool lx_sigsetmask(int signum, bool state) return old_sigmask.is_set(signum); } + #endif /* _PLATFORM__LINUX_SYSCALLS_H_ */