diff --git a/src/sql/monitor/ob_sql_plan.cpp b/src/sql/monitor/ob_sql_plan.cpp index 22f5b38cd3..c1cef19725 100644 --- a/src/sql/monitor/ob_sql_plan.cpp +++ b/src/sql/monitor/ob_sql_plan.cpp @@ -140,6 +140,40 @@ int ObSqlPlan::store_sql_plan_for_explain(ObLogPlan* plan, return ret; } +int ObSqlPlan::print_sql_plan(ObLogPlan* plan, + ExplainType type, + const ObExplainDisplayOpt& option, + ObIArray &plan_strs) +{ + int ret = OB_SUCCESS; + PlanText plan_text; + PlanText out_plan_text; + plan_text.type_ = type; + ObSEArray sql_plan_infos; + ObSEArray dummy_plan_infos; + if (OB_FAIL(init_buffer(plan_text))) { + LOG_WARN("failed to init buffer", K(ret)); + } else if (OB_FAIL(get_sql_plan_infos(plan_text, + plan, + sql_plan_infos))) { + LOG_WARN("failed to get sql plan infos", K(ret)); + } else if (OB_FAIL(format_sql_plan(sql_plan_infos, + type, + option, + dummy_plan_infos, + out_plan_text))) { + LOG_WARN("failed to format sql plan", K(ret)); + } else if (OB_FAIL(plan_text_to_strings(out_plan_text, plan_strs))) { + LOG_WARN("failed to convert plan text to strings", K(ret)); + } + if (OB_FAIL(ret)) { + LOG_WARN("failed to store sql plan", K(ret)); + ret = OB_SUCCESS; + } + destroy_buffer(plan_text); + return ret; +} + int ObSqlPlan::get_sql_plan(const ObString &sql_id, int64_t plan_id, ExplainType type, @@ -253,7 +287,9 @@ int ObSqlPlan::get_plan_outline_info_one_line(PlanText &plan_text, plan_text.is_outline_data_ = true; BUF_PRINT_CONST_STR("/*+BEGIN_OUTLINE_DATA", plan_text); const ObQueryHint &query_hint = query_ctx->get_query_hint(); - if (OB_FAIL(get_plan_tree_outline(plan_text, plan->get_plan_root()))) { + if (OB_FAIL(reset_plan_tree_outline_flag(plan->get_plan_root()))) { + LOG_WARN("failed to reset plan tree outline flag", K(ret)); + } else if (OB_FAIL(get_plan_tree_outline(plan_text, plan->get_plan_root()))) { LOG_WARN("failed to get plan tree outline", K(ret)); } else if (OB_FAIL(query_hint.print_transform_hints(plan_text))) { LOG_WARN("failed to print all transform hints", K(ret)); @@ -528,7 +564,9 @@ int ObSqlPlan::get_plan_outline_info(PlanText &plan_text, temp_text.pos_ = 0; BUF_PRINT_CONST_STR("/*+\n BEGIN_OUTLINE_DATA", temp_text); const ObQueryHint &query_hint = query_ctx->get_query_hint(); - if (OB_FAIL(get_plan_tree_outline(temp_text, plan->get_plan_root()))) { + if (OB_FAIL(reset_plan_tree_outline_flag(plan->get_plan_root()))) { + LOG_WARN("failed to reset plan tree outline flag", K(ret)); + } else if (OB_FAIL(get_plan_tree_outline(temp_text, plan->get_plan_root()))) { LOG_WARN("failed to get plan tree outline", K(ret)); } else if (OB_FAIL(query_hint.print_transform_hints(temp_text))) { LOG_WARN("failed to print all transform hints", K(ret)); @@ -544,6 +582,23 @@ int ObSqlPlan::get_plan_outline_info(PlanText &plan_text, return ret; } +int ObSqlPlan::reset_plan_tree_outline_flag(ObLogicalOperator* op) +{ + int ret = OB_SUCCESS; + if (OB_ISNULL(op) || OB_ISNULL(op->get_plan())) { + ret = OB_ERR_UNEXPECTED; + LOG_WARN("unexpect null op", K(ret)); + } else { + op->get_plan()->reset_outline_print_flags(); + } + for (int i = 0; OB_SUCC(ret) && i < op->get_num_of_child(); ++i) { + if (OB_FAIL(SMART_CALL(reset_plan_tree_outline_flag(op->get_child(i))))) { + LOG_WARN("failed to reset child plan tree outline flag", K(ret)); + } + } + return ret; +} + int ObSqlPlan::get_plan_tree_outline(PlanText &plan_text, ObLogicalOperator* op) { diff --git a/src/sql/monitor/ob_sql_plan.h b/src/sql/monitor/ob_sql_plan.h index c7300587b7..9f9d46db0e 100644 --- a/src/sql/monitor/ob_sql_plan.h +++ b/src/sql/monitor/ob_sql_plan.h @@ -126,6 +126,11 @@ public: const ObExplainDisplayOpt& option, ObIArray &plan_strs); + int print_sql_plan(ObLogPlan* plan, + ExplainType type, + const ObExplainDisplayOpt& option, + ObIArray &plan_strs); + int get_sql_plan(const ObString &sql_id, int64_t plan_id, ExplainType type, @@ -190,6 +195,8 @@ private: ObLogPlan* plan, ObSqlPlanItem* sql_plan_item); + static int reset_plan_tree_outline_flag(ObLogicalOperator* op); + static int get_plan_tree_outline(PlanText &plan_text, ObLogicalOperator* op); diff --git a/src/sql/ob_optimizer_trace_impl.cpp b/src/sql/ob_optimizer_trace_impl.cpp index eb549d8d58..e2931681ec 100644 --- a/src/sql/ob_optimizer_trace_impl.cpp +++ b/src/sql/ob_optimizer_trace_impl.cpp @@ -408,15 +408,20 @@ int ObOptimizerTraceImpl::append(const ObLogPlan *log_plan) target_plan = op->get_explain_plan(); } if (OB_NOT_NULL(target_plan)) { - if (OB_ISNULL(buf = static_cast(allocator_.alloc(buf_len)))) { - ret = OB_ALLOCATE_MEMORY_FAILED; - LOG_ERROR("Failed to allocate buffer", "buffer size", buf_len, K(ret)); - } else { - OPT_TRACE_TITLE("Query Plan"); - buf_len = target_plan->to_string(buf, buf_len, EXPLAIN_EXTENDED, option); + ObSqlPlan sql_plan(target_plan->get_allocator()); + sql_plan.set_session_info(target_plan->get_optimizer_context().get_session_info()); + ObSEArray plan_strs; + if (OB_FAIL(sql_plan.store_sql_plan_for_explain(const_cast(target_plan), + EXPLAIN_EXTENDED, + option, + plan_strs))) { + LOG_WARN("failed to store sql plan", K(ret)); + } + OPT_TRACE_TITLE("Query Plan"); + for (int64_t i = 0; OB_SUCC(ret) && i < plan_strs.count(); ++i) { if (OB_FAIL(new_line())) { LOG_WARN("failed to append msg", K(ret)); - } else if (OB_FAIL(append(ObString(buf_len, buf)))) { + } else if (OB_FAIL(append(plan_strs.at(i)))) { LOG_WARN("failed to append plan", K(ret)); } } diff --git a/src/sql/optimizer/ob_join_order.cpp b/src/sql/optimizer/ob_join_order.cpp index d409ee9dfc..ae566bdbea 100644 --- a/src/sql/optimizer/ob_join_order.cpp +++ b/src/sql/optimizer/ob_join_order.cpp @@ -9863,25 +9863,11 @@ int ObJoinOrder::get_valid_path_info(const ObJoinOrder &left_tree, } OPT_TRACE("candi distribute methods:"); int64_t distributed_methods = path_info.distributed_methods_; - const ObString dist_algo_str[] = - { - "BASIC", - "PULL TO LOCAL", - "HASH HASH", - "BROADCAST NONE", - "NONE BROADCAST", - "BC2HOST NONE", - "PARTITION NONE", - "NONE PARTITION", - "PARTITION WISE", - "UNKNOWN ALGO", - "RANDOM" - }; - for (int idx = 0; idx < sizeof(dist_algo_str) / sizeof(ObString); ++idx) { - if (distributed_methods & 1) { - OPT_TRACE(dist_algo_str[idx]); + for (int64_t k = 1; k < DistAlgo::DIST_MAX_JOIN_METHOD; k = k << 1) { + if (distributed_methods & k) { + DistAlgo dist_algo = get_dist_algo(k); + OPT_TRACE(ob_dist_algo_str(dist_algo)); } - distributed_methods >>= 1; } } } diff --git a/src/sql/optimizer/ob_log_operator_factory.h b/src/sql/optimizer/ob_log_operator_factory.h index 7cbb8b44e4..b0756f08aa 100644 --- a/src/sql/optimizer/ob_log_operator_factory.h +++ b/src/sql/optimizer/ob_log_operator_factory.h @@ -102,6 +102,10 @@ enum SetAlgo HASH_SET }; +/******** + * When modifying DistAlgo, the function ob_dist_algo_str + * needs to be modified synchronously !!! + ************/ enum DistAlgo { DIST_INVALID_METHOD = 0, @@ -132,15 +136,21 @@ inline const ObString &ob_dist_algo_str(DistAlgo algo) "UNKNOWN ALGO", "BASIC", "PULL TO LOCAL", + "HASH NONE", + "NONE HASH", "HASH HASH", "BROADCAST NONE", "NONE BROADCAST", "BC2HOST NONE", "PARTITION NONE", "NONE PARTITION", + "NONE ALL", + "ALL NONE", "PARTITION WISE", + "EXTEND PARTITION WISE", "UNKNOWN ALGO", - "RANDOM" + "SET RANDOM", + "SET PARTITION WISE" }; int64_t idx = 0; int64_t value = algo; @@ -148,7 +158,7 @@ inline const ObString &ob_dist_algo_str(DistAlgo algo) value >>= 1; ++idx; } - if (OB_LIKELY(idx >= 0) && OB_LIKELY(idx <= 11)) { + if (OB_LIKELY(idx >= 0) && OB_LIKELY(idx <= sizeof(dist_algo_str) / sizeof(ObString))) { return dist_algo_str[idx]; } else { return dist_algo_str[0];