From d54469555328facc1c3b20e741b0bc3d2061685d Mon Sep 17 00:00:00 2001 From: DeaDDooMER Date: Sun, 13 Aug 2017 21:49:53 +0300 Subject: [PATCH] =?utf8?q?JVM:=20=D0=94=D0=BE=D0=B1=D0=B0=D0=B2=D0=BB?= =?utf8?q?=D0=B5=D0=BD=D0=B0=20=D0=B8=D0=BD=D0=B8=D1=86=D0=B8=D0=B0=D0=BB?= =?utf8?q?=D0=B8=D0=B7=D0=B0=D1=86=D0=B8=D1=8F=20=D0=BC=D0=BE=D0=B4=D1=83?= =?utf8?q?=D0=BB=D0=B5=D0=B9?= MIME-Version: 1.0 Content-Type: text/plain; charset=utf8 Content-Transfer-Encoding: 8bit --- Test.obn | 10 +++------ notes | 1 - obn-compile.sh | 4 +--- proguard.conf | 4 ++++ rtl/Launcher.java | 17 +++++++++++--- rtl/Out.java | 9 +++++++- src/backends/jvm/generator-jvm.c | 38 ++++++++++++++++++++++++++------ 7 files changed, 61 insertions(+), 22 deletions(-) create mode 100644 proguard.conf diff --git a/Test.obn b/Test.obn index f769178..8249fb7 100644 --- a/Test.obn +++ b/Test.obn @@ -1,12 +1,8 @@ MODULE Test; -VAR - i : SHORTINT; - s : SET; - -PROCEDURE X; -END X; +IMPORT Out; BEGIN - i := SHORT(12345); + Out.Open; + Out.String("Hello World!"); Out.Ln; END Test. diff --git a/notes b/notes index 191dfc9..71ec669 100644 --- a/notes +++ b/notes @@ -1,4 +1,3 @@ -- JVM: Импортируемые модули не инициализируются - Нет счёта строк / столбцов - Сделать проверку повторов в CASE. diff --git a/obn-compile.sh b/obn-compile.sh index c02d178..85b71c5 100755 --- a/obn-compile.sh +++ b/obn-compile.sh @@ -11,6 +11,4 @@ jasmin -d classes tmp/*.j javac -d classes rtl/*.java -proguard -injars classes \ - -libraryjars /usr/lib/jvm/java-8-openjdk/jre/lib/rt.jar \ - -dontshrink -dontobfuscate -keep class $1 -keep class Launcher +proguard -injars classes -libraryjars /usr/lib/jvm/java-8-openjdk/jre/lib/rt.jar @proguard.conf diff --git a/proguard.conf b/proguard.conf new file mode 100644 index 0000000..155da5b --- /dev/null +++ b/proguard.conf @@ -0,0 +1,4 @@ +-dontshrink +-dontobfuscate +-dontoptimize +-keep class ** { void BEGIN(); } diff --git a/rtl/Launcher.java b/rtl/Launcher.java index 220f671..5077fa8 100644 --- a/rtl/Launcher.java +++ b/rtl/Launcher.java @@ -1,6 +1,17 @@ -class Launcher { +import java.lang.reflect.*; + +class Launcher +{ public static void main(String[] args) - throws ClassNotFoundException, InstantiationException, IllegalAccessException { - Class.forName(args[0]).newInstance();; + throws + ClassNotFoundException, + InstantiationException, + IllegalAccessException, + NoSuchMethodException, + InvocationTargetException + { + Class module = Class.forName(args[0]); + Method begin = module.getMethod("BEGIN"); + begin.invoke(null); } } diff --git a/rtl/Out.java b/rtl/Out.java index 9989977..68a7375 100644 --- a/rtl/Out.java +++ b/rtl/Out.java @@ -4,7 +4,8 @@ public class Out { public static void Open() { - + // Сюда можно что-нибудь затолкать... + // Например открытие окошка и высер в него } public static void Char(byte ch) @@ -41,4 +42,10 @@ public class Out { System.out.println(); } + + public static void BEGIN() + { + // Функция выполняется каждый раз когда модуль импортируется. + // Модуль должен сам проверять, импортировался ли он ранее. + } } diff --git a/src/backends/jvm/generator-jvm.c b/src/backends/jvm/generator-jvm.c index 2456aa7..bf5200b 100644 --- a/src/backends/jvm/generator-jvm.c +++ b/src/backends/jvm/generator-jvm.c @@ -707,6 +707,8 @@ oberon_generator_init_module(oberon_context_t * ctx, oberon_module_t * mod) fprintf(class -> fp, ".class %s\n", mod -> name); fprintf(class -> fp, ".super java/lang/Object\n\n"); + fprintf(class -> fp, ".field private static $INITIALIZED$ Z\n\n"); + m -> class = class; c -> current_m = m; @@ -724,19 +726,33 @@ push_expr(gen_proc_t * p, oberon_expr_t * expr); void oberon_generate_begin_module(oberon_context_t * ctx) { - struct gen_class * class = ctx -> mod -> gen_mod -> class; - gen_proc_t * p = jvm_create_proc(class); + gen_proc_t * p; + int label_cont; + struct gen_class * class; - jvm_generate_function_header(p, "public", "", "()V"); - jvm_alloc_register_untyped(p -> rf, false); - jvm_generate(p, 0, 1, "aload_0"); - jvm_generate(p, 1, 0, "invokespecial java/lang/Object/()V"); + class = ctx -> mod -> gen_mod -> class; + + p = jvm_create_proc(class); + jvm_generate_function_header(p, "public static", "BEGIN", "()V"); + + label_cont = jvm_new_label_id(p); + jvm_generate(p, 0, 1, "getstatic %s/$INITIALIZED$ Z", class -> full_name); + jvm_generate(p, 1, 0, "ifeq L%i", label_cont); + jvm_generate(p, 0, 0, "return"); + jvm_generate_label(p, label_cont); + + jvm_generate(p, 0, 1, "iconst_1"); + jvm_generate(p, 1, 0, "putstatic %s/$INITIALIZED$ Z", class -> full_name); /* Инициализация переменных объявленных в модуле */ oberon_object_t * x = ctx -> mod -> decl -> list -> next; while(x != NULL) { - if(x -> class == OBERON_CLASS_VAR) + if(x -> class == OBERON_CLASS_MODULE) + { + jvm_generate(p, 0, 0, "invokestatic %s/BEGIN()V", x -> module -> gen_mod -> class -> full_name); + } + else if(x -> class == OBERON_CLASS_VAR) { jvm_generate_var_initialization(p, x -> gen_var); if(x -> type -> class == OBERON_TYPE_ARRAY @@ -760,6 +776,14 @@ oberon_generate_end_module(oberon_context_t * ctx) jvm_generate(p, 0, 0, "return"); jvm_generate_function_end(class -> p); + + p = jvm_create_proc(class); + jvm_generate_function_header(p, "private", "", "()V"); + jvm_alloc_register_untyped(p -> rf, false); + jvm_generate(p, 0, 1, "aload_0"); + jvm_generate(p, 1, 0, "invokespecial java/lang/Object/()V"); + jvm_generate(p, 0, 0, "return"); + jvm_generate_function_end(class -> p); } /* -- 2.29.2