Signed-off-by: Tomek Grabiec <[email protected]>
---
Makefile | 3 +-
include/jit/bytecode-to-ir.h | 1 +
include/jit/compiler.h | 2 +
jit/arithmetic-bc.c | 14 ++++++++---
jit/bytecode-to-ir.c | 39 ++++++++++++++++---------------
jit/load-store-bc.c | 52 ++++++++++++++++++++++++-----------------
jit/wide-bc.c | 41 +++++++++++++++++++++++++++++++++
7 files changed, 106 insertions(+), 46 deletions(-)
create mode 100644 jit/wide-bc.c
diff --git a/Makefile b/Makefile
index e602e8d..9403ac5 100644
--- a/Makefile
+++ b/Makefile
@@ -87,7 +87,8 @@ JIT_OBJS = \
jit/typeconv-bc.o \
jit/vtable.o \
jit/subroutine.o \
- jit/pc-map.o
+ jit/pc-map.o \
+ jit/wide-bc.o
VM_OBJS = \
vm/bytecode.o \
diff --git a/include/jit/bytecode-to-ir.h b/include/jit/bytecode-to-ir.h
index cb487cf..c1e9b80 100644
--- a/include/jit/bytecode-to-ir.h
+++ b/include/jit/bytecode-to-ir.h
@@ -15,5 +15,6 @@ typedef int (*convert_fn_t) (struct parse_context *);
# include <vm/bytecode-def.h>
#undef BYTECODE
+int convert_instruction(struct parse_context *ctx);
#endif /* JIT_BYTECODE_TO_IR_H */
diff --git a/include/jit/compiler.h b/include/jit/compiler.h
index f56371f..4613615 100644
--- a/include/jit/compiler.h
+++ b/include/jit/compiler.h
@@ -41,6 +41,8 @@ struct parse_context {
unsigned long offset;
unsigned long code_size;
unsigned char opc;
+
+ bool is_wide;
};
void convert_expression(struct parse_context *ctx, struct expression *expr);
diff --git a/jit/arithmetic-bc.c b/jit/arithmetic-bc.c
index a9b9624..c1c6acb 100644
--- a/jit/arithmetic-bc.c
+++ b/jit/arithmetic-bc.c
@@ -234,21 +234,27 @@ int convert_iinc(struct parse_context *ctx)
struct statement *store_stmt;
struct expression *local_expression, *binop_expression,
*const_expression;
- unsigned char index;
- char const_value;
+ unsigned int index;
+ unsigned int const_value;
store_stmt = alloc_statement(STMT_STORE);
if (!store_stmt)
goto failed;
- index = bytecode_read_u8(ctx->buffer);
+ if (ctx->is_wide) {
+ index = bytecode_read_u16(ctx->buffer);
+ const_value = bytecode_read_s16(ctx->buffer);
+ } else {
+ index = bytecode_read_u8(ctx->buffer);
+ const_value = bytecode_read_s8(ctx->buffer);
+ }
+
local_expression = local_expr(J_INT, index);
if (!local_expression)
goto failed;
store_stmt->store_dest = &local_expression->node;
- const_value = bytecode_read_s8(ctx->buffer);
const_expression = value_expr(J_INT, const_value);
if (!const_expression)
goto failed;
diff --git a/jit/bytecode-to-ir.c b/jit/bytecode-to-ir.c
index 4d61232..83e577a 100644
--- a/jit/bytecode-to-ir.c
+++ b/jit/bytecode-to-ir.c
@@ -55,8 +55,8 @@ static int convert_not_implemented(struct parse_context *ctx)
#define convert_tableswitch convert_not_implemented
#define convert_lookupswitch convert_not_implemented
-#define convert_wide convert_not_implemented
-#define convert_goto_w convert_not_implemented
+
+#define convert_goto_w convert_goto
#define BYTECODE(opc, name, size, type) [opc] = convert_ ## name,
static convert_fn_t converters[] = {
@@ -161,6 +161,22 @@ error_oom:
return NULL;
}
+int convert_instruction(struct parse_context *ctx)
+{
+ convert_fn_t convert;
+
+ ctx->opc = bytecode_read_u8(ctx->buffer);
+
+ if (ctx->opc >= ARRAY_SIZE(converters))
+ return warn("%d out of bounds", ctx->opc), -EINVAL;
+
+ convert = converters[ctx->opc];
+ if (!convert)
+ return warn("no converter for %d found", ctx->opc), -EINVAL;
+
+ return convert(ctx);
+}
+
static int do_convert_bb_to_ir(struct basic_block *bb)
{
struct compilation_unit *cu = bb->b_parent;
@@ -170,6 +186,7 @@ static int do_convert_bb_to_ir(struct basic_block *bb)
.cu = cu,
.bb = bb,
.code = cu->method->code_attribute.code,
+ .is_wide = false,
};
int err = 0;
@@ -180,25 +197,9 @@ static int do_convert_bb_to_ir(struct basic_block *bb)
stack_push(bb->mimic_stack, exception_ref_expr());
while (buffer.pos < bb->end) {
- convert_fn_t convert;
-
ctx.offset = ctx.buffer->pos; /* this is fragile */
- ctx.opc = bytecode_read_u8(ctx.buffer);
-
- if (ctx.opc >= ARRAY_SIZE(converters)) {
- warn("%d out of bounds", ctx.opc);
- err = -EINVAL;
- break;
- }
-
- convert = converters[ctx.opc];
- if (!convert) {
- warn("no converter for %d found", ctx.opc);
- err = -EINVAL;
- break;
- }
- err = convert(&ctx);
+ err = convert_instruction(&ctx);
if (err)
break;
}
diff --git a/jit/load-store-bc.c b/jit/load-store-bc.c
index c6598ef..97bb44d 100644
--- a/jit/load-store-bc.c
+++ b/jit/load-store-bc.c
@@ -180,7 +180,7 @@ int convert_ldc2_w(struct parse_context *ctx)
return __convert_ldc(ctx, idx);
}
-static int convert_load(struct parse_context *ctx, unsigned char index, enum
vm_type type)
+static int convert_load(struct parse_context *ctx, unsigned int index, enum
vm_type type)
{
struct expression *expr;
@@ -192,47 +192,55 @@ static int convert_load(struct parse_context *ctx,
unsigned char index, enum vm_
return 0;
}
+static unsigned int read_index(struct parse_context *ctx)
+{
+ if (ctx->is_wide)
+ return bytecode_read_u16(ctx->buffer);
+
+ return bytecode_read_u8(ctx->buffer);
+}
+
int convert_iload(struct parse_context *ctx)
{
- unsigned char idx;
+ unsigned int idx;
- idx = bytecode_read_u8(ctx->buffer);
+ idx = read_index(ctx);
return convert_load(ctx, idx, J_INT);
}
int convert_lload(struct parse_context *ctx)
{
- unsigned char idx;
+ unsigned int idx;
- idx = bytecode_read_u8(ctx->buffer);
+ idx = read_index(ctx);
return convert_load(ctx, idx, J_LONG);
}
int convert_fload(struct parse_context *ctx)
{
- unsigned char idx;
+ unsigned int idx;
- idx = bytecode_read_u8(ctx->buffer);
+ idx = read_index(ctx);
return convert_load(ctx, idx, J_FLOAT);
}
int convert_dload(struct parse_context *ctx)
{
- unsigned char idx;
+ unsigned int idx;
- idx = bytecode_read_u8(ctx->buffer);
+ idx = read_index(ctx);
return convert_load(ctx, idx, J_DOUBLE);
}
int convert_aload(struct parse_context *ctx)
{
- unsigned char idx;
+ unsigned int idx;
- idx = bytecode_read_u8(ctx->buffer);
+ idx = read_index(ctx);
return convert_load(ctx, idx, J_REFERENCE);
}
@@ -262,7 +270,7 @@ int convert_aload_n(struct parse_context *ctx)
return convert_load(ctx, ctx->opc - OPC_ALOAD_0, J_REFERENCE);
}
-static int convert_store(struct parse_context *ctx, unsigned long index, enum
vm_type type)
+static int convert_store(struct parse_context *ctx, unsigned int index, enum
vm_type type)
{
struct expression *src_expr, *dest_expr;
struct statement *stmt = alloc_statement(STMT_STORE);
@@ -283,45 +291,45 @@ static int convert_store(struct parse_context *ctx,
unsigned long index, enum vm
int convert_istore(struct parse_context *ctx)
{
- unsigned char idx;
+ unsigned int idx;
- idx = bytecode_read_u8(ctx->buffer);
+ idx = read_index(ctx);
return convert_store(ctx, idx, J_INT);
}
int convert_lstore(struct parse_context *ctx)
{
- unsigned char idx;
+ unsigned int idx;
- idx = bytecode_read_u8(ctx->buffer);
+ idx = read_index(ctx);
return convert_store(ctx, idx, J_LONG);
}
int convert_fstore(struct parse_context *ctx)
{
- unsigned char idx;
+ unsigned int idx;
- idx = bytecode_read_u8(ctx->buffer);
+ idx = read_index(ctx);
return convert_store(ctx, idx, J_FLOAT);
}
int convert_dstore(struct parse_context *ctx)
{
- unsigned char idx;
+ unsigned int idx;
- idx = bytecode_read_u8(ctx->buffer);
+ idx = read_index(ctx);
return convert_store(ctx, idx, J_DOUBLE);
}
int convert_astore(struct parse_context *ctx)
{
- unsigned char idx;
+ unsigned int idx;
- idx = bytecode_read_u8(ctx->buffer);
+ idx = read_index(ctx);
return convert_store(ctx, idx, J_REFERENCE);
}
diff --git a/jit/wide-bc.c b/jit/wide-bc.c
new file mode 100644
index 0000000..4e1f284
--- /dev/null
+++ b/jit/wide-bc.c
@@ -0,0 +1,41 @@
+/*
+ * Copyright (c) 2009 Pekka Enberg
+ *
+ * This file is released under the GPL version 2 with the following
+ * clarification and special exception:
+ *
+ * Linking this library statically or dynamically with other modules is
+ * making a combined work based on this library. Thus, the terms and
+ * conditions of the GNU General Public License cover the whole
+ * combination.
+ *
+ * As a special exception, the copyright holders of this library give you
+ * permission to link this library with independent modules to produce an
+ * executable, regardless of the license terms of these independent
+ * modules, and to copy and distribute the resulting executable under terms
+ * of your choice, provided that you also meet, for each linked independent
+ * module, the terms and conditions of the license of that module. An
+ * independent module is a module which is not derived from or based on
+ * this library. If you modify this library, you may extend this exception
+ * to your version of the library, but you are not obligated to do so. If
+ * you do not wish to do so, delete this exception statement from your
+ * version.
+ *
+ * Please refer to the file LICENSE for details.
+ */
+
+#include "jit/bytecode-to-ir.h"
+#include "jit/compiler.h"
+
+#include "vm/bytecode.h"
+
+int convert_wide(struct parse_context *ctx)
+{
+ int result;
+
+ ctx->is_wide = true;
+ result = convert_instruction(ctx);
+ ctx->is_wide = false;
+
+ return result;
+}
--
1.6.0.6
------------------------------------------------------------------------------
Enter the BlackBerry Developer Challenge
This is your chance to win up to $100,000 in prizes! For a limited time,
vendors submitting new applications to BlackBerry App World(TM) will have
the opportunity to enter the BlackBerry Developer Challenge. See full prize
details at: http://p.sf.net/sfu/Challenge
_______________________________________________
Jatovm-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/jatovm-devel