11 #include "../../oberon-internals.h"
12 #include "generator-jvm.h"
13 #include "generator-jvm-abi.h"
14 #include "generator-jvm-asm.h"
15 #include "generator-jvm-basic.h"
18 jvm_create_proc(struct gen_class
* class)
20 gen_proc_t
* p
= GC_MALLOC(sizeof *p
);
21 memset(p
, 0, sizeof *p
);
23 struct gen_register_file
* rf
= GC_MALLOC(sizeof *rf
);
24 memset(rf
, 0, sizeof *rf
);
26 struct gen_stack
* stack
= GC_MALLOC(sizeof *stack
);
27 memset(rf
, 0, sizeof *stack
);
38 jvm_generate_function_header(gen_proc_t
* p
, char * access
, char * name
, char * signature
)
40 struct gen_class
* class;
43 /* Делаем процедуру текущей в этом классе */
44 assert(class -> p
== NULL
);
47 fprintf(class -> fp
, ".method %s %s%s\n", access
, name
, signature
);
48 fprintf(class -> fp
, " start:\n");
52 jvm_generate_function_end(gen_proc_t
* p
)
54 struct gen_class
* class;
60 int pointer
= p
-> stack
-> pointer
;
61 int max_pointer
= p
-> stack
-> max_pointer
;
62 int locals
= p
-> rf
-> num_used
;
63 int max_locals
= p
-> rf
-> max_used
;
65 fprintf(class -> fp
, " .limit stack %i \t; current(%i)\n", max_pointer
, pointer
);
66 fprintf(class -> fp
, " .limit locals %i \t; current(%i)\n", max_locals
, locals
);
67 fprintf(class -> fp
, " end:\n");
68 fprintf(class -> fp
, ".end method\n\n");
72 jvm_create_class(const char * dir
, char * full_name
)
74 struct gen_class
* class = GC_MALLOC(sizeof *class);
75 memset(class, 0, sizeof *class);
77 char * fname
= new_string("%s/%s.j", dir
, full_name
);
78 class -> full_name
= new_string(full_name
);
79 class -> fp
= fopen(fname
, "w");
80 class -> dir
= new_string(dir
);
82 if(class -> fp
== NULL
)
84 gen_error("unable to create file %s", fname
);
91 jvm_destroy_class(struct gen_class
* class)
93 assert(class -> p
== NULL
);
98 jvm_stack_push(gen_proc_t
* p
, unsigned size
)
100 p
-> stack
-> pointer
+= size
;
101 if(p
-> stack
-> pointer
> p
-> stack
-> max_pointer
)
103 p
-> stack
-> max_pointer
= p
-> stack
-> pointer
;
108 jvm_stack_pop(gen_proc_t
* p
, unsigned size
)
110 p
-> stack
-> pointer
-= size
;
112 if(p
-> stack
-> pointer
< 0)
114 printf("WARING: stack pointer %i\n", p
-> stack
-> pointer
);
119 jvm_generate(gen_proc_t
* p
, unsigned get
, unsigned push
, char * format
, ...)
122 va_start(ptr
, format
);
124 jvm_stack_pop(p
, get
);
125 fprintf(p
-> class -> fp
, " ");
126 vfprintf(p
-> class -> fp
, format
, ptr
);
127 jvm_stack_push(p
, push
);
128 fprintf(p
-> class -> fp
, " \t ;>>>> %i -- %i : current_stack(%i)\n", get
, push
, p
-> stack
-> pointer
);
134 jvm_generate_comment(gen_proc_t
* p
, char * format
, ...)
137 va_start(ptr
, format
);
139 fprintf(p
-> class -> fp
, " ;;;; ");
140 vfprintf(p
-> class -> fp
, format
, ptr
);
141 fprintf(p
-> class -> fp
, "\n");
147 jvm_generate_push_int(gen_proc_t
* p
, int64_t i
)
151 jvm_generate(p
, 0, 1, "iconst_m1");
153 else if(i
>= 0 && i
<= 5)
155 jvm_generate(p
, 0, 1, "iconst_%li", i
);
157 else if(i
>= -128 && i
<= 127)
159 jvm_generate(p
, 0, 1, "bipush %li", i
);
161 else if(i
>= -32768 && i
<= 32767)
163 jvm_generate(p
, 0, 1, "sipush %li", i
);
165 else if(i
>= -2147483648 && i
<= 2147483647)
167 jvm_generate(p
, 0, 1, "ldc %li", i
);
171 jvm_generate(p
, 0, 2, "ldc2_w %li", i
);
176 jvm_generate_push_int_size(gen_proc_t
* p
, int64_t i
, int size
)
182 jvm_generate(p
, 0, 1, "iconst_m1");
184 else if(i
>= 0 && i
<= 5)
186 jvm_generate(p
, 0, 1, "iconst_%li", i
);
188 else if(i
>= -128 && i
<= 127)
190 jvm_generate(p
, 0, 1, "bipush %li", i
);
192 else if(i
>= -32768 && i
<= 32767)
194 jvm_generate(p
, 0, 1, "sipush %li", i
);
196 else if(i
>= -2147483648 && i
<= 2147483647)
198 jvm_generate(p
, 0, 1, "ldc %li", i
);
203 jvm_generate(p
, 0, 2, "ldc2_w %li", i
);
207 if(size
> 4 && pushed_cell
== 1)
209 jvm_generate(p
, pushed_cell
, 2, "i2l");
215 jvm_generate(p
, 2, 1, "l2i");
220 jvm_generate(p
, 1, 1, "i2s");
224 jvm_generate(p
, 1, 1, "i2b");
230 jvm_generate_push_float(gen_proc_t
* p
, double f
, int size
)
236 jvm_generate(p
, 0, 1, "fconst_0");
240 jvm_generate(p
, 0, 1, "fconst_1");
244 jvm_generate(p
, 0, 1, "fconst_2");
248 jvm_generate(p
, 0, 1, "ldc %lf", f
);
255 jvm_generate(p
, 0, 2, "dconst_0");
259 jvm_generate(p
, 0, 2, "dconst_1");
263 jvm_generate(p
, 0, 2, "ldc2_w %lf", f
);
269 jvm_generate_push_string(gen_proc_t
* p
, char * str
, int char_size
)
271 assert(char_size
== 1);
272 int len
= strlen(str
);
274 jvm_generate_push_int(p
, len
+ 1);
275 jvm_generate(p
, 1, 1, "newarray byte");
277 for(int i
= 0; i
< len
; i
++)
279 jvm_generate(p
, 1, 2, "dup");
280 jvm_generate_push_int(p
, i
);
281 jvm_generate_push_int(p
, str
[i
]);
282 jvm_generate(p
, 3, 0, "bastore");
287 jvm_new_label_id(gen_proc_t
* p
)
289 int label_id
= p
-> label_id
;
295 jvm_generate_label(gen_proc_t
* p
, int label_id
)
297 jvm_generate(p
, 0, 0, "L%i:", label_id
);