diff options
Diffstat (limited to 'src/backend/jit/llvm/llvmjit_expr.c')
-rw-r--r-- | src/backend/jit/llvm/llvmjit_expr.c | 229 |
1 files changed, 83 insertions, 146 deletions
diff --git a/src/backend/jit/llvm/llvmjit_expr.c b/src/backend/jit/llvm/llvmjit_expr.c index cea0d6fa5ce..dc16b399327 100644 --- a/src/backend/jit/llvm/llvmjit_expr.c +++ b/src/backend/jit/llvm/llvmjit_expr.c @@ -2046,152 +2046,12 @@ llvm_compile_expr(ExprState *state) break; } - case EEOP_AGG_INIT_TRANS: - { - AggStatePerTrans pertrans; - - LLVMValueRef v_aggstatep; - LLVMValueRef v_pertransp; - - LLVMValueRef v_allpergroupsp; - - LLVMValueRef v_pergroupp; - - LLVMValueRef v_setoff, - v_transno; - - LLVMValueRef v_notransvalue; - - LLVMBasicBlockRef b_init; - - pertrans = op->d.agg_init_trans.pertrans; - - v_aggstatep = - LLVMBuildBitCast(b, v_parent, l_ptr(StructAggState), ""); - v_pertransp = l_ptr_const(pertrans, - l_ptr(StructAggStatePerTransData)); - - /* - * pergroup = &aggstate->all_pergroups - * [op->d.agg_init_trans_check.setoff] - * [op->d.agg_init_trans_check.transno]; - */ - v_allpergroupsp = - l_load_struct_gep(b, v_aggstatep, - FIELDNO_AGGSTATE_ALL_PERGROUPS, - "aggstate.all_pergroups"); - v_setoff = l_int32_const(op->d.agg_init_trans.setoff); - v_transno = l_int32_const(op->d.agg_init_trans.transno); - v_pergroupp = - LLVMBuildGEP(b, - l_load_gep1(b, v_allpergroupsp, v_setoff, ""), - &v_transno, 1, ""); - - v_notransvalue = - l_load_struct_gep(b, v_pergroupp, - FIELDNO_AGGSTATEPERGROUPDATA_NOTRANSVALUE, - "notransvalue"); - - b_init = l_bb_before_v(opblocks[opno + 1], - "op.%d.inittrans", opno); - - LLVMBuildCondBr(b, - LLVMBuildICmp(b, LLVMIntEQ, v_notransvalue, - l_sbool_const(1), ""), - b_init, - opblocks[opno + 1]); - - LLVMPositionBuilderAtEnd(b, b_init); - - { - LLVMValueRef params[3]; - LLVMValueRef v_curaggcontext; - LLVMValueRef v_current_set; - LLVMValueRef v_aggcontext; - - v_aggcontext = l_ptr_const(op->d.agg_init_trans.aggcontext, - l_ptr(StructExprContext)); - - v_current_set = - LLVMBuildStructGEP(b, - v_aggstatep, - FIELDNO_AGGSTATE_CURRENT_SET, - "aggstate.current_set"); - v_curaggcontext = - LLVMBuildStructGEP(b, - v_aggstatep, - FIELDNO_AGGSTATE_CURAGGCONTEXT, - "aggstate.curaggcontext"); - - LLVMBuildStore(b, l_int32_const(op->d.agg_init_trans.setno), - v_current_set); - LLVMBuildStore(b, v_aggcontext, - v_curaggcontext); - - params[0] = v_aggstatep; - params[1] = v_pertransp; - params[2] = v_pergroupp; - - LLVMBuildCall(b, - llvm_pg_func(mod, "ExecAggInitGroup"), - params, lengthof(params), - ""); - } - LLVMBuildBr(b, opblocks[op->d.agg_init_trans.jumpnull]); - - break; - } - - case EEOP_AGG_STRICT_TRANS_CHECK: - { - LLVMValueRef v_setoff, - v_transno; - - LLVMValueRef v_aggstatep; - LLVMValueRef v_allpergroupsp; - - LLVMValueRef v_transnull; - LLVMValueRef v_pergroupp; - - int jumpnull = op->d.agg_strict_trans_check.jumpnull; - - v_aggstatep = - LLVMBuildBitCast(b, v_parent, l_ptr(StructAggState), ""); - - /* - * pergroup = &aggstate->all_pergroups - * [op->d.agg_strict_trans_check.setoff] - * [op->d.agg_init_trans_check.transno]; - */ - v_allpergroupsp = - l_load_struct_gep(b, v_aggstatep, - FIELDNO_AGGSTATE_ALL_PERGROUPS, - "aggstate.all_pergroups"); - v_setoff = - l_int32_const(op->d.agg_strict_trans_check.setoff); - v_transno = - l_int32_const(op->d.agg_strict_trans_check.transno); - v_pergroupp = - LLVMBuildGEP(b, - l_load_gep1(b, v_allpergroupsp, v_setoff, ""), - &v_transno, 1, ""); - - v_transnull = - l_load_struct_gep(b, v_pergroupp, - FIELDNO_AGGSTATEPERGROUPDATA_TRANSVALUEISNULL, - "transnull"); - - LLVMBuildCondBr(b, - LLVMBuildICmp(b, LLVMIntEQ, v_transnull, - l_sbool_const(1), ""), - opblocks[jumpnull], - opblocks[opno + 1]); - - break; - } - + case EEOP_AGG_PLAIN_TRANS_INIT_STRICT_BYVAL: + case EEOP_AGG_PLAIN_TRANS_STRICT_BYVAL: case EEOP_AGG_PLAIN_TRANS_BYVAL: - case EEOP_AGG_PLAIN_TRANS: + case EEOP_AGG_PLAIN_TRANS_INIT_STRICT_BYREF: + case EEOP_AGG_PLAIN_TRANS_STRICT_BYREF: + case EEOP_AGG_PLAIN_TRANS_BYREF: { AggState *aggstate; AggStatePerTrans pertrans; @@ -2249,6 +2109,81 @@ llvm_compile_expr(ExprState *state) l_load_gep1(b, v_allpergroupsp, v_setoff, ""), &v_transno, 1, ""); + + if (opcode == EEOP_AGG_PLAIN_TRANS_INIT_STRICT_BYVAL || + opcode == EEOP_AGG_PLAIN_TRANS_INIT_STRICT_BYREF) + { + LLVMValueRef v_notransvalue; + LLVMBasicBlockRef b_init; + LLVMBasicBlockRef b_no_init; + + v_notransvalue = + l_load_struct_gep(b, v_pergroupp, + FIELDNO_AGGSTATEPERGROUPDATA_NOTRANSVALUE, + "notransvalue"); + + b_init = l_bb_before_v(opblocks[opno + 1], + "op.%d.inittrans", opno); + b_no_init = l_bb_before_v(opblocks[opno + 1], + "op.%d.no_inittrans", opno); + + LLVMBuildCondBr(b, + LLVMBuildICmp(b, LLVMIntEQ, v_notransvalue, + l_sbool_const(1), ""), + b_init, + b_no_init); + + /* block to init the transition value if necessary */ + { + LLVMValueRef params[4]; + + LLVMPositionBuilderAtEnd(b, b_init); + + v_aggcontext = l_ptr_const(op->d.agg_trans.aggcontext, + l_ptr(StructExprContext)); + + params[0] = v_aggstatep; + params[1] = v_pertransp; + params[2] = v_pergroupp; + params[3] = v_aggcontext; + + LLVMBuildCall(b, + llvm_pg_func(mod, "ExecAggInitGroup"), + params, lengthof(params), + ""); + + LLVMBuildBr(b, opblocks[opno + 1]); + + } + + LLVMPositionBuilderAtEnd(b, b_no_init); + } + + if (opcode == EEOP_AGG_PLAIN_TRANS_INIT_STRICT_BYVAL || + opcode == EEOP_AGG_PLAIN_TRANS_INIT_STRICT_BYREF || + opcode == EEOP_AGG_PLAIN_TRANS_STRICT_BYVAL || + opcode == EEOP_AGG_PLAIN_TRANS_STRICT_BYREF) + { + LLVMValueRef v_transnull; + LLVMBasicBlockRef b_strictpass; + + b_strictpass = l_bb_before_v(opblocks[opno + 1], + "op.%d.strictpass", opno); + v_transnull = + l_load_struct_gep(b, v_pergroupp, + FIELDNO_AGGSTATEPERGROUPDATA_TRANSVALUEISNULL, + "transnull"); + + LLVMBuildCondBr(b, + LLVMBuildICmp(b, LLVMIntEQ, v_transnull, + l_sbool_const(1), ""), + opblocks[opno + 1], + b_strictpass); + + LLVMPositionBuilderAtEnd(b, b_strictpass); + } + + v_fcinfo = l_ptr_const(fcinfo, l_ptr(StructFunctionCallInfoData)); v_aggcontext = l_ptr_const(op->d.agg_trans.aggcontext, @@ -2312,7 +2247,9 @@ llvm_compile_expr(ExprState *state) * child of the aggcontext, assume we can adopt that value * without copying it. */ - if (opcode == EEOP_AGG_PLAIN_TRANS) + if (opcode == EEOP_AGG_PLAIN_TRANS_INIT_STRICT_BYREF || + opcode == EEOP_AGG_PLAIN_TRANS_STRICT_BYREF || + opcode == EEOP_AGG_PLAIN_TRANS_BYREF) { LLVMBasicBlockRef b_call; LLVMBasicBlockRef b_nocall; |