return 0;
}
-static void i915_guc_log_info(struct seq_file *m,
- struct drm_i915_private *dev_priv)
+static const char *
+stringify_guc_log_type(enum guc_log_buffer_type type)
{
- struct intel_guc *guc = &dev_priv->guc;
-
- seq_puts(m, "GuC logging stats:\n");
+ switch (type) {
+ case GUC_ISR_LOG_BUFFER:
+ return "ISR";
+ case GUC_DPC_LOG_BUFFER:
+ return "DPC";
+ case GUC_CRASH_DUMP_LOG_BUFFER:
+ return "CRASH";
+ default:
+ MISSING_CASE(type);
+ }
- seq_printf(m, "\tISR: flush count %10u, overflow count %10u\n",
- guc->log.flush_count[GUC_ISR_LOG_BUFFER],
- guc->log.total_overflow_count[GUC_ISR_LOG_BUFFER]);
+ return "";
+}
- seq_printf(m, "\tDPC: flush count %10u, overflow count %10u\n",
- guc->log.flush_count[GUC_DPC_LOG_BUFFER],
- guc->log.total_overflow_count[GUC_DPC_LOG_BUFFER]);
+static void i915_guc_log_info(struct seq_file *m,
+ struct drm_i915_private *dev_priv)
+{
+ struct intel_guc_log *log = &dev_priv->guc.log;
+ enum guc_log_buffer_type type;
- seq_printf(m, "\tCRASH: flush count %10u, overflow count %10u\n",
- guc->log.flush_count[GUC_CRASH_DUMP_LOG_BUFFER],
- guc->log.total_overflow_count[GUC_CRASH_DUMP_LOG_BUFFER]);
+ if (!intel_guc_log_relay_enabled(log)) {
+ seq_puts(m, "GuC log relay disabled\n");
+ return;
+ }
- seq_printf(m, "\tTotal flush interrupt count: %u\n",
- guc->log.flush_interrupt_count);
+ seq_puts(m, "GuC logging stats:\n");
seq_printf(m, "\tRelay full count: %u\n",
- guc->log.relay.full_count);
+ log->relay.full_count);
+
+ for (type = GUC_ISR_LOG_BUFFER; type < GUC_MAX_LOG_BUFFER; type++) {
+ seq_printf(m, "\t%s:\tflush count %10u, overflow count %10u\n",
+ stringify_guc_log_type(type),
+ log->stats[type].flush,
+ log->stats[type].sampled_overflow);
+ }
}
static void i915_guc_client_info(struct seq_file *m,
spin_unlock(&guc->irq_lock);
if (msg & (INTEL_GUC_RECV_MSG_FLUSH_LOG_BUFFER |
- INTEL_GUC_RECV_MSG_CRASH_DUMP_POSTED)) {
+ INTEL_GUC_RECV_MSG_CRASH_DUMP_POSTED))
queue_work(guc->log.relay.flush_wq,
&guc->log.relay.flush_work);
-
- guc->log.flush_interrupt_count++;
- }
}
int intel_guc_sample_forcewake(struct intel_guc *guc)
enum guc_log_buffer_type type,
unsigned int full_cnt)
{
- unsigned int prev_full_cnt = log->prev_overflow_count[type];
+ unsigned int prev_full_cnt = log->stats[type].sampled_overflow;
bool overflow = false;
if (full_cnt != prev_full_cnt) {
overflow = true;
- log->prev_overflow_count[type] = full_cnt;
- log->total_overflow_count[type] += full_cnt - prev_full_cnt;
+ log->stats[type].overflow = full_cnt;
+ log->stats[type].sampled_overflow += full_cnt - prev_full_cnt;
if (full_cnt < prev_full_cnt) {
/* buffer_full_cnt is a 4 bit counter */
- log->total_overflow_count[type] += 16;
+ log->stats[type].sampled_overflow += 16;
}
DRM_ERROR_RATELIMITED("GuC log buffer overflow\n");
}
mutex_lock(&log->relay.lock);
- if (WARN_ON(!log->relay.buf_addr))
+ if (WARN_ON(!intel_guc_log_relay_enabled(log)))
goto out_unlock;
/* Get the pointer to shared GuC log buffer */
full_cnt = log_buf_state_local.buffer_full_cnt;
/* Bookkeeping stuff */
- log->flush_count[type] += log_buf_state_local.flush_to_file;
+ log->stats[type].flush += log_buf_state_local.flush_to_file;
new_overflow = guc_check_log_buf_overflow(log, type, full_cnt);
/* Update the state of shared log buffer */
guc_log_capture_logs(log);
}
-static bool guc_log_relay_enabled(struct intel_guc_log *log)
-{
- return log->relay.buf_addr;
-}
-
static int guc_log_map(struct intel_guc_log *log)
{
struct intel_guc *guc = log_to_guc(log);
return ret;
}
+bool intel_guc_log_relay_enabled(const struct intel_guc_log *log)
+{
+ return log->relay.buf_addr;
+}
+
int intel_guc_log_relay_open(struct intel_guc_log *log)
{
int ret;
mutex_lock(&log->relay.lock);
- if (guc_log_relay_enabled(log)) {
+ if (intel_guc_log_relay_enabled(log)) {
ret = -EEXIST;
goto out_unlock;
}
flush_work(&log->relay.flush_work);
mutex_lock(&log->relay.lock);
- GEM_BUG_ON(!guc_log_relay_enabled(log));
+ GEM_BUG_ON(!intel_guc_log_relay_enabled(log));
guc_log_unmap(log);
guc_log_relay_destroy(log);
mutex_unlock(&log->relay.lock);
u32 full_count;
} relay;
/* logging related stats */
- u32 flush_interrupt_count;
- u32 prev_overflow_count[GUC_MAX_LOG_BUFFER];
- u32 total_overflow_count[GUC_MAX_LOG_BUFFER];
- u32 flush_count[GUC_MAX_LOG_BUFFER];
+ struct {
+ u32 sampled_overflow;
+ u32 overflow;
+ u32 flush;
+ } stats[GUC_MAX_LOG_BUFFER];
};
void intel_guc_log_init_early(struct intel_guc_log *log);
int intel_guc_log_level_get(struct intel_guc_log *log);
int intel_guc_log_level_set(struct intel_guc_log *log, u64 control_val);
+bool intel_guc_log_relay_enabled(const struct intel_guc_log *log);
int intel_guc_log_relay_open(struct intel_guc_log *log);
void intel_guc_log_relay_flush(struct intel_guc_log *log);
void intel_guc_log_relay_close(struct intel_guc_log *log);