diff --git a/debug/accuracy_tools/api_accuracy_checker/compare/algorithm.py b/debug/accuracy_tools/api_accuracy_checker/compare/algorithm.py index 71df553503b275de16839327c8867ed4771c689b..b3392546e0f38dd8df1efe52e8f1a93b75638968 100644 --- a/debug/accuracy_tools/api_accuracy_checker/compare/algorithm.py +++ b/debug/accuracy_tools/api_accuracy_checker/compare/algorithm.py @@ -213,6 +213,12 @@ def compare_core(bench_out, npu_out): else: status, compare_result, message = compare_core(list(bench_out.values()), list(npu_out.values())) elif isinstance(bench_out, torch.Tensor): + if bench_out.numel() == 0 and npu_out.numel() == 0: + return CompareConst.PASS, compare_column, "bench and npu output is empty." + elif bench_out.numel() == 0 and npu_out.numel() != 0: + return CompareConst.ERROR, compare_column, "bench output is empty but npu output is not empty." + elif bench_out.numel() != 0 and npu_out.numel() == 0: + return CompareConst.ERROR, compare_column, "bench output is not empty but npu output is empty." copy_bench_out = bench_out.detach().clone() copy_npu_out = npu_out.detach().clone() compare_column.bench_type = str(copy_bench_out.dtype) diff --git a/debug/accuracy_tools/api_accuracy_checker/dump/api_info.py b/debug/accuracy_tools/api_accuracy_checker/dump/api_info.py index 1d4c69d9ca34190e4bebee06cef0039550aa7f07..b3fe1249486756d6709f1d9963e5353c5eebffa7 100644 --- a/debug/accuracy_tools/api_accuracy_checker/dump/api_info.py +++ b/debug/accuracy_tools/api_accuracy_checker/dump/api_info.py @@ -11,6 +11,8 @@ from ptdbg_ascend.src.python.ptdbg_ascend.common.utils import check_path_before_ def get_tensor_extremum(data, operator): if data.dtype is torch.bool: + if data.numel() == 0: + return False if operator == 'max': return True in data elif operator == 'min': diff --git a/debug/accuracy_tools/api_accuracy_checker/run_ut/data_generate.py b/debug/accuracy_tools/api_accuracy_checker/run_ut/data_generate.py index bc8c4e1a2c2abf4dfb12aa0734ed38d02ff77769..e9c25f7faf56fb24dbb4c43851e4853243172568 100644 --- a/debug/accuracy_tools/api_accuracy_checker/run_ut/data_generate.py +++ b/debug/accuracy_tools/api_accuracy_checker/run_ut/data_generate.py @@ -164,6 +164,8 @@ def gen_bool_tensor(low, high, shape): shape:The shape of Tensor """ low, high = int(low), int(high) + if low > high: + low, high = high, low tensor = torch.randint(low, high + 1, shape) data = torch.gt(tensor, 0) return data diff --git a/debug/accuracy_tools/api_accuracy_checker/run_ut/run_overflow_check.py b/debug/accuracy_tools/api_accuracy_checker/run_ut/run_overflow_check.py index df8d8b153bd3959b4fd2d0f6ae06ed94fda93d66..9f968c1d87064d81c0e6b723a1754bb6dbdcf9d0 100644 --- a/debug/accuracy_tools/api_accuracy_checker/run_ut/run_overflow_check.py +++ b/debug/accuracy_tools/api_accuracy_checker/run_ut/run_overflow_check.py @@ -70,7 +70,7 @@ def run_torch_api(api_full_name, api_info_dict): if not need_grad: print_warn_log("%s function with out=... arguments don't support automatic differentiation, skip backward." % api_full_name) - npu_args, npu_kwargs = generate_device_params(args, kwargs, False) + npu_args, npu_kwargs = generate_device_params(args, kwargs, False, api_name) if kwargs.get("device"): del kwargs["device"] out = exec_api(api_type, api_name, args, kwargs) diff --git a/debug/accuracy_tools/api_accuracy_checker/run_ut/run_ut.py b/debug/accuracy_tools/api_accuracy_checker/run_ut/run_ut.py index 5dd50566da4c188c7172eae87f7cfdc5a16c9a43..72ca05d49e92b00f165465301e59213a35242672 100644 --- a/debug/accuracy_tools/api_accuracy_checker/run_ut/run_ut.py +++ b/debug/accuracy_tools/api_accuracy_checker/run_ut/run_ut.py @@ -37,6 +37,7 @@ DETAILS_FILE_NAME = "accuracy_checking_details_" + current_time + ".csv" RunUTConfig = namedtuple('RunUTConfig', ['forward_content', 'backward_content', 'result_csv_path', 'details_csv_path', 'save_error_data', 'is_continue_run_ut', 'real_data_path']) not_backward_list = ['repeat_interleave'] +not_detach_set = {'resize_', 'resize_as_', 'set_', 'transpose_', 't_', 'squeeze_', 'unsqueeze_'} tqdm_params = { 'smoothing': 0, # 平滑进度条的预计剩余时间,取值范围0到1 @@ -77,8 +78,8 @@ def deal_dtype(arg, raise_dtype=None): return arg.type(raise_dtype) -def generate_device_params(input_args, input_kwargs, need_backward): - def recursive_arg_to_device(arg_in, to_detach=True): +def generate_device_params(input_args, input_kwargs, need_backward, api_name): + def recursive_arg_to_device(arg_in, to_detach): if isinstance(arg_in, (list, tuple)): return type(arg_in)(recursive_arg_to_device(arg, to_detach) for arg in arg_in) elif isinstance(arg_in, torch.Tensor): @@ -93,13 +94,15 @@ def generate_device_params(input_args, input_kwargs, need_backward): else: return arg_in - device_args = recursive_arg_to_device(input_args) - device_kwargs = {key: recursive_arg_to_device(value, key != "out") for key, value in input_kwargs.items()} + is_detach = api_name not in not_detach_set + device_args = recursive_arg_to_device(input_args, is_detach) + device_kwargs = \ + {key: recursive_arg_to_device(value, key != "out" and is_detach) for key, value in input_kwargs.items()} return device_args, device_kwargs -def generate_cpu_params(input_args, input_kwargs, need_backward): - def recursive_arg_to_cpu(arg_in, to_detach=True, raise_dtype=None): +def generate_cpu_params(input_args, input_kwargs, need_backward, api_name): + def recursive_arg_to_cpu(arg_in, to_detach, raise_dtype=None): if isinstance(arg_in, (list, tuple)): return type(arg_in)(recursive_arg_to_cpu(arg, to_detach, raise_dtype=raise_dtype) for arg in arg_in) elif isinstance(arg_in, torch.Tensor): @@ -128,8 +131,9 @@ def generate_cpu_params(input_args, input_kwargs, need_backward): elif len(need_raise_dtypes) >= 2: raise_dtype = torch.float32 - cpu_args = recursive_arg_to_cpu(input_args, raise_dtype=raise_dtype) - cpu_kwargs = {key: recursive_arg_to_cpu(value, key != "out") for key, value in input_kwargs.items()} + is_detach = api_name not in not_detach_set + cpu_args = recursive_arg_to_cpu(input_args, is_detach, raise_dtype=raise_dtype) + cpu_kwargs = {key: recursive_arg_to_cpu(value, key != "out" and is_detach) for key, value in input_kwargs.items()} return cpu_args, cpu_kwargs @@ -205,8 +209,8 @@ def run_torch_api(api_full_name, real_data_path, backward_content, api_info_dict need_backward = need_backward and need_grad if kwargs.get("device"): del kwargs["device"] - cpu_args, cpu_kwargs = generate_cpu_params(args, kwargs, need_backward) - device_args, device_kwargs = generate_device_params(args, kwargs, need_backward) + cpu_args, cpu_kwargs = generate_cpu_params(args, kwargs, need_backward, api_name) + device_args, device_kwargs = generate_device_params(args, kwargs, need_backward, api_name) bench_grad_out, device_grad_out = None, None out = exec_api(api_type, api_name, cpu_args, cpu_kwargs) device_out = exec_api(api_type, api_name, device_args, device_kwargs) @@ -220,7 +224,7 @@ def run_torch_api(api_full_name, real_data_path, backward_content, api_info_dict if need_backward: backward_args = backward_content[api_full_name] grad = gen_args(backward_args, real_data_path=real_data_path)[0] - bench_grad, _ = generate_cpu_params(grad, {}, False) + bench_grad, _ = generate_cpu_params(grad, {}, False, api_name) bench_grad_out = run_backward(cpu_args, bench_grad, grad_index, out) device_grad = grad.clone().detach().to(current_device) device_grad_out = run_backward(device_args, device_grad, grad_index, device_out) diff --git a/debug/accuracy_tools/api_accuracy_checker/test/ut/run_ut/test_run_ut.py b/debug/accuracy_tools/api_accuracy_checker/test/ut/run_ut/test_run_ut.py index 21ec2f0072c7b9dba5a93234ce476b48e13d5622..fdcc1cfddeb38d4fca0d2a67a09147b571b35def 100644 --- a/debug/accuracy_tools/api_accuracy_checker/test/ut/run_ut/test_run_ut.py +++ b/debug/accuracy_tools/api_accuracy_checker/test/ut/run_ut/test_run_ut.py @@ -19,7 +19,7 @@ class TestRunUtMethods(unittest.TestCase): api_info = copy.deepcopy(api_info_dict) [api_type, api_name, _] = api_full_name.split("*") args, kwargs, need_grad = get_api_info(api_info, api_name, None) - cpu_args, cpu_kwargs = generate_cpu_params(args, kwargs, True) + cpu_args, cpu_kwargs = generate_cpu_params(args, kwargs, True, '') out = exec_api(api_type, api_name, cpu_args, cpu_kwargs) self.assertEqual(out.dtype, torch.float64) self.assertTrue(out.requires_grad) @@ -42,7 +42,7 @@ class TestRunUtMethods(unittest.TestCase): mocks['retain_grad'].return_value = None mocks['to'].return_value = mock_tensor - device_args, device_kwargs = generate_device_params([mock_tensor], {'inplace': False}, True) + device_args, device_kwargs = generate_device_params([mock_tensor], {'inplace': False}, True, '') self.assertEqual(len(device_args), 1) self.assertEqual(device_args[0].dtype, torch.float32) self.assertTrue(device_args[0].requires_grad) @@ -53,7 +53,7 @@ class TestRunUtMethods(unittest.TestCase): api_info = copy.deepcopy(api_info_dict) [api_type, api_name, _] = api_full_name.split("*") args, kwargs, need_grad = get_api_info(api_info, api_name, None) - cpu_args, cpu_kwargs = generate_cpu_params(args, kwargs, True) + cpu_args, cpu_kwargs = generate_cpu_params(args, kwargs, True, '') self.assertEqual(len(cpu_args), 1) self.assertEqual(cpu_args[0].dtype, torch.float64) self.assertTrue(cpu_args[0].requires_grad)