Shadow Stack  0.2
 All Classes Namespaces Files Functions Variables Typedefs Macros
message.hpp
Go to the documentation of this file.
1 
2 #ifndef __MESSAGE_HPP__
3 #define __MESSAGE_HPP__
4 
5 #include "utilities.hpp"
6 
7 #include <sys/socket.h>
8 #include <unistd.h>
9 #include <string.h>
10 
11 
12 /*********************************************************/
13 /* */
14 /* Constant */
15 /* */
16 /*********************************************************/
17 
18 
21 #define POINTER_SIZE ( sizeof( void * ) )
22 
24 #define MESSAGE_HEADER_LENGTH 4
25 
27 #define MESSAGE_SIZE ( POINTER_SIZE + MESSAGE_HEADER_LENGTH )
28 
29 
30 /*********************************************************/
31 /* */
32 /* Message classes */
33 /* */
34 /*********************************************************/
35 
36 
40 class Message final {
41 
43  class Msg final {
44 
46 /* clang-format off */
47 #define MESSAGE_INTERNALS( HEADER_ONLY ) \
48  \
49  static const constexpr bool header_only = HEADER_ONLY; \
50  \
51  static const constexpr int size = MESSAGE_SIZE; \
52  \
53  static const constexpr char *const header = Info::header; \
54  \
58  static_assert( strlen( Info::header ) == MESSAGE_HEADER_LENGTH, \
59  "Header is of wrong size." ); \
60  \
61  MessageType<HEADER_ONLY, Info>() = delete;
62  /* clang-format on */
63 
67  static const char *set_length( char *const dst, const char *const src,
68  const int n );
69 
72  template <bool only_header, typename Info> struct MessageType;
73 
74  // Note: **ALL** messages will be of the same size.
75  // Header only messages - the contents of the body do not matter.
76 
78  template <typename Info> struct MessageType<true, Info> final {
79 
80  // Setup the internals of the message
81  MESSAGE_INTERNALS( true )
82 
83 
85  static const char *const message;
86 
87  private:
89  static char internal[size];
90  };
91 
93  template <typename Info> struct MessageType<false, Info> final {
94 
95  // Setup the internals of the message
96  MESSAGE_INTERNALS( false )
97 
98 
99  explicit MessageType<false, Info>( const char *const ptr ) {
100  memcpy( message, header, MESSAGE_HEADER_LENGTH );
101  memcpy( &message[MESSAGE_HEADER_LENGTH], ptr, POINTER_SIZE );
102  }
103 
106  char message[size];
107  };
108 
109 // Remove macros
110 #undef MESSAGE_INTERNALS
111 
112  public:
114  template <typename T> using HeaderOnly = MessageType<true, T>;
115 
117  template <typename T> using WithBody = MessageType<false, T>;
118  };
119 
120 
121  // General Headers
122 
124  struct ContinueInfo final {
126  static constexpr const char *const header = "CONT";
127  };
128 
130  struct CallInfo final {
132  static const constexpr char *const header = "CALL";
133  };
134 
136  struct RetInfo final {
138  static const constexpr char *const header = "RET-";
139  };
140 
141 
143  struct NewSignalInfo final {
145  static constexpr const char *const header = "NEWS";
146  };
147 
149  struct ExecveInfo final {
151  static constexpr const char *const header = "EXEC";
152  };
153 
155  struct ForkInfo final {
157  static const constexpr char *const header = "FORK";
158  };
159 
161  struct ThreadInfo final {
163  static const constexpr char *const header = "THRD";
164  };
165 
166  public:
168  template <class T> static bool is_a_valid( const char *const buffer ) {
169  return !memcmp( buffer, T::header, MESSAGE_HEADER_LENGTH );
170  }
171 
178 
187 };
188 
189 
191 template <typename T> char Message::Msg::MessageType<true, T>::internal[size] = {};
192 
194 template <typename T>
199 
200 
201 /*********************************************************/
202 /* */
203 /* Used to send / recieve messages */
204 /* */
205 /*********************************************************/
206 
207 
209 template <typename Msg> void send_msg( const int sock ) {
210  static_assert( Msg::header_only == true, "wrong send_msg called." );
211  const int bytes_sent = write( sock, Msg::header, Msg::size );
212  Utilities::assert( bytes_sent == Msg::size, "write() failed!" );
213 }
214 
216 template <typename Msg> void send_msg( const int sock, const char *const bdy ) {
217  static_assert( Msg::header_only == false, "wrong send_msg called." );
218  Msg to_send( bdy );
219  const int bytes_sent = write( sock, to_send.message, to_send.size );
220  Utilities::assert( bytes_sent == to_send.size, "write() failed!" );
221 }
222 
224 template <typename Msg> void recv_msg( const int sock ) {
225  static_assert( Msg::header_only == true, "wrong recv_msg called." );
226  char buffer[Msg::size];
227  const int bytes_recv = recv( sock, buffer, Msg::size, MSG_WAITALL );
228  Utilities::assert( bytes_recv == Msg::size, "Did not get full size message!" );
229  const constexpr auto is_msg = Message::is_a_valid<Message::Continue>;
230  Utilities::assert( is_msg( buffer ), "Received incorrect message!" );
231 }
232 
235 template <typename Msg> const char *recv_msg_and_body( const int sock ) {
236  static_assert( Msg::header_only == false, "wrong recv_msg called." );
237  static char buffer[Msg::size];
238  const int bytes_recv = recv( sock, buffer, Msg::size, MSG_WAITALL );
239  Utilities::assert( bytes_recv == Msg::size, "Did not get full size message!" );
240  const constexpr auto is_msg = Message::is_a_valid<Message::Continue>;
241  Utilities::assert( is_msg( buffer ), "Received incorrect message!" );
242  return buffer;
243 }
244 
245 
246 #endif
A class containing the header of Call message.
Definition: message.hpp:136
#define POINTER_SIZE
The size of a pointer in the target program Note: 64 bit can stil handle 32 bit programs.
Definition: message.hpp:21
A class containing the header of NewSignal message.
Definition: message.hpp:143
const Msg::WithBody< CallInfo > Call
A typedef for the call message.
Definition: message.hpp:175
const Msg::HeaderOnly< ForkInfo > Fork
A typedef for the fork message.
Definition: message.hpp:184
const Msg::HeaderOnly< ExecveInfo > Execve
A typedef for the execve message.
Definition: message.hpp:182
A class containing the header of Execve message.
Definition: message.hpp:149
A class containing the header of Fork message.
Definition: message.hpp:155
const Msg::HeaderOnly< ContinueInfo > Continue
A typedef for the continue message.
Definition: message.hpp:173
const Msg::HeaderOnly< NewSignalInfo > NewSignal
A typedef for the new signal message.
Definition: message.hpp:180
#define MESSAGE_HEADER_LENGTH
The number of characters a message header can be.
Definition: message.hpp:24
static void assert(const bool b, const char *const s)
assert b, if false call program_err(s)
Definition: utilities.cpp:89
A class containing the header of Call message.
Definition: message.hpp:130
Defines the types of messages which can be sent.
Definition: message.hpp:43
A class containing the header of Continue message.
Definition: message.hpp:124
const char * recv_msg_and_body(const int sock)
Reads a only Msg from sock This function is NOT re-entrant.
Definition: message.hpp:235
static int sock
Definition: dr_external_ss_events.cpp:14
void recv_msg(const int sock)
Reads a header only Msg from sock.
Definition: message.hpp:224
A class containing the header of Thread message.
Definition: message.hpp:161
static bool is_a_valid(const char *const buffer)
A function used to check if a char * may represent a message of type T.
Definition: message.hpp:168
void send_msg(const int sock)
Sends a header only Msg to sock.
Definition: message.hpp:209
const Msg::WithBody< RetInfo > Ret
A typedef for the ret message.
Definition: message.hpp:177
A class used for defining all message types Messages come in two forms.
Definition: message.hpp:40
A templated message class A valid message is defined by constructing a MessageType around it...
Definition: message.hpp:72
#define MESSAGE_INTERNALS(HEADER_ONLY)
The internals of a message.
Definition: message.hpp:47
const Msg::HeaderOnly< ThreadInfo > Thread
A typedef for the thread message.
Definition: message.hpp:186
static const char * set_length(char *const dst, const char *const src, const int n)
Copies n bytes from src into dst during static initilization If src is less than n bytes...
Definition: message.cpp:9