]> gitweb.factorcode.org Git - factor.git/blob - vm/factor.cpp
VM: refactoring which removes two not useful short methods
[factor.git] / vm / factor.cpp
1 #include "master.hpp"
2
3 namespace factor {
4
5 void init_globals() { init_mvm(); }
6
7 void factor_vm::default_parameters(vm_parameters* p) {
8   p->embedded_image = false;
9   p->image_path = NULL;
10
11   p->datastack_size = 32 * sizeof(cell);
12   p->retainstack_size = 32 * sizeof(cell);
13
14 #if defined(FACTOR_PPC)
15   p->callstack_size = 256 * sizeof(cell);
16 #else
17   p->callstack_size = 128 * sizeof(cell);
18 #endif
19
20   p->code_size = 64;
21   p->young_size = sizeof(cell) / 4;
22   p->aging_size = sizeof(cell) / 2;
23   p->tenured_size = 24 * sizeof(cell);
24
25   p->max_pic_size = 3;
26
27   p->fep = false;
28   p->signals = true;
29
30 #ifdef WINDOWS
31   p->console = GetConsoleWindow() != NULL;
32 #else
33   p->console = true;
34 #endif
35
36   p->callback_size = 256;
37 }
38
39 bool factor_vm::factor_arg(const vm_char* str, const vm_char* arg,
40                            cell* value) {
41   int val;
42   if (SSCANF(str, arg, &val) > 0) {
43     *value = val;
44     return true;
45   }
46   return false;
47 }
48
49 void factor_vm::init_parameters_from_args(vm_parameters* p, int argc,
50                                           vm_char** argv) {
51   default_parameters(p);
52   p->executable_path = argv[0];
53
54   int i = 0;
55
56   for (i = 1; i < argc; i++) {
57     vm_char* arg = argv[i];
58     if (STRCMP(arg, STRING_LITERAL("--")) == 0)
59       break;
60     else if (factor_arg(arg, STRING_LITERAL("-datastack=%d"),
61                         &p->datastack_size))
62       ;
63     else if (factor_arg(arg, STRING_LITERAL("-retainstack=%d"),
64                         &p->retainstack_size))
65       ;
66     else if (factor_arg(arg, STRING_LITERAL("-callstack=%d"),
67                         &p->callstack_size))
68       ;
69     else if (factor_arg(arg, STRING_LITERAL("-young=%d"), &p->young_size))
70       ;
71     else if (factor_arg(arg, STRING_LITERAL("-aging=%d"), &p->aging_size))
72       ;
73     else if (factor_arg(arg, STRING_LITERAL("-tenured=%d"), &p->tenured_size))
74       ;
75     else if (factor_arg(arg, STRING_LITERAL("-codeheap=%d"), &p->code_size))
76       ;
77     else if (factor_arg(arg, STRING_LITERAL("-pic=%d"), &p->max_pic_size))
78       ;
79     else if (factor_arg(arg, STRING_LITERAL("-callbacks=%d"),
80                         &p->callback_size))
81       ;
82     else if (STRNCMP(arg, STRING_LITERAL("-i="), 3) == 0)
83       p->image_path = arg + 3;
84     else if (STRCMP(arg, STRING_LITERAL("-fep")) == 0)
85       p->fep = true;
86     else if (STRCMP(arg, STRING_LITERAL("-nosignals")) == 0)
87       p->signals = false;
88     else if (STRCMP(arg, STRING_LITERAL("-console")) == 0)
89       p->console = true;
90   }
91 }
92
93 /* Compile code in boot image so that we can execute the startup quotation */
94 /* Allocates memory */
95 void factor_vm::prepare_boot_image() {
96   std::cout << "*** Stage 2 early init... " << std::flush;
97
98   // Compile all words.
99   data_root<array> words(instances(WORD_TYPE), this);
100
101   cell n_words = array_capacity(words.untagged());
102   for (cell i = 0; i < n_words; i++) {
103     data_root<word> word(array_nth(words.untagged(), i), this);
104
105     FACTOR_ASSERT(!word->entry_point);
106     jit_compile_word(word.value(), word->def, false);
107   }
108   update_code_heap_words(true);
109
110   // Initialize all quotations
111   data_root<array> quotations(instances(QUOTATION_TYPE), this);
112
113   cell n_quots = array_capacity(quotations.untagged());
114   for (cell i = 0; i < n_quots; i++) {
115     data_root<quotation> quot(array_nth(quotations.untagged(), i), this);
116
117     if (!quot->entry_point)
118       quot->entry_point = lazy_jit_compile_entry_point();
119   }
120
121   special_objects[OBJ_STAGE2] = special_objects[OBJ_CANONICAL_TRUE];
122
123   std::cout << "done" << std::endl;
124 }
125
126 void factor_vm::init_factor(vm_parameters* p) {
127   /* Kilobytes */
128   p->datastack_size = align_page(p->datastack_size << 10);
129   p->retainstack_size = align_page(p->retainstack_size << 10);
130   p->callstack_size = align_page(p->callstack_size << 10);
131   p->callback_size = align_page(p->callback_size << 10);
132
133   /* Megabytes */
134   p->young_size <<= 20;
135   p->aging_size <<= 20;
136   p->tenured_size <<= 20;
137   p->code_size <<= 20;
138
139   /* Disable GC during init as a sanity check */
140   gc_off = true;
141
142   /* OS-specific initialization */
143   early_init();
144
145   const vm_char* executable_path = vm_executable_path();
146
147   if (executable_path)
148     p->executable_path = executable_path;
149
150   if (p->image_path == NULL) {
151     if (embedded_image_p()) {
152       p->embedded_image = true;
153       p->image_path = p->executable_path;
154     } else
155       p->image_path = default_image_path();
156   }
157
158   srand((unsigned int)nano_count());
159   init_ffi();
160   init_contexts(p->datastack_size, p->retainstack_size, p->callstack_size);
161   callbacks = new callback_heap(p->callback_size, this);
162   load_image(p);
163   init_c_io();
164   init_inline_caching((int)p->max_pic_size);
165   special_objects[OBJ_CELL_SIZE] = tag_fixnum(sizeof(cell));
166   special_objects[OBJ_ARGS] = false_object;
167   special_objects[OBJ_EMBEDDED] = false_object;
168
169   cell aliens[][2] = {
170     {OBJ_CPU,             (cell)FACTOR_CPU_STRING},
171     {OBJ_EXECUTABLE,      (cell)p->executable_path},
172     {OBJ_OS,              (cell)FACTOR_OS_STRING},
173     {OBJ_VM_COMPILE_TIME, (cell)FACTOR_COMPILE_TIME},
174     {OBJ_VM_COMPILER,     (cell)FACTOR_COMPILER_VERSION},
175     {OBJ_VM_GIT_LABEL,    (cell)FACTOR_STRINGIZE(FACTOR_GIT_LABEL)},
176     {OBJ_VM_VERSION,      (cell)FACTOR_STRINGIZE(FACTOR_VERSION)},
177 #if defined(WINDOWS)
178     {WIN_EXCEPTION_HANDLER, (cell)&factor::exception_handler}
179 #endif
180   };
181   int n_items = sizeof(aliens) / sizeof(cell[2]);
182   for (int n = 0; n < n_items; n++) {
183     cell idx = aliens[n][0];
184     special_objects[idx] = allot_alien(false_object, aliens[n][1]);
185   }
186
187   /* We can GC now */
188   gc_off = false;
189
190   if (!to_boolean(special_objects[OBJ_STAGE2]))
191     prepare_boot_image();
192
193   if (p->signals)
194     init_signals();
195
196   if (p->console)
197     open_console();
198
199 }
200
201 /* Allocates memory */
202 void factor_vm::pass_args_to_factor(int argc, vm_char** argv) {
203   growable_array args(this);
204
205   for (fixnum i = 0; i < argc; i++)
206     args.add(allot_alien(false_object, (cell)argv[i]));
207
208   args.trim();
209   special_objects[OBJ_ARGS] = args.elements.value();
210 }
211
212 void factor_vm::start_factor(vm_parameters* p) {
213   if (p->fep)
214     factorbug();
215
216   c_to_factor_toplevel(special_objects[OBJ_STARTUP_QUOT]);
217 }
218
219 void factor_vm::stop_factor() {
220   c_to_factor_toplevel(special_objects[OBJ_SHUTDOWN_QUOT]);
221 }
222
223 char* factor_vm::factor_eval_string(char* string) {
224   void* func = alien_offset(special_objects[OBJ_EVAL_CALLBACK]);
225   CODE_TO_FUNCTION_POINTER(func);
226   return ((char * (*)(char*)) func)(string);
227 }
228
229 void factor_vm::factor_eval_free(char* result) { free(result); }
230
231 void factor_vm::factor_yield() {
232   void* func = alien_offset(special_objects[OBJ_YIELD_CALLBACK]);
233   CODE_TO_FUNCTION_POINTER(func);
234   ((void(*)()) func)();
235 }
236
237 void factor_vm::factor_sleep(long us) {
238   void* func = alien_offset(special_objects[OBJ_SLEEP_CALLBACK]);
239   CODE_TO_FUNCTION_POINTER(func);
240   ((void(*)(long)) func)(us);
241 }
242
243 void factor_vm::start_standalone_factor(int argc, vm_char** argv) {
244   vm_parameters p;
245   init_parameters_from_args(&p, argc, argv);
246   init_factor(&p);
247   pass_args_to_factor(argc, argv);
248   start_factor(&p);
249 }
250
251 factor_vm* new_factor_vm() {
252   THREADHANDLE thread = thread_id();
253   factor_vm* newvm = new factor_vm(thread);
254   register_vm_with_thread(newvm);
255   thread_vms[thread] = newvm;
256
257   return newvm;
258 }
259
260 VM_C_API void start_standalone_factor(int argc, vm_char** argv) {
261   factor_vm* newvm = new_factor_vm();
262   return newvm->start_standalone_factor(argc, argv);
263 }
264
265 }