Merged
[fix] 通信域重复创建时 RPT_INPUT_ERR 补充规范报错 #4965
guanzhongkangAdd on Aug 31
[fix] 通信域重复创建时 RPT_INPUT_ERR 补充规范报错 #4965
Merged
Merged fromTrouble_Im_in/hcommmr-4924-importedintocann/hcommmaster
Total: 5 files changed+146-8
| @@ -5,13 +5,13 @@ | |||
| 5 | The following is error format. The meanings of the placeholders %s in sequence are: operator name, parameter value, parameter name, expected value. | 5 | The following is error format. The meanings of the placeholders %s in sequence are: operator name, parameter value, parameter name, expected value. |
| 6 | 6 | ||
| 7 | ```text | 7 | ```text |
| 8 | -Failed to verify parameters of operator %s (operator name). Value %s for parameter %s is invalid. The expected value is %s. | 8 | +Failed to verify parameters of operator %s. Value %s for parameter %s is invalid. The expected value is %s. |
| 9 | ``` | 9 | ``` |
| 10 | 10 | ||
| 11 | Error example: | 11 | Error example: |
| 12 | 12 | ||
| 13 | ```text | 13 | ```text |
| 14 | -Failed to verify parameters of operator CheckRankID (operator name). Value 1sfa for parameter rank_id is invalid. The expected value is a non-negative decimal number. | 14 | +Failed to verify parameters of operator CheckRankID. Value 1sfa for parameter rank_id is invalid. The expected value is a non-negative decimal number. |
| 15 | ``` | 15 | ``` |
| 16 | 16 | ||
| 17 | ## Solution | 17 | ## Solution |
| @@ -5,13 +5,13 @@ | |||
| 5 | 报错格式如下,占位符%s的含义依次为算子名、参数值、参数名、期望值: | 5 | 报错格式如下,占位符%s的含义依次为算子名、参数值、参数名、期望值: |
| 6 | 6 | ||
| 7 | ```text | 7 | ```text |
| 8 | -Failed to verify parameters of operator %s (operator name). Value %s for parameter %s is invalid. The expected value is %s. | 8 | +Failed to verify parameters of operator %s. Value %s for parameter %s is invalid. The expected value is %s. |
| 9 | ``` | 9 | ``` |
| 10 | 10 | ||
| 11 | 报错示例如下: | 11 | 报错示例如下: |
| 12 | 12 | ||
| 13 | ```text | 13 | ```text |
| 14 | -Failed to verify parameters of operator CheckRankID (operator name). Value 1sfa for parameter rank_id is invalid. The expected value is a non-negative decimal number. | 14 | +Failed to verify parameters of operator CheckRankID. Value 1sfa for parameter rank_id is invalid. The expected value is a non-negative decimal number. |
| 15 | ``` | 15 | ``` |
| 16 | 16 | ||
| 17 | ## 解决方法 | 17 | ## 解决方法 |
| @@ -42,7 +42,7 @@ const std::string hcomm_g_msg = R"( | |||
| 42 | "errClass": "HCCL Errors", | 42 | "errClass": "HCCL Errors", |
| 43 | "errTitle": "Invalid_Argument_Collective_Communication_Operator", | 43 | "errTitle": "Invalid_Argument_Collective_Communication_Operator", |
| 44 | "ErrCode": "EI0003", | 44 | "ErrCode": "EI0003", |
| 45 | - "ErrMessage": "Failed to verify parameters of operator %s (operator name). Value %s for parameter %s is invalid. The expected value is %s.", | 45 | + "ErrMessage": "Failed to verify parameters of operator %s. Value %s for parameter %s is invalid. The expected value is %s.", |
| 46 | "Arglist": "ccl_op,value,parameter,expect", | 46 | "Arglist": "ccl_op,value,parameter,expect", |
| 47 | "suggestion": { | 47 | "suggestion": { |
| 48 | "Possible Cause": "N/A", | 48 | "Possible Cause": "N/A", |
| @@ -225,8 +225,12 @@ HcclResult CreateCommConfigRootInfo( | |||
| 225 | { | 225 | { |
| 226 | // check | 226 | // check |
| 227 | HcclCommInfoV2& opbasedCommInfoV2 = GetCommInfoV2(); | 227 | HcclCommInfoV2& opbasedCommInfoV2 = GetCommInfoV2(); |
| 228 | + bool commExists = opbasedCommInfoV2.hcclGroupMap.find(identifier) != opbasedCommInfoV2.hcclGroupMap.end(); | ||
| 229 | + RPT_INPUT_ERR( | ||
| 230 | + commExists, "EI0003", vector<string>({"ccl_op", "value", "parameter", "expect"}), | ||
| 231 | + vector<string>({"HcclCommInitRootInfo", identifier, "identifier", "an identifier that is not in use"})); | ||
| 228 | CHK_PRT_RET( | 232 | CHK_PRT_RET( |
| 229 | - opbasedCommInfoV2.hcclGroupMap.find(identifier) != opbasedCommInfoV2.hcclGroupMap.end(), | 233 | + commExists, |
| 230 | HCCL_ERROR( | 234 | HCCL_ERROR( |
| 231 | "[HcclCommInitRootInfoConfigV2]errNo[0x%016llx] The comm name[%s] already exists in Group2Comm map.", | 235 | "[HcclCommInitRootInfoConfigV2]errNo[0x%016llx] The comm name[%s] already exists in Group2Comm map.", |
| 232 | HCCL_ERROR_CODE(HCCL_E_PARA), identifier.c_str()), | 236 | HCCL_ERROR_CODE(HCCL_E_PARA), identifier.c_str()), |
| @@ -1783,8 +1787,12 @@ CommInitRootInfo(u32 nRanks, u32 rank, const HcclRootHandleV2& rootHandle, const | |||
| 1783 | CHK_RET(CallSingletons()); | 1787 | CHK_RET(CallSingletons()); |
| 1784 | // check | 1788 | // check |
| 1785 | HcclCommInfoV2& opbasedCommInfoV2 = GetCommInfoV2(); | 1789 | HcclCommInfoV2& opbasedCommInfoV2 = GetCommInfoV2(); |
| 1790 | + bool commExists = opbasedCommInfoV2.hcclGroupMap.find(identifier) != opbasedCommInfoV2.hcclGroupMap.end(); | ||
| 1791 | + RPT_INPUT_ERR( | ||
| 1792 | + commExists, "EI0003", vector<string>({"ccl_op", "value", "parameter", "expect"}), | ||
[MEDIUM] 重复创建分支无 UT 覆盖,PR 描述"补充的UT用例"一节为空 问题分析:
建议修复:
在 ![]() ![]() | |||
| 1793 | + vector<string>({"HcclCommInitRootInfo", identifier, "identifier", "an identifier that is not in use"})); | ||
| 1786 | CHK_PRT_RET( | 1794 | CHK_PRT_RET( |
| 1787 | - opbasedCommInfoV2.hcclGroupMap.find(identifier) != opbasedCommInfoV2.hcclGroupMap.end(), | 1795 | + commExists, |
| 1788 | HCCL_ERROR( | 1796 | HCCL_ERROR( |
| 1789 | "[CreateCommConfig] errNo[0x%016llx] The rootHandle[%s] already exists in Group2Comm map.", | 1797 | "[CreateCommConfig] errNo[0x%016llx] The rootHandle[%s] already exists in Group2Comm map.", |
| 1790 | HCCL_ERROR_CODE(HCCL_E_PARA), identifier.c_str()), | 1798 | HCCL_ERROR_CODE(HCCL_E_PARA), identifier.c_str()), |
| @@ -1943,8 +1951,12 @@ HcclResult HcclCommInitRootInfoConfigV2( | |||
| 1943 | // 临时规避,在初始化通信域前声明单例保证时序 | 1951 | // 临时规避,在初始化通信域前声明单例保证时序 |
| 1944 | CHK_RET(CallSingletons()); | 1952 | CHK_RET(CallSingletons()); |
| 1945 | HcclCommInfoV2& opbasedCommInfoV2 = GetCommInfoV2(); | 1953 | HcclCommInfoV2& opbasedCommInfoV2 = GetCommInfoV2(); |
| 1954 | + bool commExists = opbasedCommInfoV2.hcclGroupMap.find(identifier) != opbasedCommInfoV2.hcclGroupMap.end(); | ||
| 1955 | + RPT_INPUT_ERR( | ||
| 1956 | + commExists, "EI0003", vector<string>({"ccl_op", "value", "parameter", "expect"}), | ||
[MEDIUM] 910 legacy 侧同型"通信域重复创建"查重未补充 EI0003 上报,修复范围存在缺口 问题分析:
建议修复:
二选一:
(1) 在 op_base.cc ![]() ![]() | |||
| 1957 | + vector<string>({"HcclCommInitRootInfo", identifier, "identifier", "an identifier that is not in use"})); | ||
| 1946 | CHK_PRT_RET( | 1958 | CHK_PRT_RET( |
| 1947 | - opbasedCommInfoV2.hcclGroupMap.find(identifier) != opbasedCommInfoV2.hcclGroupMap.end(), | 1959 | + commExists, |
| 1948 | HCCL_ERROR( | 1960 | HCCL_ERROR( |
| 1949 | "[HcclCommInitRootInfoConfigV2]errNo[0x%016llx] The comm name[%s] already exists in Group2Comm map.", | 1961 | "[HcclCommInitRootInfoConfigV2]errNo[0x%016llx] The comm name[%s] already exists in Group2Comm map.", |
| 1950 | HCCL_ERROR_CODE(HCCL_E_PARA), identifier.c_str()), | 1962 | HCCL_ERROR_CODE(HCCL_E_PARA), identifier.c_str()), |
| @@ -2490,6 +2490,132 @@ TEST_F(OpbaseTestV2, Ut_HcclCommInitRootInfoConfigV2_When_ProviderFails_Expect_R | |||
| 2490 | EXPECT_EQ(HcclCommInitRootInfoConfigV2(nRanks, &rootInfo, rank, &config, &comm), HCCL_E_INTERNAL); | 2490 | EXPECT_EQ(HcclCommInitRootInfoConfigV2(nRanks, &rootInfo, rank, &config, &comm), HCCL_E_INTERNAL); |
| 2491 | } | 2491 | } |
| 2492 | 2492 | ||
| 2493 | +namespace { | ||
| 2494 | +// 捕获 RptInputErr 上报内容, 用于断言通信域重复创建时触发 EI0003 规范报错 | ||
| 2495 | +std::string g_dupRptErrorCode; | ||
| 2496 | +std::vector<std::string> g_dupRptKeys; | ||
| 2497 | +std::vector<std::string> g_dupRptValues; | ||
| 2498 | + | ||
| 2499 | +void stub_RptInputErr_capture(std::string error_code, std::vector<std::string> key, std::vector<std::string> value) | ||
| 2500 | +{ | ||
| 2501 | + g_dupRptErrorCode = error_code; | ||
| 2502 | + g_dupRptKeys = key; | ||
| 2503 | + g_dupRptValues = value; | ||
| 2504 | +} | ||
| 2505 | +} // namespace | ||
| 2506 | + | ||
| 2507 | +// op_base_v2.cc 内部接口(未在头文件中声明): 其查重分支被 HcclCommInitRootInfoConfigV2 入口查重遮蔽, | ||
| 2508 | +// 公共接口无法触达, 此处声明用于直接测试 | ||
| 2509 | +HcclResult CreateCommConfigRootInfo( | ||
| 2510 | + uint32_t rank, const HcclCommConfig* config, const std::string& identifier, const RankTableInfo& ranktable, | ||
| 2511 | + HcclComm* comm); | ||
| 2512 | + | ||
| 2513 | +// 相同 identifier 重复创建通信域: CommInitRootInfo 查重命中, 上报 EI0003 并返回 HCCL_E_PARA | ||
| 2514 | +TEST_F(OpbaseTestV2, Ut_HcclCommInitRootInfoV2_When_DuplicateCreation_Expect_Return_HCCL_E_PARA) | ||
| 2515 | +{ | ||
| 2516 | + // when | ||
| 2517 | + MOCKER(HrtGetDeviceType).stubs().with(mockcpp::any()).will(returnValue((DevType)DevType::DEV_TYPE_950)); | ||
| 2518 | + MOCKER(HrtGetDeviceCount).stubs().will(returnValue(1)); | ||
| 2519 | + MOCKER_CPP(&HcclCommunicator::Init, HcclResult(HcclCommunicator::*)(const RankTableInfo&)) | ||
| 2520 | + .stubs() | ||
| 2521 | + .with(mockcpp::any()) | ||
| 2522 | + .will(returnValue(HCCL_SUCCESS)); | ||
| 2523 | + MOCKER_CPP(&CommunicatorImpl::SetCommExecuteConfig).stubs().will(ignoreReturnValue()); | ||
| 2524 | + MOCKER(RptInputErr).stubs().will(invoke(stub_RptInputErr_capture)); | ||
| 2525 | + CommManager::GetInstance(0).GetCommInfoV2().hcclGroupMap.clear(); | ||
| 2526 | + CommManager::GetInstance(0).GetCommInfoV2().pComm = nullptr; | ||
| 2527 | + | ||
| 2528 | + // then: 首次创建成功, 不触发规范报错 | ||
| 2529 | + uint32_t nRanks = 1; | ||
| 2530 | + HcclRootInfo rootInfo{}; | ||
| 2531 | + uint32_t rank = 0; | ||
| 2532 | + HcclComm commFirst{}; | ||
| 2533 | + std::string identifier{}; | ||
| 2534 | + g_dupRptErrorCode.clear(); | ||
| 2535 | + EXPECT_EQ(HcclCommInitRootInfoV2(nRanks, &rootInfo, rank, &commFirst, identifier), HCCL_SUCCESS); | ||
| 2536 | + EXPECT_TRUE(g_dupRptErrorCode.empty()); | ||
| 2537 | + | ||
| 2538 | + // 相同 rootInfo(即相同 identifier)重复创建: 查重命中, 上报 EI0003 并返回 HCCL_E_PARA | ||
| 2539 | + HcclComm commSecond{}; | ||
| 2540 | + EXPECT_EQ(HcclCommInitRootInfoV2(nRanks, &rootInfo, rank, &commSecond, identifier), HCCL_E_PARA); | ||
| 2541 | + EXPECT_EQ(g_dupRptErrorCode, "EI0003"); | ||
| 2542 | + ASSERT_EQ(g_dupRptValues.size(), 4); // ccl_op/value/parameter/expect | ||
| 2543 | + EXPECT_EQ(g_dupRptValues[0], "HcclCommInitRootInfo"); | ||
| 2544 | + EXPECT_EQ(g_dupRptValues[2], "identifier"); | ||
| 2545 | + | ||
| 2546 | + // 清理现场, 避免残留通信域信息影响后续用例 | ||
| 2547 | + CommManager::GetInstance(0).GetCommInfoV2().hcclGroupMap.clear(); | ||
| 2548 | + CommManager::GetInstance(0).GetCommInfoV2().pComm = nullptr; | ||
| 2549 | +} | ||
| 2550 | + | ||
| 2551 | +// 相同 identifier 重复创建通信域(带 config): HcclCommInitRootInfoConfigV2 查重命中, | ||
| 2552 | +// 上报 EI0003 并返回 HCCL_E_PARA | ||
| 2553 | +TEST_F(OpbaseTestV2, Ut_HcclCommInitRootInfoConfigV2_When_DuplicateCreation_Expect_Return_HCCL_E_PARA) | ||
| 2554 | +{ | ||
| 2555 | + // when | ||
| 2556 | + MOCKER(HrtGetDeviceType).stubs().with(mockcpp::any()).will(returnValue((DevType)DevType::DEV_TYPE_950)); | ||
| 2557 | + MOCKER(HrtGetDeviceCount).stubs().will(returnValue(1)); | ||
| 2558 | + MOCKER_CPP(&HcclCommunicator::Init, HcclResult(HcclCommunicator::*)(const RankTableInfo&)) | ||
| 2559 | + .stubs() | ||
| 2560 | + .with(mockcpp::any()) | ||
| 2561 | + .will(returnValue(HCCL_SUCCESS)); | ||
| 2562 | + MOCKER_CPP(&CommunicatorImpl::SetCommExecuteConfig).stubs().will(ignoreReturnValue()); | ||
| 2563 | + MOCKER(RptInputErr).stubs().will(invoke(stub_RptInputErr_capture)); | ||
| 2564 | + CommManager::GetInstance(0).GetCommInfoV2().hcclGroupMap.clear(); | ||
| 2565 | + CommManager::GetInstance(0).GetCommInfoV2().pComm = nullptr; | ||
| 2566 | + | ||
| 2567 | + // then: 首次创建成功, 不触发规范报错 | ||
| 2568 | + uint32_t nRanks{2}; | ||
| 2569 | + HcclRootInfo rootInfo{}; | ||
| 2570 | + uint32_t rank{}; | ||
| 2571 | + HcclComm commFirst{}; | ||
| 2572 | + HcclCommConfig config{}; | ||
| 2573 | + string worldgroup = "ut_dup_rootinfo_config"; | ||
| 2574 | + PrepareCommConfig(config, 200, worldgroup, 1, 0); | ||
| 2575 | + g_dupRptErrorCode.clear(); | ||
| 2576 | + EXPECT_EQ(HcclCommInitRootInfoConfigV2(nRanks, &rootInfo, rank, &config, &commFirst), HCCL_SUCCESS); | ||
| 2577 | + EXPECT_TRUE(g_dupRptErrorCode.empty()); | ||
| 2578 | + | ||
| 2579 | + // 相同 config(即相同 identifier)重复创建: 查重命中, 上报 EI0003 并返回 HCCL_E_PARA | ||
| 2580 | + HcclComm commSecond{}; | ||
| 2581 | + EXPECT_EQ(HcclCommInitRootInfoConfigV2(nRanks, &rootInfo, rank, &config, &commSecond), HCCL_E_PARA); | ||
| 2582 | + EXPECT_EQ(g_dupRptErrorCode, "EI0003"); | ||
| 2583 | + ASSERT_EQ(g_dupRptValues.size(), 4); // ccl_op/value/parameter/expect | ||
| 2584 | + EXPECT_EQ(g_dupRptValues[0], "HcclCommInitRootInfo"); | ||
| 2585 | + EXPECT_EQ(g_dupRptValues[1], worldgroup); | ||
| 2586 | + EXPECT_EQ(g_dupRptValues[2], "identifier"); | ||
| 2587 | + | ||
| 2588 | + // 清理现场, 避免残留通信域信息影响后续用例 | ||
| 2589 | + CommManager::GetInstance(0).GetCommInfoV2().hcclGroupMap.clear(); | ||
| 2590 | + CommManager::GetInstance(0).GetCommInfoV2().pComm = nullptr; | ||
| 2591 | +} | ||
| 2592 | + | ||
| 2593 | +// 相同 identifier 重复创建通信域: CreateCommConfigRootInfo 查重命中, | ||
| 2594 | +// 上报 EI0003 并返回 HCCL_E_PARA(该分支位于接口内部, 需预置 map 后直接调用) | ||
| 2595 | +TEST_F(OpbaseTestV2, Ut_CreateCommConfigRootInfo_When_DuplicateCreation_Expect_Return_HCCL_E_PARA) | ||
| 2596 | +{ | ||
| 2597 | + // 预置 identifier 已存在的通信域信息 | ||
| 2598 | + MOCKER(RptInputErr).stubs().will(invoke(stub_RptInputErr_capture)); | ||
| 2599 | + const string dupIdentifier = "ut_dup_createcommconfig_rootinfo"; | ||
| 2600 | + HcclGroupParamsV2 params{}; | ||
| 2601 | + CommManager::GetInstance(0).GetCommInfoV2().hcclGroupMap[dupIdentifier] = params; | ||
| 2602 | + | ||
| 2603 | + uint32_t rank{}; | ||
| 2604 | + HcclCommConfig config{}; | ||
| 2605 | + HcclCommConfigInit(&config); | ||
| 2606 | + HcclComm comm{}; | ||
| 2607 | + g_dupRptErrorCode.clear(); | ||
| 2608 | + EXPECT_EQ(CreateCommConfigRootInfo(rank, &config, dupIdentifier, RankTableInfo{}, &comm), HCCL_E_PARA); | ||
| 2609 | + EXPECT_EQ(g_dupRptErrorCode, "EI0003"); | ||
| 2610 | + ASSERT_EQ(g_dupRptValues.size(), 4); // ccl_op/value/parameter/expect | ||
| 2611 | + EXPECT_EQ(g_dupRptValues[0], "HcclCommInitRootInfo"); | ||
| 2612 | + EXPECT_EQ(g_dupRptValues[1], dupIdentifier); | ||
| 2613 | + EXPECT_EQ(g_dupRptValues[2], "identifier"); | ||
| 2614 | + | ||
| 2615 | + // 清理现场, 避免残留通信域信息影响后续用例 | ||
| 2616 | + CommManager::GetInstance(0).GetCommInfoV2().hcclGroupMap.clear(); | ||
| 2617 | +} | ||
| 2618 | + | ||
| 2493 | TEST_F(OpbaseTestV2, Ut_HcclCommInitAllV2_When_InputValue_Expect_Return_HCCL_SUCCESS) | 2619 | TEST_F(OpbaseTestV2, Ut_HcclCommInitAllV2_When_InputValue_Expect_Return_HCCL_SUCCESS) |
| 2494 | { | 2620 | { |
| 2495 | // when | 2621 | // when |


[LOW] PR 描述“文档更新:无”与实际改动 2 个错误码文档不符
问题描述: 本 PR 实际修改了
docs/zh/error_codes/EI0003-*.md与docs/en/error_codes/EI0003-*.md两个文档(错误格式与示例中删除了%s后的(operator name)括号注释),以及src/legacy/ascend910/common/error_code/error_code.cc中 EI0003 的 ErrMessage 模板(同步删除(operator name))。但 PR 描述的“文档更新”栏填的是“无”,“描述”栏也未提及模板文案变更。这属于错误码模板的行为变更:凡是 EI0003 渲染出的报错文案都会少一段
(operator name)注释,影响用户可见的报错格式与资料一致性。建议修复: 在 PR 描述中补充说明:
(operator name)括号注释(error_code.cc 与中英文档同步),并说明该变更与本次 RPT_INPUT_ERR 上报的关系(如:新上报的 ccl_op 槽直接渲染算子名,模板中的重复注释不再需要)。若该模板变更是顺手修复而非本 PR 目标,建议在描述中单独声明,便于 committer 评审时确认影响面。