From a70ea61d5f87c16daf05f653593f721dfc949d01 Mon Sep 17 00:00:00 2001 From: David Schleef Date: Wed, 30 Jun 2010 19:33:39 -0700 Subject: [PATCH] arm: Implement 2d support --- orc/orcprogram-arm.c | 97 +++++++++++++++++++++++++++++++++++++++++++++++++--- 1 file changed, 92 insertions(+), 5 deletions(-) diff --git a/orc/orcprogram-arm.c b/orc/orcprogram-arm.c index 8d199e0..21652a3 100644 --- a/orc/orcprogram-arm.c +++ b/orc/orcprogram-arm.c @@ -24,6 +24,7 @@ void orc_compiler_orc_arm_assemble (OrcCompiler *compiler); void orc_compiler_rewrite_vars (OrcCompiler *compiler); void orc_compiler_dump (OrcCompiler *compiler); +void arm_add_strides (OrcCompiler *compiler); void orc_arm_emit_prologue (OrcCompiler *compiler) @@ -139,7 +140,7 @@ orc_compiler_orc_arm_init (OrcCompiler *compiler) } void -orc_arm_load_constants (OrcCompiler *compiler) +orc_arm_load_constants_outer (OrcCompiler *compiler) { int i; for(i=0;ivars[i].value); break; case ORC_VAR_TYPE_PARAM: - orc_arm_loadw (compiler, compiler->vars[i].alloc, - compiler->exec_reg, - (int)ORC_STRUCT_OFFSET(OrcExecutor, params[i])); + ORC_PROGRAM_ERROR(compiler,"unimplemented"); + return; + /* FIXME offset is too large */ + //orc_arm_loadw (compiler, compiler->vars[i].alloc, + // compiler->exec_reg, + // (int)ORC_STRUCT_OFFSET(OrcExecutor, params[i])); + break; + case ORC_VAR_TYPE_SRC: + case ORC_VAR_TYPE_DEST: + break; + default: + break; + } + } +} + +void +orc_arm_load_constants_inner (OrcCompiler *compiler) +{ + int i; + for(i=0;ivars[i].name == NULL) continue; + switch (compiler->vars[i].vartype) { + case ORC_VAR_TYPE_CONST: + case ORC_VAR_TYPE_PARAM: break; case ORC_VAR_TYPE_SRC: case ORC_VAR_TYPE_DEST: @@ -255,9 +278,27 @@ orc_compiler_orc_arm_assemble (OrcCompiler *compiler) orc_arm_emit_prologue (compiler); + orc_arm_load_constants_outer (compiler); + + if (compiler->program->is_2d) { + if (compiler->program->constant_m > 0) { + orc_arm_emit_load_imm (compiler, ORC_ARM_A3, compiler->program->constant_m +); + orc_arm_emit_store_reg (compiler, ORC_ARM_A3, compiler->exec_reg, + (int)ORC_STRUCT_OFFSET(OrcExecutor,params[ORC_VAR_A2])); + } else { + orc_arm_emit_load_reg (compiler, ORC_ARM_A3, compiler->exec_reg, + (int)ORC_STRUCT_OFFSET(OrcExecutor, params[ORC_VAR_A1])); + orc_arm_emit_store_reg (compiler, ORC_ARM_A3, compiler->exec_reg, + (int)ORC_STRUCT_OFFSET(OrcExecutor,params[ORC_VAR_A2])); + } + + orc_arm_emit_label (compiler, 8); + } + orc_arm_emit_load_reg (compiler, ORC_ARM_IP, compiler->exec_reg, (int)ORC_STRUCT_OFFSET(OrcExecutor,n)); - orc_arm_load_constants (compiler); + orc_arm_load_constants_inner (compiler); orc_arm_emit_label (compiler, 1); @@ -271,6 +312,18 @@ orc_compiler_orc_arm_assemble (OrcCompiler *compiler) orc_arm_emit_branch (compiler, ORC_ARM_COND_NE, 2); orc_arm_emit_label (compiler, 3); + if (compiler->program->is_2d) { + neon_add_strides (compiler); + + orc_arm_emit_load_reg (compiler, ORC_ARM_A3, compiler->exec_reg, + (int)ORC_STRUCT_OFFSET(OrcExecutor, params[ORC_VAR_A2])); + orc_arm_emit_sub_imm (compiler, ORC_ARM_A3, ORC_ARM_A3, 1); + orc_arm_emit_store_reg (compiler, ORC_ARM_A3, compiler->exec_reg, + (int)ORC_STRUCT_OFFSET(OrcExecutor,params[ORC_VAR_A2])); + orc_arm_emit_cmp_imm (compiler, ORC_ARM_A3, 0); + orc_arm_emit_branch (compiler, ORC_ARM_COND_NE, 8); + } + orc_arm_emit_epilogue (compiler); orc_arm_do_fixups (compiler); @@ -308,6 +361,7 @@ orc_arm_emit_loop (OrcCompiler *compiler) switch (compiler->vars[insn->src_args[k]].vartype) { case ORC_VAR_TYPE_SRC: + case ORC_VAR_TYPE_DEST: orc_arm_emit_load_src (compiler, &compiler->vars[insn->src_args[k]]); break; case ORC_VAR_TYPE_CONST: @@ -368,3 +422,36 @@ orc_arm_emit_loop (OrcCompiler *compiler) } } +void +arm_add_strides (OrcCompiler *compiler) +{ + int i; + + for(i=0;ivars[i].name == NULL) continue; + switch (compiler->vars[i].vartype) { + case ORC_VAR_TYPE_CONST: + break; + case ORC_VAR_TYPE_PARAM: + break; + case ORC_VAR_TYPE_SRC: + case ORC_VAR_TYPE_DEST: + orc_arm_emit_load_reg (compiler, ORC_ARM_A3, compiler->exec_reg, + (int)ORC_STRUCT_OFFSET(OrcExecutor, arrays[i])); + orc_arm_emit_load_reg (compiler, ORC_ARM_A2, compiler->exec_reg, + (int)ORC_STRUCT_OFFSET(OrcExecutor, params[i])); + orc_arm_emit_add (compiler, ORC_ARM_A3, ORC_ARM_A3, ORC_ARM_A2); + orc_arm_emit_store_reg (compiler, ORC_ARM_A3, compiler->exec_reg, + (int)ORC_STRUCT_OFFSET(OrcExecutor, arrays[i])); + break; + case ORC_VAR_TYPE_ACCUMULATOR: + break; + case ORC_VAR_TYPE_TEMP: + break; + default: + ORC_COMPILER_ERROR(compiler,"bad vartype"); + break; + } + } +} + -- 2.7.4