Re: [PATCH v5 01/10] hyperv: Convert Hyper-V status codes to strings
From: Nuno Das Neves <hidden>
Date: 2025-02-27 23:48:10
Also in:
linux-acpi, linux-arch, linux-arm-kernel, lkml
On 2/26/2025 8:22 PM, Easwar Hariharan wrote:
On 2/26/2025 3:07 PM, Nuno Das Neves wrote:quoted
Introduce hv_result_to_string() for this purpose. This allows hypercall failures to be debugged more easily with dmesg.Let the commit message stand on its own, i.e. state that hv_result_to_string() is introduced to convert hyper-v status codes to string.
I thought since the subject line is part of the commit message, this kind of phrasing is ok. However I see that in my email client it is a little odd because the subject line is a bit far removed from the rest of the message. I'll change it :)
quoted
Signed-off-by: Nuno Das Neves <redacted> --- drivers/hv/hv_common.c | 65 ++++++++++++++++++++++++++++++++++ drivers/hv/hv_proc.c | 13 ++++--- include/asm-generic/mshyperv.h | 1 + 3 files changed, 74 insertions(+), 5 deletions(-)diff --git a/drivers/hv/hv_common.c b/drivers/hv/hv_common.c index 9804adb4cc56..ce20818688fe 100644 --- a/drivers/hv/hv_common.c +++ b/drivers/hv/hv_common.c@@ -740,3 +740,68 @@ void hv_identify_partition_type(void) pr_crit("Hyper-V: CONFIG_MSHV_ROOT not enabled!\n"); } } + +const char *hv_result_to_string(u64 hv_status) +{ + switch (hv_result(hv_status)) { + case HV_STATUS_SUCCESS: + return "HV_STATUS_SUCCESS"; + case HV_STATUS_INVALID_HYPERCALL_CODE: + return "HV_STATUS_INVALID_HYPERCALL_CODE"; + case HV_STATUS_INVALID_HYPERCALL_INPUT: + return "HV_STATUS_INVALID_HYPERCALL_INPUT"; + case HV_STATUS_INVALID_ALIGNMENT: + return "HV_STATUS_INVALID_ALIGNMENT"; + case HV_STATUS_INVALID_PARAMETER: + return "HV_STATUS_INVALID_PARAMETER"; + case HV_STATUS_ACCESS_DENIED: + return "HV_STATUS_ACCESS_DENIED"; + case HV_STATUS_INVALID_PARTITION_STATE: + return "HV_STATUS_INVALID_PARTITION_STATE"; + case HV_STATUS_OPERATION_DENIED: + return "HV_STATUS_OPERATION_DENIED"; + case HV_STATUS_UNKNOWN_PROPERTY: + return "HV_STATUS_UNKNOWN_PROPERTY"; + case HV_STATUS_PROPERTY_VALUE_OUT_OF_RANGE: + return "HV_STATUS_PROPERTY_VALUE_OUT_OF_RANGE"; + case HV_STATUS_INSUFFICIENT_MEMORY: + return "HV_STATUS_INSUFFICIENT_MEMORY"; + case HV_STATUS_INVALID_PARTITION_ID: + return "HV_STATUS_INVALID_PARTITION_ID"; + case HV_STATUS_INVALID_VP_INDEX: + return "HV_STATUS_INVALID_VP_INDEX"; + case HV_STATUS_NOT_FOUND: + return "HV_STATUS_NOT_FOUND"; + case HV_STATUS_INVALID_PORT_ID: + return "HV_STATUS_INVALID_PORT_ID"; + case HV_STATUS_INVALID_CONNECTION_ID: + return "HV_STATUS_INVALID_CONNECTION_ID"; + case HV_STATUS_INSUFFICIENT_BUFFERS: + return "HV_STATUS_INSUFFICIENT_BUFFERS"; + case HV_STATUS_NOT_ACKNOWLEDGED: + return "HV_STATUS_NOT_ACKNOWLEDGED"; + case HV_STATUS_INVALID_VP_STATE: + return "HV_STATUS_INVALID_VP_STATE"; + case HV_STATUS_NO_RESOURCES: + return "HV_STATUS_NO_RESOURCES"; + case HV_STATUS_PROCESSOR_FEATURE_NOT_SUPPORTED: + return "HV_STATUS_PROCESSOR_FEATURE_NOT_SUPPORTED"; + case HV_STATUS_INVALID_LP_INDEX: + return "HV_STATUS_INVALID_LP_INDEX"; + case HV_STATUS_INVALID_REGISTER_VALUE: + return "HV_STATUS_INVALID_REGISTER_VALUE"; + case HV_STATUS_OPERATION_FAILED: + return "HV_STATUS_OPERATION_FAILED"; + case HV_STATUS_TIME_OUT: + return "HV_STATUS_TIME_OUT"; + case HV_STATUS_CALL_PENDING: + return "HV_STATUS_CALL_PENDING"; + case HV_STATUS_VTL_ALREADY_ENABLED: + return "HV_STATUS_VTL_ALREADY_ENABLED"; + default: + return "Unknown"; + }; + return "Unknown";Unnecessary extra return since the default case already returns "Unknown"
Good point, I think I'd prefer to remove the first return and leave the default case empty.
quoted
+} +EXPORT_SYMBOL_GPL(hv_result_to_string); +Extra line here ^
Thanks
quoted
diff --git a/drivers/hv/hv_proc.c b/drivers/hv/hv_proc.c index 2fae18e4f7d2..8fc30f509fa7 100644 --- a/drivers/hv/hv_proc.c +++ b/drivers/hv/hv_proc.c@@ -87,7 +87,8 @@ int hv_call_deposit_pages(int node, u64 partition_id, u32 num_pages) page_count, 0, input_page, NULL); local_irq_restore(flags); if (!hv_result_success(status)) { - pr_err("Failed to deposit pages: %lld\n", status); + pr_err("%s: Failed to deposit pages: %s\n", __func__, + hv_result_to_string(status)); ret = hv_result_to_errno(status); goto err_free_allocations; }@@ -137,8 +138,9 @@ int hv_call_add_logical_proc(int node, u32 lp_index, u32 apic_id) if (hv_result(status) != HV_STATUS_INSUFFICIENT_MEMORY) { if (!hv_result_success(status)) { - pr_err("%s: cpu %u apic ID %u, %lld\n", __func__, - lp_index, apic_id, status); + pr_err("%s: cpu %u apic ID %u, %s\n", + __func__, lp_index, apic_id, + hv_result_to_string(status)); ret = hv_result_to_errno(status); } break;@@ -179,8 +181,9 @@ int hv_call_create_vp(int node, u64 partition_id, u32 vp_index, u32 flags) if (hv_result(status) != HV_STATUS_INSUFFICIENT_MEMORY) { if (!hv_result_success(status)) { - pr_err("%s: vcpu %u, lp %u, %lld\n", __func__, - vp_index, flags, status); + pr_err("%s: vcpu %u, lp %u, %s\n", + __func__, vp_index, flags, + hv_result_to_string(status)); ret = hv_result_to_errno(status); } break;There are more convertible instances in arch/x86/hyperv/irqdomain.c and drivers/iommu/hyperv-iommu.c
Ah, thank you, happy to add those!
quoted
diff --git a/include/asm-generic/mshyperv.h b/include/asm-generic/mshyperv.h index b13b0cda4ac8..dc4729dba9ef 100644 --- a/include/asm-generic/mshyperv.h +++ b/include/asm-generic/mshyperv.h@@ -298,6 +298,7 @@ static inline int cpumask_to_vpset_skip(struct hv_vpset *vpset, return __cpumask_to_vpset(vpset, cpus, func); } +const char *hv_result_to_string(u64 hv_status); int hv_result_to_errno(u64 status); void hyperv_report_panic(struct pt_regs *regs, long err, bool in_die); bool hv_is_hyperv_initialized(void);