-
Notifications
You must be signed in to change notification settings - Fork 71
Expand file tree
/
Copy pathCommon.h
More file actions
146 lines (127 loc) · 5.87 KB
/
Common.h
File metadata and controls
146 lines (127 loc) · 5.87 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
/*
===========================================================================
Daemon BSD Source Code
Copyright (c) 2013-2016, Daemon Developers
All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above copyright
notice, this list of conditions and the following disclaimer in the
documentation and/or other materials provided with the distribution.
* Neither the name of the Daemon developers nor the
names of its contributors may be used to endorse or promote products
derived from this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
DISCLAIMED. IN NO EVENT SHALL DAEMON DEVELOPERS BE LIABLE FOR ANY
DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
===========================================================================
*/
#ifndef COMMON_IPC_COMMON_H_
#define COMMON_IPC_COMMON_H_
#include <utility>
#include "common/System.h"
/*
* Contains definitions that are common to all IPC methods so that they are consistent
*/
namespace IPC {
/*
* IPC is everything that is related to the communication between the engine and
* the VMs: in NaCl they are in different processes which means that communication
* has to be Inter-Process Communication, via sockets and shared memory.
* The most basic level of communication goes through a socket and is somewhat
* expensive (10us overhead for a synchronous message, 1us for an async one) but
* it has a strong ordering of messages and is the only way to wait one another
* process: spinlocks in shared memory would prevent the OS from rescheduling etc.
* For larger but very asynchronous messages, there is a command buffer in shared
* memory that is more efficient but doesn't give a guarantee on when the messages
* will be received.
*/
/*
* IPC descriptor which can be sent over a socket. You should treat this as an
* opaque type and not access any of the fields directly.
*/
struct FileDesc {
Sys::OSHandle handle;
#ifndef __native_client__
int type;
union {
uint64_t size;
int32_t flags;
};
#endif
void Close() const;
};
// Version of the protocol for detecting what ABI version the VM has upon startup
constexpr uint32_t ABI_VERSION_DETECTION_ABI_VERSION = 5;
// Version for the syscall signatures between engine and VM. This must change if the syscall
// IDs, argument types, or return types change, or if serialization procedures change.
// This is updated by update-version-number.py when a "major" release is indicated.
// For the master branch with a stable ABI, this follows Daemon major versions.
// For next-release branches, the convention is to use "test/<next release version>". On
// the next-release branch the ABI is unstable so any two commits may be incompatible.
constexpr const char* SYSCALL_ABI_VERSION = "test/0.57.0";
/*
* The messages sent between the VM and the engine are defined by a numerical
* ID used for dispatch, a list of input types and an optional list of return
* types. The ID is on 32 bits with usually 16 bits for coarse dispatch (at the
* services level) and 16 bits for fine dispatch (function level).
*/
// Special message ID used to indicate an RPC return and VM exit
const uint32_t ID_RETURN = 0xffffffff;
const uint32_t ID_EXIT = 0xfffffffe;
// Combine a major and minor ID into a single number.
// TODO we use a template, because we need the ID to be part of template
// arguments and some compilers do not support constexpr yet.
template<uint16_t Major, uint16_t Minor> struct Id {
enum {
value = (Major << 16) + Minor
};
};
/*
* Asynchronous message which does not wait for a reply, the argument types
* can be any serializable type, you can declare a message type like so:
*
* using MyMethodMsg = IPC::Message<IPC::Id<MY_MODULE, MY_METHOD>, std::string, int, bool>;
*/
template<typename Id, typename... T> struct Message {
enum {
id = Id::value
};
using Inputs = std::tuple<T...>;
};
// Reply class which should only be used for the second parameter of SyncMessage
template<typename... T> struct Reply {
using Outputs = std::tuple<T...>;
};
/*
* Synchronous message which waits for a reply. The reply can contain data. Both
* the input and output types can be any serializable type, you can declare a
* synchronous message type like so:
*
* using MyMethodMsg = IPC::SyncMessage<
* Message<IPC::Id<MY_MODULE, MY_METHOD>, std::string, int, bool>,
* IPC::Reply<std::string>
* >;
*
* You can skip the Reply part if there is no return value, this is useful for
* messages whose invocation will contain other sync messages, such as most
* Engine -> VM messages.
*/
template<typename Msg, typename Reply = Reply<>> struct SyncMessage {
enum {
id = Msg::id
};
using Inputs = typename Msg::Inputs;
using Outputs = typename Reply::Outputs;
};
} // namespace IPC
#endif // COMMON_IPC_COMMON_H_