OSDN Git Service

2009-07-09 Tobias Burnus <burnus@net-b.de>
[pf3gnuchains/gcc-fork.git] / libjava / include / execution.h
1 // execution.h - Execution engines. -*- c++ -*-
2
3 /* Copyright (C) 2004, 2006, 2007  Free Software Foundation
4
5    This file is part of libgcj.
6
7 This software is copyrighted work licensed under the terms of the
8 Libgcj License.  Please consult the file "LIBGCJ_LICENSE" for
9 details.  */
10
11 #ifndef __JAVA_EXECUTION_H__
12 #define __JAVA_EXECUTION_H__
13
14 // This represents one execution engine.  Note that we use function
15 // pointers and not virtual methods to avoid calls to
16 // __cxa_call_unexpected and the like.
17 struct _Jv_ExecutionEngine
18 {
19  public:
20
21   void (*unregister) (jclass);
22   // FIXME: probably should handle this elsewhere, see how
23   // interpreter does it.
24   bool (*need_resolve_string_fields) ();
25   void (*verify) (jclass);
26   void (*allocate_static_fields) (jclass, int, int);
27   void (*allocate_field_initializers) (jclass);
28   void (*create_ncode) (jclass);
29   _Jv_ResolvedMethod *(*resolve_method) (_Jv_Method *, jclass,
30                                          jboolean);
31   void (*post_miranda_hook) (jclass);
32   _Jv_ClosureList **(*get_closure_list) (jclass);
33 };
34
35 // This handles gcj-compiled code except that compiled with
36 // -findirect-classes.
37 struct _Jv_CompiledEngine : public _Jv_ExecutionEngine
38 {
39  public:
40
41   static void do_unregister (jclass)
42   {
43   }
44
45   static bool do_need_resolve_string_fields ()
46   {
47     return true;
48   }
49
50   static void do_verify (jclass klass)
51   {
52     _Jv_Linker::verify_type_assertions (klass);
53   }
54
55   static _Jv_ResolvedMethod *do_resolve_method (_Jv_Method *, jclass,
56                                                 jboolean)
57   {
58     return NULL;
59   }
60
61   static void do_allocate_static_fields (jclass,
62                                          int,
63                                          int)
64   {
65   }
66
67   static void do_allocate_field_initializers (jclass)
68   {
69   }
70
71   static void do_create_ncode (jclass)
72   {
73     // Not needed.
74   }
75
76   static void do_post_miranda_hook (jclass)
77   {
78     // Not needed.
79   }
80
81   static _Jv_ClosureList **do_get_closure_list (jclass)
82   {
83     return NULL;
84   }
85
86   _Jv_CompiledEngine ()
87   {
88     unregister = do_unregister;
89     need_resolve_string_fields = do_need_resolve_string_fields;
90     verify = do_verify;
91     allocate_static_fields = do_allocate_static_fields;
92     allocate_field_initializers = do_allocate_field_initializers;
93     create_ncode = do_create_ncode;
94     resolve_method = do_resolve_method;
95     post_miranda_hook = do_post_miranda_hook;
96     get_closure_list = do_get_closure_list;
97   }
98
99   // These operators make it so we don't have to link in libstdc++.
100   void *operator new (size_t bytes)
101   {
102     return _Jv_Malloc(bytes);
103   }
104
105   void operator delete (void *mem)
106   {
107     _Jv_Free(mem);
108   }
109 };
110
111 class _Jv_IndirectCompiledClass
112 {
113 public:
114   void **field_initializers;
115   _Jv_ClosureList **closures;
116 };
117
118 // This handles gcj-compiled code compiled with -findirect-classes.
119 struct _Jv_IndirectCompiledEngine : public _Jv_CompiledEngine
120 {
121   _Jv_IndirectCompiledEngine () : _Jv_CompiledEngine ()
122   {
123     allocate_static_fields = do_allocate_static_fields;
124     allocate_field_initializers = do_allocate_field_initializers;
125     get_closure_list = do_get_closure_list;
126   }
127   
128   static _Jv_IndirectCompiledClass *get_aux_info (jclass klass)
129   {
130     _Jv_IndirectCompiledClass *aux =
131       (_Jv_IndirectCompiledClass*)klass->aux_info;
132     if (!aux)
133       {
134         aux = (_Jv_IndirectCompiledClass*)
135           _Jv_AllocRawObj (sizeof (_Jv_IndirectCompiledClass));
136         klass->aux_info = aux;
137       }
138
139     return aux;
140   }
141
142   static void do_allocate_field_initializers (jclass klass)
143   {
144     _Jv_IndirectCompiledClass *aux = get_aux_info (klass);
145     if (!aux)
146       {
147         aux = (_Jv_IndirectCompiledClass*)
148           _Jv_AllocRawObj (sizeof (_Jv_IndirectCompiledClass));
149         klass->aux_info = aux;
150       }
151
152     aux->field_initializers = (void **)_Jv_Malloc (klass->field_count 
153                                                    * sizeof (void*));    
154
155     for (int i = 0; i < klass->field_count; i++)
156       {
157         _Jv_Field *field = &klass->fields[i];
158         if (field->flags & java::lang::reflect::Modifier::STATIC)
159           {
160             aux->field_initializers[i] = field->u.addr;
161             field->u.addr = NULL; 
162           }
163       }
164   }
165
166   static void do_allocate_static_fields (jclass klass,
167                                          int pointer_size,
168                                          int other_size)
169   {
170     // Splitting the allocations here lets us scan reference fields
171     // and avoid scanning non-reference fields.
172     char *reference_fields = (char *) _Jv_AllocRawObj (pointer_size);
173     char *non_reference_fields = (char *) _Jv_AllocBytes (other_size);
174
175     _Jv_IndirectCompiledClass *aux 
176       =  (_Jv_IndirectCompiledClass*)klass->aux_info;
177
178     for (int i = 0; i < klass->field_count; i++)
179       {
180         _Jv_Field *field = &klass->fields[i];
181
182         if ((field->flags & java::lang::reflect::Modifier::STATIC) == 0)
183           continue;
184
185         char *base = field->isRef() ? reference_fields : non_reference_fields;
186         field->u.addr  = base + field->u.boffset;
187
188         if (aux->field_initializers[i])
189           {
190             int field_size;
191             if (! field->isRef ())
192               field_size = field->type->size ();
193             else 
194               field_size = sizeof (jobject);
195
196             memcpy (field->u.addr, aux->field_initializers[i], field_size);
197           }
198       } 
199     _Jv_Free (aux->field_initializers);
200   }
201
202 #ifdef INTERPRETER
203   static _Jv_ClosureList **do_get_closure_list (jclass klass)
204   {
205     _Jv_IndirectCompiledClass *aux = get_aux_info (klass);
206
207     if (!aux->closures)
208       aux->closures = _Jv_ClosureListFinalizer ();
209
210     return aux->closures;
211   }
212 #endif
213 };
214
215 #ifdef INTERPRETER
216
217 // This handles interpreted code.
218 class _Jv_InterpreterEngine : public _Jv_ExecutionEngine
219 {
220  public:
221
222   static void do_verify (jclass);
223   static void do_allocate_static_fields (jclass, int, int);
224   static void do_create_ncode (jclass);
225   static _Jv_ResolvedMethod *do_resolve_method (_Jv_Method *, jclass,
226                                                 jboolean);
227
228   static bool do_need_resolve_string_fields ()
229   {
230     return false;
231   }
232
233   static void do_unregister(jclass klass)
234   {
235     _Jv_UnregisterClass(klass);
236   }
237
238   static void do_allocate_field_initializers (jclass)
239   {
240   }
241
242   static void do_post_miranda_hook (jclass);
243
244   static _Jv_ClosureList **do_get_closure_list (jclass klass);
245
246   _Jv_InterpreterEngine ()
247   {
248     unregister = do_unregister;
249     need_resolve_string_fields = do_need_resolve_string_fields;
250     verify = do_verify;
251     allocate_static_fields = do_allocate_static_fields;
252     allocate_field_initializers = do_allocate_field_initializers;
253     create_ncode = do_create_ncode;
254     resolve_method = do_resolve_method;
255     post_miranda_hook = do_post_miranda_hook;
256     get_closure_list = do_get_closure_list;
257   }
258
259   // These operators make it so we don't have to link in libstdc++.
260   void *operator new (size_t bytes)
261   {
262     return _Jv_Malloc(bytes);
263   }
264
265   void operator delete (void *mem)
266   {
267     _Jv_Free(mem);
268   }
269 };
270
271 extern _Jv_InterpreterEngine _Jv_soleInterpreterEngine;
272 #endif // INTERPRETER
273
274 extern _Jv_CompiledEngine _Jv_soleCompiledEngine;
275 extern _Jv_IndirectCompiledEngine _Jv_soleIndirectCompiledEngine;
276 #endif // __JAVA_EXECUTION_H__