示例#1
0
文件: llvm.cpp 项目: WoodMath/mathmap
void
code_emitter::emit_phis (statement_t *stmt, BasicBlock *left_bb, BasicBlock *right_bb,
			 map<rhs_t*, Value*> &rhs_map, int slice_flag)
{
    for (; stmt != NULL; stmt = stmt->next)
    {
	if (!must_emit_stmt(stmt, slice_flag))
	    continue;

	switch (stmt->kind)
	{
	    case STMT_NIL :
		g_assert(slice_flag == SLICE_IGNORE);
		break;

	    case STMT_PHI_ASSIGN :
		{
		    Value *left = NULL;
		    Value *right = NULL;
		    int compvar_type = stmt->v.assign.lhs->compvar->type;
		    const Type *type = llvm_type_for_type(module, compvar_type);

#ifdef DEBUG_OUTPUT
		    compiler_print_assign_statement(stmt);
		    printf("\n");
#endif

		    if (left_bb)
		    {
			left = rhs_map[stmt->v.assign.rhs];
			g_assert(left != NULL);
#ifdef DEBUG_OUTPUT
			printf("left:\n");
			left->dump();
#endif
		    }
		    if (right_bb)
		    {
			right = rhs_map[stmt->v.assign.rhs2];
			g_assert(right != NULL);
#ifdef DEBUG_OUTPUT
			printf("right:\n");
			right->dump();
#endif
		    }

		    PHINode *phi;

		    if (left_bb)
		    {
			phi = builder->CreatePHI(type);
			phi->addIncoming(promote(left, compvar_type), left_bb);
			set_value(stmt->v.assign.lhs, phi, false);
			phi_map[stmt->v.assign.lhs] = phi;
		    }
		    else
		    {
			g_assert(phi_map.find(stmt->v.assign.lhs) != phi_map.end());
			phi = phi_map[stmt->v.assign.lhs];
		    }

#ifdef DEBUG_OUTPUT
		    printf("phi:\n");
		    phi->dump();
#endif

		    if (right_bb)
			phi->addIncoming(promote(right, compvar_type), right_bb);
		}
		break;

	    default:
		g_assert_not_reached();
	}
    }

    commit_set_const_values();
}