File multipath-tools-retry-tur-on-driver-errors of Package multipath-tools

From 29df4e54fbbefd046cc5ed0f91406cef725a2821 Mon Sep 17 00:00:00 2001
From: Hannes Reinecke <hare@suse.de>
Date: Wed, 4 Feb 2009 11:34:15 +0100
Subject: [PATCH] Retry tur on driver errors

Sending SG_IO commands might return driver errors, too. And
some of these errors should cause the tur to be retried.

References: bnc#456961

Signed-off-by: Hannes Reinecke <hare@suse.de>
---
 libmultipath/checkers/tur.c |   14 ++++++++++++++
 libmultipath/sg_include.h   |   23 +++++++++++++++++++++++
 2 files changed, 37 insertions(+), 0 deletions(-)

diff --git a/libmultipath/checkers/tur.c b/libmultipath/checkers/tur.c
index 820a2e3..aa6e3ad 100644
--- a/libmultipath/checkers/tur.c
+++ b/libmultipath/checkers/tur.c
@@ -63,6 +63,20 @@ libcheck_check (struct checker * c)
 	if (io_hdr.info & SG_INFO_OK_MASK) {
 		int key = 0, asc, ascq;
 
+		switch (io_hdr.host_status) {
+		case DID_OK:
+		case DID_NO_CONNECT:
+		case DID_BAD_TARGET:
+		case DID_ABORT:
+		case DID_TRANSPORT_DISRUPTED:
+		case DID_TRANSPORT_FAILFAST:
+			break;
+		default:
+			/* Driver error, retry */
+			if (--retry_tur)
+				goto retry;
+			break;
+		}
 		if (io_hdr.sb_len_wr > 3) {
 			if (io_hdr.sbp[0] == 0x72 || io_hdr.sbp[0] == 0x73) {
 				key = io_hdr.sbp[1] & 0x0f;
diff --git a/libmultipath/sg_include.h b/libmultipath/sg_include.h
index 3cb107a..750a13a 100644
--- a/libmultipath/sg_include.h
+++ b/libmultipath/sg_include.h
@@ -1,2 +1,25 @@
 #define __user
 #include <scsi/sg.h>
+
+#ifndef DID_OK
+#define DID_OK          0x00	/* NO error                                */
+#define DID_NO_CONNECT  0x01	/* Couldn't connect before timeout period  */
+#define DID_BUS_BUSY    0x02	/* BUS stayed busy through time out period */
+#define DID_TIME_OUT    0x03	/* TIMED OUT for other reason              */
+#define DID_BAD_TARGET  0x04	/* BAD target.                             */
+#define DID_ABORT       0x05	/* Told to abort for some other reason     */
+#define DID_PARITY      0x06	/* Parity error                            */
+#define DID_ERROR       0x07	/* Internal error                          */
+#define DID_RESET       0x08	/* Reset by somebody.                      */
+#define DID_BAD_INTR    0x09	/* Got an interrupt we weren't expecting.  */
+#define DID_PASSTHROUGH 0x0a	/* Force command past mid-layer            */
+#define DID_SOFT_ERROR  0x0b	/* The low level driver just wish a retry  */
+#define DID_IMM_RETRY   0x0c	/* Retry without decrementing retry count  */
+#define DID_REQUEUE	0x0d	/* Requeue command (no immediate retry) also
+				 * without decrementing the retry count	   */
+#define DID_TRANSPORT_DISRUPTED 0x0e /* Transport error disrupted execution
+				      * and the driver blocked the port to
+				      * recover the link. Transport class will
+				      * retry or fail IO */
+#define DID_TRANSPORT_FAILFAST	0x0f /* Transport class fastfailed the io */
+#endif
-- 
1.6.0.2

openSUSE Build Service is sponsored by