From 1513061fdd87516f34c82d613983dbdc57adcfb0 Mon Sep 17 00:00:00 2001 From: Sagar Kamble Date: Fri, 3 Jan 2020 21:42:51 +0530 Subject: [PATCH] gpu: nvgpu: falcon: test and code updates for more branch coverage Passing branch of nvgpu_timeout_peek_expired was not covered due to jump over it in nvgpu_falcon_mem_scrub_wait. Remove that jump to cover the branch. Add unit test for covering the error handling in case of read from DMEM control register returns invalid data using fault injection. JIRA NVGPU-4814 Change-Id: I9f99186bd2b1c5f39ead130d3161d3e7fa622ac4 Signed-off-by: Sagar Kamble Reviewed-on: https://git-master.nvidia.com/r/2272937 Reviewed-by: mobile promotions Tested-by: mobile promotions --- drivers/gpu/nvgpu/common/falcon/falcon.c | 5 ++- .../nvgpu/posix/posix-fault-injection.h | 1 + drivers/gpu/nvgpu/libnvgpu-drv_safe.export | 4 ++- userspace/required_tests.json | 6 ++++ userspace/units/falcon/falcon_tests/falcon.c | 35 ++++++++++++++++++- .../units/falcon/falcon_tests/nvgpu-falcon.h | 25 ++++++++++++- userspace/units/falcon/falcon_utf.c | 18 +++++++++- userspace/units/falcon/falcon_utf.h | 4 ++- userspace/units/falcon/libfalcon_utf.export | 3 +- 9 files changed, 92 insertions(+), 9 deletions(-) diff --git a/drivers/gpu/nvgpu/common/falcon/falcon.c b/drivers/gpu/nvgpu/common/falcon/falcon.c index c30a57874..54e44d317 100644 --- a/drivers/gpu/nvgpu/common/falcon/falcon.c +++ b/drivers/gpu/nvgpu/common/falcon/falcon.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2019, NVIDIA CORPORATION. All rights reserved. + * Copyright (c) 2017-2020, NVIDIA CORPORATION. All rights reserved. * * Permission is hereby granted, free of charge, to any person obtaining a * copy of this software and associated documentation files (the "Software"), @@ -164,7 +164,7 @@ int nvgpu_falcon_mem_scrub_wait(struct nvgpu_falcon *flcn) do { if (g->ops.falcon.is_falcon_scrubbing_done(flcn)) { - goto exit; + break; } nvgpu_udelay(MEM_SCRUBBING_TIMEOUT_DEFAULT); } while (nvgpu_timeout_expired(&timeout) == 0); @@ -173,7 +173,6 @@ int nvgpu_falcon_mem_scrub_wait(struct nvgpu_falcon *flcn) status = -ETIMEDOUT; } -exit: return status; } diff --git a/drivers/gpu/nvgpu/include/nvgpu/posix/posix-fault-injection.h b/drivers/gpu/nvgpu/include/nvgpu/posix/posix-fault-injection.h index 035f1c3c0..72a447719 100644 --- a/drivers/gpu/nvgpu/include/nvgpu/posix/posix-fault-injection.h +++ b/drivers/gpu/nvgpu/include/nvgpu/posix/posix-fault-injection.h @@ -48,6 +48,7 @@ struct nvgpu_posix_fault_inj_container { struct nvgpu_posix_fault_inj dma_fi; struct nvgpu_posix_fault_inj queue_out_fi; struct nvgpu_posix_fault_inj timers_fi; + struct nvgpu_posix_fault_inj falcon_memcpy_fi; /* qnx */ struct nvgpu_posix_fault_inj sdl_nvguard_fi; diff --git a/drivers/gpu/nvgpu/libnvgpu-drv_safe.export b/drivers/gpu/nvgpu/libnvgpu-drv_safe.export index 57a060c85..dd6525e63 100644 --- a/drivers/gpu/nvgpu/libnvgpu-drv_safe.export +++ b/drivers/gpu/nvgpu/libnvgpu-drv_safe.export @@ -1,4 +1,4 @@ -# Copyright (c) 2019, NVIDIA CORPORATION. All rights reserved. +# Copyright (c) 2019-2020, NVIDIA CORPORATION. All rights reserved. bitmap_find_next_zero_area_off bug_handler_cancel @@ -587,6 +587,8 @@ nvgpu_pmu_reset nvgpu_posix_bug nvgpu_posix_cleanup nvgpu_posix_enable_fault_injection +nvgpu_posix_fault_injection_get_container +nvgpu_posix_fault_injection_handle_call nvgpu_posix_ffs nvgpu_posix_fls nvgpu_posix_init_fault_injection diff --git a/userspace/required_tests.json b/userspace/required_tests.json index 1fecb8a5d..481e5125c 100644 --- a/userspace/required_tests.json +++ b/userspace/required_tests.json @@ -593,6 +593,12 @@ "unit": "falcon", "test_level": 0 }, + { + "test": "test_falcon_mem_rw_fault", + "case": "falcon_mem_rw_fault", + "unit": "falcon", + "test_level": 0 + }, { "test": "test_falcon_mem_rw_init", "case": "falcon_mem_rw_init", diff --git a/userspace/units/falcon/falcon_tests/falcon.c b/userspace/units/falcon/falcon_tests/falcon.c index 7fac36f72..6c9354169 100644 --- a/userspace/units/falcon/falcon_tests/falcon.c +++ b/userspace/units/falcon/falcon_tests/falcon.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2019, NVIDIA CORPORATION. All rights reserved. + * Copyright (c) 2019-2020, NVIDIA CORPORATION. All rights reserved. * * Permission is hereby granted, free of charge, to any person obtaining a * copy of this software and associated documentation files (the "Software"), @@ -964,6 +964,38 @@ int test_falcon_mem_rw_range(struct unit_module *m, struct gk20a *g, return UNIT_SUCCESS; } +/* + * Writing data to falcon's DMEM should not succeed when DMEMC + * read returns invalid value due to HW fault. + */ +int test_falcon_mem_rw_fault(struct unit_module *m, struct gk20a *g, + void *__args) +{ + struct nvgpu_posix_fault_inj *falcon_memcpy_fi = + nvgpu_utf_falcon_memcpy_get_fault_injection(); + u32 byte_cnt = RAND_DATA_SIZE; + u32 dst = 0; + int err = UNIT_FAIL; + + if (pmu_flcn == NULL || !pmu_flcn->is_falcon_supported) { + unit_return_fail(m, "test environment not initialized."); + } + + /* cause write failure */ + nvgpu_posix_enable_fault_injection(falcon_memcpy_fi, true, 0); + unit_info(m, "Writing %d bytes to dmem with hw fault injected.\n", + byte_cnt); + err = nvgpu_falcon_copy_to_dmem(pmu_flcn, dst, (u8 *) rand_test_data, + byte_cnt, 0); + nvgpu_posix_enable_fault_injection(falcon_memcpy_fi, false, 0); + + if (err == 0) { + unit_return_fail(m, "Copy to DMEM succeeded with faulty hw.\n"); + } + + return UNIT_SUCCESS; +} + /* * Valid/Invalid: Reading and writing data at offset that is word (4-byte) * aligned data should work and fail otherwise. @@ -1353,6 +1385,7 @@ struct unit_module_test falcon_tests[] = { UNIT_TEST(falcon_mem_rw_unaligned_cpu_buffer, test_falcon_mem_rw_unaligned_cpu_buffer, NULL, 0), UNIT_TEST(falcon_mem_rw_range, test_falcon_mem_rw_range, NULL, 0), + UNIT_TEST(falcon_mem_rw_fault, test_falcon_mem_rw_fault, NULL, 0), UNIT_TEST(falcon_mem_rw_aligned, test_falcon_mem_rw_aligned, NULL, 0), UNIT_TEST(falcon_mem_rw_zero, test_falcon_mem_rw_zero, NULL, 0), UNIT_TEST(falcon_mailbox, test_falcon_mailbox, NULL, 0), diff --git a/userspace/units/falcon/falcon_tests/nvgpu-falcon.h b/userspace/units/falcon/falcon_tests/nvgpu-falcon.h index 6af5ffef3..1145985d3 100644 --- a/userspace/units/falcon/falcon_tests/nvgpu-falcon.h +++ b/userspace/units/falcon/falcon_tests/nvgpu-falcon.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2019, NVIDIA CORPORATION. All rights reserved. + * Copyright (c) 2019-2020, NVIDIA CORPORATION. All rights reserved. * * Permission is hereby granted, free of charge, to any person obtaining a * copy of this software and associated documentation files (the "Software"), @@ -216,6 +216,29 @@ int test_falcon_mem_rw_init(struct unit_module *m, struct gk20a *g, int test_falcon_mem_rw_range(struct unit_module *m, struct gk20a *g, void *__args); +/** + * Test specification for: test_falcon_mem_rw_fault + * + * Description: The falcon unit shall fail the call to copy to DMEM when + * DMEMC reads return invalid value due to HW fault. + * + * Test Type: Error injection + * + * Input: None. + * + * Steps: + * - Enable the falcon DMEMC read fault. + * - Invoke nvgpu_falcon_copy_to_dmem with initialized falcon struct with + * sample random data and valid range. + * - Disable the falcon DMEMC read fault. + * - Verify that writes failed. + * + * Output: Returns PASS if the steps above were executed successfully. FAIL + * otherwise. + */ +int test_falcon_mem_rw_fault(struct unit_module *m, struct gk20a *g, + void *__args); + /** * Test specification for: test_falcon_mem_rw_aligned * diff --git a/userspace/units/falcon/falcon_utf.c b/userspace/units/falcon/falcon_utf.c index d7f382c6f..583902214 100644 --- a/userspace/units/falcon/falcon_utf.c +++ b/userspace/units/falcon/falcon_utf.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2019, NVIDIA CORPORATION. All rights reserved. + * Copyright (c) 2019-2020, NVIDIA CORPORATION. All rights reserved. * * Permission is hereby granted, free of charge, to any person obtaining a * copy of this software and associated documentation files (the "Software"), @@ -29,6 +29,16 @@ #include "falcon_utf.h" +#include + +struct nvgpu_posix_fault_inj *nvgpu_utf_falcon_memcpy_get_fault_injection(void) +{ + struct nvgpu_posix_fault_inj_container *c = + nvgpu_posix_fault_injection_get_container(); + + return &c->falcon_memcpy_fi; +} + void nvgpu_utf_falcon_writel_access_reg_fn(struct gk20a *g, struct utf_falcon *flcn, struct nvgpu_reg_access *access) @@ -139,6 +149,12 @@ void nvgpu_utf_falcon_readl_access_reg_fn(struct gk20a *g, ctrl_r = nvgpu_posix_io_readl_reg_space(g, flcn_base + falcon_falcon_dmemc_r(0)); + if (nvgpu_posix_fault_injection_handle_call( + nvgpu_utf_falcon_memcpy_get_fault_injection())) { + access->value = 0; + return; + } + access->value = ctrl_r & addr_mask; } else { access->value = nvgpu_posix_io_readl_reg_space(g, access->addr); diff --git a/userspace/units/falcon/falcon_utf.h b/userspace/units/falcon/falcon_utf.h index 3ca6cb73e..520213ab7 100644 --- a/userspace/units/falcon/falcon_utf.h +++ b/userspace/units/falcon/falcon_utf.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2019, NVIDIA CORPORATION. All rights reserved. + * Copyright (c) 2019-2020, NVIDIA CORPORATION. All rights reserved. * * Permission is hereby granted, free of charge, to any person obtaining a * copy of this software and associated documentation files (the "Software"), @@ -38,6 +38,8 @@ struct utf_falcon { u32 *dmem; }; +struct nvgpu_posix_fault_inj *nvgpu_utf_falcon_memcpy_get_fault_injection(void); + void nvgpu_utf_falcon_writel_access_reg_fn(struct gk20a *g, struct utf_falcon *flcn, struct nvgpu_reg_access *access); diff --git a/userspace/units/falcon/libfalcon_utf.export b/userspace/units/falcon/libfalcon_utf.export index 50a81d377..b29689d2a 100644 --- a/userspace/units/falcon/libfalcon_utf.export +++ b/userspace/units/falcon/libfalcon_utf.export @@ -1,5 +1,5 @@ # -# Copyright (c) 2019, NVIDIA CORPORATION. All rights reserved. +# Copyright (c) 2019-2020, NVIDIA CORPORATION. All rights reserved. # # Permission is hereby granted, free of charge, to any person obtaining a # copy of this software and associated documentation files (the "Software"), @@ -25,3 +25,4 @@ nvgpu_utf_falcon_init nvgpu_utf_falcon_readl_access_reg_fn nvgpu_utf_falcon_set_dmactl nvgpu_utf_falcon_writel_access_reg_fn +nvgpu_utf_falcon_memcpy_get_fault_injection