source: trunk/RuntimeLibrary/src/evaluator/jmi_evaluator.c @ 13719

Last change on this file since 13719 was 13719, checked in by Christian Andersson, 2 months ago

Recommitted changeset:13700 to trunk with two bug fixes. Related to ticket:5837

File size: 12.4 KB
Line 
1#include "jmi_evaluator_util.h"
2
3/* Must be defined here in order to override the methods from jmi_global.c */
4void jmi_global_log(int warning, const char* name, const char* fmt, const char* value) {
5    _jmi_global_log(warning, name, fmt, value);
6}
7void jmi_throw() {
8    _jmi_throw();
9}
10void* jmi_global_calloc(size_t n, size_t s) {
11    return _jmi_global_calloc(n,s);
12}
13
14/* Builtins */
15extern const char* ModelicaStrings_substring(const char*, int, int);
16extern int ModelicaStrings_length(const char*);
17extern int ModelicaStrings_skipWhiteSpace(const char*, int);
18extern int ModelicaStrings_compare(const char*, const char*, int);
19
20/* Record definitions */
21typedef struct R_ddddddddddd_ R_ddddddddddd;
22struct R_ddddddddddd_ {
23    double member_0;
24    double member_1;
25    double member_2;
26    double member_3;
27    double member_4;
28    double member_5;
29    double member_6;
30    double member_7;
31    double member_8;
32    double member_9;
33    double member_10;
34};
35JMI_ARRAY_TYPE(R_ddddddddddd, R_ddddddddddd_a)
36
37#define JMI_EVAL_CALLING_CONVENTION
38
39typedef const char* (JMI_EVAL_CALLING_CONVENTION *f_s_sii)(const char*, int, int);
40typedef double (JMI_EVAL_CALLING_CONVENTION *f_d_dd)(double, double);
41typedef double (JMI_EVAL_CALLING_CONVENTION *f_d_i)(int);
42typedef double(JMI_EVAL_CALLING_CONVENTION *f_d_idd)(int, double, double);
43typedef int (JMI_EVAL_CALLING_CONVENTION *f_i_ii)(int, int);
44typedef int (JMI_EVAL_CALLING_CONVENTION *f_i_s)(const char*);
45typedef int (JMI_EVAL_CALLING_CONVENTION *f_i_si)(const char*, int);
46typedef int (JMI_EVAL_CALLING_CONVENTION *f_i_ssi)(const char*, const char*, int);
47typedef void(JMI_EVAL_CALLING_CONVENTION *f___iddpR_ddddddddddd_)(int, double, double, R_ddddddddddd**);
48typedef void(JMI_EVAL_CALLING_CONVENTION *f___ddpd)(double, double, double*);
49typedef void (*generic_funcptr)(void);
50
51
52void jmi_call_void_fcn_ddpd(generic_funcptr fcn) { 
53    JMI_DEF(REA, arg_0)
54    JMI_DEF(REA, arg_1)
55    JMI_DEF(REA, arg_2)
56
57    JMCEVAL_parse(Real, arg_0);
58    JMCEVAL_parse(Real, arg_1);
59    JMCEVAL_parse(Real, arg_2);
60   
61    JMCEVAL_check("CALC");
62    if (JMCEVAL_try()) {
63        /* Calc phase */
64        ((f___ddpd)fcn)(arg_0, arg_1, &arg_2);
65
66        JMCEVAL_check("DONE");
67        JMCEVAL_print(Real, arg_2);
68    }
69    else {
70        JMCEVAL_failed();
71    }
72}
73
74void jmi_call_void_fcn_iddpR_ddddddddddd_(generic_funcptr fcn) {
75    JMI_DEF(INT, arg_0)
76    JMI_DEF(INT_EXT, tmp_0)   
77    JMI_DEF(REA, arg_1)
78    JMI_DEF(REA, arg_2)
79    JMI_RECORD_STATIC(R_ddddddddddd, arg_3)
80
81    JMCEVAL_parse(Integer, arg_0);
82    JMCEVAL_parse(Real, arg_1);
83    JMCEVAL_parse(Real, arg_2);
84    JMCEVAL_parse(Real, arg_3->member_0);
85    JMCEVAL_parse(Real, arg_3->member_1);
86    JMCEVAL_parse(Real, arg_3->member_2);
87    JMCEVAL_parse(Real, arg_3->member_3);
88    JMCEVAL_parse(Real, arg_3->member_4);
89    JMCEVAL_parse(Real, arg_3->member_5);
90    JMCEVAL_parse(Real, arg_3->member_6);
91    JMCEVAL_parse(Real, arg_3->member_7);
92    JMCEVAL_parse(Real, arg_3->member_8);
93    JMCEVAL_parse(Real, arg_3->member_9);
94    JMCEVAL_parse(Real, arg_3->member_10);
95
96    JMCEVAL_check("CALC");
97    if (JMCEVAL_try()) {
98        /* Calc phase */
99        tmp_0 = (int)arg_0;
100        ((f___iddpR_ddddddddddd_)fcn)(tmp_0, arg_1, arg_2, arg_3);
101
102
103        JMCEVAL_check("DONE");
104        JMCEVAL_print(Real, arg_3->member_0);
105        JMCEVAL_print(Real, arg_3->member_1);
106        JMCEVAL_print(Real, arg_3->member_2);
107        JMCEVAL_print(Real, arg_3->member_3);
108        JMCEVAL_print(Real, arg_3->member_4);
109        JMCEVAL_print(Real, arg_3->member_5);
110        JMCEVAL_print(Real, arg_3->member_6);
111        JMCEVAL_print(Real, arg_3->member_7);
112        JMCEVAL_print(Real, arg_3->member_8);
113        JMCEVAL_print(Real, arg_3->member_9);
114        JMCEVAL_print(Real, arg_3->member_10);
115    }
116    else {
117        JMCEVAL_failed();
118    }
119}
120
121void jmi_call_double_fcn_dd(generic_funcptr fcn, double *out) {
122    JMI_DEF(REA, arg_0)
123    JMI_DEF(REA, arg_1)
124
125    JMCEVAL_parse(Real, arg_0);
126    JMCEVAL_parse(Real, arg_1);
127
128    JMCEVAL_check("CALC");
129    if (JMCEVAL_try()) {
130        /* Calc phase */
131        *out = ((f_d_dd)fcn)(arg_0, arg_1);
132    } else {
133        JMCEVAL_failed();
134    }
135}
136
137void jmi_call_double_fcn_i(generic_funcptr fcn, double *out) {
138    JMI_DEF(INT, arg_0)
139    JMI_DEF(INT_EXT, tmp_1)
140
141    JMCEVAL_parse(Integer, arg_0);
142
143    JMCEVAL_check("CALC");
144    if (JMCEVAL_try()) {
145        /* Calc phase */
146        tmp_1 = (int)arg_0;
147        *out = ((f_d_i)fcn)(tmp_1);
148    } else {
149        JMCEVAL_failed();
150    }
151}
152
153void jmi_call_double_fcn_idd(generic_funcptr fcn, double *out) {
154    JMI_DEF(INT, arg_0)
155    JMI_DEF(INT_EXT, tmp_0)
156    JMI_DEF(REA, arg_1)
157    JMI_DEF(REA, arg_2)
158
159    JMCEVAL_parse(Integer, arg_0);
160    JMCEVAL_parse(Real, arg_1);
161    JMCEVAL_parse(Real, arg_2);
162
163    JMCEVAL_check("CALC");
164    if (JMCEVAL_try()) {
165        /* Calc phase */
166        tmp_0 = (int)arg_0;
167        *out = ((f_d_idd)fcn)(tmp_0, arg_1, arg_2);
168    }
169    else {
170        JMCEVAL_failed();
171    }
172}
173
174void jmi_call_double_fcn(generic_funcptr fcn, const char* inputs) {
175    JMI_DEF(REA, d_output)
176    JMCEVAL_parse(Real, d_output);
177
178    if (strcmp(inputs, "d,d,") == 0) {
179        jmi_call_double_fcn_dd(fcn, &d_output);
180    } else if (strcmp(inputs, "i,") == 0) {
181        jmi_call_double_fcn_i(fcn, &d_output);
182    } else if (strcmp(inputs, "i,d,d,") == 0) {
183        jmi_call_double_fcn_idd(fcn, &d_output);
184    } else {
185        printf(ERROR_NOT_SUPPORTED_INPUT_ARGS_MSG);
186        exit(ERROR_NOT_SUPPORTED_INPUT_ARGS);
187    }
188
189    JMCEVAL_check("DONE");
190    JMCEVAL_print(Real, d_output);
191}
192
193void jmi_call_integer_fcn_s(generic_funcptr fcn, int *out) {
194    JMI_DEF(STR, arg_0)
195
196    JMCEVAL_parse(String, arg_0);
197
198    JMCEVAL_check("CALC");
199    if (JMCEVAL_try()) {
200        /* Calc phase */
201        *out = ((f_i_s)fcn)(arg_0);
202    }
203    else {
204        JMCEVAL_failed();
205    }
206}
207
208void jmi_call_integer_fcn_si(generic_funcptr fcn, int *out) {
209    JMI_DEF(STR, arg_0)
210    JMI_DEF(INT, arg_1)
211    JMI_DEF(INT_EXT, tmp_1)
212
213    JMCEVAL_parse(String, arg_0);
214    JMCEVAL_parse(Integer, arg_1);
215
216    JMCEVAL_check("CALC");
217    if (JMCEVAL_try()) {
218        /* Calc phase */
219        tmp_1 = (int)arg_1;
220        *out = ((f_i_si)fcn)(arg_0, tmp_1);
221    }
222    else {
223        JMCEVAL_failed();
224    }
225}
226
227void jmi_call_integer_fcn_ssi(generic_funcptr fcn, int *out) {
228    JMI_DEF(STR, arg_0)
229    JMI_DEF(STR, arg_1)
230    JMI_DEF(INT, arg_2)
231    JMI_DEF(INT_EXT, tmp_2)
232
233    JMCEVAL_parse(String, arg_0);
234    JMCEVAL_parse(String, arg_1);
235    JMCEVAL_parse(Integer, arg_2);
236
237    JMCEVAL_check("CALC");
238    if (JMCEVAL_try()) {
239        /* Calc phase */
240        tmp_2 = (int)arg_2;
241        *out = ((f_i_ssi)fcn)(arg_0, arg_1, tmp_2);
242    }
243    else {
244        JMCEVAL_failed();
245    }
246}
247
248void jmi_call_integer_fcn_ii(generic_funcptr fcn, int *out) {
249    JMI_DEF(INT, arg_0)
250    JMI_DEF(INT, arg_1)
251    JMI_DEF(INT_EXT, tmp_0)
252    JMI_DEF(INT_EXT, tmp_1)
253
254    JMCEVAL_parse(Integer, arg_0);
255    JMCEVAL_parse(Integer, arg_1);
256
257    JMCEVAL_check("CALC");
258    if (JMCEVAL_try()) {
259        /* Calc phase */
260        tmp_0 = (int)arg_0;
261        tmp_1 = (int)arg_1;
262        *out = ((f_i_ii)fcn)(arg_0, arg_1);
263    }
264    else {
265        JMCEVAL_failed();
266    }
267}
268
269void jmi_call_integer_fcn(generic_funcptr fcn, const char* inputs) {
270    JMI_DEF(INT, i_output)
271    JMI_DEF(INT_EXT, tmp_output)
272    JMCEVAL_parse(Integer, i_output);
273   
274    tmp_output = (int)i_output;
275
276    if (strcmp(inputs, "s,") == 0) {
277        jmi_call_integer_fcn_s(fcn, &tmp_output);
278    } else if (strcmp(inputs, "s,i,") == 0) {
279        jmi_call_integer_fcn_si(fcn, &tmp_output);
280    } else if (strcmp(inputs, "s,s,i,") == 0) {
281        jmi_call_integer_fcn_ssi(fcn, &tmp_output);
282    } else if (strcmp(inputs, "i,i,") == 0) {
283        jmi_call_integer_fcn_ii(fcn, &tmp_output);
284    } else {
285        printf(ERROR_NOT_SUPPORTED_INPUT_ARGS_MSG);
286        exit(ERROR_NOT_SUPPORTED_INPUT_ARGS);
287    }
288   
289    i_output = (double)tmp_output;
290
291    JMCEVAL_check("DONE");
292    JMCEVAL_print(Integer, i_output);
293}
294
295void jmi_call_string_fcn_sii(generic_funcptr fcn, char **out) {
296    JMI_DEF(STR, arg_0)
297    JMI_DEF(INT, arg_1)
298    JMI_DEF(INT, arg_2)
299    JMI_DEF(INT_EXT, tmp_1)
300    JMI_DEF(INT_EXT, tmp_2)
301
302    JMCEVAL_parse(String, arg_0);
303    JMCEVAL_parse(Integer, arg_1);
304    JMCEVAL_parse(Integer, arg_2);
305
306    JMCEVAL_check("CALC");
307    if (JMCEVAL_try()) {
308        /* Calc phase */
309        tmp_1 = (int)arg_1;
310        tmp_2 = (int)arg_2;
311        *out = ((f_s_sii)fcn)(arg_0, tmp_1, tmp_2);
312    } else {
313        JMCEVAL_failed();
314    }
315}
316
317void jmi_call_string_fcn(generic_funcptr fcn, const char* inputs) {
318    JMI_DEF(STR, s_output)
319    JMCEVAL_parse(String, s_output);
320
321    if (strcmp(inputs, "s,i,i,") == 0) {
322        jmi_call_string_fcn_sii(fcn, &s_output);
323    } else {
324        printf(ERROR_NOT_SUPPORTED_INPUT_ARGS_MSG);
325        exit(ERROR_NOT_SUPPORTED_INPUT_ARGS);
326    }
327
328    JMCEVAL_check("DONE");
329    JMCEVAL_print(String, s_output);
330}
331
332void jmi_call_void_fcn(generic_funcptr fcn, const char* inputs) {
333
334    if (strcmp(inputs, "i,d,d,*R[d,d,d,d,d,d,d,d,d,d,d,],") == 0) {
335        jmi_call_void_fcn_iddpR_ddddddddddd_(fcn);
336    } else if (strcmp(inputs, "d,d,*d,") == 0) {
337        jmi_call_void_fcn_ddpd(fcn);
338    } else {
339        printf(ERROR_NOT_SUPPORTED_INPUT_ARGS_MSG);
340        exit(ERROR_NOT_SUPPORTED_INPUT_ARGS);
341    }
342}
343
344/* Main */
345int main(int argc, const char* argv[])
346{
347    /* Size buffer for reading array dimensions */
348    int d[25];
349   
350    /* Indices for parsing/printing vars, dimensions */
351    size_t vi,di;
352
353    /* Function ptr that holds the specific function */
354    generic_funcptr funci = NULL;
355
356    const char *output_args = NULL;
357    const char *input_args = NULL;
358
359    /* Builtins */
360    if (strcmp(argv[2], "ModelicaStrings_substring") == 0) {
361        funci = (generic_funcptr)ModelicaStrings_substring;
362    } else if (strcmp(argv[2], "ModelicaStrings_length") == 0) {
363        funci = (generic_funcptr)ModelicaStrings_length;
364    } else if (strcmp(argv[2], "ModelicaStrings_skipWhiteSpace") == 0) {
365        funci = (generic_funcptr)ModelicaStrings_skipWhiteSpace;
366    } else if (strcmp(argv[2], "ModelicaStrings_compare") == 0) {
367        funci = (generic_funcptr)ModelicaStrings_compare;
368    }
369
370    if (funci == NULL) {
371        #ifdef _WIN32
372            HINSTANCE dll = LoadLibrary(argv[1]);
373       
374            if (!dll) {
375                DWORD error_code = GetLastError();
376                printf(ERROR_LOAD_DLL_MSG);
377                printf("error code: %d\n", error_code);
378                exit(ERROR_LOAD_DLL);
379            }
380
381            funci = (generic_funcptr)GetProcAddress(dll, argv[2]);
382            if (!funci) {
383                printf(ERROR_LOAD_FUNCTION_MSG);
384                exit(ERROR_LOAD_FUNCTION);
385            }
386        #else
387            void *so = dlopen(argv[1], RTLD_LOCAL | RTLD_LAZY);
388           
389            if (!so) {
390                printf(ERROR_LOAD_DLL_MSG);
391                exit(ERROR_LOAD_DLL);
392            }
393           
394            funci = (generic_funcptr)dlsym(so, argv[2]);
395            if (!funci) {
396                printf(ERROR_LOAD_FUNCTION_MSG);
397                exit(ERROR_LOAD_FUNCTION);
398            }
399        #endif
400    }
401
402    output_args = argv[3];
403    if (output_args == NULL) { 
404        printf(ERROR_OUTPUT_ARGS_NOT_SPECIFIED_MSG);
405        exit(ERROR_OUTPUT_ARGS_NOT_SPECIFIED); 
406    }
407
408    input_args  = argv[4];
409    if (input_args == NULL) { 
410        printf(ERROR_INPUT_ARGS_NOT_SPECIFIED_MSG);
411        exit(ERROR_INPUT_ARGS_NOT_SPECIFIED); 
412    }
413
414    JMCEVAL_setup(); /* This needs to happen first */
415
416    JMCEVAL_check("START");
417    if (JMCEVAL_try()) {
418        JMI_DYNAMIC_INIT()
419        /* Init phase */
420
421        JMI_DYNAMIC_FREE()
422    } else {
423        JMCEVAL_failed();
424    }
425   
426    JMCEVAL_check("READY");
427    while (JMCEVAL_cont("EVAL\n")) {
428        JMI_DYNAMIC_INIT()
429
430        if (strcmp(output_args, "d") == 0) {
431            jmi_call_double_fcn(funci, input_args);
432        } else if (strcmp(output_args, "s") == 0) {
433            jmi_call_string_fcn(funci, input_args);
434        } else if (strcmp(output_args, "i") == 0) {
435            jmi_call_integer_fcn(funci, input_args);
436        } else if (strcmp(output_args, "void") == 0) {
437            jmi_call_void_fcn(funci, input_args);
438        } else {
439            printf(ERROR_NOT_SUPPORTED_OUTPUT_ARGS_MSG);
440            exit(ERROR_NOT_SUPPORTED_OUTPUT_ARGS);
441        }
442
443        JMI_DYNAMIC_FREE()
444        JMCEVAL_check("READY");
445    }
446
447    if (JMCEVAL_try()) {
448        /* End phase */
449
450
451    } else {
452        JMCEVAL_failed();
453    }
454    _jmi_dynamic_function_pool_destroy();
455    JMCEVAL_check("END");
456    return 0;
457}
458
Note: See TracBrowser for help on using the repository browser.