]> git.buserror.net Git - polintos/scott/priv.git/blob - include/c++/orb.h
ORBMM changes and other stuff
[polintos/scott/priv.git] / include / c++ / orb.h
1 #ifndef _CPP_ORB_H
2 #define _CPP_ORB_H
3
4 #include <stdint.h>
5 #include <stddef.h>
6 #include <string.h>
7
8 namespace System {
9         struct _i_Object;
10
11         namespace Mem {
12                 struct Region;
13         }
14
15         namespace RunTime {
16                 class ORBMM {
17                         void *priv;
18                         
19                 public:
20                         class AllocGroup {
21                                 friend class ORBMM;
22                         };
23                         
24                         typedef ::System::Mem::Region Region;
25                         
26                         ORBMM();
27                         
28                         void *alloc(size_t size, int refs = 1);
29                         void retain(void *ptr, int refs = 1);
30                         void release(void *ptr, int refs = 1);
31                         void add_region(Region region, bool unmap_orig, int refs = 1);
32                 };
33                 
34                 extern ORBMM *orbmm;
35                 
36                 // FIXME: should be an IDL exception
37                 struct ArrayException
38                 {
39                 };
40                 
41                 class NullArray {
42                 };
43                 
44                 static const NullArray nullarray = {};
45                 
46                 template<typename T> struct MutableArray {
47                         T *ptr;
48                         size_t count;
49                 
50                         bool valid_index(size_t index)
51                         {
52                                 return index >= 0 && index < count;
53                         }
54                         
55                         T &operator[](size_t index)
56                         {
57 #ifndef POLINTOS_NO_ARRAY_BOUNDS_CHECK
58                                 if (!valid_index(index))
59                                         throw ArrayException();
60 #endif
61                 
62                                 return ptr[index];
63                         }
64                         
65                         MutableArray()
66                         {
67                                 ptr = NULL;
68                                 count = 0;
69                         }
70                         
71                         MutableArray(NullArray na)
72                         {
73                                 ptr = NULL;
74                                 count = 0;
75                         }
76                         
77                         MutableArray(T *PTR, size_t COUNT)
78                         {
79                                 ptr = PTR;
80                                 count = COUNT;
81                         }
82                         
83                         MutableArray &slice_nocheck(size_t first, size_t newcount)
84                         {
85                                 MutableArray ret;
86                                 ret.ptr = ptr + first;
87                                 ret.count = newcount;
88                                 return ret;
89                         }
90
91                         MutableArray &slice_nocheck(size_t first)
92                         {
93                                 MutableArray ret;
94                                 ret.ptr = ptr + first;
95                                 ret.count = count - first;
96                                 return ret;
97                         }
98
99                         MutableArray &slice(size_t first, size_t count)
100                         {
101 #ifndef POLINTOS_NO_ARRAY_BOUNDS_CHECK
102                                 if (!valid_index(first) || !valid_index(first + count - 1))
103                                         throw ArrayException();
104 #endif
105                                 
106                                 return slice_nocheck(first, count);
107                         }
108
109                         MutableArray &slice(size_t first)
110                         {
111 #ifndef POLINTOS_NO_ARRAY_BOUNDS_CHECK
112                                 if (!valid_index(first))
113                                         throw ArrayException();
114 #endif
115                                 
116                                 return slice_nocheck(first);
117                         }
118                         
119                         MutableArray copy()
120                         {
121                                 MutableArray new_arr;
122                                 new_arr.ptr = new(orbmm) T[count];
123                                 new_arr.count = count;
124                                 memcpy(new_arr.ptr, ptr, count);
125                                 return new_arr;
126                         }
127                 };
128
129                 template<typename T> struct Array {
130                         const T *ptr;
131                         size_t count;
132                 
133                         bool valid_index(size_t index)
134                         {
135                                 return index >= 0 && index < count;
136                         }
137                         
138                         const T &operator[](size_t index)
139                         {
140 #ifndef POLINTOS_NO_ARRAY_BOUNDS_CHECK
141                                 if (!valid_index(index))
142                                         throw ArrayException();
143 #endif
144                 
145                                 return ptr[index];
146                         }
147                         
148                         Array()
149                         {
150                                 ptr = NULL;
151                                 count = 0;
152                         }
153                         
154                         Array(NullArray na)
155                         {
156                                 ptr = NULL;
157                                 count = 0;
158                         }
159                         
160                         Array(const T *PTR, size_t COUNT)
161                         {
162                                 ptr = PTR;
163                                 count = COUNT;
164                         }
165                         
166                         Array(MutableArray<T> ma)
167                         {
168                                 ptr = ma.ptr;
169                                 count = ma.count;
170                         }
171                         
172                         MutableArray<T> constcast()
173                         {
174                                 MutableArray<T> ma;
175                                 ma.ptr = const_cast<T>(ptr);
176                                 ma.count = count;
177                                 return ma;
178                         }
179                         
180                         Array &slice_nocheck(size_t first, size_t newcount)
181                         {
182                                 Array ret;
183                                 ret.ptr = ptr + first;
184                                 ret.count = newcount;
185                                 return ret;
186                         }
187
188                         Array &slice_nocheck(size_t first)
189                         {
190                                 Array ret;
191                                 ret.ptr = ptr + first;
192                                 ret.count = count - first;
193                                 return ret;
194                         }
195
196                         Array &slice(size_t first, size_t count)
197                         {
198 #ifndef POLINTOS_NO_ARRAY_BOUNDS_CHECK
199                                 if (!valid_index(first) || !valid_index(first + count - 1))
200                                         throw ArrayException();
201 #endif
202                                 
203                                 return slice_nocheck(first, count);
204                         }
205
206                         Array &slice(size_t first)
207                         {
208 #ifndef POLINTOS_NO_ARRAY_BOUNDS_CHECK
209                                 if (!valid_index(first))
210                                         throw ArrayException();
211 #endif
212                                 
213                                 return slice_nocheck(first);
214                         }
215                         
216                         MutableArray<T> copy()
217                         {
218                                 MutableArray<T> new_arr;
219                                 new_arr.ptr = new(orbmm) T[count];
220                                 new_arr.count = count;
221                                 memcpy(new_arr.ptr, ptr, count);
222                                 return new_arr;
223                         }
224                 };
225
226                 static inline Array<uint8_t> countarray(const char *ptr)
227                 {
228                         Array<uint8_t> ret;
229                         ret.ptr = reinterpret_cast<const uint8_t *>(ptr);
230                         ret.count = strlen(ptr);
231                         return ret;
232                 }
233
234                 static inline MutableArray<uint8_t> countarray(char *ptr)
235                 {
236                         MutableArray<uint8_t> ret;
237                         ret.ptr = reinterpret_cast<uint8_t *>(ptr);
238                         ret.count = strlen(ptr);
239                         return ret;
240                 }
241                 
242                 struct IFaceTable {
243                         const unsigned long *const guid;
244                         const ptrdiff_t offset;
245                 };
246                 
247                 struct VStructInfo {
248                         // List of GUIDs of the struct and its superstructs,
249                         // starting with System.VStruct and ending with
250                         // the concrete struct.
251                         
252                         const unsigned long *const *const guids;
253
254                         // Length of inheritance chain; 1 for System.VStruct
255                         
256                         const int chainlen;
257                 };
258                 
259                 uintptr_t downcast(::System::_i_Object *obj,
260                                    const unsigned long *new_guid);
261
262                 static inline bool guids_equal(const unsigned long *guid1,
263                                                const unsigned long *guid2)
264                 {
265                         return (guid1[0] == guid2[0] && 
266                                 guid1[1] == guid2[1] &&
267                                 (sizeof(long) == 8 ||
268                                  (guid1[2] == guid2[2] &&
269                                   guid1[3] == guid2[3])));
270                 }
271                 
272                 // Return the caller's PC.  It'd be nice if GCC had a builtin for
273                 // the current PC, so that a simple relocation could be used rather
274                 // than a function call.  OPT: put this in lowlevel-lib, so that
275                 // architectures can provide a faster version.
276                 
277                 unsigned long get_pc();
278                 
279                 struct ParamInfoBlock {
280                         uintptr_t buffer_size;
281                         uintptr_t copy_size;
282                         uintptr_t *objlist_ptr;
283                         uintptr_t objlist_len;
284                         uintptr_t num_segments;
285
286                         struct Segment {
287                                 void *ptr;
288                                 uintptr_t len;
289                                 uintptr_t flags;
290                                 uintptr_t reserved;
291                         } segments[0];
292                 };
293         }
294         
295         namespace Priv {
296                 bool in_kernel()
297                 {
298 #ifdef _KERNEL
299                         return true;
300 #else
301                         return false;
302 #endif
303                 }
304         };
305 }
306
307 inline void *operator new(size_t len, ::System::RunTime::ORBMM *orbmm,
308                           int refs = 1)
309 {
310         return orbmm->alloc(len, refs);
311 }
312
313 inline void *operator new[](size_t len, ::System::RunTime::ORBMM *orbmm,
314                             int refs = 1)
315 {
316         return orbmm->alloc(len, refs);
317 }
318
319 inline void operator delete(void *ptr, ::System::RunTime::ORBMM *orbmm,
320                             int refs = 1)
321 {
322         orbmm->release(ptr, refs);
323 }
324
325 inline void operator delete[](void *ptr, ::System::RunTime::ORBMM *orbmm,
326                               int refs = 1)
327 {
328         orbmm->release(ptr, refs);
329 }
330
331 // This is a macro rather than an inline template function so that the
332 // caller shows up as file/line number in the debugging information rather
333 // than this header file, and so that a variable argument list can be
334 // passed to a fixed arg ctor.
335 //
336 // To throw an IDL exception of type Foo, do this:
337 // throw_idl(Foo, args, to, foo);
338
339 #ifndef POLINTOS_NO_THROW_IDL
340 #define throw_idl(T, args...) do { \
341         throw T(NULL, NULL, \
342                 new(::System::RunTime::orbmm) \
343                    ::System::Exceptions::NativeCodeExceptionOriginInfo \
344                    (::System::RunTime::get_pc()), \
345                 ::System::Priv::in_kernel(), ##args); \
346 } while (0)
347
348 #define rethrow_idl(oldex, T, args...) do { \
349         throw T(new(::System::RunTime::orbmm) typeof(oldex)(oldex), NULL, \
350                 new(::System::RunTime::orbmm) \
351                    ::System::Exceptions::NativeCodeExceptionOriginInfo \
352                    (::System::RunTime::get_pc()), \
353                 ::System::Priv::in_kernel(), ##args); \
354 } while (0)
355 #endif
356
357 #endif