Commit bd839171 authored by Julian Wiedmann's avatar Julian Wiedmann Committed by Vasily Gorbik
Browse files

s390/qdio: track time of last data IRQ for each device



We currently track the time of the most recent QDIO Adapter Interrupt.
This is a system-wide timestamp (as such interrupts are not bound to
one specific qdio device).

If interrupt processing stalls on one device but is functional for a
different device, the timestamp continues to be updated and is of no
help for problem diagnosis.
So for debugging purposes also track the time of the last Data IRQ on
a per-device level. Collect this data in the legacy non-AI path as well.

Signed-off-by: default avatarJulian Wiedmann <jwi@linux.ibm.com>
Reviewed-by: default avatarBenjamin Block <bblock@linux.ibm.com>
Signed-off-by: default avatarVasily Gorbik <gor@linux.ibm.com>
parent 954d6235
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -252,6 +252,7 @@ struct qdio_irq {
	struct ccw_device *cdev;
	struct list_head entry;		/* list of thinint devices */
	struct dentry *debugfs_dev;
	u64 last_data_irq_time;

	unsigned long int_parm;
	struct subchannel_id schid;
+3 −2
Original line number Diff line number Diff line
@@ -105,8 +105,9 @@ static int qstat_show(struct seq_file *m, void *v)
	if (!q)
		return 0;

	seq_printf(m, "Timestamp: %Lx  Last AI: %Lx\n",
		   q->timestamp, last_ai_time);
	seq_printf(m, "Timestamp: %llx\n", q->timestamp);
	seq_printf(m, "Last Data IRQ: %llx  Last AI: %llx\n",
		   q->irq_ptr->last_data_irq_time, last_ai_time);
	seq_printf(m, "nr_used: %d  ftc: %d\n",
		   atomic_read(&q->nr_buf_used), q->first_to_check);
	if (q->is_input_q) {
+1 −0
Original line number Diff line number Diff line
@@ -804,6 +804,7 @@ static void qdio_int_handler_pci(struct qdio_irq *irq_ptr)
		return;

	qdio_deliver_irq(irq_ptr);
	irq_ptr->last_data_irq_time = S390_lowcore.int_clock;

	if (!pci_out_supported(irq_ptr) || !irq_ptr->scan_threshold)
		return;
+3 −1
Original line number Diff line number Diff line
@@ -97,10 +97,11 @@ static inline u32 clear_shared_ind(void)
 */
static void tiqdio_thinint_handler(struct airq_struct *airq, bool floating)
{
	u64 irq_time = S390_lowcore.int_clock;
	u32 si_used = clear_shared_ind();
	struct qdio_irq *irq;

	last_ai_time = S390_lowcore.int_clock;
	last_ai_time = irq_time;
	inc_irq_stat(IRQIO_QAI);

	/* protect tiq_list entries, only changed in activate or shutdown */
@@ -119,6 +120,7 @@ static void tiqdio_thinint_handler(struct airq_struct *airq, bool floating)
		}

		qdio_deliver_irq(irq);
		irq->last_data_irq_time = irq_time;

		QDIO_PERF_STAT_INC(irq, adapter_int);
	}