diff options
Diffstat (limited to 'drivers/gpu/drm/i915/gt/uc')
25 files changed, 676 insertions, 314 deletions
diff --git a/drivers/gpu/drm/i915/gt/uc/abi/guc_errors_abi.h b/drivers/gpu/drm/i915/gt/uc/abi/guc_errors_abi.h index 8085fb181274..bcb1129b3610 100644 --- a/drivers/gpu/drm/i915/gt/uc/abi/guc_errors_abi.h +++ b/drivers/gpu/drm/i915/gt/uc/abi/guc_errors_abi.h @@ -21,6 +21,9 @@ enum intel_guc_load_status { INTEL_GUC_LOAD_STATUS_ERROR_DEVID_BUILD_MISMATCH = 0x02, INTEL_GUC_LOAD_STATUS_GUC_PREPROD_BUILD_MISMATCH = 0x03, INTEL_GUC_LOAD_STATUS_ERROR_DEVID_INVALID_GUCTYPE = 0x04, + INTEL_GUC_LOAD_STATUS_HWCONFIG_START = 0x05, + INTEL_GUC_LOAD_STATUS_HWCONFIG_DONE = 0x06, + INTEL_GUC_LOAD_STATUS_HWCONFIG_ERROR = 0x07, INTEL_GUC_LOAD_STATUS_GDT_DONE = 0x10, INTEL_GUC_LOAD_STATUS_IDT_DONE = 0x20, INTEL_GUC_LOAD_STATUS_LAPIC_DONE = 0x30, @@ -38,4 +41,18 @@ enum intel_guc_load_status { INTEL_GUC_LOAD_STATUS_READY = 0xF0, }; +enum intel_bootrom_load_status { + INTEL_BOOTROM_STATUS_NO_KEY_FOUND = 0x13, + INTEL_BOOTROM_STATUS_AES_PROD_KEY_FOUND = 0x1A, + INTEL_BOOTROM_STATUS_RSA_FAILED = 0x50, + INTEL_BOOTROM_STATUS_PAVPC_FAILED = 0x73, + INTEL_BOOTROM_STATUS_WOPCM_FAILED = 0x74, + INTEL_BOOTROM_STATUS_LOADLOC_FAILED = 0x75, + INTEL_BOOTROM_STATUS_JUMP_PASSED = 0x76, + INTEL_BOOTROM_STATUS_JUMP_FAILED = 0x77, + INTEL_BOOTROM_STATUS_RC6CTXCONFIG_FAILED = 0x79, + INTEL_BOOTROM_STATUS_MPUMAP_INCORRECT = 0x7A, + INTEL_BOOTROM_STATUS_EXCEPTION = 0x7E, +}; + #endif /* _ABI_GUC_ERRORS_ABI_H */ diff --git a/drivers/gpu/drm/i915/gt/uc/intel_gsc_fw.c b/drivers/gpu/drm/i915/gt/uc/intel_gsc_fw.c index e73d4440c5e8..1d9fdfb11268 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_gsc_fw.c +++ b/drivers/gpu/drm/i915/gt/uc/intel_gsc_fw.c @@ -6,6 +6,7 @@ #include "gt/intel_engine_pm.h" #include "gt/intel_gpu_commands.h" #include "gt/intel_gt.h" +#include "gt/intel_gt_print.h" #include "gt/intel_ring.h" #include "intel_gsc_fw.h" @@ -88,9 +89,8 @@ out_rq: i915_request_put(rq); if (err) - drm_err(&gsc_uc_to_gt(gsc)->i915->drm, - "Request submission for GSC load failed (%d)\n", - err); + gt_err(gsc_uc_to_gt(gsc), "Request submission for GSC load failed %pe\n", + ERR_PTR(err)); return err; } @@ -200,8 +200,7 @@ int intel_gsc_uc_fw_upload(struct intel_gsc_uc *gsc) /* FW is not fully operational until we enable SW proxy */ intel_uc_fw_change_status(gsc_fw, INTEL_UC_FIRMWARE_TRANSFERRED); - drm_info(>->i915->drm, "Loaded GSC firmware %s\n", - gsc_fw->file_selected.path); + gt_info(gt, "Loaded GSC firmware %s\n", gsc_fw->file_selected.path); return 0; diff --git a/drivers/gpu/drm/i915/gt/uc/intel_gsc_fw.h b/drivers/gpu/drm/i915/gt/uc/intel_gsc_fw.h index 4b5dbb44afb4..f4c1106bb2a9 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_gsc_fw.h +++ b/drivers/gpu/drm/i915/gt/uc/intel_gsc_fw.h @@ -9,7 +9,9 @@ #include <linux/types.h> struct intel_gsc_uc; +struct intel_uncore; int intel_gsc_uc_fw_upload(struct intel_gsc_uc *gsc); bool intel_gsc_uc_fw_init_done(struct intel_gsc_uc *gsc); + #endif diff --git a/drivers/gpu/drm/i915/gt/uc/intel_gsc_uc.c b/drivers/gpu/drm/i915/gt/uc/intel_gsc_uc.c index fd21dbd2663b..2d5b70b3384c 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_gsc_uc.c +++ b/drivers/gpu/drm/i915/gt/uc/intel_gsc_uc.c @@ -6,6 +6,7 @@ #include <linux/types.h> #include "gt/intel_gt.h" +#include "gt/intel_gt_print.h" #include "intel_gsc_uc.h" #include "intel_gsc_fw.h" #include "i915_drv.h" @@ -59,7 +60,6 @@ int intel_gsc_uc_init(struct intel_gsc_uc *gsc) { static struct lock_class_key gsc_lock; struct intel_gt *gt = gsc_uc_to_gt(gsc); - struct drm_i915_private *i915 = gt->i915; struct intel_engine_cs *engine = gt->engine[GSC0]; struct intel_context *ce; struct i915_vma *vma; @@ -81,8 +81,7 @@ int intel_gsc_uc_init(struct intel_gsc_uc *gsc) I915_GEM_HWS_GSC_ADDR, &gsc_lock, "gsc_context"); if (IS_ERR(ce)) { - drm_err(>->i915->drm, - "failed to create GSC CS ctx for FW communication\n"); + gt_err(gt, "failed to create GSC CS ctx for FW communication\n"); err = PTR_ERR(ce); goto out_vma; } @@ -98,7 +97,7 @@ out_vma: out_fw: intel_uc_fw_fini(&gsc->fw); out: - i915_probe_error(i915, "failed with %d\n", err); + gt_probe_error(gt, "GSC init failed %pe\n", ERR_PTR(err)); return err; } @@ -117,7 +116,7 @@ void intel_gsc_uc_fini(struct intel_gsc_uc *gsc) intel_uc_fw_fini(&gsc->fw); } -void intel_gsc_uc_suspend(struct intel_gsc_uc *gsc) +void intel_gsc_uc_flush_work(struct intel_gsc_uc *gsc) { if (!intel_uc_fw_is_loadable(&gsc->fw)) return; @@ -125,6 +124,25 @@ void intel_gsc_uc_suspend(struct intel_gsc_uc *gsc) flush_work(&gsc->work); } +void intel_gsc_uc_resume(struct intel_gsc_uc *gsc) +{ + if (!intel_uc_fw_is_loadable(&gsc->fw)) + return; + + /* + * we only want to start the GSC worker from here in the actual resume + * flow and not during driver load. This is because GSC load is slow and + * therefore we want to make sure that the default state init completes + * first to not slow down the init thread. A separate call to + * intel_gsc_uc_load_start will ensure that the GSC is loaded during + * driver load. + */ + if (!gsc_uc_to_gt(gsc)->engine[GSC0]->default_state) + return; + + intel_gsc_uc_load_start(gsc); +} + void intel_gsc_uc_load_start(struct intel_gsc_uc *gsc) { if (!intel_uc_fw_is_loadable(&gsc->fw)) diff --git a/drivers/gpu/drm/i915/gt/uc/intel_gsc_uc.h b/drivers/gpu/drm/i915/gt/uc/intel_gsc_uc.h index 03fd0a8e8db1..5f50fa1ff8b9 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_gsc_uc.h +++ b/drivers/gpu/drm/i915/gt/uc/intel_gsc_uc.h @@ -26,6 +26,8 @@ void intel_gsc_uc_init_early(struct intel_gsc_uc *gsc); int intel_gsc_uc_init(struct intel_gsc_uc *gsc); void intel_gsc_uc_fini(struct intel_gsc_uc *gsc); void intel_gsc_uc_suspend(struct intel_gsc_uc *gsc); +void intel_gsc_uc_resume(struct intel_gsc_uc *gsc); +void intel_gsc_uc_flush_work(struct intel_gsc_uc *gsc); void intel_gsc_uc_load_start(struct intel_gsc_uc *gsc); static inline bool intel_gsc_uc_is_supported(struct intel_gsc_uc *gsc) diff --git a/drivers/gpu/drm/i915/gt/uc/intel_gsc_uc_heci_cmd_submit.c b/drivers/gpu/drm/i915/gt/uc/intel_gsc_uc_heci_cmd_submit.c new file mode 100644 index 000000000000..ea0da06e2f39 --- /dev/null +++ b/drivers/gpu/drm/i915/gt/uc/intel_gsc_uc_heci_cmd_submit.c @@ -0,0 +1,109 @@ +// SPDX-License-Identifier: MIT +/* + * Copyright © 2023 Intel Corporation + */ + +#include "gt/intel_engine_pm.h" +#include "gt/intel_gpu_commands.h" +#include "gt/intel_gt.h" +#include "gt/intel_ring.h" +#include "intel_gsc_uc_heci_cmd_submit.h" + +struct gsc_heci_pkt { + u64 addr_in; + u32 size_in; + u64 addr_out; + u32 size_out; +}; + +static int emit_gsc_heci_pkt(struct i915_request *rq, struct gsc_heci_pkt *pkt) +{ + u32 *cs; + + cs = intel_ring_begin(rq, 8); + if (IS_ERR(cs)) + return PTR_ERR(cs); + + *cs++ = GSC_HECI_CMD_PKT; + *cs++ = lower_32_bits(pkt->addr_in); + *cs++ = upper_32_bits(pkt->addr_in); + *cs++ = pkt->size_in; + *cs++ = lower_32_bits(pkt->addr_out); + *cs++ = upper_32_bits(pkt->addr_out); + *cs++ = pkt->size_out; + *cs++ = 0; + + intel_ring_advance(rq, cs); + + return 0; +} + +int intel_gsc_uc_heci_cmd_submit_packet(struct intel_gsc_uc *gsc, u64 addr_in, + u32 size_in, u64 addr_out, + u32 size_out) +{ + struct intel_context *ce = gsc->ce; + struct i915_request *rq; + struct gsc_heci_pkt pkt = { + .addr_in = addr_in, + .size_in = size_in, + .addr_out = addr_out, + .size_out = size_out + }; + int err; + + if (!ce) + return -ENODEV; + + rq = i915_request_create(ce); + if (IS_ERR(rq)) + return PTR_ERR(rq); + + if (ce->engine->emit_init_breadcrumb) { + err = ce->engine->emit_init_breadcrumb(rq); + if (err) + goto out_rq; + } + + err = emit_gsc_heci_pkt(rq, &pkt); + + if (err) + goto out_rq; + + err = ce->engine->emit_flush(rq, 0); + +out_rq: + i915_request_get(rq); + + if (unlikely(err)) + i915_request_set_error_once(rq, err); + + i915_request_add(rq); + + if (!err && i915_request_wait(rq, 0, msecs_to_jiffies(500)) < 0) + err = -ETIME; + + i915_request_put(rq); + + if (err) + drm_err(&gsc_uc_to_gt(gsc)->i915->drm, + "Request submission for GSC heci cmd failed (%d)\n", + err); + + return err; +} + +void intel_gsc_uc_heci_cmd_emit_mtl_header(struct intel_gsc_mtl_header *header, + u8 heci_client_id, u32 message_size, + u64 host_session_id) +{ + host_session_id &= ~HOST_SESSION_MASK; + if (heci_client_id == HECI_MEADDRESS_PXP) + host_session_id |= HOST_SESSION_PXP_SINGLE; + + header->validity_marker = GSC_HECI_VALIDITY_MARKER; + header->heci_client_id = heci_client_id; + header->host_session_handle = host_session_id; + header->header_version = MTL_GSC_HEADER_VERSION; + header->message_size = message_size; +} diff --git a/drivers/gpu/drm/i915/gt/uc/intel_gsc_uc_heci_cmd_submit.h b/drivers/gpu/drm/i915/gt/uc/intel_gsc_uc_heci_cmd_submit.h new file mode 100644 index 000000000000..3d56ae501991 --- /dev/null +++ b/drivers/gpu/drm/i915/gt/uc/intel_gsc_uc_heci_cmd_submit.h @@ -0,0 +1,61 @@ +/* SPDX-License-Identifier: MIT */ +/* + * Copyright © 2023 Intel Corporation + */ + +#ifndef _INTEL_GSC_UC_HECI_CMD_SUBMIT_H_ +#define _INTEL_GSC_UC_HECI_CMD_SUBMIT_H_ + +#include <linux/types.h> + +struct intel_gsc_uc; +struct intel_gsc_mtl_header { + u32 validity_marker; +#define GSC_HECI_VALIDITY_MARKER 0xA578875A + + u8 heci_client_id; +#define HECI_MEADDRESS_PXP 17 +#define HECI_MEADDRESS_HDCP 18 + + u8 reserved1; + + u16 header_version; +#define MTL_GSC_HEADER_VERSION 1 + + /* + * FW allows host to decide host_session handle + * as it sees fit. + * For intertracebility reserving select bits(60-63) + * to differentiate caller-target subsystem + * 0000 - HDCP + * 0001 - PXP Single Session + */ + u64 host_session_handle; +#define HOST_SESSION_MASK REG_GENMASK64(63, 60) +#define HOST_SESSION_PXP_SINGLE BIT_ULL(60) + u64 gsc_message_handle; + + u32 message_size; /* lower 20 bits only, upper 12 are reserved */ + + /* + * Flags mask: + * Bit 0: Pending + * Bit 1: Session Cleanup; + * Bits 2-15: Flags + * Bits 16-31: Extension Size + * According to internal spec flags are either input or output + * we distinguish the flags using OUTFLAG or INFLAG + */ + u32 flags; +#define GSC_OUTFLAG_MSG_PENDING 1 + + u32 status; +} __packed; + +int intel_gsc_uc_heci_cmd_submit_packet(struct intel_gsc_uc *gsc, + u64 addr_in, u32 size_in, + u64 addr_out, u32 size_out); +void intel_gsc_uc_heci_cmd_emit_mtl_header(struct intel_gsc_mtl_header *header, + u8 heci_client_id, u32 message_size, + u64 host_session_id); +#endif diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc.h b/drivers/gpu/drm/i915/gt/uc/intel_guc.h index bb4dfe707a7d..e46aac1a41e6 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_guc.h +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc.h @@ -42,6 +42,8 @@ struct intel_guc { /** @capture: the error-state-capture module's data and objects */ struct intel_guc_state_capture *capture; + struct dentry *dbgfs_node; + /** @sched_engine: Global engine used to submit requests to GuC */ struct i915_sched_engine *sched_engine; /** diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc_capture.c b/drivers/gpu/drm/i915/gt/uc/intel_guc_capture.c index 710999d7189e..cf49188db6a6 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_guc_capture.c +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc_capture.c @@ -15,6 +15,7 @@ #include "guc_capture_fwif.h" #include "intel_guc_capture.h" #include "intel_guc_fwif.h" +#include "intel_guc_print.h" #include "i915_drv.h" #include "i915_gpu_error.h" #include "i915_irq.h" @@ -353,7 +354,6 @@ guc_capture_alloc_steered_lists_xe_hpg(struct intel_guc *guc, u32 ipver) { struct intel_gt *gt = guc_to_gt(guc); - struct drm_i915_private *i915 = guc_to_gt(guc)->i915; struct sseu_dev_info *sseu; int slice, subslice, i, iter, num_steer_regs, num_tot_regs = 0; const struct __guc_mmio_reg_descr_group *list; @@ -402,7 +402,7 @@ guc_capture_alloc_steered_lists_xe_hpg(struct intel_guc *guc, } } - drm_dbg(&i915->drm, "GuC-capture found %d-ext-regs.\n", num_tot_regs); + guc_dbg(guc, "capture found %d ext-regs.\n", num_tot_regs); guc->capture->extlists = extlists; } @@ -477,7 +477,6 @@ guc_capture_list_init(struct intel_guc *guc, u32 owner, u32 type, u32 classid, struct guc_mmio_reg *ptr, u16 num_entries) { u32 i = 0, j = 0; - struct drm_i915_private *i915 = guc_to_gt(guc)->i915; const struct __guc_mmio_reg_descr_group *reglists = guc->capture->reglists; struct __guc_mmio_reg_descr_group *extlists = guc->capture->extlists; const struct __guc_mmio_reg_descr_group *match; @@ -509,8 +508,7 @@ guc_capture_list_init(struct intel_guc *guc, u32 owner, u32 type, u32 classid, } } if (i < num_entries) - drm_dbg(&i915->drm, "GuC-capture: Init reglist short %d out %d.\n", - (int)i, (int)num_entries); + guc_dbg(guc, "Got short capture reglist init: %d out %d.\n", i, num_entries); return 0; } @@ -540,12 +538,11 @@ guc_capture_getlistsize(struct intel_guc *guc, u32 owner, u32 type, u32 classid, size_t *size, bool is_purpose_est) { struct intel_guc_state_capture *gc = guc->capture; - struct drm_i915_private *i915 = guc_to_gt(guc)->i915; struct __guc_capture_ads_cache *cache = &gc->ads_cache[owner][type][classid]; int num_regs; if (!gc->reglists) { - drm_warn(&i915->drm, "GuC-capture: No reglist on this device\n"); + guc_warn(guc, "No capture reglist for this device\n"); return -ENODEV; } @@ -557,9 +554,9 @@ guc_capture_getlistsize(struct intel_guc *guc, u32 owner, u32 type, u32 classid, if (!is_purpose_est && owner == GUC_CAPTURE_LIST_INDEX_PF && !guc_capture_get_one_list(gc->reglists, owner, type, classid)) { if (type == GUC_CAPTURE_LIST_TYPE_GLOBAL) - drm_warn(&i915->drm, "Missing GuC-Err-Cap reglist Global!\n"); + guc_warn(guc, "Missing capture reglist: global!\n"); else - drm_warn(&i915->drm, "Missing GuC-Err-Cap reglist %s(%u):%s(%u)!\n", + guc_warn(guc, "Missing capture reglist: %s(%u):%s(%u)!\n", __stringify_type(type), type, __stringify_engclass(classid), classid); return -ENODATA; @@ -592,7 +589,6 @@ intel_guc_capture_getlist(struct intel_guc *guc, u32 owner, u32 type, u32 classi { struct intel_guc_state_capture *gc = guc->capture; struct __guc_capture_ads_cache *cache = &gc->ads_cache[owner][type][classid]; - struct drm_i915_private *i915 = guc_to_gt(guc)->i915; struct guc_debug_capture_list *listnode; int ret, num_regs; u8 *caplist, *tmp; @@ -623,7 +619,7 @@ intel_guc_capture_getlist(struct intel_guc *guc, u32 owner, u32 type, u32 classi caplist = kzalloc(size, GFP_KERNEL); if (!caplist) { - drm_dbg(&i915->drm, "GuC-capture: failed to alloc cached caplist"); + guc_dbg(guc, "Failed to alloc cached register capture list"); return -ENOMEM; } @@ -653,7 +649,6 @@ intel_guc_capture_getnullheader(struct intel_guc *guc, void **outptr, size_t *size) { struct intel_guc_state_capture *gc = guc->capture; - struct drm_i915_private *i915 = guc_to_gt(guc)->i915; int tmp = sizeof(u32) * 4; void *null_header; @@ -665,7 +660,7 @@ intel_guc_capture_getnullheader(struct intel_guc *guc, null_header = kzalloc(tmp, GFP_KERNEL); if (!null_header) { - drm_dbg(&i915->drm, "GuC-capture: failed to alloc cached nulllist"); + guc_dbg(guc, "Failed to alloc cached register capture null list"); return -ENOMEM; } @@ -727,7 +722,6 @@ guc_capture_output_min_size_est(struct intel_guc *guc) static void check_guc_capture_size(struct intel_guc *guc) { - struct drm_i915_private *i915 = guc_to_gt(guc)->i915; int min_size = guc_capture_output_min_size_est(guc); int spare_size = min_size * GUC_CAPTURE_OVERBUFFER_MULTIPLIER; u32 buffer_size = intel_guc_log_section_size_capture(&guc->log); @@ -741,13 +735,13 @@ static void check_guc_capture_size(struct intel_guc *guc) * INTEL_GUC_STATE_CAPTURE_EVENT_STATUS_NOSPACE. */ if (min_size < 0) - drm_warn(&i915->drm, "Failed to calculate GuC error state capture buffer minimum size: %d!\n", + guc_warn(guc, "Failed to calculate error state capture buffer minimum size: %d!\n", min_size); else if (min_size > buffer_size) - drm_warn(&i915->drm, "GuC error state capture buffer maybe small: %d < %d\n", + guc_warn(guc, "Error state capture buffer maybe small: %d < %d\n", buffer_size, min_size); else if (spare_size > buffer_size) - drm_dbg(&i915->drm, "GuC error state capture buffer lacks spare size: %d < %d (min = %d)\n", + guc_dbg(guc, "Error state capture buffer lacks spare size: %d < %d (min = %d)\n", buffer_size, spare_size, min_size); } @@ -848,7 +842,6 @@ static int guc_capture_log_remove_dw(struct intel_guc *guc, struct __guc_capture_bufstate *buf, u32 *dw) { - struct drm_i915_private *i915 = guc_to_gt(guc)->i915; int tries = 2; int avail = 0; u32 *src_data; @@ -865,7 +858,7 @@ guc_capture_log_remove_dw(struct intel_guc *guc, struct __guc_capture_bufstate * return 4; } if (avail) - drm_dbg(&i915->drm, "GuC-Cap-Logs not dword aligned, skipping.\n"); + guc_dbg(guc, "Register capture log not dword aligned, skipping.\n"); buf->rd = 0; } @@ -1118,13 +1111,12 @@ static void __guc_capture_create_prealloc_nodes(struct intel_guc *guc) { struct __guc_capture_parsed_output *node = NULL; - struct drm_i915_private *i915 = guc_to_gt(guc)->i915; int i; for (i = 0; i < PREALLOC_NODES_MAX_COUNT; ++i) { node = guc_capture_alloc_one_node(guc); if (!node) { - drm_warn(&i915->drm, "GuC Capture pre-alloc-cache failure\n"); + guc_warn(guc, "Register capture pre-alloc-cache failure\n"); /* dont free the priors, use what we got and cleanup at shutdown */ return; } @@ -1169,7 +1161,6 @@ guc_capture_create_prealloc_nodes(struct intel_guc *guc) static int guc_capture_extract_reglists(struct intel_guc *guc, struct __guc_capture_bufstate *buf) { - struct drm_i915_private *i915 = guc_to_gt(guc)->i915; struct guc_state_capture_group_header_t ghdr = {0}; struct guc_state_capture_header_t hdr = {0}; struct __guc_capture_parsed_output *node = NULL; @@ -1183,7 +1174,7 @@ guc_capture_extract_reglists(struct intel_guc *guc, struct __guc_capture_bufstat if (!i) return -ENODATA; if (i % sizeof(u32)) { - drm_warn(&i915->drm, "GuC Capture new entries unaligned\n"); + guc_warn(guc, "Got mis-aligned register capture entries\n"); ret = -EIO; goto bailout; } @@ -1301,7 +1292,7 @@ guc_capture_extract_reglists(struct intel_guc *guc, struct __guc_capture_bufstat break; } if (datatype != GUC_CAPTURE_LIST_TYPE_GLOBAL) - drm_dbg(&i915->drm, "GuC Capture missing global dump: %08x!\n", + guc_dbg(guc, "Register capture missing global dump: %08x!\n", datatype); } node->is_partial = is_partial; @@ -1322,7 +1313,7 @@ guc_capture_extract_reglists(struct intel_guc *guc, struct __guc_capture_bufstat numregs = FIELD_GET(CAP_HDR_NUM_MMIOS, hdr.num_mmios); if (numregs > guc->capture->max_mmio_per_node) { - drm_dbg(&i915->drm, "GuC Capture list extraction clipped by prealloc!\n"); + guc_dbg(guc, "Register capture list extraction clipped by prealloc!\n"); numregs = guc->capture->max_mmio_per_node; } node->reginfo[datatype].num_regs = numregs; @@ -1367,7 +1358,6 @@ static void __guc_capture_process_output(struct intel_guc *guc) { unsigned int buffer_size, read_offset, write_offset, full_count; struct intel_uc *uc = container_of(guc, typeof(*uc), guc); - struct drm_i915_private *i915 = guc_to_gt(guc)->i915; struct guc_log_buffer_state log_buf_state_local; struct guc_log_buffer_state *log_buf_state; struct __guc_capture_bufstate buf; @@ -1403,7 +1393,8 @@ static void __guc_capture_process_output(struct intel_guc *guc) write_offset = buffer_size; } else if (unlikely((read_offset > buffer_size) || (write_offset > buffer_size))) { - drm_err(&i915->drm, "invalid GuC log capture buffer state!\n"); + guc_err(guc, "Register capture buffer in invalid state: read = 0x%X, size = 0x%X!\n", + read_offset, buffer_size); /* copy whole buffer as offsets are unreliable */ read_offset = 0; write_offset = buffer_size; @@ -1607,13 +1598,11 @@ void intel_guc_capture_get_matching_node(struct intel_gt *gt, struct intel_context *ce) { struct __guc_capture_parsed_output *n, *ntmp; - struct drm_i915_private *i915; struct intel_guc *guc; if (!gt || !ee || !ce) return; - i915 = gt->i915; guc = >->uc.guc; if (!guc->capture) return; @@ -1627,9 +1616,8 @@ void intel_guc_capture_get_matching_node(struct intel_gt *gt, list_for_each_entry_safe(n, ntmp, &guc->capture->outlist, link) { if (n->eng_inst == GUC_ID_TO_ENGINE_INSTANCE(ee->engine->guc_id) && n->eng_class == GUC_ID_TO_ENGINE_CLASS(ee->engine->guc_id) && - n->guc_id && n->guc_id == ce->guc_id.id && - (n->lrca & CTX_GTT_ADDRESS_MASK) && (n->lrca & CTX_GTT_ADDRESS_MASK) == - (ce->lrc.lrca & CTX_GTT_ADDRESS_MASK)) { + n->guc_id == ce->guc_id.id && + (n->lrca & CTX_GTT_ADDRESS_MASK) == (ce->lrc.lrca & CTX_GTT_ADDRESS_MASK)) { list_del(&n->link); ee->guc_capture_node = n; ee->guc_capture = guc->capture; @@ -1637,7 +1625,9 @@ void intel_guc_capture_get_matching_node(struct intel_gt *gt, return; } } - drm_dbg(&i915->drm, "GuC capture can't match ee to node\n"); + + guc_warn(guc, "No register capture node found for 0x%04X / 0x%08X\n", + ce->guc_id.id, ce->lrc.lrca); } void intel_guc_capture_process(struct intel_guc *guc) diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc_fw.c b/drivers/gpu/drm/i915/gt/uc/intel_guc_fw.c index 69133420c78b..6fda3aec5c66 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_guc_fw.c +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc_fw.c @@ -12,6 +12,7 @@ #include "gt/intel_gt.h" #include "gt/intel_gt_mcr.h" #include "gt/intel_gt_regs.h" +#include "gt/intel_rps.h" #include "intel_guc_fw.h" #include "intel_guc_print.h" #include "i915_drv.h" @@ -88,31 +89,80 @@ static int guc_xfer_rsa(struct intel_uc_fw *guc_fw, /* * Read the GuC status register (GUC_STATUS) and store it in the * specified location; then return a boolean indicating whether - * the value matches either of two values representing completion - * of the GuC boot process. + * the value matches either completion or a known failure code. * * This is used for polling the GuC status in a wait_for() * loop below. */ -static inline bool guc_ready(struct intel_uncore *uncore, u32 *status) +static inline bool guc_load_done(struct intel_uncore *uncore, u32 *status, bool *success) { u32 val = intel_uncore_read(uncore, GUC_STATUS); u32 uk_val = REG_FIELD_GET(GS_UKERNEL_MASK, val); + u32 br_val = REG_FIELD_GET(GS_BOOTROM_MASK, val); *status = val; - return uk_val == INTEL_GUC_LOAD_STATUS_READY; + switch (uk_val) { + case INTEL_GUC_LOAD_STATUS_READY: + *success = true; + return true; + + case INTEL_GUC_LOAD_STATUS_ERROR_DEVID_BUILD_MISMATCH: + case INTEL_GUC_LOAD_STATUS_GUC_PREPROD_BUILD_MISMATCH: + case INTEL_GUC_LOAD_STATUS_ERROR_DEVID_INVALID_GUCTYPE: + case INTEL_GUC_LOAD_STATUS_HWCONFIG_ERROR: + case INTEL_GUC_LOAD_STATUS_DPC_ERROR: + case INTEL_GUC_LOAD_STATUS_EXCEPTION: + case INTEL_GUC_LOAD_STATUS_INIT_DATA_INVALID: + case INTEL_GUC_LOAD_STATUS_MPU_DATA_INVALID: + case INTEL_GUC_LOAD_STATUS_INIT_MMIO_SAVE_RESTORE_INVALID: + *success = false; + return true; + } + + switch (br_val) { + case INTEL_BOOTROM_STATUS_NO_KEY_FOUND: + case INTEL_BOOTROM_STATUS_RSA_FAILED: + case INTEL_BOOTROM_STATUS_PAVPC_FAILED: + case INTEL_BOOTROM_STATUS_WOPCM_FAILED: + case INTEL_BOOTROM_STATUS_LOADLOC_FAILED: + case INTEL_BOOTROM_STATUS_JUMP_FAILED: + case INTEL_BOOTROM_STATUS_RC6CTXCONFIG_FAILED: + case INTEL_BOOTROM_STATUS_MPUMAP_INCORRECT: + case INTEL_BOOTROM_STATUS_EXCEPTION: + *success = false; + return true; + } + + return false; } +/* + * Use a longer timeout for debug builds so that problems can be detected + * and analysed. But a shorter timeout for releases so that user's don't + * wait forever to find out there is a problem. Note that the only reason + * an end user should hit the timeout is in case of extreme thermal throttling. + * And a system that is that hot during boot is probably dead anyway! + */ +#if defined(CONFIG_DRM_I915_DEBUG_GEM) +#define GUC_LOAD_RETRY_LIMIT 20 +#else +#define GUC_LOAD_RETRY_LIMIT 3 +#endif + static int guc_wait_ucode(struct intel_guc *guc) { struct intel_gt *gt = guc_to_gt(guc); struct intel_uncore *uncore = gt->uncore; + ktime_t before, after, delta; + bool success; u32 status; - int ret; + int ret, count; + u64 delta_ms; + u32 before_freq; /* * Wait for the GuC to start up. - * NB: Docs recommend not using the interrupt for completion. + * * Measurements indicate this should take no more than 20ms * (assuming the GT clock is at maximum frequency). So, a * timeout here indicates that the GuC has failed and is unusable. @@ -126,29 +176,80 @@ static int guc_wait_ucode(struct intel_guc *guc) * issues to be resolved. In the meantime bump the timeout to * 200ms. Even at slowest clock, this should be sufficient. And * in the working case, a larger timeout makes no difference. + * + * IFWI updates have also been seen to cause sporadic failures due to + * the requested frequency not being granted and thus the firmware + * load is attempted at minimum frequency. That can lead to load times + * in the seconds range. However, there is a limit on how long an + * individual wait_for() can wait. So wrap it in a loop. */ - ret = wait_for(guc_ready(uncore, &status), 200); - if (ret) { - guc_info(guc, "load failed: status = 0x%08X\n", status); - guc_info(guc, "load failed: status: Reset = %d, " - "BootROM = 0x%02X, UKernel = 0x%02X, " - "MIA = 0x%02X, Auth = 0x%02X\n", - REG_FIELD_GET(GS_MIA_IN_RESET, status), - REG_FIELD_GET(GS_BOOTROM_MASK, status), - REG_FIELD_GET(GS_UKERNEL_MASK, status), - REG_FIELD_GET(GS_MIA_MASK, status), - REG_FIELD_GET(GS_AUTH_STATUS_MASK, status)); - - if ((status & GS_BOOTROM_MASK) == GS_BOOTROM_RSA_FAILED) { + before_freq = intel_rps_read_actual_frequency(&uncore->gt->rps); + before = ktime_get(); + for (count = 0; count < GUC_LOAD_RETRY_LIMIT; count++) { + ret = wait_for(guc_load_done(uncore, &status, &success), 1000); + if (!ret || !success) + break; + + guc_dbg(guc, "load still in progress, count = %d, freq = %dMHz\n", + count, intel_rps_read_actual_frequency(&uncore->gt->rps)); + } + after = ktime_get(); + delta = ktime_sub(after, before); + delta_ms = ktime_to_ms(delta); + if (ret || !success) { + u32 ukernel = REG_FIELD_GET(GS_UKERNEL_MASK, status); + u32 bootrom = REG_FIELD_GET(GS_BOOTROM_MASK, status); + + guc_info(guc, "load failed: status = 0x%08X, time = %lldms, freq = %dMHz, ret = %d\n", + status, delta_ms, intel_rps_read_actual_frequency(&uncore->gt->rps), ret); + guc_info(guc, "load failed: status: Reset = %d, BootROM = 0x%02X, UKernel = 0x%02X, MIA = 0x%02X, Auth = 0x%02X\n", + REG_FIELD_GET(GS_MIA_IN_RESET, status), + bootrom, ukernel, + REG_FIELD_GET(GS_MIA_MASK, status), + REG_FIELD_GET(GS_AUTH_STATUS_MASK, status)); + + switch (bootrom) { + case INTEL_BOOTROM_STATUS_NO_KEY_FOUND: + guc_info(guc, "invalid key requested, header = 0x%08X\n", + intel_uncore_read(uncore, GUC_HEADER_INFO)); + ret = -ENOEXEC; + break; + + case INTEL_BOOTROM_STATUS_RSA_FAILED: guc_info(guc, "firmware signature verification failed\n"); ret = -ENOEXEC; + break; } - if (REG_FIELD_GET(GS_UKERNEL_MASK, status) == INTEL_GUC_LOAD_STATUS_EXCEPTION) { + switch (ukernel) { + case INTEL_GUC_LOAD_STATUS_EXCEPTION: guc_info(guc, "firmware exception. EIP: %#x\n", intel_uncore_read(uncore, SOFT_SCRATCH(13))); ret = -ENXIO; + break; + + case INTEL_GUC_LOAD_STATUS_INIT_MMIO_SAVE_RESTORE_INVALID: + guc_info(guc, "illegal register in save/restore workaround list\n"); + ret = -EPERM; + break; + + case INTEL_GUC_LOAD_STATUS_HWCONFIG_START: + guc_info(guc, "still extracting hwconfig table.\n"); + ret = -ETIMEDOUT; + break; } + + /* Uncommon/unexpected error, see earlier status code print for details */ + if (ret == 0) + ret = -ENXIO; + } else if (delta_ms > 200) { + guc_warn(guc, "excessive init time: %lldms! [freq = %dMHz, before = %dMHz, status = 0x%08X, count = %d, ret = %d]\n", + delta_ms, intel_rps_read_actual_frequency(&uncore->gt->rps), + before_freq, status, count, ret); + } else { + guc_dbg(guc, "init took %lldms, freq = %dMHz, before = %dMHz, status = 0x%08X, count = %d, ret = %d\n", + delta_ms, intel_rps_read_actual_frequency(&uncore->gt->rps), + before_freq, status, count, ret); } return ret; diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc_hwconfig.c b/drivers/gpu/drm/i915/gt/uc/intel_guc_hwconfig.c index 4781fccc2687..852bea0208ce 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_guc_hwconfig.c +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc_hwconfig.c @@ -102,7 +102,7 @@ static bool has_table(struct drm_i915_private *i915) return false; } -/** +/* * intel_guc_hwconfig_init - Initialize the HWConfig * * Retrieve the HWConfig table from the GuC and save it locally. @@ -136,7 +136,7 @@ static int guc_hwconfig_init(struct intel_gt *gt) return 0; } -/** +/* * intel_gt_init_hwconfig - Initialize the HWConfig if available * * Retrieve the HWConfig table if available on the current platform. @@ -149,7 +149,7 @@ int intel_gt_init_hwconfig(struct intel_gt *gt) return guc_hwconfig_init(gt); } -/** +/* * intel_gt_fini_hwconfig - Finalize the HWConfig * * Free up the memory allocation holding the table. diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc_log.c b/drivers/gpu/drm/i915/gt/uc/intel_guc_log.c index c3792ddeec80..55bc8b55fbc0 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_guc_log.c +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc_log.c @@ -333,8 +333,7 @@ bool intel_guc_check_log_buf_overflow(struct intel_guc_log *log, log->stats[type].sampled_overflow += 16; } - dev_notice_ratelimited(guc_to_gt(log_to_guc(log))->i915->drm.dev, - "GuC log buffer overflow\n"); + guc_notice_ratelimited(log_to_guc(log), "log buffer overflow\n"); } return overflow; @@ -521,7 +520,7 @@ void intel_guc_log_init_early(struct intel_guc_log *log) static int guc_log_relay_create(struct intel_guc_log *log) { struct intel_guc *guc = log_to_guc(log); - struct drm_i915_private *dev_priv = guc_to_gt(guc)->i915; + struct drm_i915_private *i915 = guc_to_gt(guc)->i915; struct rchan *guc_log_relay_chan; size_t n_subbufs, subbuf_size; int ret; @@ -543,10 +542,13 @@ static int guc_log_relay_create(struct intel_guc_log *log) */ n_subbufs = 8; + if (!guc->dbgfs_node) + return -ENOENT; + guc_log_relay_chan = relay_open("guc_log", - dev_priv->drm.primary->debugfs_root, + guc->dbgfs_node, subbuf_size, n_subbufs, - &relay_callbacks, dev_priv); + &relay_callbacks, i915); if (!guc_log_relay_chan) { guc_err(guc, "Couldn't create relay channel for logging\n"); @@ -571,7 +573,7 @@ static void guc_log_relay_destroy(struct intel_guc_log *log) static void guc_log_copy_debuglogs_for_relay(struct intel_guc_log *log) { struct intel_guc *guc = log_to_guc(log); - struct drm_i915_private *dev_priv = guc_to_gt(guc)->i915; + struct drm_i915_private *i915 = guc_to_gt(guc)->i915; intel_wakeref_t wakeref; _guc_log_copy_debuglogs_for_relay(log); @@ -580,7 +582,7 @@ static void guc_log_copy_debuglogs_for_relay(struct intel_guc_log *log) * Generally device is expected to be active only at this * time, so get/put should be really quick. */ - with_intel_runtime_pm(&dev_priv->runtime_pm, wakeref) + with_intel_runtime_pm(&i915->runtime_pm, wakeref) guc_action_flush_log_complete(guc); } @@ -662,7 +664,7 @@ void intel_guc_log_destroy(struct intel_guc_log *log) int intel_guc_log_set_level(struct intel_guc_log *log, u32 level) { struct intel_guc *guc = log_to_guc(log); - struct drm_i915_private *dev_priv = guc_to_gt(guc)->i915; + struct drm_i915_private *i915 = guc_to_gt(guc)->i915; intel_wakeref_t wakeref; int ret = 0; @@ -676,12 +678,12 @@ int intel_guc_log_set_level(struct intel_guc_log *log, u32 level) if (level < GUC_LOG_LEVEL_DISABLED || level > GUC_LOG_LEVEL_MAX) return -EINVAL; - mutex_lock(&dev_priv->drm.struct_mutex); + mutex_lock(&i915->drm.struct_mutex); if (log->level == level) goto out_unlock; - with_intel_runtime_pm(&dev_priv->runtime_pm, wakeref) + with_intel_runtime_pm(&i915->runtime_pm, wakeref) ret = guc_action_control_log(guc, GUC_LOG_LEVEL_IS_VERBOSE(level), GUC_LOG_LEVEL_IS_ENABLED(level), @@ -694,7 +696,7 @@ int intel_guc_log_set_level(struct intel_guc_log *log, u32 level) log->level = level; out_unlock: - mutex_unlock(&dev_priv->drm.struct_mutex); + mutex_unlock(&i915->drm.struct_mutex); return ret; } diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc_print.h b/drivers/gpu/drm/i915/gt/uc/intel_guc_print.h index e75989d4ba06..2465d05638b4 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_guc_print.h +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc_print.h @@ -30,6 +30,9 @@ #define guc_err_ratelimited(_guc, _fmt, ...) \ guc_printk((_guc), err_ratelimited, _fmt, ##__VA_ARGS__) +#define guc_notice_ratelimited(_guc, _fmt, ...) \ + guc_printk((_guc), notice_ratelimited, _fmt, ##__VA_ARGS__) + #define guc_probe_error(_guc, _fmt, ...) \ guc_printk((_guc), probe_error, _fmt, ##__VA_ARGS__) diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc_rc.c b/drivers/gpu/drm/i915/gt/uc/intel_guc_rc.c index 8f8dd05835c5..1adec6de223c 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_guc_rc.c +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc_rc.c @@ -6,6 +6,7 @@ #include <linux/string_helpers.h> #include "intel_guc_rc.h" +#include "intel_guc_print.h" #include "gt/intel_gt.h" #include "i915_drv.h" @@ -59,13 +60,12 @@ static int __guc_rc_control(struct intel_guc *guc, bool enable) ret = guc_action_control_gucrc(guc, enable); if (ret) { - i915_probe_error(guc_to_gt(guc)->i915, "Failed to %s GuC RC (%pe)\n", - str_enable_disable(enable), ERR_PTR(ret)); + guc_probe_error(guc, "Failed to %s RC (%pe)\n", + str_enable_disable(enable), ERR_PTR(ret)); return ret; } - drm_info(>->i915->drm, "GuC RC: %s\n", - str_enabled_disabled(enable)); + guc_info(guc, "RC %s\n", str_enabled_disabled(enable)); return 0; } diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc_reg.h b/drivers/gpu/drm/i915/gt/uc/intel_guc_reg.h index 9915de32e894..3fd798837502 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_guc_reg.h +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc_reg.h @@ -18,8 +18,6 @@ #define GS_MIA_IN_RESET (0x01 << GS_RESET_SHIFT) #define GS_BOOTROM_SHIFT 1 #define GS_BOOTROM_MASK (0x7F << GS_BOOTROM_SHIFT) -#define GS_BOOTROM_RSA_FAILED (0x50 << GS_BOOTROM_SHIFT) -#define GS_BOOTROM_JUMP_PASSED (0x76 << GS_BOOTROM_SHIFT) #define GS_UKERNEL_SHIFT 8 #define GS_UKERNEL_MASK (0xFF << GS_UKERNEL_SHIFT) #define GS_MIA_SHIFT 16 @@ -32,6 +30,8 @@ #define GS_AUTH_STATUS_BAD (0x01 << GS_AUTH_STATUS_SHIFT) #define GS_AUTH_STATUS_GOOD (0x02 << GS_AUTH_STATUS_SHIFT) +#define GUC_HEADER_INFO _MMIO(0xc014) + #define SOFT_SCRATCH(n) _MMIO(0xc180 + (n) * 4) #define SOFT_SCRATCH_COUNT 16 diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc_slpc.c b/drivers/gpu/drm/i915/gt/uc/intel_guc_slpc.c index 63464933cbce..026d73855f36 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_guc_slpc.c +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc_slpc.c @@ -9,6 +9,7 @@ #include "i915_drv.h" #include "i915_reg.h" #include "intel_guc_slpc.h" +#include "intel_guc_print.h" #include "intel_mchbar_regs.h" #include "gt/intel_gt.h" #include "gt/intel_gt_regs.h" @@ -171,14 +172,12 @@ static int guc_action_slpc_query(struct intel_guc *guc, u32 offset) static int slpc_query_task_state(struct intel_guc_slpc *slpc) { struct intel_guc *guc = slpc_to_guc(slpc); - struct drm_i915_private *i915 = slpc_to_i915(slpc); u32 offset = intel_guc_ggtt_offset(guc, slpc->vma); int ret; ret = guc_action_slpc_query(guc, offset); if (unlikely(ret)) - i915_probe_error(i915, "Failed to query task state (%pe)\n", - ERR_PTR(ret)); + guc_probe_error(guc, "Failed to query task state: %pe\n", ERR_PTR(ret)); drm_clflush_virt_range(slpc->vaddr, SLPC_PAGE_SIZE_BYTES); @@ -188,15 +187,14 @@ static int slpc_query_task_state(struct intel_guc_slpc *slpc) static int slpc_set_param(struct intel_guc_slpc *slpc, u8 id, u32 value) { struct intel_guc *guc = slpc_to_guc(slpc); - struct drm_i915_private *i915 = slpc_to_i915(slpc); int ret; GEM_BUG_ON(id >= SLPC_MAX_PARAM); ret = guc_action_slpc_set_param(guc, id, value); if (ret) - i915_probe_error(i915, "Failed to set param %d to %u (%pe)\n", - id, value, ERR_PTR(ret)); + guc_probe_error(guc, "Failed to set param %d to %u: %pe\n", + id, value, ERR_PTR(ret)); return ret; } @@ -212,8 +210,8 @@ static int slpc_unset_param(struct intel_guc_slpc *slpc, u8 id) static int slpc_force_min_freq(struct intel_guc_slpc *slpc, u32 freq) { - struct drm_i915_private *i915 = slpc_to_i915(slpc); struct intel_guc *guc = slpc_to_guc(slpc); + struct drm_i915_private *i915 = slpc_to_i915(slpc); intel_wakeref_t wakeref; int ret = 0; @@ -236,9 +234,8 @@ static int slpc_force_min_freq(struct intel_guc_slpc *slpc, u32 freq) SLPC_PARAM_GLOBAL_MIN_GT_UNSLICE_FREQ_MHZ, freq); if (ret) - drm_notice(&i915->drm, - "Failed to send set_param for min freq(%d): (%d)\n", - freq, ret); + guc_notice(guc, "Failed to send set_param for min freq(%d): %pe\n", + freq, ERR_PTR(ret)); } return ret; @@ -267,7 +264,6 @@ static void slpc_boost_work(struct work_struct *work) int intel_guc_slpc_init(struct intel_guc_slpc *slpc) { struct intel_guc *guc = slpc_to_guc(slpc); - struct drm_i915_private *i915 = slpc_to_i915(slpc); u32 size = PAGE_ALIGN(sizeof(struct slpc_shared_data)); int err; @@ -275,9 +271,7 @@ int intel_guc_slpc_init(struct intel_guc_slpc *slpc) err = intel_guc_allocate_and_map_vma(guc, size, &slpc->vma, (void **)&slpc->vaddr); if (unlikely(err)) { - i915_probe_error(i915, - "Failed to allocate SLPC struct (err=%pe)\n", - ERR_PTR(err)); + guc_probe_error(guc, "Failed to allocate SLPC struct: %pe\n", ERR_PTR(err)); return err; } @@ -338,7 +332,6 @@ static int guc_action_slpc_reset(struct intel_guc *guc, u32 offset) static int slpc_reset(struct intel_guc_slpc *slpc) { - struct drm_i915_private *i915 = slpc_to_i915(slpc); struct intel_guc *guc = slpc_to_guc(slpc); u32 offset = intel_guc_ggtt_offset(guc, slpc->vma); int ret; @@ -346,15 +339,14 @@ static int slpc_reset(struct intel_guc_slpc *slpc) ret = guc_action_slpc_reset(guc, offset); if (unlikely(ret < 0)) { - i915_probe_error(i915, "SLPC reset action failed (%pe)\n", - ERR_PTR(ret)); + guc_probe_error(guc, "SLPC reset action failed: %pe\n", ERR_PTR(ret)); return ret; } if (!ret) { if (wait_for(slpc_is_running(slpc), SLPC_RESET_TIMEOUT_MS)) { - i915_probe_error(i915, "SLPC not enabled! State = %s\n", - slpc_get_state_string(slpc)); + guc_probe_error(guc, "SLPC not enabled! State = %s\n", + slpc_get_state_string(slpc)); return -EIO; } } @@ -495,8 +487,8 @@ int intel_guc_slpc_set_min_freq(struct intel_guc_slpc *slpc, u32 val) SLPC_PARAM_IGNORE_EFFICIENT_FREQUENCY, val < slpc->rp1_freq); if (ret) { - i915_probe_error(i915, "Failed to toggle efficient freq (%pe)\n", - ERR_PTR(ret)); + guc_probe_error(slpc_to_guc(slpc), "Failed to toggle efficient freq: %pe\n", + ERR_PTR(ret)); goto out; } @@ -611,15 +603,12 @@ static int slpc_set_softlimits(struct intel_guc_slpc *slpc) static bool is_slpc_min_freq_rpmax(struct intel_guc_slpc *slpc) { - struct drm_i915_private *i915 = slpc_to_i915(slpc); int slpc_min_freq; int ret; ret = intel_guc_slpc_get_min_freq(slpc, &slpc_min_freq); if (ret) { - drm_err(&i915->drm, - "Failed to get min freq: (%d)\n", - ret); + guc_err(slpc_to_guc(slpc), "Failed to get min freq: %pe\n", ERR_PTR(ret)); return false; } @@ -685,9 +674,8 @@ int intel_guc_slpc_override_gucrc_mode(struct intel_guc_slpc *slpc, u32 mode) with_intel_runtime_pm(&i915->runtime_pm, wakeref) { ret = slpc_set_param(slpc, SLPC_PARAM_PWRGATE_RC_MODE, mode); if (ret) - drm_err(&i915->drm, - "Override gucrc mode %d failed %d\n", - mode, ret); + guc_err(slpc_to_guc(slpc), "Override RC mode %d failed: %pe\n", + mode, ERR_PTR(ret)); } return ret; @@ -702,9 +690,7 @@ int intel_guc_slpc_unset_gucrc_mode(struct intel_guc_slpc *slpc) with_intel_runtime_pm(&i915->runtime_pm, wakeref) { ret = slpc_unset_param(slpc, SLPC_PARAM_PWRGATE_RC_MODE); if (ret) - drm_err(&i915->drm, - "Unsetting gucrc mode failed %d\n", - ret); + guc_err(slpc_to_guc(slpc), "Unsetting RC mode failed: %pe\n", ERR_PTR(ret)); } return ret; @@ -725,7 +711,7 @@ int intel_guc_slpc_unset_gucrc_mode(struct intel_guc_slpc *slpc) */ int intel_guc_slpc_enable(struct intel_guc_slpc *slpc) { - struct drm_i915_private *i915 = slpc_to_i915(slpc); + struct intel_guc *guc = slpc_to_guc(slpc); int ret; GEM_BUG_ON(!slpc->vma); @@ -734,8 +720,7 @@ int intel_guc_slpc_enable(struct intel_guc_slpc *slpc) ret = slpc_reset(slpc); if (unlikely(ret < 0)) { - i915_probe_error(i915, "SLPC Reset event returned (%pe)\n", - ERR_PTR(ret)); + guc_probe_error(guc, "SLPC Reset event returned: %pe\n", ERR_PTR(ret)); return ret; } @@ -743,7 +728,7 @@ int intel_guc_slpc_enable(struct intel_guc_slpc *slpc) if (unlikely(ret < 0)) return ret; - intel_guc_pm_intrmsk_enable(to_gt(i915)); + intel_guc_pm_intrmsk_enable(slpc_to_gt(slpc)); slpc_get_rp_values(slpc); @@ -753,16 +738,14 @@ int intel_guc_slpc_enable(struct intel_guc_slpc *slpc) /* Set SLPC max limit to RP0 */ ret = slpc_use_fused_rp0(slpc); if (unlikely(ret)) { - i915_probe_error(i915, "Failed to set SLPC max to RP0 (%pe)\n", - ERR_PTR(ret)); + guc_probe_error(guc, "Failed to set SLPC max to RP0: %pe\n", ERR_PTR(ret)); return ret; } /* Revert SLPC min/max to softlimits if necessary */ ret = slpc_set_softlimits(slpc); if (unlikely(ret)) { - i915_probe_error(i915, "Failed to set SLPC softlimits (%pe)\n", - ERR_PTR(ret)); + guc_probe_error(guc, "Failed to set SLPC softlimits: %pe\n", ERR_PTR(ret)); return ret; } diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.c b/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.c index 53f3ed3244d5..88e881b100cf 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.c +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.c @@ -1352,6 +1352,16 @@ static ktime_t guc_engine_busyness(struct intel_engine_cs *engine, ktime_t *now) return ns_to_ktime(total); } +static void guc_enable_busyness_worker(struct intel_guc *guc) +{ + mod_delayed_work(system_highpri_wq, &guc->timestamp.work, guc->timestamp.ping_delay); +} + +static void guc_cancel_busyness_worker(struct intel_guc *guc) +{ + cancel_delayed_work_sync(&guc->timestamp.work); +} + static void __reset_guc_busyness_stats(struct intel_guc *guc) { struct intel_gt *gt = guc_to_gt(guc); @@ -1360,7 +1370,7 @@ static void __reset_guc_busyness_stats(struct intel_guc *guc) unsigned long flags; ktime_t unused; - cancel_delayed_work_sync(&guc->timestamp.work); + guc_cancel_busyness_worker(guc); spin_lock_irqsave(&guc->timestamp.lock, flags); @@ -1416,8 +1426,7 @@ static void guc_timestamp_ping(struct work_struct *wrk) intel_gt_reset_unlock(gt, srcu); - mod_delayed_work(system_highpri_wq, &guc->timestamp.work, - guc->timestamp.ping_delay); + guc_enable_busyness_worker(guc); } static int guc_action_enable_usage_stats(struct intel_guc *guc) @@ -1432,20 +1441,26 @@ static int guc_action_enable_usage_stats(struct intel_guc *guc) return intel_guc_send(guc, action, ARRAY_SIZE(action)); } -static void guc_init_engine_stats(struct intel_guc *guc) +static int guc_init_engine_stats(struct intel_guc *guc) { struct intel_gt *gt = guc_to_gt(guc); intel_wakeref_t wakeref; + int ret; - mod_delayed_work(system_highpri_wq, &guc->timestamp.work, - guc->timestamp.ping_delay); + with_intel_runtime_pm(>->i915->runtime_pm, wakeref) + ret = guc_action_enable_usage_stats(guc); - with_intel_runtime_pm(>->i915->runtime_pm, wakeref) { - int ret = guc_action_enable_usage_stats(guc); + if (ret) + guc_err(guc, "Failed to enable usage stats: %pe\n", ERR_PTR(ret)); + else + guc_enable_busyness_worker(guc); - if (ret) - guc_err(guc, "Failed to enable usage stats: %pe\n", ERR_PTR(ret)); - } + return ret; +} + +static void guc_fini_engine_stats(struct intel_guc *guc) +{ + guc_cancel_busyness_worker(guc); } void intel_guc_busyness_park(struct intel_gt *gt) @@ -1460,7 +1475,7 @@ void intel_guc_busyness_park(struct intel_gt *gt) * and causes an unclaimed register access warning. Cancel the worker * synchronously here. */ - cancel_delayed_work_sync(&guc->timestamp.work); + guc_cancel_busyness_worker(guc); /* * Before parking, we should sample engine busyness stats if we need to. @@ -1487,8 +1502,7 @@ void intel_guc_busyness_unpark(struct intel_gt *gt) spin_lock_irqsave(&guc->timestamp.lock, flags); guc_update_pm_timestamp(guc, &unused); spin_unlock_irqrestore(&guc->timestamp.lock, flags); - mod_delayed_work(system_highpri_wq, &guc->timestamp.work, - guc->timestamp.ping_delay); + guc_enable_busyness_worker(guc); } static inline bool @@ -4102,9 +4116,11 @@ static void guc_set_default_submission(struct intel_engine_cs *engine) engine->submit_request = guc_submit_request; } -static inline void guc_kernel_context_pin(struct intel_guc *guc, - struct intel_context *ce) +static inline int guc_kernel_context_pin(struct intel_guc *guc, + struct intel_context *ce) { + int ret; + /* * Note: we purposefully do not check the returns below because * the registration can only fail if a reset is just starting. @@ -4112,16 +4128,24 @@ static inline void guc_kernel_context_pin(struct intel_guc *guc, * isn't happening and even it did this code would be run again. */ - if (context_guc_id_invalid(ce)) - pin_guc_id(guc, ce); + if (context_guc_id_invalid(ce)) { + ret = pin_guc_id(guc, ce); + + if (ret < 0) + return ret; + } if (!test_bit(CONTEXT_GUC_INIT, &ce->flags)) guc_context_init(ce); - try_context_registration(ce, true); + ret = try_context_registration(ce, true); + if (ret) + unpin_guc_id(guc, ce); + + return ret; } -static inline void guc_init_lrc_mapping(struct intel_guc *guc) +static inline int guc_init_submission(struct intel_guc *guc) { struct intel_gt *gt = guc_to_gt(guc); struct intel_engine_cs *engine; @@ -4148,9 +4172,17 @@ static inline void guc_init_lrc_mapping(struct intel_guc *guc) struct intel_context *ce; list_for_each_entry(ce, &engine->pinned_contexts_list, - pinned_contexts_link) - guc_kernel_context_pin(guc, ce); + pinned_contexts_link) { + int ret = guc_kernel_context_pin(guc, ce); + + if (ret) { + /* No point in trying to clean up as i915 will wedge on failure */ + return ret; + } + } } + + return 0; } static void guc_release(struct intel_engine_cs *engine) @@ -4393,30 +4425,57 @@ static int guc_init_global_schedule_policy(struct intel_guc *guc) return ret; } -void intel_guc_submission_enable(struct intel_guc *guc) +static void guc_route_semaphores(struct intel_guc *guc, bool to_guc) { struct intel_gt *gt = guc_to_gt(guc); + u32 val; - /* Enable and route to GuC */ - if (GRAPHICS_VER(gt->i915) >= 12) - intel_uncore_write(gt->uncore, GEN12_GUC_SEM_INTR_ENABLES, - GUC_SEM_INTR_ROUTE_TO_GUC | - GUC_SEM_INTR_ENABLE_ALL); + if (GRAPHICS_VER(gt->i915) < 12) + return; + + if (to_guc) + val = GUC_SEM_INTR_ROUTE_TO_GUC | GUC_SEM_INTR_ENABLE_ALL; + else + val = 0; - guc_init_lrc_mapping(guc); - guc_init_engine_stats(guc); - guc_init_global_schedule_policy(guc); + intel_uncore_write(gt->uncore, GEN12_GUC_SEM_INTR_ENABLES, val); } -void intel_guc_submission_disable(struct intel_guc *guc) +int intel_guc_submission_enable(struct intel_guc *guc) { - struct intel_gt *gt = guc_to_gt(guc); + int ret; + + /* Semaphore interrupt enable and route to GuC */ + guc_route_semaphores(guc, true); - /* Note: By the time we're here, GuC may have already been reset */ + ret = guc_init_submission(guc); + if (ret) + goto fail_sem; + + ret = guc_init_engine_stats(guc); + if (ret) + goto fail_sem; + + ret = guc_init_global_schedule_policy(guc); + if (ret) + goto fail_stats; + + return 0; + +fail_stats: + guc_fini_engine_stats(guc); +fail_sem: + guc_route_semaphores(guc, false); + return ret; +} + +/* Note: By the time we're here, GuC may have already been reset */ +void intel_guc_submission_disable(struct intel_guc *guc) +{ + guc_cancel_busyness_worker(guc); - /* Disable and route to host */ - if (GRAPHICS_VER(gt->i915) >= 12) - intel_uncore_write(gt->uncore, GEN12_GUC_SEM_INTR_ENABLES, 0x0); + /* Semaphore interrupt disable and route to host */ + guc_route_semaphores(guc, false); } static bool __guc_submission_supported(struct intel_guc *guc) @@ -4660,9 +4719,10 @@ static void guc_handle_context_reset(struct intel_guc *guc, { trace_intel_context_reset(ce); - drm_dbg(&guc_to_gt(guc)->i915->drm, "Got GuC reset of 0x%04X, exiting = %d, banned = %d\n", - ce->guc_id.id, test_bit(CONTEXT_EXITING, &ce->flags), - test_bit(CONTEXT_BANNED, &ce->flags)); + guc_dbg(guc, "Got context reset notification: 0x%04X on %s, exiting = %s, banned = %s\n", + ce->guc_id.id, ce->engine->name, + str_yes_no(intel_context_is_exiting(ce)), + str_yes_no(intel_context_is_banned(ce))); if (likely(intel_context_is_schedulable(ce))) { capture_error_state(guc, ce); diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.h b/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.h index 5a95a9f0a8e3..c57b29cdb1a6 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.h +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.h @@ -15,7 +15,7 @@ struct intel_engine_cs; void intel_guc_submission_init_early(struct intel_guc *guc); int intel_guc_submission_init(struct intel_guc *guc); -void intel_guc_submission_enable(struct intel_guc *guc); +int intel_guc_submission_enable(struct intel_guc *guc); void intel_guc_submission_disable(struct intel_guc *guc); void intel_guc_submission_fini(struct intel_guc *guc); int intel_guc_preempt_work_create(struct intel_guc *guc); diff --git a/drivers/gpu/drm/i915/gt/uc/intel_huc.c b/drivers/gpu/drm/i915/gt/uc/intel_huc.c index 0c103ca160d1..aefdaa62da99 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_huc.c +++ b/drivers/gpu/drm/i915/gt/uc/intel_huc.c @@ -6,6 +6,7 @@ #include <linux/types.h> #include "gt/intel_gt.h" +#include "gt/intel_gt_print.h" #include "intel_guc_reg.h" #include "intel_huc.h" #include "i915_drv.h" @@ -13,6 +14,15 @@ #include <linux/device/bus.h> #include <linux/mei_aux.h> +#define huc_printk(_huc, _level, _fmt, ...) \ + gt_##_level(huc_to_gt(_huc), "HuC: " _fmt, ##__VA_ARGS__) +#define huc_err(_huc, _fmt, ...) huc_printk((_huc), err, _fmt, ##__VA_ARGS__) +#define huc_warn(_huc, _fmt, ...) huc_printk((_huc), warn, _fmt, ##__VA_ARGS__) +#define huc_notice(_huc, _fmt, ...) huc_printk((_huc), notice, _fmt, ##__VA_ARGS__) +#define huc_info(_huc, _fmt, ...) huc_printk((_huc), info, _fmt, ##__VA_ARGS__) +#define huc_dbg(_huc, _fmt, ...) huc_printk((_huc), dbg, _fmt, ##__VA_ARGS__) +#define huc_probe_error(_huc, _fmt, ...) huc_printk((_huc), probe_error, _fmt, ##__VA_ARGS__) + /** * DOC: HuC * @@ -107,11 +117,9 @@ static enum hrtimer_restart huc_delayed_load_timer_callback(struct hrtimer *hrti if (!intel_huc_is_authenticated(huc)) { if (huc->delayed_load.status == INTEL_HUC_WAITING_ON_GSC) - drm_notice(&huc_to_gt(huc)->i915->drm, - "timed out waiting for MEI GSC init to load HuC\n"); + huc_notice(huc, "timed out waiting for MEI GSC\n"); else if (huc->delayed_load.status == INTEL_HUC_WAITING_ON_PXP) - drm_notice(&huc_to_gt(huc)->i915->drm, - "timed out waiting for MEI PXP init to load HuC\n"); + huc_notice(huc, "timed out waiting for MEI PXP\n"); else MISSING_CASE(huc->delayed_load.status); @@ -174,8 +182,7 @@ static int gsc_notifier(struct notifier_block *nb, unsigned long action, void *d case BUS_NOTIFY_DRIVER_NOT_BOUND: /* mei driver fails to be bound */ case BUS_NOTIFY_UNBIND_DRIVER: /* mei driver about to be unbound */ - drm_info(&huc_to_gt(huc)->i915->drm, - "mei driver not bound, disabling HuC load\n"); + huc_info(huc, "MEI driver not bound, disabling load\n"); gsc_init_error(huc); break; } @@ -193,8 +200,7 @@ void intel_huc_register_gsc_notifier(struct intel_huc *huc, struct bus_type *bus huc->delayed_load.nb.notifier_call = gsc_notifier; ret = bus_register_notifier(bus, &huc->delayed_load.nb); if (ret) { - drm_err(&huc_to_gt(huc)->i915->drm, - "failed to register GSC notifier\n"); + huc_err(huc, "failed to register GSC notifier %pe\n", ERR_PTR(ret)); huc->delayed_load.nb.notifier_call = NULL; gsc_init_error(huc); } @@ -313,29 +319,25 @@ static int check_huc_loading_mode(struct intel_huc *huc) GSC_LOADS_HUC; if (fw_needs_gsc != hw_uses_gsc) { - drm_err(>->i915->drm, - "mismatch between HuC FW (%s) and HW (%s) load modes\n", - HUC_LOAD_MODE_STRING(fw_needs_gsc), - HUC_LOAD_MODE_STRING(hw_uses_gsc)); + huc_err(huc, "mismatch between FW (%s) and HW (%s) load modes\n", + HUC_LOAD_MODE_STRING(fw_needs_gsc), HUC_LOAD_MODE_STRING(hw_uses_gsc)); return -ENOEXEC; } /* make sure we can access the GSC via the mei driver if we need it */ if (!(IS_ENABLED(CONFIG_INTEL_MEI_PXP) && IS_ENABLED(CONFIG_INTEL_MEI_GSC)) && fw_needs_gsc) { - drm_info(>->i915->drm, - "Can't load HuC due to missing MEI modules\n"); + huc_info(huc, "can't load due to missing MEI modules\n"); return -EIO; } - drm_dbg(>->i915->drm, "GSC loads huc=%s\n", str_yes_no(fw_needs_gsc)); + huc_dbg(huc, "loaded by GSC = %s\n", str_yes_no(fw_needs_gsc)); return 0; } int intel_huc_init(struct intel_huc *huc) { - struct drm_i915_private *i915 = huc_to_gt(huc)->i915; int err; err = check_huc_loading_mode(huc); @@ -352,7 +354,7 @@ int intel_huc_init(struct intel_huc *huc) out: intel_uc_fw_change_status(&huc->fw, INTEL_UC_FIRMWARE_INIT_FAIL); - drm_info(&i915->drm, "HuC init failed with %d\n", err); + huc_info(huc, "initialization failed %pe\n", ERR_PTR(err)); return err; } @@ -396,13 +398,13 @@ int intel_huc_wait_for_auth_complete(struct intel_huc *huc) delayed_huc_load_complete(huc); if (ret) { - drm_err(>->i915->drm, "HuC: Firmware not verified %d\n", ret); + huc_err(huc, "firmware not verified %pe\n", ERR_PTR(ret)); intel_uc_fw_change_status(&huc->fw, INTEL_UC_FIRMWARE_LOAD_FAIL); return ret; } intel_uc_fw_change_status(&huc->fw, INTEL_UC_FIRMWARE_RUNNING); - drm_info(>->i915->drm, "HuC authenticated\n"); + huc_info(huc, "authenticated!\n"); return 0; } @@ -437,7 +439,7 @@ int intel_huc_auth(struct intel_huc *huc) ret = intel_guc_auth_huc(guc, intel_guc_ggtt_offset(guc, huc->fw.rsa_data)); if (ret) { - DRM_ERROR("HuC: GuC did not ack Auth request %d\n", ret); + huc_err(huc, "authentication by GuC failed %pe\n", ERR_PTR(ret)); goto fail; } @@ -449,7 +451,7 @@ int intel_huc_auth(struct intel_huc *huc) return 0; fail: - i915_probe_error(gt->i915, "HuC: Authentication failed %d\n", ret); + huc_probe_error(huc, "authentication failed %pe\n", ERR_PTR(ret)); return ret; } diff --git a/drivers/gpu/drm/i915/gt/uc/intel_uc.c b/drivers/gpu/drm/i915/gt/uc/intel_uc.c index de7f987cf611..4ccb4be4c9cb 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_uc.c +++ b/drivers/gpu/drm/i915/gt/uc/intel_uc.c @@ -83,15 +83,15 @@ static int __intel_uc_reset_hw(struct intel_uc *uc) static void __confirm_options(struct intel_uc *uc) { - struct drm_i915_private *i915 = uc_to_gt(uc)->i915; + struct intel_gt *gt = uc_to_gt(uc); + struct drm_i915_private *i915 = gt->i915; - drm_dbg(&i915->drm, - "enable_guc=%d (guc:%s submission:%s huc:%s slpc:%s)\n", - i915->params.enable_guc, - str_yes_no(intel_uc_wants_guc(uc)), - str_yes_no(intel_uc_wants_guc_submission(uc)), - str_yes_no(intel_uc_wants_huc(uc)), - str_yes_no(intel_uc_wants_guc_slpc(uc))); + gt_dbg(gt, "enable_guc=%d (guc:%s submission:%s huc:%s slpc:%s)\n", + i915->params.enable_guc, + str_yes_no(intel_uc_wants_guc(uc)), + str_yes_no(intel_uc_wants_guc_submission(uc)), + str_yes_no(intel_uc_wants_huc(uc)), + str_yes_no(intel_uc_wants_guc_slpc(uc))); if (i915->params.enable_guc == 0) { GEM_BUG_ON(intel_uc_wants_guc(uc)); @@ -102,26 +102,22 @@ static void __confirm_options(struct intel_uc *uc) } if (!intel_uc_supports_guc(uc)) - drm_info(&i915->drm, - "Incompatible option enable_guc=%d - %s\n", - i915->params.enable_guc, "GuC is not supported!"); + gt_info(gt, "Incompatible option enable_guc=%d - %s\n", + i915->params.enable_guc, "GuC is not supported!"); if (i915->params.enable_guc & ENABLE_GUC_LOAD_HUC && !intel_uc_supports_huc(uc)) - drm_info(&i915->drm, - "Incompatible option enable_guc=%d - %s\n", - i915->params.enable_guc, "HuC is not supported!"); + gt_info(gt, "Incompatible option enable_guc=%d - %s\n", + i915->params.enable_guc, "HuC is not supported!"); if (i915->params.enable_guc & ENABLE_GUC_SUBMISSION && !intel_uc_supports_guc_submission(uc)) - drm_info(&i915->drm, - "Incompatible option enable_guc=%d - %s\n", - i915->params.enable_guc, "GuC submission is N/A"); + gt_info(gt, "Incompatible option enable_guc=%d - %s\n", + i915->params.enable_guc, "GuC submission is N/A"); if (i915->params.enable_guc & ~ENABLE_GUC_MASK) - drm_info(&i915->drm, - "Incompatible option enable_guc=%d - %s\n", - i915->params.enable_guc, "undocumented flag"); + gt_info(gt, "Incompatible option enable_guc=%d - %s\n", + i915->params.enable_guc, "undocumented flag"); } void intel_uc_init_early(struct intel_uc *uc) @@ -143,6 +139,7 @@ void intel_uc_init_early(struct intel_uc *uc) void intel_uc_init_late(struct intel_uc *uc) { intel_guc_init_late(&uc->guc); + intel_gsc_uc_load_start(&uc->gsc); } void intel_uc_driver_late_release(struct intel_uc *uc) @@ -535,8 +532,11 @@ static int __uc_init_hw(struct intel_uc *uc) else intel_huc_auth(huc); - if (intel_uc_uses_guc_submission(uc)) - intel_guc_submission_enable(guc); + if (intel_uc_uses_guc_submission(uc)) { + ret = intel_guc_submission_enable(guc); + if (ret) + goto err_log_capture; + } if (intel_uc_uses_guc_slpc(uc)) { ret = intel_guc_slpc_enable(&guc->slpc); @@ -547,12 +547,8 @@ static int __uc_init_hw(struct intel_uc *uc) intel_rps_lower_unslice(&uc_to_gt(uc)->rps); } - intel_gsc_uc_load_start(&uc->gsc); - - gt_info(gt, "GuC submission %s\n", - str_enabled_disabled(intel_uc_uses_guc_submission(uc))); - gt_info(gt, "GuC SLPC %s\n", - str_enabled_disabled(intel_uc_uses_guc_slpc(uc))); + guc_info(guc, "submission %s\n", str_enabled_disabled(intel_uc_uses_guc_submission(uc))); + guc_info(guc, "SLPC %s\n", str_enabled_disabled(intel_uc_uses_guc_slpc(uc))); return 0; @@ -678,7 +674,7 @@ void intel_uc_suspend(struct intel_uc *uc) int err; /* flush the GSC worker */ - intel_gsc_uc_suspend(&uc->gsc); + intel_gsc_uc_flush_work(&uc->gsc); if (!intel_guc_is_ready(guc)) { guc->interrupts.enabled = false; @@ -720,6 +716,8 @@ static int __uc_resume(struct intel_uc *uc, bool enable_communication) return err; } + intel_gsc_uc_resume(&uc->gsc); + return 0; } diff --git a/drivers/gpu/drm/i915/gt/uc/intel_uc_debugfs.c b/drivers/gpu/drm/i915/gt/uc/intel_uc_debugfs.c index 284d6fbc2d08..2f93cc4e408a 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_uc_debugfs.c +++ b/drivers/gpu/drm/i915/gt/uc/intel_uc_debugfs.c @@ -54,6 +54,8 @@ void intel_uc_debugfs_register(struct intel_uc *uc, struct dentry *gt_root) if (IS_ERR(root)) return; + uc->guc.dbgfs_node = root; + intel_gt_debugfs_register_files(root, files, ARRAY_SIZE(files), uc); intel_guc_debugfs_register(&uc->guc, root); diff --git a/drivers/gpu/drm/i915/gt/uc/intel_uc_fw.c b/drivers/gpu/drm/i915/gt/uc/intel_uc_fw.c index 65672ff82605..24765c30a0e1 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_uc_fw.c +++ b/drivers/gpu/drm/i915/gt/uc/intel_uc_fw.c @@ -11,6 +11,7 @@ #include <drm/drm_print.h> #include "gem/i915_gem_lmem.h" +#include "gt/intel_gt_print.h" #include "intel_uc_fw.h" #include "intel_uc_fw_abi.h" #include "i915_drv.h" @@ -44,11 +45,10 @@ void intel_uc_fw_change_status(struct intel_uc_fw *uc_fw, enum intel_uc_fw_status status) { uc_fw->__status = status; - drm_dbg(&__uc_fw_to_gt(uc_fw)->i915->drm, - "%s firmware -> %s\n", - intel_uc_fw_type_repr(uc_fw->type), - status == INTEL_UC_FIRMWARE_SELECTED ? - uc_fw->file_selected.path : intel_uc_fw_status_repr(status)); + gt_dbg(__uc_fw_to_gt(uc_fw), "%s firmware -> %s\n", + intel_uc_fw_type_repr(uc_fw->type), + status == INTEL_UC_FIRMWARE_SELECTED ? + uc_fw->file_selected.path : intel_uc_fw_status_repr(status)); } #endif @@ -488,12 +488,25 @@ static void __force_fw_fetch_failures(struct intel_uc_fw *uc_fw, int e) } } -static int check_gsc_manifest(const struct firmware *fw, +static int check_gsc_manifest(struct intel_gt *gt, + const struct firmware *fw, struct intel_uc_fw *uc_fw) { u32 *dw = (u32 *)fw->data; - u32 version_hi = dw[HUC_GSC_VERSION_HI_DW]; - u32 version_lo = dw[HUC_GSC_VERSION_LO_DW]; + u32 version_hi, version_lo; + size_t min_size; + + /* Check the size of the blob before examining buffer contents */ + min_size = sizeof(u32) * (HUC_GSC_VERSION_LO_DW + 1); + if (unlikely(fw->size < min_size)) { + gt_warn(gt, "%s firmware %s: invalid size: %zu < %zu\n", + intel_uc_fw_type_repr(uc_fw->type), uc_fw->file_selected.path, + fw->size, min_size); + return -ENODATA; + } + + version_hi = dw[HUC_GSC_VERSION_HI_DW]; + version_lo = dw[HUC_GSC_VERSION_LO_DW]; uc_fw->file_selected.ver.major = FIELD_GET(HUC_GSC_MAJOR_VER_HI_MASK, version_hi); uc_fw->file_selected.ver.minor = FIELD_GET(HUC_GSC_MINOR_VER_HI_MASK, version_hi); @@ -562,15 +575,14 @@ static int check_ccs_header(struct intel_gt *gt, const struct firmware *fw, struct intel_uc_fw *uc_fw) { - struct drm_i915_private *i915 = gt->i915; struct uc_css_header *css; size_t size; /* Check the size of the blob before examining buffer contents */ if (unlikely(fw->size < sizeof(struct uc_css_header))) { - drm_warn(&i915->drm, "%s firmware %s: invalid size: %zu < %zu\n", - intel_uc_fw_type_repr(uc_fw->type), uc_fw->file_selected.path, - fw->size, sizeof(struct uc_css_header)); + gt_warn(gt, "%s firmware %s: invalid size: %zu < %zu\n", + intel_uc_fw_type_repr(uc_fw->type), uc_fw->file_selected.path, + fw->size, sizeof(struct uc_css_header)); return -ENODATA; } @@ -580,10 +592,9 @@ static int check_ccs_header(struct intel_gt *gt, size = (css->header_size_dw - css->key_size_dw - css->modulus_size_dw - css->exponent_size_dw) * sizeof(u32); if (unlikely(size != sizeof(struct uc_css_header))) { - drm_warn(&i915->drm, - "%s firmware %s: unexpected header size: %zu != %zu\n", - intel_uc_fw_type_repr(uc_fw->type), uc_fw->file_selected.path, - fw->size, sizeof(struct uc_css_header)); + gt_warn(gt, "%s firmware %s: unexpected header size: %zu != %zu\n", + intel_uc_fw_type_repr(uc_fw->type), uc_fw->file_selected.path, + fw->size, sizeof(struct uc_css_header)); return -EPROTO; } @@ -596,18 +607,18 @@ static int check_ccs_header(struct intel_gt *gt, /* At least, it should have header, uCode and RSA. Size of all three. */ size = sizeof(struct uc_css_header) + uc_fw->ucode_size + uc_fw->rsa_size; if (unlikely(fw->size < size)) { - drm_warn(&i915->drm, "%s firmware %s: invalid size: %zu < %zu\n", - intel_uc_fw_type_repr(uc_fw->type), uc_fw->file_selected.path, - fw->size, size); + gt_warn(gt, "%s firmware %s: invalid size: %zu < %zu\n", + intel_uc_fw_type_repr(uc_fw->type), uc_fw->file_selected.path, + fw->size, size); return -ENOEXEC; } /* Sanity check whether this fw is not larger than whole WOPCM memory */ size = __intel_uc_fw_get_upload_size(uc_fw); if (unlikely(size >= gt->wopcm.size)) { - drm_warn(&i915->drm, "%s firmware %s: invalid size: %zu > %zu\n", - intel_uc_fw_type_repr(uc_fw->type), uc_fw->file_selected.path, - size, (size_t)gt->wopcm.size); + gt_warn(gt, "%s firmware %s: invalid size: %zu > %zu\n", + intel_uc_fw_type_repr(uc_fw->type), uc_fw->file_selected.path, + size, (size_t)gt->wopcm.size); return -E2BIG; } @@ -635,20 +646,20 @@ static bool guc_check_version_range(struct intel_uc_fw *uc_fw) */ if (!is_ver_8bit(&uc_fw->file_selected.ver)) { - drm_warn(&__uc_fw_to_gt(uc_fw)->i915->drm, "%s firmware: invalid file version: 0x%02X:%02X:%02X\n", - intel_uc_fw_type_repr(uc_fw->type), - uc_fw->file_selected.ver.major, - uc_fw->file_selected.ver.minor, - uc_fw->file_selected.ver.patch); + gt_warn(__uc_fw_to_gt(uc_fw), "%s firmware: invalid file version: 0x%02X:%02X:%02X\n", + intel_uc_fw_type_repr(uc_fw->type), + uc_fw->file_selected.ver.major, + uc_fw->file_selected.ver.minor, + uc_fw->file_selected.ver.patch); return false; } if (!is_ver_8bit(&guc->submission_version)) { - drm_warn(&__uc_fw_to_gt(uc_fw)->i915->drm, "%s firmware: invalid submit version: 0x%02X:%02X:%02X\n", - intel_uc_fw_type_repr(uc_fw->type), - guc->submission_version.major, - guc->submission_version.minor, - guc->submission_version.patch); + gt_warn(__uc_fw_to_gt(uc_fw), "%s firmware: invalid submit version: 0x%02X:%02X:%02X\n", + intel_uc_fw_type_repr(uc_fw->type), + guc->submission_version.major, + guc->submission_version.minor, + guc->submission_version.patch); return false; } @@ -666,7 +677,7 @@ static int check_fw_header(struct intel_gt *gt, return 0; if (uc_fw->loaded_via_gsc) - err = check_gsc_manifest(fw, uc_fw); + err = check_gsc_manifest(gt, fw, uc_fw); else err = check_ccs_header(gt, fw, uc_fw); if (err) @@ -687,10 +698,9 @@ static int try_firmware_load(struct intel_uc_fw *uc_fw, const struct firmware ** return err; if ((*fw)->size > INTEL_UC_RSVD_GGTT_PER_FW) { - drm_err(>->i915->drm, - "%s firmware %s: size (%zuKB) exceeds max supported size (%uKB)\n", - intel_uc_fw_type_repr(uc_fw->type), uc_fw->file_selected.path, - (*fw)->size / SZ_1K, INTEL_UC_RSVD_GGTT_PER_FW / SZ_1K); + gt_err(gt, "%s firmware %s: size (%zuKB) exceeds max supported size (%uKB)\n", + intel_uc_fw_type_repr(uc_fw->type), uc_fw->file_selected.path, + (*fw)->size / SZ_1K, INTEL_UC_RSVD_GGTT_PER_FW / SZ_1K); /* try to find another blob to load */ release_firmware(*fw); @@ -768,10 +778,10 @@ int intel_uc_fw_fetch(struct intel_uc_fw *uc_fw) if (uc_fw->file_wanted.ver.major && uc_fw->file_selected.ver.major) { /* Check the file's major version was as it claimed */ if (uc_fw->file_selected.ver.major != uc_fw->file_wanted.ver.major) { - drm_notice(&i915->drm, "%s firmware %s: unexpected version: %u.%u != %u.%u\n", - intel_uc_fw_type_repr(uc_fw->type), uc_fw->file_selected.path, - uc_fw->file_selected.ver.major, uc_fw->file_selected.ver.minor, - uc_fw->file_wanted.ver.major, uc_fw->file_wanted.ver.minor); + gt_notice(gt, "%s firmware %s: unexpected version: %u.%u != %u.%u\n", + intel_uc_fw_type_repr(uc_fw->type), uc_fw->file_selected.path, + uc_fw->file_selected.ver.major, uc_fw->file_selected.ver.minor, + uc_fw->file_wanted.ver.major, uc_fw->file_wanted.ver.minor); if (!intel_uc_fw_is_overridden(uc_fw)) { err = -ENOEXEC; goto fail; @@ -786,16 +796,14 @@ int intel_uc_fw_fetch(struct intel_uc_fw *uc_fw) /* Preserve the version that was really wanted */ memcpy(&uc_fw->file_wanted, &file_ideal, sizeof(uc_fw->file_wanted)); - drm_notice(&i915->drm, - "%s firmware %s (%d.%d) is recommended, but only %s (%d.%d) was found\n", - intel_uc_fw_type_repr(uc_fw->type), - uc_fw->file_wanted.path, - uc_fw->file_wanted.ver.major, uc_fw->file_wanted.ver.minor, - uc_fw->file_selected.path, - uc_fw->file_selected.ver.major, uc_fw->file_selected.ver.minor); - drm_info(&i915->drm, - "Consider updating your linux-firmware pkg or downloading from %s\n", - INTEL_UC_FIRMWARE_URL); + gt_notice(gt, "%s firmware %s (%d.%d) is recommended, but only %s (%d.%d) was found\n", + intel_uc_fw_type_repr(uc_fw->type), + uc_fw->file_wanted.path, + uc_fw->file_wanted.ver.major, uc_fw->file_wanted.ver.minor, + uc_fw->file_selected.path, + uc_fw->file_selected.ver.major, uc_fw->file_selected.ver.minor); + gt_info(gt, "Consider updating your linux-firmware pkg or downloading from %s\n", + INTEL_UC_FIRMWARE_URL); } if (HAS_LMEM(i915)) { @@ -823,10 +831,10 @@ fail: INTEL_UC_FIRMWARE_MISSING : INTEL_UC_FIRMWARE_ERROR); - i915_probe_error(i915, "%s firmware %s: fetch failed with error %d\n", - intel_uc_fw_type_repr(uc_fw->type), uc_fw->file_selected.path, err); - drm_info(&i915->drm, "%s firmware(s) can be downloaded from %s\n", - intel_uc_fw_type_repr(uc_fw->type), INTEL_UC_FIRMWARE_URL); + gt_probe_error(gt, "%s firmware %s: fetch failed %pe\n", + intel_uc_fw_type_repr(uc_fw->type), uc_fw->file_selected.path, ERR_PTR(err)); + gt_info(gt, "%s firmware(s) can be downloaded from %s\n", + intel_uc_fw_type_repr(uc_fw->type), INTEL_UC_FIRMWARE_URL); release_firmware(fw); /* OK even if fw is NULL */ return err; @@ -932,9 +940,9 @@ static int uc_fw_xfer(struct intel_uc_fw *uc_fw, u32 dst_offset, u32 dma_flags) /* Wait for DMA to finish */ ret = intel_wait_for_register_fw(uncore, DMA_CTRL, START_DMA, 0, 100); if (ret) - drm_err(>->i915->drm, "DMA for %s fw failed, DMA_CTRL=%u\n", - intel_uc_fw_type_repr(uc_fw->type), - intel_uncore_read_fw(uncore, DMA_CTRL)); + gt_err(gt, "DMA for %s fw failed, DMA_CTRL=%u\n", + intel_uc_fw_type_repr(uc_fw->type), + intel_uncore_read_fw(uncore, DMA_CTRL)); /* Disable the bits once DMA is over */ intel_uncore_write_fw(uncore, DMA_CTRL, _MASKED_BIT_DISABLE(dma_flags)); @@ -950,9 +958,8 @@ int intel_uc_fw_mark_load_failed(struct intel_uc_fw *uc_fw, int err) GEM_BUG_ON(!intel_uc_fw_is_loadable(uc_fw)); - i915_probe_error(gt->i915, "Failed to load %s firmware %s (%d)\n", - intel_uc_fw_type_repr(uc_fw->type), uc_fw->file_selected.path, - err); + gt_probe_error(gt, "Failed to load %s firmware %s %pe\n", + intel_uc_fw_type_repr(uc_fw->type), uc_fw->file_selected.path, ERR_PTR(err)); intel_uc_fw_change_status(uc_fw, INTEL_UC_FIRMWARE_LOAD_FAIL); return err; @@ -1078,15 +1085,15 @@ int intel_uc_fw_init(struct intel_uc_fw *uc_fw) err = i915_gem_object_pin_pages_unlocked(uc_fw->obj); if (err) { - DRM_DEBUG_DRIVER("%s fw pin-pages err=%d\n", - intel_uc_fw_type_repr(uc_fw->type), err); + gt_dbg(__uc_fw_to_gt(uc_fw), "%s fw pin-pages failed %pe\n", + intel_uc_fw_type_repr(uc_fw->type), ERR_PTR(err)); goto out; } err = uc_fw_rsa_data_create(uc_fw); if (err) { - DRM_DEBUG_DRIVER("%s fw rsa data creation failed, err=%d\n", - intel_uc_fw_type_repr(uc_fw->type), err); + gt_dbg(__uc_fw_to_gt(uc_fw), "%s fw rsa data creation failed %pe\n", + intel_uc_fw_type_repr(uc_fw->type), ERR_PTR(err)); goto out_unpin; } diff --git a/drivers/gpu/drm/i915/gt/uc/selftest_guc.c b/drivers/gpu/drm/i915/gt/uc/selftest_guc.c index e28518fe8b90..1fd760539f77 100644 --- a/drivers/gpu/drm/i915/gt/uc/selftest_guc.c +++ b/drivers/gpu/drm/i915/gt/uc/selftest_guc.c @@ -3,6 +3,8 @@ * Copyright �� 2021 Intel Corporation */ +#include "gt/intel_gt_print.h" +#include "intel_guc_print.h" #include "selftests/igt_spinner.h" #include "selftests/intel_scheduler_helpers.h" @@ -65,7 +67,7 @@ static int intel_guc_scrub_ctbs(void *arg) ce = intel_context_create(engine); if (IS_ERR(ce)) { ret = PTR_ERR(ce); - drm_err(>->i915->drm, "Failed to create context, %d: %d\n", i, ret); + gt_err(gt, "Failed to create context %d: %pe\n", i, ce); goto err; } @@ -86,7 +88,7 @@ static int intel_guc_scrub_ctbs(void *arg) if (IS_ERR(rq)) { ret = PTR_ERR(rq); - drm_err(>->i915->drm, "Failed to create request, %d: %d\n", i, ret); + gt_err(gt, "Failed to create request %d: %pe\n", i, rq); goto err; } @@ -96,7 +98,7 @@ static int intel_guc_scrub_ctbs(void *arg) for (i = 0; i < 3; ++i) { ret = i915_request_wait(last[i], 0, HZ); if (ret < 0) { - drm_err(>->i915->drm, "Last request failed to complete: %d\n", ret); + gt_err(gt, "Last request failed to complete: %pe\n", ERR_PTR(ret)); goto err; } i915_request_put(last[i]); @@ -113,7 +115,7 @@ static int intel_guc_scrub_ctbs(void *arg) /* GT will not idle if G2H are lost */ ret = intel_gt_wait_for_idle(gt, HZ); if (ret < 0) { - drm_err(>->i915->drm, "GT failed to idle: %d\n", ret); + gt_err(gt, "GT failed to idle: %pe\n", ERR_PTR(ret)); goto err; } @@ -153,7 +155,7 @@ static int intel_guc_steal_guc_ids(void *arg) ce = kcalloc(GUC_MAX_CONTEXT_ID, sizeof(*ce), GFP_KERNEL); if (!ce) { - drm_err(>->i915->drm, "Context array allocation failed\n"); + guc_err(guc, "Context array allocation failed\n"); return -ENOMEM; } @@ -166,25 +168,25 @@ static int intel_guc_steal_guc_ids(void *arg) ce[context_index] = intel_context_create(engine); if (IS_ERR(ce[context_index])) { ret = PTR_ERR(ce[context_index]); + guc_err(guc, "Failed to create context: %pe\n", ce[context_index]); ce[context_index] = NULL; - drm_err(>->i915->drm, "Failed to create context: %d\n", ret); goto err_wakeref; } ret = igt_spinner_init(&spin, engine->gt); if (ret) { - drm_err(>->i915->drm, "Failed to create spinner: %d\n", ret); + guc_err(guc, "Failed to create spinner: %pe\n", ERR_PTR(ret)); goto err_contexts; } spin_rq = igt_spinner_create_request(&spin, ce[context_index], MI_ARB_CHECK); if (IS_ERR(spin_rq)) { ret = PTR_ERR(spin_rq); - drm_err(>->i915->drm, "Failed to create spinner request: %d\n", ret); + guc_err(guc, "Failed to create spinner request: %pe\n", spin_rq); goto err_contexts; } ret = request_add_spin(spin_rq, &spin); if (ret) { - drm_err(>->i915->drm, "Failed to add Spinner request: %d\n", ret); + guc_err(guc, "Failed to add Spinner request: %pe\n", ERR_PTR(ret)); goto err_spin_rq; } @@ -192,9 +194,9 @@ static int intel_guc_steal_guc_ids(void *arg) while (ret != -EAGAIN) { ce[++context_index] = intel_context_create(engine); if (IS_ERR(ce[context_index])) { - ret = PTR_ERR(ce[context_index--]); - ce[context_index] = NULL; - drm_err(>->i915->drm, "Failed to create context: %d\n", ret); + ret = PTR_ERR(ce[context_index]); + guc_err(guc, "Failed to create context: %pe\n", ce[context_index]); + ce[context_index--] = NULL; goto err_spin_rq; } @@ -203,8 +205,8 @@ static int intel_guc_steal_guc_ids(void *arg) ret = PTR_ERR(rq); rq = NULL; if (ret != -EAGAIN) { - drm_err(>->i915->drm, "Failed to create request, %d: %d\n", - context_index, ret); + guc_err(guc, "Failed to create request %d: %pe\n", + context_index, ERR_PTR(ret)); goto err_spin_rq; } } else { @@ -218,7 +220,7 @@ static int intel_guc_steal_guc_ids(void *arg) igt_spinner_end(&spin); ret = intel_selftest_wait_for_rq(spin_rq); if (ret) { - drm_err(>->i915->drm, "Spin request failed to complete: %d\n", ret); + guc_err(guc, "Spin request failed to complete: %pe\n", ERR_PTR(ret)); i915_request_put(last); goto err_spin_rq; } @@ -230,7 +232,7 @@ static int intel_guc_steal_guc_ids(void *arg) ret = i915_request_wait(last, 0, HZ * 30); i915_request_put(last); if (ret < 0) { - drm_err(>->i915->drm, "Last request failed to complete: %d\n", ret); + guc_err(guc, "Last request failed to complete: %pe\n", ERR_PTR(ret)); goto err_spin_rq; } @@ -238,7 +240,7 @@ static int intel_guc_steal_guc_ids(void *arg) rq = nop_user_request(ce[context_index], NULL); if (IS_ERR(rq)) { ret = PTR_ERR(rq); - drm_err(>->i915->drm, "Failed to steal guc_id, %d: %d\n", context_index, ret); + guc_err(guc, "Failed to steal guc_id %d: %pe\n", context_index, rq); goto err_spin_rq; } @@ -246,20 +248,20 @@ static int intel_guc_steal_guc_ids(void *arg) ret = i915_request_wait(rq, 0, HZ); i915_request_put(rq); if (ret < 0) { - drm_err(>->i915->drm, "Request with stolen guc_id failed to complete: %d\n", ret); + guc_err(guc, "Request with stolen guc_id failed to complete: %pe\n", ERR_PTR(ret)); goto err_spin_rq; } /* Wait for idle */ ret = intel_gt_wait_for_idle(gt, HZ * 30); if (ret < 0) { - drm_err(>->i915->drm, "GT failed to idle: %d\n", ret); + guc_err(guc, "GT failed to idle: %pe\n", ERR_PTR(ret)); goto err_spin_rq; } /* Verify a guc_id was stolen */ if (guc->number_guc_id_stolen == number_guc_id_stolen) { - drm_err(>->i915->drm, "No guc_id was stolen"); + guc_err(guc, "No guc_id was stolen"); ret = -EINVAL; } else { ret = 0; diff --git a/drivers/gpu/drm/i915/gt/uc/selftest_guc_hangcheck.c b/drivers/gpu/drm/i915/gt/uc/selftest_guc_hangcheck.c index d91b58f70403..34b5d952e2bc 100644 --- a/drivers/gpu/drm/i915/gt/uc/selftest_guc_hangcheck.c +++ b/drivers/gpu/drm/i915/gt/uc/selftest_guc_hangcheck.c @@ -3,6 +3,7 @@ * Copyright © 2022 Intel Corporation */ +#include "gt/intel_gt_print.h" #include "selftests/igt_spinner.h" #include "selftests/igt_reset.h" #include "selftests/intel_scheduler_helpers.h" @@ -45,7 +46,7 @@ static int intel_hang_guc(void *arg) ctx = kernel_context(gt->i915, NULL); if (IS_ERR(ctx)) { - drm_err(>->i915->drm, "Failed get kernel context: %ld\n", PTR_ERR(ctx)); + gt_err(gt, "Failed get kernel context: %pe\n", ctx); return PTR_ERR(ctx); } @@ -54,7 +55,7 @@ static int intel_hang_guc(void *arg) ce = intel_context_create(engine); if (IS_ERR(ce)) { ret = PTR_ERR(ce); - drm_err(>->i915->drm, "Failed to create spinner request: %d\n", ret); + gt_err(gt, "Failed to create spinner request: %pe\n", ce); goto err; } @@ -63,13 +64,13 @@ static int intel_hang_guc(void *arg) old_beat = engine->props.heartbeat_interval_ms; ret = intel_engine_set_heartbeat(engine, BEAT_INTERVAL); if (ret) { - drm_err(>->i915->drm, "Failed to boost heatbeat interval: %d\n", ret); + gt_err(gt, "Failed to boost heatbeat interval: %pe\n", ERR_PTR(ret)); goto err; } ret = igt_spinner_init(&spin, engine->gt); if (ret) { - drm_err(>->i915->drm, "Failed to create spinner: %d\n", ret); + gt_err(gt, "Failed to create spinner: %pe\n", ERR_PTR(ret)); goto err; } @@ -77,28 +78,28 @@ static int intel_hang_guc(void *arg) intel_context_put(ce); if (IS_ERR(rq)) { ret = PTR_ERR(rq); - drm_err(>->i915->drm, "Failed to create spinner request: %d\n", ret); + gt_err(gt, "Failed to create spinner request: %pe\n", rq); goto err_spin; } ret = request_add_spin(rq, &spin); if (ret) { i915_request_put(rq); - drm_err(>->i915->drm, "Failed to add Spinner request: %d\n", ret); + gt_err(gt, "Failed to add Spinner request: %pe\n", ERR_PTR(ret)); goto err_spin; } ret = intel_reset_guc(gt); if (ret) { i915_request_put(rq); - drm_err(>->i915->drm, "Failed to reset GuC, ret = %d\n", ret); + gt_err(gt, "Failed to reset GuC: %pe\n", ERR_PTR(ret)); goto err_spin; } guc_status = intel_uncore_read(gt->uncore, GUC_STATUS); if (!(guc_status & GS_MIA_IN_RESET)) { i915_request_put(rq); - drm_err(>->i915->drm, "GuC failed to reset: status = 0x%08X\n", guc_status); + gt_err(gt, "Failed to reset GuC: status = 0x%08X\n", guc_status); ret = -EIO; goto err_spin; } @@ -107,12 +108,12 @@ static int intel_hang_guc(void *arg) ret = intel_selftest_wait_for_rq(rq); i915_request_put(rq); if (ret) { - drm_err(>->i915->drm, "Request failed to complete: %d\n", ret); + gt_err(gt, "Request failed to complete: %pe\n", ERR_PTR(ret)); goto err_spin; } if (i915_reset_count(global) == reset_count) { - drm_err(>->i915->drm, "Failed to record a GPU reset\n"); + gt_err(gt, "Failed to record a GPU reset\n"); ret = -EINVAL; goto err_spin; } @@ -132,7 +133,7 @@ err_spin: ret = intel_selftest_wait_for_rq(rq); i915_request_put(rq); if (ret) { - drm_err(>->i915->drm, "No-op failed to complete: %d\n", ret); + gt_err(gt, "No-op failed to complete: %pe\n", ERR_PTR(ret)); goto err; } } diff --git a/drivers/gpu/drm/i915/gt/uc/selftest_guc_multi_lrc.c b/drivers/gpu/drm/i915/gt/uc/selftest_guc_multi_lrc.c index d17982c36d25..a40e7c32e613 100644 --- a/drivers/gpu/drm/i915/gt/uc/selftest_guc_multi_lrc.c +++ b/drivers/gpu/drm/i915/gt/uc/selftest_guc_multi_lrc.c @@ -3,6 +3,7 @@ * Copyright �� 2019 Intel Corporation */ +#include "gt/intel_gt_print.h" #include "selftests/igt_spinner.h" #include "selftests/igt_reset.h" #include "selftests/intel_scheduler_helpers.h" @@ -115,30 +116,30 @@ static int __intel_guc_multi_lrc_basic(struct intel_gt *gt, unsigned int class) parent = multi_lrc_create_parent(gt, class, 0); if (IS_ERR(parent)) { - drm_err(>->i915->drm, "Failed creating contexts: %ld", PTR_ERR(parent)); + gt_err(gt, "Failed creating contexts: %pe\n", parent); return PTR_ERR(parent); } else if (!parent) { - drm_dbg(>->i915->drm, "Not enough engines in class: %d", class); + gt_dbg(gt, "Not enough engines in class: %d\n", class); return 0; } rq = multi_lrc_nop_request(parent); if (IS_ERR(rq)) { ret = PTR_ERR(rq); - drm_err(>->i915->drm, "Failed creating requests: %d", ret); + gt_err(gt, "Failed creating requests: %pe\n", rq); goto out; } ret = intel_selftest_wait_for_rq(rq); if (ret) - drm_err(>->i915->drm, "Failed waiting on request: %d", ret); + gt_err(gt, "Failed waiting on request: %pe\n", ERR_PTR(ret)); i915_request_put(rq); if (ret >= 0) { ret = intel_gt_wait_for_idle(gt, HZ * 5); if (ret < 0) - drm_err(>->i915->drm, "GT failed to idle: %d\n", ret); + gt_err(gt, "GT failed to idle: %pe\n", ERR_PTR(ret)); } out: |