vserver 1.9.5.x5
[linux-2.6.git] / drivers / s390 / block / dasd_3990_erp.c
1 /* 
2  * File...........: linux/drivers/s390/block/dasd_3990_erp.c
3  * Author(s)......: Horst  Hummel    <Horst.Hummel@de.ibm.com> 
4  *                  Holger Smolinski <Holger.Smolinski@de.ibm.com>
5  * Bugreports.to..: <Linux390@de.ibm.com>
6  * (C) IBM Corporation, IBM Deutschland Entwicklung GmbH, 2000, 2001
7  *
8  * $Revision: 1.36 $
9  */
10
11 #include <linux/timer.h>
12 #include <linux/slab.h>
13 #include <asm/idals.h>
14 #include <asm/todclk.h>
15
16 #define PRINTK_HEADER "dasd_erp(3990): "
17
18 #include "dasd_int.h"
19 #include "dasd_eckd.h"
20
21
22 struct DCTL_data {
23         unsigned char subcommand;  /* e.g Inhibit Write, Enable Write,... */
24         unsigned char modifier;    /* Subcommand modifier */
25         unsigned short res;        /* reserved */
26 } __attribute__ ((packed));
27
28 /*
29  ***************************************************************************** 
30  * SECTION ERP EXAMINATION
31  ***************************************************************************** 
32  */
33
34 /*
35  * DASD_3990_ERP_EXAMINE_24 
36  *
37  * DESCRIPTION
38  *   Checks only for fatal (unrecoverable) error. 
39  *   A detailed examination of the sense data is done later outside
40  *   the interrupt handler.
41  *
42  *   Each bit configuration leading to an action code 2 (Exit with
43  *   programming error or unusual condition indication)
44  *   are handled as fatal errorĀ“s.
45  * 
46  *   All other configurations are handled as recoverable errors.
47  *
48  * RETURN VALUES
49  *   dasd_era_fatal     for all fatal (unrecoverable errors)
50  *   dasd_era_recover   for all others.
51  */
52 static dasd_era_t
53 dasd_3990_erp_examine_24(struct dasd_ccw_req * cqr, char *sense)
54 {
55
56         struct dasd_device *device = cqr->device;
57
58         /* check for 'Command Reject' */
59         if ((sense[0] & SNS0_CMD_REJECT) &&
60             (!(sense[2] & SNS2_ENV_DATA_PRESENT))) {
61
62                 DEV_MESSAGE(KERN_ERR, device, "%s",
63                             "EXAMINE 24: Command Reject detected - "
64                             "fatal error");
65
66                 return dasd_era_fatal;
67         }
68
69         /* check for 'Invalid Track Format' */
70         if ((sense[1] & SNS1_INV_TRACK_FORMAT) &&
71             (!(sense[2] & SNS2_ENV_DATA_PRESENT))) {
72
73                 DEV_MESSAGE(KERN_ERR, device, "%s",
74                             "EXAMINE 24: Invalid Track Format detected "
75                             "- fatal error");
76
77                 return dasd_era_fatal;
78         }
79
80         /* check for 'No Record Found' */
81         if (sense[1] & SNS1_NO_REC_FOUND) {
82
83                 /* FIXME: fatal error ?!? */
84                 DEV_MESSAGE(KERN_ERR, device,
85                             "EXAMINE 24: No Record Found detected %s",
86                             device->state <= DASD_STATE_BASIC ?
87                             " " : "- fatal error");
88
89                 return dasd_era_fatal;
90         }
91
92         /* return recoverable for all others */
93         return dasd_era_recover;
94 }                               /* END dasd_3990_erp_examine_24 */
95
96 /*
97  * DASD_3990_ERP_EXAMINE_32 
98  *
99  * DESCRIPTION
100  *   Checks only for fatal/no/recoverable error. 
101  *   A detailed examination of the sense data is done later outside
102  *   the interrupt handler.
103  *
104  * RETURN VALUES
105  *   dasd_era_none      no error 
106  *   dasd_era_fatal     for all fatal (unrecoverable errors)
107  *   dasd_era_recover   for recoverable others.
108  */
109 static dasd_era_t
110 dasd_3990_erp_examine_32(struct dasd_ccw_req * cqr, char *sense)
111 {
112
113         struct dasd_device *device = cqr->device;
114
115         switch (sense[25]) {
116         case 0x00:
117                 return dasd_era_none;
118
119         case 0x01:
120                 DEV_MESSAGE(KERN_ERR, device, "%s", "EXAMINE 32: fatal error");
121
122                 return dasd_era_fatal;
123
124         default:
125
126                 return dasd_era_recover;
127         }
128
129 }                               /* end dasd_3990_erp_examine_32 */
130
131 /*
132  * DASD_3990_ERP_EXAMINE 
133  *
134  * DESCRIPTION
135  *   Checks only for fatal/no/recover error. 
136  *   A detailed examination of the sense data is done later outside
137  *   the interrupt handler.
138  *
139  *   The logic is based on the 'IBM 3990 Storage Control  Reference' manual
140  *   'Chapter 7. Error Recovery Procedures'.
141  *
142  * RETURN VALUES
143  *   dasd_era_none      no error 
144  *   dasd_era_fatal     for all fatal (unrecoverable errors)
145  *   dasd_era_recover   for all others.
146  */
147 dasd_era_t
148 dasd_3990_erp_examine(struct dasd_ccw_req * cqr, struct irb * irb)
149 {
150
151         char *sense = irb->ecw;
152         dasd_era_t era = dasd_era_recover;
153         struct dasd_device *device = cqr->device;
154
155         /* check for successful execution first */
156         if (irb->scsw.cstat == 0x00 &&
157             irb->scsw.dstat == (DEV_STAT_CHN_END | DEV_STAT_DEV_END))
158                 return dasd_era_none;
159
160         /* distinguish between 24 and 32 byte sense data */
161         if (sense[27] & DASD_SENSE_BIT_0) {
162
163                 era = dasd_3990_erp_examine_24(cqr, sense);
164
165         } else {
166
167                 era = dasd_3990_erp_examine_32(cqr, sense);
168
169         }
170
171         /* log the erp chain if fatal error occurred */
172         if ((era == dasd_era_fatal) && (device->state >= DASD_STATE_READY)) {
173                 dasd_log_sense(cqr, irb);
174                 dasd_log_ccw(cqr, 0, irb->scsw.cpa);
175         }
176
177         return era;
178
179 }                               /* END dasd_3990_erp_examine */
180
181 /*
182  ***************************************************************************** 
183  * SECTION ERP HANDLING
184  ***************************************************************************** 
185  */
186 /*
187  ***************************************************************************** 
188  * 24 and 32 byte sense ERP functions
189  ***************************************************************************** 
190  */
191
192 /*
193  * DASD_3990_ERP_CLEANUP 
194  *
195  * DESCRIPTION
196  *   Removes the already build but not necessary ERP request and sets
197  *   the status of the original cqr / erp to the given (final) status
198  *
199  *  PARAMETER
200  *   erp                request to be blocked
201  *   final_status       either DASD_CQR_DONE or DASD_CQR_FAILED 
202  *
203  * RETURN VALUES
204  *   cqr                original cqr               
205  */
206 static struct dasd_ccw_req *
207 dasd_3990_erp_cleanup(struct dasd_ccw_req * erp, char final_status)
208 {
209         struct dasd_ccw_req *cqr = erp->refers;
210
211         dasd_free_erp_request(erp, erp->device);
212         cqr->status = final_status;
213         return cqr;
214
215 }                               /* end dasd_3990_erp_cleanup */
216
217 /*
218  * DASD_3990_ERP_BLOCK_QUEUE 
219  *
220  * DESCRIPTION
221  *   Block the given device request queue to prevent from further
222  *   processing until the started timer has expired or an related
223  *   interrupt was received.
224  */
225 static void
226 dasd_3990_erp_block_queue(struct dasd_ccw_req * erp, int expires)
227 {
228
229         struct dasd_device *device = erp->device;
230
231         DEV_MESSAGE(KERN_INFO, device,
232                     "blocking request queue for %is", expires/HZ);
233
234         device->stopped |= DASD_STOPPED_PENDING;
235         erp->status = DASD_CQR_QUEUED;
236
237         dasd_set_timer(device, expires);
238 }
239
240 /*
241  * DASD_3990_ERP_INT_REQ 
242  *
243  * DESCRIPTION
244  *   Handles 'Intervention Required' error.
245  *   This means either device offline or not installed.
246  *
247  * PARAMETER
248  *   erp                current erp
249  * RETURN VALUES
250  *   erp                modified erp
251  */
252 static struct dasd_ccw_req *
253 dasd_3990_erp_int_req(struct dasd_ccw_req * erp)
254 {
255
256         struct dasd_device *device = erp->device;
257
258         /* first time set initial retry counter and erp_function */
259         /* and retry once without blocking queue                 */
260         /* (this enables easier enqueing of the cqr)             */
261         if (erp->function != dasd_3990_erp_int_req) {
262
263                 erp->retries = 256;
264                 erp->function = dasd_3990_erp_int_req;
265
266         } else {
267
268                 /* issue a message and wait for 'device ready' interrupt */
269                 DEV_MESSAGE(KERN_ERR, device, "%s",
270                             "is offline or not installed - "
271                             "INTERVENTION REQUIRED!!");
272
273                 dasd_3990_erp_block_queue(erp, 60*HZ);
274         }
275
276         return erp;
277
278 }                               /* end dasd_3990_erp_int_req */
279
280 /*
281  * DASD_3990_ERP_ALTERNATE_PATH 
282  *
283  * DESCRIPTION
284  *   Repeat the operation on a different channel path.
285  *   If all alternate paths have been tried, the request is posted with a
286  *   permanent error.
287  *
288  *  PARAMETER
289  *   erp                pointer to the current ERP
290  *
291  * RETURN VALUES
292  *   erp                modified pointer to the ERP
293  */
294 static void
295 dasd_3990_erp_alternate_path(struct dasd_ccw_req * erp)
296 {
297         struct dasd_device *device = erp->device;
298         __u8 opm;
299
300         /* try alternate valid path */
301         opm = ccw_device_get_path_mask(device->cdev);
302         //FIXME: start with get_opm ?
303         if (erp->lpm == 0)
304                 erp->lpm = LPM_ANYPATH & ~(erp->irb.esw.esw0.sublog.lpum);
305         else
306                 erp->lpm &= ~(erp->irb.esw.esw0.sublog.lpum);
307
308         if ((erp->lpm & opm) != 0x00) {
309
310                 DEV_MESSAGE(KERN_DEBUG, device,
311                             "try alternate lpm=%x (lpum=%x / opm=%x)",
312                             erp->lpm, erp->irb.esw.esw0.sublog.lpum, opm);
313
314                 /* reset status to queued to handle the request again... */
315                 if (erp->status > DASD_CQR_QUEUED)
316                         erp->status = DASD_CQR_QUEUED;
317                 erp->retries = 1;
318         } else {
319                 DEV_MESSAGE(KERN_ERR, device,
320                             "No alternate channel path left (lpum=%x / "
321                             "opm=%x) -> permanent error",
322                             erp->irb.esw.esw0.sublog.lpum, opm);
323
324                 /* post request with permanent error */
325                 if (erp->status > DASD_CQR_QUEUED)
326                         erp->status = DASD_CQR_FAILED;
327         }
328 }                               /* end dasd_3990_erp_alternate_path */
329
330 /*
331  * DASD_3990_ERP_DCTL
332  *
333  * DESCRIPTION
334  *   Setup cqr to do the Diagnostic Control (DCTL) command with an 
335  *   Inhibit Write subcommand (0x20) and the given modifier.
336  *
337  *  PARAMETER
338  *   erp                pointer to the current (failed) ERP
339  *   modifier           subcommand modifier
340  *   
341  * RETURN VALUES
342  *   dctl_cqr           pointer to NEW dctl_cqr 
343  *
344  */
345 static struct dasd_ccw_req *
346 dasd_3990_erp_DCTL(struct dasd_ccw_req * erp, char modifier)
347 {
348
349         struct dasd_device *device = erp->device;
350         struct DCTL_data *DCTL_data;
351         struct ccw1 *ccw;
352         struct dasd_ccw_req *dctl_cqr;
353
354         dctl_cqr = dasd_alloc_erp_request((char *) &erp->magic, 1,
355                                           sizeof (struct DCTL_data),
356                                           erp->device);
357         if (IS_ERR(dctl_cqr)) {
358                 DEV_MESSAGE(KERN_ERR, device, "%s",
359                             "Unable to allocate DCTL-CQR");
360                 erp->status = DASD_CQR_FAILED;
361                 return erp;
362         }
363
364         DCTL_data = dctl_cqr->data;
365
366         DCTL_data->subcommand = 0x02;   /* Inhibit Write */
367         DCTL_data->modifier = modifier;
368
369         ccw = dctl_cqr->cpaddr;
370         memset(ccw, 0, sizeof (struct ccw1));
371         ccw->cmd_code = CCW_CMD_DCTL;
372         ccw->count = 4;
373         ccw->cda = (__u32)(addr_t) DCTL_data;
374         dctl_cqr->function = dasd_3990_erp_DCTL;
375         dctl_cqr->refers = erp;
376         dctl_cqr->device = erp->device;
377         dctl_cqr->magic = erp->magic;
378         dctl_cqr->expires = 5 * 60 * HZ;
379         dctl_cqr->retries = 2;
380
381         dctl_cqr->buildclk = get_clock();
382
383         dctl_cqr->status = DASD_CQR_FILLED;
384
385         return dctl_cqr;
386
387 }                               /* end dasd_3990_erp_DCTL */
388
389 /*
390  * DASD_3990_ERP_ACTION_1 
391  *
392  * DESCRIPTION
393  *   Setup ERP to do the ERP action 1 (see Reference manual).
394  *   Repeat the operation on a different channel path.
395  *   If all alternate paths have been tried, the request is posted with a
396  *   permanent error.
397  *   Note: duplex handling is not implemented (yet).
398  *
399  *  PARAMETER
400  *   erp                pointer to the current ERP
401  *
402  * RETURN VALUES
403  *   erp                pointer to the ERP
404  *
405  */
406 static struct dasd_ccw_req *
407 dasd_3990_erp_action_1(struct dasd_ccw_req * erp)
408 {
409
410         erp->function = dasd_3990_erp_action_1;
411
412         dasd_3990_erp_alternate_path(erp);
413
414         return erp;
415
416 }                               /* end dasd_3990_erp_action_1 */
417
418 /*
419  * DASD_3990_ERP_ACTION_4 
420  *
421  * DESCRIPTION
422  *   Setup ERP to do the ERP action 4 (see Reference manual).
423  *   Set the current request to PENDING to block the CQR queue for that device
424  *   until the state change interrupt appears.
425  *   Use a timer (20 seconds) to retry the cqr if the interrupt is still
426  *   missing.
427  *
428  *  PARAMETER
429  *   sense              sense data of the actual error
430  *   erp                pointer to the current ERP
431  *
432  * RETURN VALUES
433  *   erp                pointer to the ERP
434  *
435  */
436 static struct dasd_ccw_req *
437 dasd_3990_erp_action_4(struct dasd_ccw_req * erp, char *sense)
438 {
439
440         struct dasd_device *device = erp->device;
441
442         /* first time set initial retry counter and erp_function    */
443         /* and retry once without waiting for state change pending  */
444         /* interrupt (this enables easier enqueing of the cqr)      */
445         if (erp->function != dasd_3990_erp_action_4) {
446
447                 DEV_MESSAGE(KERN_INFO, device, "%s",
448                             "dasd_3990_erp_action_4: first time retry");
449
450                 erp->retries = 256;
451                 erp->function = dasd_3990_erp_action_4;
452
453         } else {
454
455                 if (sense[25] == 0x1D) {        /* state change pending */
456
457                         DEV_MESSAGE(KERN_INFO, device, 
458                                     "waiting for state change pending "
459                                     "interrupt, %d retries left",
460                                     erp->retries);
461                         
462                         dasd_3990_erp_block_queue(erp, 30*HZ);
463
464                 } else if (sense[25] == 0x1E) { /* busy */
465                         DEV_MESSAGE(KERN_INFO, device,
466                                     "busy - redriving request later, "
467                                     "%d retries left",
468                                     erp->retries);
469                         dasd_3990_erp_block_queue(erp, HZ);
470                 } else {
471
472                         /* no state change pending - retry */
473                         DEV_MESSAGE (KERN_INFO, device, 
474                                      "redriving request immediately, "
475                                      "%d retries left", 
476                                      erp->retries);
477                         erp->status = DASD_CQR_QUEUED;
478                 }
479         }
480
481         return erp;
482
483 }                               /* end dasd_3990_erp_action_4 */
484
485 /*
486  ***************************************************************************** 
487  * 24 byte sense ERP functions (only)
488  ***************************************************************************** 
489  */
490
491 /*
492  * DASD_3990_ERP_ACTION_5 
493  *
494  * DESCRIPTION
495  *   Setup ERP to do the ERP action 5 (see Reference manual).
496  *   NOTE: Further handling is done in xxx_further_erp after the retries.
497  *
498  *  PARAMETER
499  *   erp                pointer to the current ERP
500  *
501  * RETURN VALUES
502  *   erp                pointer to the ERP
503  *
504  */
505 static struct dasd_ccw_req *
506 dasd_3990_erp_action_5(struct dasd_ccw_req * erp)
507 {
508
509         /* first of all retry */
510         erp->retries = 10;
511         erp->function = dasd_3990_erp_action_5;
512
513         return erp;
514
515 }                               /* end dasd_3990_erp_action_5 */
516
517 /*
518  * DASD_3990_HANDLE_ENV_DATA
519  *
520  * DESCRIPTION
521  *   Handles 24 byte 'Environmental data present'.
522  *   Does a analysis of the sense data (message Format)
523  *   and prints the error messages.
524  *
525  * PARAMETER
526  *   sense              current sense data
527  *   
528  * RETURN VALUES
529  *   void
530  */
531 static void
532 dasd_3990_handle_env_data(struct dasd_ccw_req * erp, char *sense)
533 {
534
535         struct dasd_device *device = erp->device;
536         char msg_format = (sense[7] & 0xF0);
537         char msg_no = (sense[7] & 0x0F);
538
539         switch (msg_format) {
540         case 0x00:              /* Format 0 - Program or System Checks */
541
542                 if (sense[1] & 0x10) {  /* check message to operator bit */
543
544                         switch (msg_no) {
545                         case 0x00:      /* No Message */
546                                 break;
547                         case 0x01:
548                                 DEV_MESSAGE(KERN_WARNING, device, "%s",
549                                             "FORMAT 0 - Invalid Command");
550                                 break;
551                         case 0x02:
552                                 DEV_MESSAGE(KERN_WARNING, device, "%s",
553                                             "FORMAT 0 - Invalid Command "
554                                             "Sequence");
555                                 break;
556                         case 0x03:
557                                 DEV_MESSAGE(KERN_WARNING, device, "%s",
558                                             "FORMAT 0 - CCW Count less than "
559                                             "required");
560                                 break;
561                         case 0x04:
562                                 DEV_MESSAGE(KERN_WARNING, device, "%s",
563                                             "FORMAT 0 - Invalid Parameter");
564                                 break;
565                         case 0x05:
566                                 DEV_MESSAGE(KERN_WARNING, device, "%s",
567                                             "FORMAT 0 - Diagnostic of Sepecial"
568                                             " Command Violates File Mask");
569                                 break;
570                         case 0x07:
571                                 DEV_MESSAGE(KERN_WARNING, device, "%s",
572                                             "FORMAT 0 - Channel Returned with "
573                                             "Incorrect retry CCW");
574                                 break;
575                         case 0x08:
576                                 DEV_MESSAGE(KERN_WARNING, device, "%s",
577                                             "FORMAT 0 - Reset Notification");
578                                 break;
579                         case 0x09:
580                                 DEV_MESSAGE(KERN_WARNING, device, "%s",
581                                             "FORMAT 0 - Storage Path Restart");
582                                 break;
583                         case 0x0A:
584                                 DEV_MESSAGE(KERN_WARNING, device,
585                                             "FORMAT 0 - Channel requested "
586                                             "... %02x", sense[8]);
587                                 break;
588                         case 0x0B:
589                                 DEV_MESSAGE(KERN_WARNING, device, "%s",
590                                             "FORMAT 0 - Invalid Defective/"
591                                             "Alternate Track Pointer");
592                                 break;
593                         case 0x0C:
594                                 DEV_MESSAGE(KERN_WARNING, device, "%s",
595                                             "FORMAT 0 - DPS Installation "
596                                             "Check");
597                                 break;
598                         case 0x0E:
599                                 DEV_MESSAGE(KERN_WARNING, device, "%s",
600                                             "FORMAT 0 - Command Invalid on "
601                                             "Secondary Address");
602                                 break;
603                         case 0x0F:
604                                 DEV_MESSAGE(KERN_WARNING, device,
605                                             "FORMAT 0 - Status Not As "
606                                             "Required: reason %02x", sense[8]);
607                                 break;
608                         default:
609                                 DEV_MESSAGE(KERN_WARNING, device, "%s",
610                                             "FORMAT 0 - Reseved");
611                         }
612                 } else {
613                         switch (msg_no) {
614                         case 0x00:      /* No Message */
615                                 break;
616                         case 0x01:
617                                 DEV_MESSAGE(KERN_WARNING, device, "%s",
618                                             "FORMAT 0 - Device Error Source");
619                                 break;
620                         case 0x02:
621                                 DEV_MESSAGE(KERN_WARNING, device, "%s",
622                                             "FORMAT 0 - Reserved");
623                                 break;
624                         case 0x03:
625                                 DEV_MESSAGE(KERN_WARNING, device,
626                                             "FORMAT 0 - Device Fenced - "
627                                             "device = %02x", sense[4]);
628                                 break;
629                         case 0x04:
630                                 DEV_MESSAGE(KERN_WARNING, device, "%s",
631                                             "FORMAT 0 - Data Pinned for "
632                                             "Device");
633                                 break;
634                         default:
635                                 DEV_MESSAGE(KERN_WARNING, device, "%s",
636                                             "FORMAT 0 - Reserved");
637                         }
638                 }
639                 break;
640
641         case 0x10:              /* Format 1 - Device Equipment Checks */
642                 switch (msg_no) {
643                 case 0x00:      /* No Message */
644                         break;
645                 case 0x01:
646                         DEV_MESSAGE(KERN_WARNING, device, "%s",
647                                     "FORMAT 1 - Device Status 1 not as "
648                                     "expected");
649                         break;
650                 case 0x03:
651                         DEV_MESSAGE(KERN_WARNING, device, "%s",
652                                     "FORMAT 1 - Index missing");
653                         break;
654                 case 0x04:
655                         DEV_MESSAGE(KERN_WARNING, device, "%s",
656                                     "FORMAT 1 - Interruption cannot be reset");
657                         break;
658                 case 0x05:
659                         DEV_MESSAGE(KERN_WARNING, device, "%s",
660                                     "FORMAT 1 - Device did not respond to "
661                                     "selection");
662                         break;
663                 case 0x06:
664                         DEV_MESSAGE(KERN_WARNING, device, "%s",
665                                     "FORMAT 1 - Device check-2 error or Set "
666                                     "Sector is not complete");
667                         break;
668                 case 0x07:
669                         DEV_MESSAGE(KERN_WARNING, device, "%s",
670                                     "FORMAT 1 - Head address does not "
671                                     "compare");
672                         break;
673                 case 0x08:
674                         DEV_MESSAGE(KERN_WARNING, device, "%s",
675                                     "FORMAT 1 - Device status 1 not valid");
676                         break;
677                 case 0x09:
678                         DEV_MESSAGE(KERN_WARNING, device, "%s",
679                                     "FORMAT 1 - Device not ready");
680                         break;
681                 case 0x0A:
682                         DEV_MESSAGE(KERN_WARNING, device, "%s",
683                                     "FORMAT 1 - Track physical address did "
684                                     "not compare");
685                         break;
686                 case 0x0B:
687                         DEV_MESSAGE(KERN_WARNING, device, "%s",
688                                     "FORMAT 1 - Missing device address bit");
689                         break;
690                 case 0x0C:
691                         DEV_MESSAGE(KERN_WARNING, device, "%s",
692                                     "FORMAT 1 - Drive motor switch is off");
693                         break;
694                 case 0x0D:
695                         DEV_MESSAGE(KERN_WARNING, device, "%s",
696                                     "FORMAT 1 - Seek incomplete");
697                         break;
698                 case 0x0E:
699                         DEV_MESSAGE(KERN_WARNING, device, "%s",
700                                     "FORMAT 1 - Cylinder address did not "
701                                     "compare");
702                         break;
703                 case 0x0F:
704                         DEV_MESSAGE(KERN_WARNING, device, "%s",
705                                     "FORMAT 1 - Offset active cannot be "
706                                     "reset");
707                         break;
708                 default:
709                         DEV_MESSAGE(KERN_WARNING, device, "%s",
710                                     "FORMAT 1 - Reserved");
711                 }
712                 break;
713
714         case 0x20:              /* Format 2 - 3990 Equipment Checks */
715                 switch (msg_no) {
716                 case 0x08:
717                         DEV_MESSAGE(KERN_WARNING, device, "%s",
718                                     "FORMAT 2 - 3990 check-2 error");
719                         break;
720                 case 0x0E:
721                         DEV_MESSAGE(KERN_WARNING, device, "%s",
722                                     "FORMAT 2 - Support facility errors");
723                         break;
724                 case 0x0F:
725                         DEV_MESSAGE(KERN_WARNING, device,
726                                     "FORMAT 2 - Microcode detected error %02x",
727                                     sense[8]);
728                         break;
729                 default:
730                         DEV_MESSAGE(KERN_WARNING, device, "%s",
731                                     "FORMAT 2 - Reserved");
732                 }
733                 break;
734
735         case 0x30:              /* Format 3 - 3990 Control Checks */
736                 switch (msg_no) {
737                 case 0x0F:
738                         DEV_MESSAGE(KERN_WARNING, device, "%s",
739                                     "FORMAT 3 - Allegiance terminated");
740                         break;
741                 default:
742                         DEV_MESSAGE(KERN_WARNING, device, "%s",
743                                     "FORMAT 3 - Reserved");
744                 }
745                 break;
746
747         case 0x40:              /* Format 4 - Data Checks */
748                 switch (msg_no) {
749                 case 0x00:
750                         DEV_MESSAGE(KERN_WARNING, device, "%s",
751                                     "FORMAT 4 - Home address area error");
752                         break;
753                 case 0x01:
754                         DEV_MESSAGE(KERN_WARNING, device, "%s",
755                                     "FORMAT 4 - Count area error");
756                         break;
757                 case 0x02:
758                         DEV_MESSAGE(KERN_WARNING, device, "%s",
759                                     "FORMAT 4 - Key area error");
760                         break;
761                 case 0x03:
762                         DEV_MESSAGE(KERN_WARNING, device, "%s",
763                                     "FORMAT 4 - Data area error");
764                         break;
765                 case 0x04:
766                         DEV_MESSAGE(KERN_WARNING, device, "%s",
767                                     "FORMAT 4 - No sync byte in home address "
768                                     "area");
769                         break;
770                 case 0x05:
771                         DEV_MESSAGE(KERN_WARNING, device, "%s",
772                                     "FORMAT 4 - No sync byte in count address "
773                                     "area");
774                         break;
775                 case 0x06:
776                         DEV_MESSAGE(KERN_WARNING, device, "%s",
777                                     "FORMAT 4 - No sync byte in key area");
778                         break;
779                 case 0x07:
780                         DEV_MESSAGE(KERN_WARNING, device, "%s",
781                                     "FORMAT 4 - No sync byte in data area");
782                         break;
783                 case 0x08:
784                         DEV_MESSAGE(KERN_WARNING, device, "%s",
785                                     "FORMAT 4 - Home address area error; "
786                                     "offset active");
787                         break;
788                 case 0x09:
789                         DEV_MESSAGE(KERN_WARNING, device, "%s",
790                                     "FORMAT 4 - Count area error; offset "
791                                     "active");
792                         break;
793                 case 0x0A:
794                         DEV_MESSAGE(KERN_WARNING, device, "%s",
795                                     "FORMAT 4 - Key area error; offset "
796                                     "active");
797                         break;
798                 case 0x0B:
799                         DEV_MESSAGE(KERN_WARNING, device, "%s",
800                                     "FORMAT 4 - Data area error; "
801                                     "offset active");
802                         break;
803                 case 0x0C:
804                         DEV_MESSAGE(KERN_WARNING, device, "%s",
805                                     "FORMAT 4 - No sync byte in home "
806                                     "address area; offset active");
807                         break;
808                 case 0x0D:
809                         DEV_MESSAGE(KERN_WARNING, device, "%s",
810                                     "FORMAT 4 - No syn byte in count "
811                                     "address area; offset active");
812                         break;
813                 case 0x0E:
814                         DEV_MESSAGE(KERN_WARNING, device, "%s",
815                                     "FORMAT 4 - No sync byte in key area; "
816                                     "offset active");
817                         break;
818                 case 0x0F:
819                         DEV_MESSAGE(KERN_WARNING, device, "%s",
820                                     "FORMAT 4 - No syn byte in data area; "
821                                     "offset active");
822                         break;
823                 default:
824                         DEV_MESSAGE(KERN_WARNING, device, "%s",
825                                     "FORMAT 4 - Reserved");
826                 }
827                 break;
828
829         case 0x50:  /* Format 5 - Data Check with displacement information */
830                 switch (msg_no) {
831                 case 0x00:
832                         DEV_MESSAGE(KERN_WARNING, device, "%s",
833                                     "FORMAT 5 - Data Check in the "
834                                     "home address area");
835                         break;
836                 case 0x01:
837                         DEV_MESSAGE(KERN_WARNING, device, "%s",
838                                     "FORMAT 5 - Data Check in the count area");
839                         break;
840                 case 0x02:
841                         DEV_MESSAGE(KERN_WARNING, device, "%s",
842                                     "FORMAT 5 - Data Check in the key area");
843                         break;
844                 case 0x03:
845                         DEV_MESSAGE(KERN_WARNING, device, "%s",
846                                     "FORMAT 5 - Data Check in the data area");
847                         break;
848                 case 0x08:
849                         DEV_MESSAGE(KERN_WARNING, device, "%s",
850                                     "FORMAT 5 - Data Check in the "
851                                     "home address area; offset active");
852                         break;
853                 case 0x09:
854                         DEV_MESSAGE(KERN_WARNING, device, "%s",
855                                     "FORMAT 5 - Data Check in the count area; "
856                                     "offset active");
857                         break;
858                 case 0x0A:
859                         DEV_MESSAGE(KERN_WARNING, device, "%s",
860                                     "FORMAT 5 - Data Check in the key area; "
861                                     "offset active");
862                         break;
863                 case 0x0B:
864                         DEV_MESSAGE(KERN_WARNING, device, "%s",
865                                     "FORMAT 5 - Data Check in the data area; "
866                                     "offset active");
867                         break;
868                 default:
869                         DEV_MESSAGE(KERN_WARNING, device, "%s",
870                                     "FORMAT 5 - Reserved");
871                 }
872                 break;
873
874         case 0x60:  /* Format 6 - Usage Statistics/Overrun Errors */
875                 switch (msg_no) {
876                 case 0x00:
877                         DEV_MESSAGE(KERN_WARNING, device, "%s",
878                                     "FORMAT 6 - Overrun on channel A");
879                         break;
880                 case 0x01:
881                         DEV_MESSAGE(KERN_WARNING, device, "%s",
882                                     "FORMAT 6 - Overrun on channel B");
883                         break;
884                 case 0x02:
885                         DEV_MESSAGE(KERN_WARNING, device, "%s",
886                                     "FORMAT 6 - Overrun on channel C");
887                         break;
888                 case 0x03:
889                         DEV_MESSAGE(KERN_WARNING, device, "%s",
890                                     "FORMAT 6 - Overrun on channel D");
891                         break;
892                 case 0x04:
893                         DEV_MESSAGE(KERN_WARNING, device, "%s",
894                                     "FORMAT 6 - Overrun on channel E");
895                         break;
896                 case 0x05:
897                         DEV_MESSAGE(KERN_WARNING, device, "%s",
898                                     "FORMAT 6 - Overrun on channel F");
899                         break;
900                 case 0x06:
901                         DEV_MESSAGE(KERN_WARNING, device, "%s",
902                                     "FORMAT 6 - Overrun on channel G");
903                         break;
904                 case 0x07:
905                         DEV_MESSAGE(KERN_WARNING, device, "%s",
906                                     "FORMAT 6 - Overrun on channel H");
907                         break;
908                 default:
909                         DEV_MESSAGE(KERN_WARNING, device, "%s",
910                                     "FORMAT 6 - Reserved");
911                 }
912                 break;
913
914         case 0x70:  /* Format 7 - Device Connection Control Checks */
915                 switch (msg_no) {
916                 case 0x00:
917                         DEV_MESSAGE(KERN_WARNING, device, "%s",
918                                     "FORMAT 7 - RCC initiated by a connection "
919                                     "check alert");
920                         break;
921                 case 0x01:
922                         DEV_MESSAGE(KERN_WARNING, device, "%s",
923                                     "FORMAT 7 - RCC 1 sequence not "
924                                     "successful");
925                         break;
926                 case 0x02:
927                         DEV_MESSAGE(KERN_WARNING, device, "%s",
928                                     "FORMAT 7 - RCC 1 and RCC 2 sequences not "
929                                     "successful");
930                         break;
931                 case 0x03:
932                         DEV_MESSAGE(KERN_WARNING, device, "%s",
933                                     "FORMAT 7 - Invalid tag-in during "
934                                     "selection sequence");
935                         break;
936                 case 0x04:
937                         DEV_MESSAGE(KERN_WARNING, device, "%s",
938                                     "FORMAT 7 - extra RCC required");
939                         break;
940                 case 0x05:
941                         DEV_MESSAGE(KERN_WARNING, device, "%s",
942                                     "FORMAT 7 - Invalid DCC selection "
943                                     "response or timeout");
944                         break;
945                 case 0x06:
946                         DEV_MESSAGE(KERN_WARNING, device, "%s",
947                                     "FORMAT 7 - Missing end operation; device "
948                                     "transfer complete");
949                         break;
950                 case 0x07:
951                         DEV_MESSAGE(KERN_WARNING, device, "%s",
952                                     "FORMAT 7 - Missing end operation; device "
953                                     "transfer incomplete");
954                         break;
955                 case 0x08:
956                         DEV_MESSAGE(KERN_WARNING, device, "%s",
957                                     "FORMAT 7 - Invalid tag-in for an "
958                                     "immediate command sequence");
959                         break;
960                 case 0x09:
961                         DEV_MESSAGE(KERN_WARNING, device, "%s",
962                                     "FORMAT 7 - Invalid tag-in for an "
963                                     "extended command sequence");
964                         break;
965                 case 0x0A:
966                         DEV_MESSAGE(KERN_WARNING, device, "%s",
967                                     "FORMAT 7 - 3990 microcode time out when "
968                                     "stopping selection");
969                         break;
970                 case 0x0B:
971                         DEV_MESSAGE(KERN_WARNING, device, "%s",
972                                     "FORMAT 7 - No response to selection "
973                                     "after a poll interruption");
974                         break;
975                 case 0x0C:
976                         DEV_MESSAGE(KERN_WARNING, device, "%s",
977                                     "FORMAT 7 - Permanent path error (DASD "
978                                     "controller not available)");
979                         break;
980                 case 0x0D:
981                         DEV_MESSAGE(KERN_WARNING, device, "%s",
982                                     "FORMAT 7 - DASD controller not available"
983                                     " on disconnected command chain");
984                         break;
985                 default:
986                         DEV_MESSAGE(KERN_WARNING, device, "%s",
987                                     "FORMAT 7 - Reserved");
988                 }
989                 break;
990
991         case 0x80:  /* Format 8 - Additional Device Equipment Checks */
992                 switch (msg_no) {
993                 case 0x00:      /* No Message */
994                 case 0x01:
995                         DEV_MESSAGE(KERN_WARNING, device, "%s",
996                                     "FORMAT 8 - Error correction code "
997                                     "hardware fault");
998                         break;
999                 case 0x03:
1000                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1001                                     "FORMAT 8 - Unexpected end operation "
1002                                     "response code");
1003                         break;
1004                 case 0x04:
1005                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1006                                     "FORMAT 8 - End operation with transfer "
1007                                     "count not zero");
1008                         break;
1009                 case 0x05:
1010                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1011                                     "FORMAT 8 - End operation with transfer "
1012                                     "count zero");
1013                         break;
1014                 case 0x06:
1015                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1016                                     "FORMAT 8 - DPS checks after a system "
1017                                     "reset or selective reset");
1018                         break;
1019                 case 0x07:
1020                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1021                                     "FORMAT 8 - DPS cannot be filled");
1022                         break;
1023                 case 0x08:
1024                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1025                                     "FORMAT 8 - Short busy time-out during "
1026                                     "device selection");
1027                         break;
1028                 case 0x09:
1029                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1030                                     "FORMAT 8 - DASD controller failed to "
1031                                     "set or reset the long busy latch");
1032                         break;
1033                 case 0x0A:
1034                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1035                                     "FORMAT 8 - No interruption from device "
1036                                     "during a command chain");
1037                         break;
1038                 default:
1039                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1040                                     "FORMAT 8 - Reserved");
1041                 }
1042                 break;
1043
1044         case 0x90:  /* Format 9 - Device Read, Write, and Seek Checks */
1045                 switch (msg_no) {
1046                 case 0x00:
1047                         break;  /* No Message */
1048                 case 0x06:
1049                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1050                                     "FORMAT 9 - Device check-2 error");
1051                         break;
1052                 case 0x07:
1053                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1054                                     "FORMAT 9 - Head address did not compare");
1055                         break;
1056                 case 0x0A:
1057                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1058                                     "FORMAT 9 - Track physical address did "
1059                                     "not compare while oriented");
1060                         break;
1061                 case 0x0E:
1062                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1063                                     "FORMAT 9 - Cylinder address did not "
1064                                     "compare");
1065                         break;
1066                 default:
1067                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1068                                     "FORMAT 9 - Reserved");
1069                 }
1070                 break;
1071
1072         case 0xF0:              /* Format F - Cache Storage Checks */
1073                 switch (msg_no) {
1074                 case 0x00:
1075                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1076                                     "FORMAT F - Operation Terminated");
1077                         break;
1078                 case 0x01:
1079                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1080                                     "FORMAT F - Subsystem Processing Error");
1081                         break;
1082                 case 0x02:
1083                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1084                                     "FORMAT F - Cache or nonvolatile storage "
1085                                     "equipment failure");
1086                         break;
1087                 case 0x04:
1088                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1089                                     "FORMAT F - Caching terminated");
1090                         break;
1091                 case 0x06:
1092                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1093                                     "FORMAT F - Cache fast write access not "
1094                                     "authorized");
1095                         break;
1096                 case 0x07:
1097                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1098                                     "FORMAT F - Track format incorrect");
1099                         break;
1100                 case 0x09:
1101                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1102                                     "FORMAT F - Caching reinitiated");
1103                         break;
1104                 case 0x0A:
1105                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1106                                     "FORMAT F - Nonvolatile storage "
1107                                     "terminated");
1108                         break;
1109                 case 0x0B:
1110                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1111                                     "FORMAT F - Volume is suspended duplex");
1112                         break;
1113                 case 0x0C:
1114                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1115                                     "FORMAT F - Subsystem status connot be "
1116                                     "determined");
1117                         break;
1118                 case 0x0D:
1119                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1120                                     "FORMAT F - Caching status reset to "
1121                                     "default");
1122                         break;
1123                 case 0x0E:
1124                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1125                                     "FORMAT F - DASD Fast Write inhibited");
1126                         break;
1127                 default:
1128                         DEV_MESSAGE(KERN_WARNING, device, "%s",
1129                                     "FORMAT D - Reserved");
1130                 }
1131                 break;
1132
1133         default:        /* unknown message format - should not happen */
1134                 DEV_MESSAGE (KERN_WARNING, device,
1135                              "unknown message format %02x",
1136                              msg_format);
1137                 break;
1138         }                       /* end switch message format */
1139
1140 }                               /* end dasd_3990_handle_env_data */
1141
1142 /*
1143  * DASD_3990_ERP_COM_REJ
1144  *
1145  * DESCRIPTION
1146  *   Handles 24 byte 'Command Reject' error.
1147  *
1148  * PARAMETER
1149  *   erp                current erp_head
1150  *   sense              current sense data
1151  * 
1152  * RETURN VALUES
1153  *   erp                'new' erp_head - pointer to new ERP 
1154  */
1155 static struct dasd_ccw_req *
1156 dasd_3990_erp_com_rej(struct dasd_ccw_req * erp, char *sense)
1157 {
1158
1159         struct dasd_device *device = erp->device;
1160
1161         erp->function = dasd_3990_erp_com_rej;
1162
1163         /* env data present (ACTION 10 - retry should work) */
1164         if (sense[2] & SNS2_ENV_DATA_PRESENT) {
1165
1166                 DEV_MESSAGE(KERN_DEBUG, device, "%s",
1167                             "Command Reject - environmental data present");
1168
1169                 dasd_3990_handle_env_data(erp, sense);
1170
1171                 erp->retries = 5;
1172
1173         } else {
1174                 /* fatal error -  set status to FAILED */
1175                 DEV_MESSAGE(KERN_ERR, device, "%s",
1176                             "Command Reject - Fatal error");
1177
1178                 erp = dasd_3990_erp_cleanup(erp, DASD_CQR_FAILED);
1179         }
1180
1181         return erp;
1182
1183 }                               /* end dasd_3990_erp_com_rej */
1184
1185 /*
1186  * DASD_3990_ERP_BUS_OUT 
1187  *
1188  * DESCRIPTION
1189  *   Handles 24 byte 'Bus Out Parity Check' error.
1190  *
1191  * PARAMETER
1192  *   erp                current erp_head
1193  * RETURN VALUES
1194  *   erp                new erp_head - pointer to new ERP
1195  */
1196 static struct dasd_ccw_req *
1197 dasd_3990_erp_bus_out(struct dasd_ccw_req * erp)
1198 {
1199
1200         struct dasd_device *device = erp->device;
1201
1202         /* first time set initial retry counter and erp_function */
1203         /* and retry once without blocking queue                 */
1204         /* (this enables easier enqueing of the cqr)             */
1205         if (erp->function != dasd_3990_erp_bus_out) {
1206                 erp->retries = 256;
1207                 erp->function = dasd_3990_erp_bus_out;
1208
1209         } else {
1210
1211                 /* issue a message and wait for 'device ready' interrupt */
1212                 DEV_MESSAGE(KERN_DEBUG, device, "%s",
1213                             "bus out parity error or BOPC requested by "
1214                             "channel");
1215
1216                 dasd_3990_erp_block_queue(erp, 60*HZ);
1217
1218         }
1219
1220         return erp;
1221
1222 }                               /* end dasd_3990_erp_bus_out */
1223
1224 /*
1225  * DASD_3990_ERP_EQUIP_CHECK
1226  *
1227  * DESCRIPTION
1228  *   Handles 24 byte 'Equipment Check' error.
1229  *
1230  * PARAMETER
1231  *   erp                current erp_head
1232  * RETURN VALUES
1233  *   erp                new erp_head - pointer to new ERP
1234  */
1235 static struct dasd_ccw_req *
1236 dasd_3990_erp_equip_check(struct dasd_ccw_req * erp, char *sense)
1237 {
1238
1239         struct dasd_device *device = erp->device;
1240
1241         erp->function = dasd_3990_erp_equip_check;
1242
1243         if (sense[1] & SNS1_WRITE_INHIBITED) {
1244
1245                 DEV_MESSAGE(KERN_DEBUG, device, "%s",
1246                             "Write inhibited path encountered");
1247
1248                 /* vary path offline */
1249                 DEV_MESSAGE(KERN_ERR, device, "%s",
1250                             "Path should be varied off-line. "
1251                             "This is not implemented yet \n - please report "
1252                             "to linux390@de.ibm.com");
1253
1254                 erp = dasd_3990_erp_action_1(erp);
1255
1256         } else if (sense[2] & SNS2_ENV_DATA_PRESENT) {
1257
1258                 DEV_MESSAGE(KERN_DEBUG, device, "%s",
1259                             "Equipment Check - " "environmental data present");
1260
1261                 dasd_3990_handle_env_data(erp, sense);
1262
1263                 erp = dasd_3990_erp_action_4(erp, sense);
1264
1265         } else if (sense[1] & SNS1_PERM_ERR) {
1266
1267                 DEV_MESSAGE(KERN_DEBUG, device, "%s",
1268                             "Equipment Check - retry exhausted or "
1269                             "undesirable");
1270
1271                 erp = dasd_3990_erp_action_1(erp);
1272
1273         } else {
1274                 /* all other equipment checks - Action 5 */
1275                 /* rest is done when retries == 0 */
1276                 DEV_MESSAGE(KERN_DEBUG, device, "%s",
1277                             "Equipment check or processing error");
1278
1279                 erp = dasd_3990_erp_action_5(erp);
1280         }
1281
1282         return erp;
1283
1284 }                               /* end dasd_3990_erp_equip_check */
1285
1286 /*
1287  * DASD_3990_ERP_DATA_CHECK
1288  *
1289  * DESCRIPTION
1290  *   Handles 24 byte 'Data Check' error.
1291  *
1292  * PARAMETER
1293  *   erp                current erp_head
1294  * RETURN VALUES
1295  *   erp                new erp_head - pointer to new ERP
1296  */
1297 static struct dasd_ccw_req *
1298 dasd_3990_erp_data_check(struct dasd_ccw_req * erp, char *sense)
1299 {
1300
1301         struct dasd_device *device = erp->device;
1302
1303         erp->function = dasd_3990_erp_data_check;
1304
1305         if (sense[2] & SNS2_CORRECTABLE) {      /* correctable data check */
1306
1307                 /* issue message that the data has been corrected */
1308                 DEV_MESSAGE(KERN_EMERG, device, "%s",
1309                             "Data recovered during retry with PCI "
1310                             "fetch mode active");
1311
1312                 /* not possible to handle this situation in Linux */
1313                 panic("No way to inform application about the possibly "
1314                       "incorrect data");
1315
1316         } else if (sense[2] & SNS2_ENV_DATA_PRESENT) {
1317
1318                 DEV_MESSAGE(KERN_DEBUG, device, "%s",
1319                             "Uncorrectable data check recovered secondary "
1320                             "addr of duplex pair");
1321
1322                 erp = dasd_3990_erp_action_4(erp, sense);
1323
1324         } else if (sense[1] & SNS1_PERM_ERR) {
1325
1326                 DEV_MESSAGE(KERN_DEBUG, device, "%s",
1327                             "Uncorrectable data check with internal "
1328                             "retry exhausted");
1329
1330                 erp = dasd_3990_erp_action_1(erp);
1331
1332         } else {
1333                 /* all other data checks */
1334                 DEV_MESSAGE(KERN_DEBUG, device, "%s",
1335                             "Uncorrectable data check with retry count "
1336                             "exhausted...");
1337
1338                 erp = dasd_3990_erp_action_5(erp);
1339         }
1340
1341         return erp;
1342
1343 }                               /* end dasd_3990_erp_data_check */
1344
1345 /*
1346  * DASD_3990_ERP_OVERRUN
1347  *
1348  * DESCRIPTION
1349  *   Handles 24 byte 'Overrun' error.
1350  *
1351  * PARAMETER
1352  *   erp                current erp_head
1353  * RETURN VALUES
1354  *   erp                new erp_head - pointer to new ERP
1355  */
1356 static struct dasd_ccw_req *
1357 dasd_3990_erp_overrun(struct dasd_ccw_req * erp, char *sense)
1358 {
1359
1360         struct dasd_device *device = erp->device;
1361
1362         erp->function = dasd_3990_erp_overrun;
1363
1364         DEV_MESSAGE(KERN_DEBUG, device, "%s",
1365                     "Overrun - service overrun or overrun"
1366                     " error requested by channel");
1367
1368         erp = dasd_3990_erp_action_5(erp);
1369
1370         return erp;
1371
1372 }                               /* end dasd_3990_erp_overrun */
1373
1374 /*
1375  * DASD_3990_ERP_INV_FORMAT
1376  *
1377  * DESCRIPTION
1378  *   Handles 24 byte 'Invalid Track Format' error.
1379  *
1380  * PARAMETER
1381  *   erp                current erp_head
1382  * RETURN VALUES
1383  *   erp                new erp_head - pointer to new ERP
1384  */
1385 static struct dasd_ccw_req *
1386 dasd_3990_erp_inv_format(struct dasd_ccw_req * erp, char *sense)
1387 {
1388
1389         struct dasd_device *device = erp->device;
1390
1391         erp->function = dasd_3990_erp_inv_format;
1392
1393         if (sense[2] & SNS2_ENV_DATA_PRESENT) {
1394
1395                 DEV_MESSAGE(KERN_DEBUG, device, "%s",
1396                             "Track format error when destaging or "
1397                             "staging data");
1398
1399                 dasd_3990_handle_env_data(erp, sense);
1400
1401                 erp = dasd_3990_erp_action_4(erp, sense);
1402
1403         } else {
1404                 DEV_MESSAGE(KERN_ERR, device, "%s",
1405                             "Invalid Track Format - Fatal error should have "
1406                             "been handled within the interrupt handler");
1407
1408                 erp = dasd_3990_erp_cleanup(erp, DASD_CQR_FAILED);
1409         }
1410
1411         return erp;
1412
1413 }                               /* end dasd_3990_erp_inv_format */
1414
1415 /*
1416  * DASD_3990_ERP_EOC
1417  *
1418  * DESCRIPTION
1419  *   Handles 24 byte 'End-of-Cylinder' error.
1420  *
1421  * PARAMETER
1422  *   erp                already added default erp
1423  * RETURN VALUES
1424  *   erp                pointer to original (failed) cqr.
1425  */
1426 static struct dasd_ccw_req *
1427 dasd_3990_erp_EOC(struct dasd_ccw_req * default_erp, char *sense)
1428 {
1429
1430         struct dasd_device *device = default_erp->device;
1431
1432         DEV_MESSAGE(KERN_ERR, device, "%s",
1433                     "End-of-Cylinder - must never happen");
1434
1435         /* implement action 7 - BUG */
1436         return dasd_3990_erp_cleanup(default_erp, DASD_CQR_FAILED);
1437
1438 }                               /* end dasd_3990_erp_EOC */
1439
1440 /*
1441  * DASD_3990_ERP_ENV_DATA
1442  *
1443  * DESCRIPTION
1444  *   Handles 24 byte 'Environmental-Data Present' error.
1445  *
1446  * PARAMETER
1447  *   erp                current erp_head
1448  * RETURN VALUES
1449  *   erp                new erp_head - pointer to new ERP
1450  */
1451 static struct dasd_ccw_req *
1452 dasd_3990_erp_env_data(struct dasd_ccw_req * erp, char *sense)
1453 {
1454
1455         struct dasd_device *device = erp->device;
1456
1457         erp->function = dasd_3990_erp_env_data;
1458
1459         DEV_MESSAGE(KERN_DEBUG, device, "%s", "Environmental data present");
1460
1461         dasd_3990_handle_env_data(erp, sense);
1462
1463         /* don't retry on disabled interface */
1464         if (sense[7] != 0x0F) {
1465
1466                 erp = dasd_3990_erp_action_4(erp, sense);
1467         } else {
1468
1469                 erp = dasd_3990_erp_cleanup(erp, DASD_CQR_IN_IO);
1470         }
1471
1472         return erp;
1473
1474 }                               /* end dasd_3990_erp_env_data */
1475
1476 /*
1477  * DASD_3990_ERP_NO_REC
1478  *
1479  * DESCRIPTION
1480  *   Handles 24 byte 'No Record Found' error.
1481  *
1482  * PARAMETER
1483  *   erp                already added default ERP
1484  *              
1485  * RETURN VALUES
1486  *   erp                new erp_head - pointer to new ERP
1487  */
1488 static struct dasd_ccw_req *
1489 dasd_3990_erp_no_rec(struct dasd_ccw_req * default_erp, char *sense)
1490 {
1491
1492         struct dasd_device *device = default_erp->device;
1493
1494         DEV_MESSAGE(KERN_ERR, device, "%s",
1495                     "No Record Found - Fatal error should "
1496                     "have been handled within the interrupt handler");
1497
1498         return dasd_3990_erp_cleanup(default_erp, DASD_CQR_FAILED);
1499
1500 }                               /* end dasd_3990_erp_no_rec */
1501
1502 /*
1503  * DASD_3990_ERP_FILE_PROT
1504  *
1505  * DESCRIPTION
1506  *   Handles 24 byte 'File Protected' error.
1507  *   Note: Seek related recovery is not implemented because
1508  *         wee don't use the seek command yet.
1509  *
1510  * PARAMETER
1511  *   erp                current erp_head
1512  * RETURN VALUES
1513  *   erp                new erp_head - pointer to new ERP
1514  */
1515 static struct dasd_ccw_req *
1516 dasd_3990_erp_file_prot(struct dasd_ccw_req * erp)
1517 {
1518
1519         struct dasd_device *device = erp->device;
1520
1521         DEV_MESSAGE(KERN_ERR, device, "%s", "File Protected");
1522
1523         return dasd_3990_erp_cleanup(erp, DASD_CQR_FAILED);
1524
1525 }                               /* end dasd_3990_erp_file_prot */
1526
1527 /*
1528  * DASD_3990_ERP_INSPECT_24 
1529  *
1530  * DESCRIPTION
1531  *   Does a detailed inspection of the 24 byte sense data
1532  *   and sets up a related error recovery action.  
1533  *
1534  * PARAMETER
1535  *   sense              sense data of the actual error
1536  *   erp                pointer to the currently created default ERP
1537  *
1538  * RETURN VALUES
1539  *   erp                pointer to the (addtitional) ERP
1540  */
1541 static struct dasd_ccw_req *
1542 dasd_3990_erp_inspect_24(struct dasd_ccw_req * erp, char *sense)
1543 {
1544
1545         struct dasd_ccw_req *erp_filled = NULL;
1546
1547         /* Check sense for ....    */
1548         /* 'Command Reject'        */
1549         if ((erp_filled == NULL) && (sense[0] & SNS0_CMD_REJECT)) {
1550                 erp_filled = dasd_3990_erp_com_rej(erp, sense);
1551         }
1552         /* 'Intervention Required' */
1553         if ((erp_filled == NULL) && (sense[0] & SNS0_INTERVENTION_REQ)) {
1554                 erp_filled = dasd_3990_erp_int_req(erp);
1555         }
1556         /* 'Bus Out Parity Check'  */
1557         if ((erp_filled == NULL) && (sense[0] & SNS0_BUS_OUT_CHECK)) {
1558                 erp_filled = dasd_3990_erp_bus_out(erp);
1559         }
1560         /* 'Equipment Check'       */
1561         if ((erp_filled == NULL) && (sense[0] & SNS0_EQUIPMENT_CHECK)) {
1562                 erp_filled = dasd_3990_erp_equip_check(erp, sense);
1563         }
1564         /* 'Data Check'            */
1565         if ((erp_filled == NULL) && (sense[0] & SNS0_DATA_CHECK)) {
1566                 erp_filled = dasd_3990_erp_data_check(erp, sense);
1567         }
1568         /* 'Overrun'               */
1569         if ((erp_filled == NULL) && (sense[0] & SNS0_OVERRUN)) {
1570                 erp_filled = dasd_3990_erp_overrun(erp, sense);
1571         }
1572         /* 'Invalid Track Format'  */
1573         if ((erp_filled == NULL) && (sense[1] & SNS1_INV_TRACK_FORMAT)) {
1574                 erp_filled = dasd_3990_erp_inv_format(erp, sense);
1575         }
1576         /* 'End-of-Cylinder'       */
1577         if ((erp_filled == NULL) && (sense[1] & SNS1_EOC)) {
1578                 erp_filled = dasd_3990_erp_EOC(erp, sense);
1579         }
1580         /* 'Environmental Data'    */
1581         if ((erp_filled == NULL) && (sense[2] & SNS2_ENV_DATA_PRESENT)) {
1582                 erp_filled = dasd_3990_erp_env_data(erp, sense);
1583         }
1584         /* 'No Record Found'       */
1585         if ((erp_filled == NULL) && (sense[1] & SNS1_NO_REC_FOUND)) {
1586                 erp_filled = dasd_3990_erp_no_rec(erp, sense);
1587         }
1588         /* 'File Protected'        */
1589         if ((erp_filled == NULL) && (sense[1] & SNS1_FILE_PROTECTED)) {
1590                 erp_filled = dasd_3990_erp_file_prot(erp);
1591         }
1592         /* other (unknown) error - do default ERP */
1593         if (erp_filled == NULL) {
1594
1595                 erp_filled = erp;
1596         }
1597
1598         return erp_filled;
1599
1600 }                               /* END dasd_3990_erp_inspect_24 */
1601
1602 /*
1603  ***************************************************************************** 
1604  * 32 byte sense ERP functions (only)
1605  ***************************************************************************** 
1606  */
1607
1608 /*
1609  * DASD_3990_ERPACTION_10_32 
1610  *
1611  * DESCRIPTION
1612  *   Handles 32 byte 'Action 10' of Single Program Action Codes.
1613  *   Just retry and if retry doesn't work, return with error.
1614  *
1615  * PARAMETER
1616  *   erp                current erp_head
1617  *   sense              current sense data 
1618  * RETURN VALUES
1619  *   erp                modified erp_head
1620  */
1621 static struct dasd_ccw_req *
1622 dasd_3990_erp_action_10_32(struct dasd_ccw_req * erp, char *sense)
1623 {
1624
1625         struct dasd_device *device = erp->device;
1626
1627         erp->retries = 256;
1628         erp->function = dasd_3990_erp_action_10_32;
1629
1630         DEV_MESSAGE(KERN_DEBUG, device, "%s", "Perform logging requested");
1631
1632         return erp;
1633
1634 }                               /* end dasd_3990_erp_action_10_32 */
1635
1636 /*
1637  * DASD_3990_ERP_ACTION_1B_32
1638  *
1639  * DESCRIPTION
1640  *   Handles 32 byte 'Action 1B' of Single Program Action Codes.
1641  *   A write operation could not be finished because of an unexpected 
1642  *   condition.
1643  *   The already created 'default erp' is used to get the link to 
1644  *   the erp chain, but it can not be used for this recovery 
1645  *   action because it contains no DE/LO data space.
1646  *
1647  * PARAMETER
1648  *   default_erp        already added default erp.
1649  *   sense              current sense data 
1650  *
1651  * RETURN VALUES
1652  *   erp                new erp or 
1653  *                      default_erp in case of imprecise ending or error
1654  */
1655 static struct dasd_ccw_req *
1656 dasd_3990_erp_action_1B_32(struct dasd_ccw_req * default_erp, char *sense)
1657 {
1658
1659         struct dasd_device *device = default_erp->device;
1660         __u32 cpa = 0;
1661         struct dasd_ccw_req *cqr;
1662         struct dasd_ccw_req *erp;
1663         struct DE_eckd_data *DE_data;
1664         char *LO_data;          /* LO_eckd_data_t */
1665         struct ccw1 *ccw;
1666
1667         DEV_MESSAGE(KERN_DEBUG, device, "%s",
1668                     "Write not finished because of unexpected condition");
1669
1670         default_erp->function = dasd_3990_erp_action_1B_32;
1671
1672         /* determine the original cqr */
1673         cqr = default_erp;
1674
1675         while (cqr->refers != NULL) {
1676                 cqr = cqr->refers;
1677         }
1678
1679         /* for imprecise ending just do default erp */
1680         if (sense[1] & 0x01) {
1681
1682                 DEV_MESSAGE(KERN_DEBUG, device, "%s",
1683                             "Imprecise ending is set - just retry");
1684
1685                 return default_erp;
1686         }
1687
1688         /* determine the address of the CCW to be restarted */
1689         /* Imprecise ending is not set -> addr from IRB-SCSW */
1690         cpa = default_erp->refers->irb.scsw.cpa;
1691
1692         if (cpa == 0) {
1693
1694                 DEV_MESSAGE(KERN_DEBUG, device, "%s",
1695                             "Unable to determine address of the CCW "
1696                             "to be restarted");
1697
1698                 return dasd_3990_erp_cleanup(default_erp, DASD_CQR_FAILED);
1699         }
1700
1701         /* Build new ERP request including DE/LO */
1702         erp = dasd_alloc_erp_request((char *) &cqr->magic,
1703                                      2 + 1,/* DE/LO + TIC */
1704                                      sizeof (struct DE_eckd_data) +
1705                                      sizeof (struct LO_eckd_data), device);
1706
1707         if (IS_ERR(erp)) {
1708                 DEV_MESSAGE(KERN_ERR, device, "%s", "Unable to allocate ERP");
1709                 return dasd_3990_erp_cleanup(default_erp, DASD_CQR_FAILED);
1710         }
1711
1712         /* use original DE */
1713         DE_data = erp->data;
1714         memcpy(DE_data, cqr->data, sizeof (struct DE_eckd_data));
1715
1716         /* create LO */
1717         LO_data = erp->data + sizeof (struct DE_eckd_data);
1718
1719         if ((sense[3] == 0x01) && (LO_data[1] & 0x01)) {
1720
1721                 DEV_MESSAGE(KERN_ERR, device, "%s",
1722                             "BUG - this should not happen");
1723
1724                 return dasd_3990_erp_cleanup(default_erp, DASD_CQR_FAILED);
1725         }
1726
1727         if ((sense[7] & 0x3F) == 0x01) {
1728                 /* operation code is WRITE DATA -> data area orientation */
1729                 LO_data[0] = 0x81;
1730
1731         } else if ((sense[7] & 0x3F) == 0x03) {
1732                 /* operation code is FORMAT WRITE -> index orientation */
1733                 LO_data[0] = 0xC3;
1734
1735         } else {
1736                 LO_data[0] = sense[7];  /* operation */
1737         }
1738
1739         LO_data[1] = sense[8];  /* auxiliary */
1740         LO_data[2] = sense[9];
1741         LO_data[3] = sense[3];  /* count */
1742         LO_data[4] = sense[29]; /* seek_addr.cyl */
1743         LO_data[5] = sense[30]; /* seek_addr.cyl 2nd byte */
1744         LO_data[7] = sense[31]; /* seek_addr.head 2nd byte */
1745
1746         memcpy(&(LO_data[8]), &(sense[11]), 8);
1747
1748         /* create DE ccw */
1749         ccw = erp->cpaddr;
1750         memset(ccw, 0, sizeof (struct ccw1));
1751         ccw->cmd_code = DASD_ECKD_CCW_DEFINE_EXTENT;
1752         ccw->flags = CCW_FLAG_CC;
1753         ccw->count = 16;
1754         ccw->cda = (__u32)(addr_t) DE_data;
1755
1756         /* create LO ccw */
1757         ccw++;
1758         memset(ccw, 0, sizeof (struct ccw1));
1759         ccw->cmd_code = DASD_ECKD_CCW_LOCATE_RECORD;
1760         ccw->flags = CCW_FLAG_CC;
1761         ccw->count = 16;
1762         ccw->cda = (__u32)(addr_t) LO_data;
1763
1764         /* TIC to the failed ccw */
1765         ccw++;
1766         ccw->cmd_code = CCW_CMD_TIC;
1767         ccw->cda = cpa;
1768
1769         /* fill erp related fields */
1770         erp->function = dasd_3990_erp_action_1B_32;
1771         erp->refers = default_erp->refers;
1772         erp->device = device;
1773         erp->magic = default_erp->magic;
1774         erp->expires = 0;
1775         erp->retries = 256;
1776         erp->buildclk = get_clock();
1777         erp->status = DASD_CQR_FILLED;
1778
1779         /* remove the default erp */
1780         dasd_free_erp_request(default_erp, device);
1781
1782         return erp;
1783
1784 }                               /* end dasd_3990_erp_action_1B_32 */
1785
1786 /*
1787  * DASD_3990_UPDATE_1B
1788  *
1789  * DESCRIPTION
1790  *   Handles the update to the 32 byte 'Action 1B' of Single Program 
1791  *   Action Codes in case the first action was not successful.
1792  *   The already created 'previous_erp' is the currently not successful
1793  *   ERP. 
1794  *
1795  * PARAMETER
1796  *   previous_erp       already created previous erp.
1797  *   sense              current sense data 
1798  * RETURN VALUES
1799  *   erp                modified erp 
1800  */
1801 static struct dasd_ccw_req *
1802 dasd_3990_update_1B(struct dasd_ccw_req * previous_erp, char *sense)
1803 {
1804
1805         struct dasd_device *device = previous_erp->device;
1806         __u32 cpa = 0;
1807         struct dasd_ccw_req *cqr;
1808         struct dasd_ccw_req *erp;
1809         char *LO_data;          /* struct LO_eckd_data */
1810         struct ccw1 *ccw;
1811
1812         DEV_MESSAGE(KERN_DEBUG, device, "%s",
1813                     "Write not finished because of unexpected condition"
1814                     " - follow on");
1815
1816         /* determine the original cqr */
1817         cqr = previous_erp;
1818
1819         while (cqr->refers != NULL) {
1820                 cqr = cqr->refers;
1821         }
1822
1823         /* for imprecise ending just do default erp */
1824         if (sense[1] & 0x01) {
1825
1826                 DEV_MESSAGE(KERN_DEBUG, device, "%s",
1827                             "Imprecise ending is set - just retry");
1828
1829                 previous_erp->status = DASD_CQR_QUEUED;
1830
1831                 return previous_erp;
1832         }
1833
1834         /* determine the address of the CCW to be restarted */
1835         /* Imprecise ending is not set -> addr from IRB-SCSW */
1836         cpa = previous_erp->irb.scsw.cpa;
1837
1838         if (cpa == 0) {
1839
1840                 DEV_MESSAGE(KERN_DEBUG, device, "%s",
1841                             "Unable to determine address of the CCW "
1842                             "to be restarted");
1843
1844                 previous_erp->status = DASD_CQR_FAILED;
1845
1846                 return previous_erp;
1847         }
1848
1849         erp = previous_erp;
1850
1851         /* update the LO with the new returned sense data  */
1852         LO_data = erp->data + sizeof (struct DE_eckd_data);
1853
1854         if ((sense[3] == 0x01) && (LO_data[1] & 0x01)) {
1855
1856                 DEV_MESSAGE(KERN_ERR, device, "%s",
1857                             "BUG - this should not happen");
1858
1859                 previous_erp->status = DASD_CQR_FAILED;
1860
1861                 return previous_erp;
1862         }
1863
1864         if ((sense[7] & 0x3F) == 0x01) {
1865                 /* operation code is WRITE DATA -> data area orientation */
1866                 LO_data[0] = 0x81;
1867
1868         } else if ((sense[7] & 0x3F) == 0x03) {
1869                 /* operation code is FORMAT WRITE -> index orientation */
1870                 LO_data[0] = 0xC3;
1871
1872         } else {
1873                 LO_data[0] = sense[7];  /* operation */
1874         }
1875
1876         LO_data[1] = sense[8];  /* auxiliary */
1877         LO_data[2] = sense[9];
1878         LO_data[3] = sense[3];  /* count */
1879         LO_data[4] = sense[29]; /* seek_addr.cyl */
1880         LO_data[5] = sense[30]; /* seek_addr.cyl 2nd byte */
1881         LO_data[7] = sense[31]; /* seek_addr.head 2nd byte */
1882
1883         memcpy(&(LO_data[8]), &(sense[11]), 8);
1884
1885         /* TIC to the failed ccw */
1886         ccw = erp->cpaddr;      /* addr of DE ccw */
1887         ccw++;                  /* addr of LE ccw */
1888         ccw++;                  /* addr of TIC ccw */
1889         ccw->cda = cpa;
1890
1891         erp->status = DASD_CQR_QUEUED;
1892
1893         return erp;
1894
1895 }                               /* end dasd_3990_update_1B */
1896
1897 /*
1898  * DASD_3990_ERP_COMPOUND_RETRY 
1899  *
1900  * DESCRIPTION
1901  *   Handles the compound ERP action retry code.
1902  *   NOTE: At least one retry is done even if zero is specified
1903  *         by the sense data. This makes enqueueing of the request
1904  *         easier.
1905  *
1906  * PARAMETER
1907  *   sense              sense data of the actual error
1908  *   erp                pointer to the currently created ERP
1909  *
1910  * RETURN VALUES
1911  *   erp                modified ERP pointer
1912  *
1913  */
1914 static void
1915 dasd_3990_erp_compound_retry(struct dasd_ccw_req * erp, char *sense)
1916 {
1917
1918         switch (sense[25] & 0x03) {
1919         case 0x00:              /* no not retry */
1920                 erp->retries = 1;
1921                 break;
1922
1923         case 0x01:              /* retry 2 times */
1924                 erp->retries = 2;
1925                 break;
1926
1927         case 0x02:              /* retry 10 times */
1928                 erp->retries = 10;
1929                 break;
1930
1931         case 0x03:              /* retry 256 times */
1932                 erp->retries = 256;
1933                 break;
1934
1935         default:
1936                 BUG();
1937         }
1938
1939         erp->function = dasd_3990_erp_compound_retry;
1940
1941 }                               /* end dasd_3990_erp_compound_retry */
1942
1943 /*
1944  * DASD_3990_ERP_COMPOUND_PATH 
1945  *
1946  * DESCRIPTION
1947  *   Handles the compound ERP action for retry on alternate
1948  *   channel path.
1949  *
1950  * PARAMETER
1951  *   sense              sense data of the actual error
1952  *   erp                pointer to the currently created ERP
1953  *
1954  * RETURN VALUES
1955  *   erp                modified ERP pointer
1956  *
1957  */
1958 static void
1959 dasd_3990_erp_compound_path(struct dasd_ccw_req * erp, char *sense)
1960 {
1961
1962         if (sense[25] & DASD_SENSE_BIT_3) {
1963                 dasd_3990_erp_alternate_path(erp);
1964
1965                 if (erp->status == DASD_CQR_FAILED) {
1966                         /* reset the lpm and the status to be able to 
1967                          * try further actions. */
1968
1969                         erp->lpm = 0;
1970
1971                         erp->status = DASD_CQR_ERROR;
1972
1973                 }
1974         }
1975
1976         erp->function = dasd_3990_erp_compound_path;
1977
1978 }                               /* end dasd_3990_erp_compound_path */
1979
1980 /*
1981  * DASD_3990_ERP_COMPOUND_CODE 
1982  *
1983  * DESCRIPTION
1984  *   Handles the compound ERP action for retry code.
1985  *
1986  * PARAMETER
1987  *   sense              sense data of the actual error
1988  *   erp                pointer to the currently created ERP
1989  *
1990  * RETURN VALUES
1991  *   erp                NEW ERP pointer
1992  *
1993  */
1994 static struct dasd_ccw_req *
1995 dasd_3990_erp_compound_code(struct dasd_ccw_req * erp, char *sense)
1996 {
1997
1998         if (sense[25] & DASD_SENSE_BIT_2) {
1999
2000                 switch (sense[28]) {
2001                 case 0x17:
2002                         /* issue a Diagnostic Control command with an 
2003                          * Inhibit Write subcommand and controler modifier */
2004                         erp = dasd_3990_erp_DCTL(erp, 0x20);
2005                         break;
2006                         
2007                 case 0x25:
2008                         /* wait for 5 seconds and retry again */
2009                         erp->retries = 1;
2010                         
2011                         dasd_3990_erp_block_queue (erp, 5*HZ);
2012                         break;
2013                         
2014                 default:
2015                         /* should not happen - continue */
2016                         break;
2017                 }
2018         }
2019
2020         erp->function = dasd_3990_erp_compound_code;
2021
2022         return erp;
2023
2024 }                               /* end dasd_3990_erp_compound_code */
2025
2026 /*
2027  * DASD_3990_ERP_COMPOUND_CONFIG 
2028  *
2029  * DESCRIPTION
2030  *   Handles the compound ERP action for configruation
2031  *   dependent error.
2032  *   Note: duplex handling is not implemented (yet).
2033  *
2034  * PARAMETER
2035  *   sense              sense data of the actual error
2036  *   erp                pointer to the currently created ERP
2037  *
2038  * RETURN VALUES
2039  *   erp                modified ERP pointer
2040  *
2041  */
2042 static void
2043 dasd_3990_erp_compound_config(struct dasd_ccw_req * erp, char *sense)
2044 {
2045
2046         if ((sense[25] & DASD_SENSE_BIT_1) && (sense[26] & DASD_SENSE_BIT_2)) {
2047
2048                 /* set to suspended duplex state then restart */
2049                 struct dasd_device *device = erp->device;
2050
2051                 DEV_MESSAGE(KERN_ERR, device, "%s",
2052                             "Set device to suspended duplex state should be "
2053                             "done!\n"
2054                             "This is not implemented yet (for compound ERP)"
2055                             " - please report to linux390@de.ibm.com");
2056
2057         }
2058
2059         erp->function = dasd_3990_erp_compound_config;
2060
2061 }                               /* end dasd_3990_erp_compound_config */
2062
2063 /*
2064  * DASD_3990_ERP_COMPOUND 
2065  *
2066  * DESCRIPTION
2067  *   Does the further compound program action if 
2068  *   compound retry was not successful.
2069  *
2070  * PARAMETER
2071  *   sense              sense data of the actual error
2072  *   erp                pointer to the current (failed) ERP
2073  *
2074  * RETURN VALUES
2075  *   erp                (additional) ERP pointer
2076  *
2077  */
2078 static struct dasd_ccw_req *
2079 dasd_3990_erp_compound(struct dasd_ccw_req * erp, char *sense)
2080 {
2081
2082         if ((erp->function == dasd_3990_erp_compound_retry) &&
2083             (erp->status == DASD_CQR_ERROR)) {
2084
2085                 dasd_3990_erp_compound_path(erp, sense);
2086         }
2087
2088         if ((erp->function == dasd_3990_erp_compound_path) &&
2089             (erp->status == DASD_CQR_ERROR)) {
2090
2091                 erp = dasd_3990_erp_compound_code(erp, sense);
2092         }
2093
2094         if ((erp->function == dasd_3990_erp_compound_code) &&
2095             (erp->status == DASD_CQR_ERROR)) {
2096
2097                 dasd_3990_erp_compound_config(erp, sense);
2098         }
2099
2100         /* if no compound action ERP specified, the request failed */
2101         if (erp->status == DASD_CQR_ERROR) {
2102
2103                 erp->status = DASD_CQR_FAILED;
2104         }
2105
2106         return erp;
2107
2108 }                               /* end dasd_3990_erp_compound */
2109
2110 /*
2111  * DASD_3990_ERP_INSPECT_32 
2112  *
2113  * DESCRIPTION
2114  *   Does a detailed inspection of the 32 byte sense data
2115  *   and sets up a related error recovery action.  
2116  *
2117  * PARAMETER
2118  *   sense              sense data of the actual error
2119  *   erp                pointer to the currently created default ERP
2120  *
2121  * RETURN VALUES
2122  *   erp_filled         pointer to the ERP
2123  *
2124  */
2125 static struct dasd_ccw_req *
2126 dasd_3990_erp_inspect_32(struct dasd_ccw_req * erp, char *sense)
2127 {
2128
2129         struct dasd_device *device = erp->device;
2130
2131         erp->function = dasd_3990_erp_inspect_32;
2132
2133         if (sense[25] & DASD_SENSE_BIT_0) {
2134
2135                 /* compound program action codes (byte25 bit 0 == '1') */
2136                 dasd_3990_erp_compound_retry(erp, sense);
2137
2138         } else {
2139
2140                 /* single program action codes (byte25 bit 0 == '0') */
2141                 switch (sense[25]) {
2142
2143                 case 0x00:      /* success - use default ERP for retries */
2144                         DEV_MESSAGE(KERN_DEBUG, device, "%s",
2145                                     "ERP called for successful request"
2146                                     " - just retry");
2147                         break;
2148
2149                 case 0x01:      /* fatal error */
2150                         DEV_MESSAGE(KERN_ERR, device, "%s",
2151                                     "Fatal error should have been "
2152                                     "handled within the interrupt handler");
2153
2154                         erp = dasd_3990_erp_cleanup(erp, DASD_CQR_FAILED);
2155                         break;
2156
2157                 case 0x02:      /* intervention required */
2158                 case 0x03:      /* intervention required during dual copy */
2159                         erp = dasd_3990_erp_int_req(erp);
2160                         break;
2161
2162                 case 0x0F:  /* length mismatch during update write command */
2163                         DEV_MESSAGE(KERN_ERR, device, "%s",
2164                                     "update write command error - should not "
2165                                     "happen;\n"
2166                                     "Please send this message together with "
2167                                     "the above sense data to linux390@de."
2168                                     "ibm.com");
2169
2170                         erp = dasd_3990_erp_cleanup(erp, DASD_CQR_FAILED);
2171                         break;
2172
2173                 case 0x10:  /* logging required for other channel program */
2174                         erp = dasd_3990_erp_action_10_32(erp, sense);
2175                         break;
2176
2177                 case 0x15:      /* next track outside defined extend */
2178                         DEV_MESSAGE(KERN_ERR, device, "%s",
2179                                     "next track outside defined extend - "
2180                                     "should not happen;\n"
2181                                     "Please send this message together with "
2182                                     "the above sense data to linux390@de."
2183                                     "ibm.com");
2184
2185                         erp = dasd_3990_erp_cleanup(erp, DASD_CQR_FAILED);
2186                         break;
2187
2188                 case 0x1B:      /* unexpected condition during write */
2189
2190                         erp = dasd_3990_erp_action_1B_32(erp, sense);
2191                         break;
2192
2193                 case 0x1C:      /* invalid data */
2194                         DEV_MESSAGE(KERN_EMERG, device, "%s",
2195                                     "Data recovered during retry with PCI "
2196                                     "fetch mode active");
2197
2198                         /* not possible to handle this situation in Linux */
2199                         panic
2200                             ("Invalid data - No way to inform application "
2201                              "about the possibly incorrect data");
2202                         break;
2203
2204                 case 0x1D:      /* state-change pending */
2205                         DEV_MESSAGE(KERN_DEBUG, device, "%s",
2206                                     "A State change pending condition exists "
2207                                     "for the subsystem or device");
2208
2209                         erp = dasd_3990_erp_action_4(erp, sense);
2210                         break;
2211
2212                 case 0x1E:      /* busy */
2213                         DEV_MESSAGE(KERN_DEBUG, device, "%s",
2214                                     "Busy condition exists "
2215                                     "for the subsystem or device");
2216                         erp = dasd_3990_erp_action_4(erp, sense);
2217                         break;
2218
2219                 default:        /* all others errors - default erp  */
2220                         break;
2221                 }
2222         }
2223
2224         return erp;
2225
2226 }                               /* end dasd_3990_erp_inspect_32 */
2227
2228 /*
2229  ***************************************************************************** 
2230  * main ERP control fuctions (24 and 32 byte sense)
2231  ***************************************************************************** 
2232  */
2233
2234 /*
2235  * DASD_3990_ERP_INSPECT
2236  *
2237  * DESCRIPTION
2238  *   Does a detailed inspection for sense data by calling either
2239  *   the 24-byte or the 32-byte inspection routine.
2240  *
2241  * PARAMETER
2242  *   erp                pointer to the currently created default ERP
2243  * RETURN VALUES
2244  *   erp_new            contens was possibly modified 
2245  */
2246 static struct dasd_ccw_req *
2247 dasd_3990_erp_inspect(struct dasd_ccw_req * erp)
2248 {
2249
2250         struct dasd_ccw_req *erp_new = NULL;
2251         /* sense data are located in the refers record of the */
2252         /* already set up new ERP !                           */
2253         char *sense = erp->refers->irb.ecw;
2254
2255         /* distinguish between 24 and 32 byte sense data */
2256         if (sense[27] & DASD_SENSE_BIT_0) {
2257
2258                 /* inspect the 24 byte sense data */
2259                 erp_new = dasd_3990_erp_inspect_24(erp, sense);
2260
2261         } else {
2262
2263                 /* inspect the 32 byte sense data */
2264                 erp_new = dasd_3990_erp_inspect_32(erp, sense);
2265
2266         }       /* end distinguish between 24 and 32 byte sense data */
2267
2268         return erp_new;
2269 }
2270
2271 /*
2272  * DASD_3990_ERP_ADD_ERP
2273  * 
2274  * DESCRIPTION
2275  *   This funtion adds an additional request block (ERP) to the head of
2276  *   the given cqr (or erp).
2277  *   This erp is initialized as an default erp (retry TIC)
2278  *
2279  * PARAMETER
2280  *   cqr                head of the current ERP-chain (or single cqr if 
2281  *                      first error)
2282  * RETURN VALUES
2283  *   erp                pointer to new ERP-chain head
2284  */
2285 static struct dasd_ccw_req *
2286 dasd_3990_erp_add_erp(struct dasd_ccw_req * cqr)
2287 {
2288
2289         struct dasd_device *device = cqr->device;
2290         struct ccw1 *ccw;
2291
2292         /* allocate additional request block */
2293         struct dasd_ccw_req *erp;
2294
2295         erp = dasd_alloc_erp_request((char *) &cqr->magic, 2, 0, cqr->device);
2296         if (IS_ERR(erp)) {
2297                 if (cqr->retries <= 0) {
2298                         DEV_MESSAGE(KERN_ERR, device, "%s",
2299                                     "Unable to allocate ERP request");
2300                         cqr->status = DASD_CQR_FAILED;
2301                         cqr->stopclk = get_clock ();
2302                 } else {
2303                         DEV_MESSAGE (KERN_ERR, device,
2304                                      "Unable to allocate ERP request "
2305                                      "(%i retries left)",
2306                                      cqr->retries);
2307                         dasd_set_timer(device, (HZ << 3));
2308                 }
2309                 return cqr;
2310         }
2311
2312         /* initialize request with default TIC to current ERP/CQR */
2313         ccw = erp->cpaddr;
2314         ccw->cmd_code = CCW_CMD_NOOP;
2315         ccw->flags = CCW_FLAG_CC;
2316         ccw++;
2317         ccw->cmd_code = CCW_CMD_TIC;
2318         ccw->cda      = (long)(cqr->cpaddr);
2319         erp->function = dasd_3990_erp_add_erp;
2320         erp->refers   = cqr;
2321         erp->device   = cqr->device;
2322         erp->magic    = cqr->magic;
2323         erp->expires  = 0;
2324         erp->retries  = 256;
2325         erp->buildclk = get_clock();
2326
2327         erp->status = DASD_CQR_FILLED;
2328
2329         return erp;
2330 }
2331
2332 /*
2333  * DASD_3990_ERP_ADDITIONAL_ERP 
2334  * 
2335  * DESCRIPTION
2336  *   An additional ERP is needed to handle the current error.
2337  *   Add ERP to the head of the ERP-chain containing the ERP processing
2338  *   determined based on the sense data.
2339  *
2340  * PARAMETER
2341  *   cqr                head of the current ERP-chain (or single cqr if 
2342  *                      first error)
2343  *
2344  * RETURN VALUES
2345  *   erp                pointer to new ERP-chain head
2346  */
2347 static struct dasd_ccw_req *
2348 dasd_3990_erp_additional_erp(struct dasd_ccw_req * cqr)
2349 {
2350
2351         struct dasd_ccw_req *erp = NULL;
2352
2353         /* add erp and initialize with default TIC */
2354         erp = dasd_3990_erp_add_erp(cqr);
2355
2356         /* inspect sense, determine specific ERP if possible */
2357         if (erp != cqr) {
2358
2359                 erp = dasd_3990_erp_inspect(erp);
2360         }
2361
2362         return erp;
2363
2364 }                               /* end dasd_3990_erp_additional_erp */
2365
2366 /*
2367  * DASD_3990_ERP_ERROR_MATCH
2368  *
2369  * DESCRIPTION
2370  *   Check if the device status of the given cqr is the same.
2371  *   This means that the failed CCW and the relevant sense data
2372  *   must match.
2373  *   I don't distinguish between 24 and 32 byte sense because in case of
2374  *   24 byte sense byte 25 and 27 is set as well.
2375  *
2376  * PARAMETER
2377  *   cqr1               first cqr, which will be compared with the 
2378  *   cqr2               second cqr.
2379  *
2380  * RETURN VALUES
2381  *   match              'boolean' for match found
2382  *                      returns 1 if match found, otherwise 0.
2383  */
2384 static int
2385 dasd_3990_erp_error_match(struct dasd_ccw_req *cqr1, struct dasd_ccw_req *cqr2)
2386 {
2387
2388         /* check failed CCW */
2389         if (cqr1->irb.scsw.cpa != cqr2->irb.scsw.cpa) {
2390                 //      return 0;       /* CCW doesn't match */
2391         }
2392
2393         /* check sense data; byte 0-2,25,27 */
2394         if (!((memcmp (cqr1->irb.ecw, cqr2->irb.ecw, 3) == 0) &&
2395               (cqr1->irb.ecw[27] == cqr2->irb.ecw[27]) &&
2396               (cqr1->irb.ecw[25] == cqr2->irb.ecw[25]))) {
2397
2398                 return 0;       /* sense doesn't match */
2399         }
2400
2401         return 1;               /* match */
2402
2403 }                               /* end dasd_3990_erp_error_match */
2404
2405 /*
2406  * DASD_3990_ERP_IN_ERP
2407  *
2408  * DESCRIPTION
2409  *   check if the current error already happened before.
2410  *   quick exit if current cqr is not an ERP (cqr->refers=NULL)
2411  *
2412  * PARAMETER
2413  *   cqr                failed cqr (either original cqr or already an erp)
2414  *
2415  * RETURN VALUES
2416  *   erp                erp-pointer to the already defined error 
2417  *                      recovery procedure OR
2418  *                      NULL if a 'new' error occurred.
2419  */
2420 static struct dasd_ccw_req *
2421 dasd_3990_erp_in_erp(struct dasd_ccw_req *cqr)
2422 {
2423
2424         struct dasd_ccw_req *erp_head = cqr,    /* save erp chain head */
2425         *erp_match = NULL;      /* save erp chain head */
2426         int match = 0;          /* 'boolean' for matching error found */
2427
2428         if (cqr->refers == NULL) {      /* return if not in erp */
2429                 return NULL;
2430         }
2431
2432         /* check the erp/cqr chain for current error */
2433         do {
2434                 match = dasd_3990_erp_error_match(erp_head, cqr->refers);
2435                 erp_match = cqr;        /* save possible matching erp  */
2436                 cqr = cqr->refers;      /* check next erp/cqr in queue */
2437
2438         } while ((cqr->refers != NULL) && (!match));
2439
2440         if (!match) {
2441                 return NULL;    /* no match was found */
2442         }
2443
2444         return erp_match;       /* return address of matching erp */
2445
2446 }                               /* END dasd_3990_erp_in_erp */
2447
2448 /*
2449  * DASD_3990_ERP_FURTHER_ERP (24 & 32 byte sense)
2450  *
2451  * DESCRIPTION
2452  *   No retry is left for the current ERP. Check what has to be done 
2453  *   with the ERP.
2454  *     - do further defined ERP action or
2455  *     - wait for interrupt or  
2456  *     - exit with permanent error
2457  *
2458  * PARAMETER
2459  *   erp                ERP which is in progress with no retry left
2460  *
2461  * RETURN VALUES
2462  *   erp                modified/additional ERP
2463  */
2464 static struct dasd_ccw_req *
2465 dasd_3990_erp_further_erp(struct dasd_ccw_req *erp)
2466 {
2467
2468         struct dasd_device *device = erp->device;
2469         char *sense = erp->irb.ecw;
2470
2471         /* check for 24 byte sense ERP */
2472         if ((erp->function == dasd_3990_erp_bus_out) ||
2473             (erp->function == dasd_3990_erp_action_1) ||
2474             (erp->function == dasd_3990_erp_action_4)) {
2475
2476                 erp = dasd_3990_erp_action_1(erp);
2477
2478         } else if (erp->function == dasd_3990_erp_action_5) {
2479
2480                 /* retries have not been successful */
2481                 /* prepare erp for retry on different channel path */
2482                 erp = dasd_3990_erp_action_1(erp);
2483
2484                 if (!(sense[2] & DASD_SENSE_BIT_0)) {
2485
2486                         /* issue a Diagnostic Control command with an 
2487                          * Inhibit Write subcommand */
2488
2489                         switch (sense[25]) {
2490                         case 0x17:
2491                         case 0x57:{     /* controller */
2492                                         erp = dasd_3990_erp_DCTL(erp, 0x20);
2493                                         break;
2494                                 }
2495                         case 0x18:
2496                         case 0x58:{     /* channel path */
2497                                         erp = dasd_3990_erp_DCTL(erp, 0x40);
2498                                         break;
2499                                 }
2500                         case 0x19:
2501                         case 0x59:{     /* storage director */
2502                                         erp = dasd_3990_erp_DCTL(erp, 0x80);
2503                                         break;
2504                                 }
2505                         default:
2506                                 DEV_MESSAGE(KERN_DEBUG, device,
2507                                             "invalid subcommand modifier 0x%x "
2508                                             "for Diagnostic Control Command",
2509                                             sense[25]);
2510                         }
2511                 }
2512
2513                 /* check for 32 byte sense ERP */
2514         } else if ((erp->function == dasd_3990_erp_compound_retry) ||
2515                    (erp->function == dasd_3990_erp_compound_path) ||
2516                    (erp->function == dasd_3990_erp_compound_code) ||
2517                    (erp->function == dasd_3990_erp_compound_config)) {
2518
2519                 erp = dasd_3990_erp_compound(erp, sense);
2520
2521         } else {
2522                 /* No retry left and no additional special handling */
2523                 /*necessary */
2524                 DEV_MESSAGE(KERN_ERR, device,
2525                             "no retries left for erp %p - "
2526                             "set status to FAILED", erp);
2527
2528                 erp->status = DASD_CQR_FAILED;
2529         }
2530
2531         return erp;
2532
2533 }                               /* end dasd_3990_erp_further_erp */
2534
2535 /*
2536  * DASD_3990_ERP_HANDLE_MATCH_ERP 
2537  *
2538  * DESCRIPTION
2539  *   An error occurred again and an ERP has been detected which is already
2540  *   used to handle this error (e.g. retries). 
2541  *   All prior ERP's are asumed to be successful and therefore removed
2542  *   from queue.
2543  *   If retry counter of matching erp is already 0, it is checked if further 
2544  *   action is needed (besides retry) or if the ERP has failed.
2545  *
2546  * PARAMETER
2547  *   erp_head           first ERP in ERP-chain
2548  *   erp                ERP that handles the actual error.
2549  *                      (matching erp)
2550  *
2551  * RETURN VALUES
2552  *   erp                modified/additional ERP
2553  */
2554 static struct dasd_ccw_req *
2555 dasd_3990_erp_handle_match_erp(struct dasd_ccw_req *erp_head,
2556                                struct dasd_ccw_req *erp)
2557 {
2558
2559         struct dasd_device *device = erp_head->device;
2560         struct dasd_ccw_req *erp_done = erp_head;       /* finished req */
2561         struct dasd_ccw_req *erp_free = NULL;   /* req to be freed */
2562
2563         /* loop over successful ERPs and remove them from chanq */
2564         while (erp_done != erp) {
2565
2566                 if (erp_done == NULL)   /* end of chain reached */
2567                         panic(PRINTK_HEADER "Programming error in ERP! The "
2568                               "original request was lost\n");
2569
2570                 /* remove the request from the device queue */
2571                 list_del(&erp_done->list);
2572
2573                 erp_free = erp_done;
2574                 erp_done = erp_done->refers;
2575
2576                 /* free the finished erp request */
2577                 dasd_free_erp_request(erp_free, erp_free->device);
2578
2579         }                       /* end while */
2580
2581         if (erp->retries > 0) {
2582
2583                 char *sense = erp->refers->irb.ecw;
2584
2585                 /* check for special retries */
2586                 if (erp->function == dasd_3990_erp_action_4) {
2587
2588                         erp = dasd_3990_erp_action_4(erp, sense);
2589
2590                 } else if (erp->function == dasd_3990_erp_action_1B_32) {
2591
2592                         erp = dasd_3990_update_1B(erp, sense);
2593
2594                 } else if (erp->function == dasd_3990_erp_int_req) {
2595
2596                         erp = dasd_3990_erp_int_req(erp);
2597
2598                 } else {
2599                         /* simple retry   */
2600                         DEV_MESSAGE(KERN_DEBUG, device,
2601                                     "%i retries left for erp %p",
2602                                     erp->retries, erp);
2603
2604                         /* handle the request again... */
2605                         erp->status = DASD_CQR_QUEUED;
2606                 }
2607
2608         } else {
2609                 /* no retry left - check for further necessary action    */
2610                 /* if no further actions, handle rest as permanent error */
2611                 erp = dasd_3990_erp_further_erp(erp);
2612         }
2613
2614         return erp;
2615
2616 }                               /* end dasd_3990_erp_handle_match_erp */
2617
2618 /*
2619  * DASD_3990_ERP_ACTION
2620  *
2621  * DESCRIPTION
2622  *   controll routine for 3990 erp actions.
2623  *   Has to be called with the queue lock (namely the s390_irq_lock) acquired.
2624  *
2625  * PARAMETER
2626  *   cqr                failed cqr (either original cqr or already an erp)
2627  *
2628  * RETURN VALUES
2629  *   erp                erp-pointer to the head of the ERP action chain.
2630  *                      This means:
2631  *                       - either a ptr to an additional ERP cqr or
2632  *                       - the original given cqr (which's status might 
2633  *                         be modified)
2634  */
2635 struct dasd_ccw_req *
2636 dasd_3990_erp_action(struct dasd_ccw_req * cqr)
2637 {
2638
2639         struct dasd_ccw_req *erp = NULL;
2640         struct dasd_device *device = cqr->device;
2641         __u32 cpa = cqr->irb.scsw.cpa;
2642
2643 #ifdef ERP_DEBUG
2644         /* print current erp_chain */
2645         DEV_MESSAGE(KERN_ERR, device, "%s",
2646                     "ERP chain at BEGINNING of ERP-ACTION");
2647         {
2648                 struct dasd_ccw_req *temp_erp = NULL;
2649
2650                 for (temp_erp = cqr;
2651                      temp_erp != NULL; temp_erp = temp_erp->refers) {
2652
2653                         DEV_MESSAGE(KERN_ERR, device,
2654                                     "   erp %p (%02x) refers to %p",
2655                                     temp_erp, temp_erp->status,
2656                                     temp_erp->refers);
2657                 }
2658         }
2659 #endif                          /* ERP_DEBUG */
2660
2661         /* double-check if current erp/cqr was successfull */
2662         if ((cqr->irb.scsw.cstat == 0x00) &&
2663             (cqr->irb.scsw.dstat == (DEV_STAT_CHN_END|DEV_STAT_DEV_END))) {
2664
2665                 DEV_MESSAGE(KERN_DEBUG, device,
2666                             "ERP called for successful request %p"
2667                             " - NO ERP necessary", cqr);
2668
2669                 cqr->status = DASD_CQR_DONE;
2670
2671                 return cqr;
2672         }
2673         /* check if sense data are available */
2674         if (!cqr->irb.ecw) {
2675                 DEV_MESSAGE(KERN_DEBUG, device,
2676                             "ERP called witout sense data avail ..."
2677                             "request %p - NO ERP possible", cqr);
2678
2679                 cqr->status = DASD_CQR_FAILED;
2680
2681                 return cqr;
2682
2683         }
2684
2685         /* check if error happened before */
2686         erp = dasd_3990_erp_in_erp(cqr);
2687
2688         if (erp == NULL) {
2689                 /* no matching erp found - set up erp */
2690                 erp = dasd_3990_erp_additional_erp(cqr);
2691         } else {
2692                 /* matching erp found - set all leading erp's to DONE */
2693                 erp = dasd_3990_erp_handle_match_erp(cqr, erp);
2694         }
2695
2696 #ifdef ERP_DEBUG
2697         /* print current erp_chain */
2698         DEV_MESSAGE(KERN_ERR, device, "%s", "ERP chain at END of ERP-ACTION");
2699         {
2700                 struct dasd_ccw_req *temp_erp = NULL;
2701                 for (temp_erp = erp;
2702                      temp_erp != NULL; temp_erp = temp_erp->refers) {
2703
2704                         DEV_MESSAGE(KERN_ERR, device,
2705                                     "   erp %p (%02x) refers to %p",
2706                                     temp_erp, temp_erp->status,
2707                                     temp_erp->refers);
2708                 }
2709         }
2710 #endif                          /* ERP_DEBUG */
2711
2712         if (erp->status == DASD_CQR_FAILED)
2713                 dasd_log_ccw(erp, 1, cpa);
2714
2715         /* enqueue added ERP request */
2716         if (erp->status == DASD_CQR_FILLED) {
2717                 erp->status = DASD_CQR_QUEUED;
2718                 list_add(&erp->list, &device->ccw_queue);
2719         }
2720
2721         return erp;
2722
2723 }                               /* end dasd_3990_erp_action */
2724
2725 /*
2726  * Overrides for Emacs so that we follow Linus's tabbing style.
2727  * Emacs will notice this stuff at the end of the file and automatically
2728  * adjust the settings for this buffer only.  This must remain at the end
2729  * of the file.
2730  * ---------------------------------------------------------------------------
2731  * Local variables:
2732  * c-indent-level: 4 
2733  * c-brace-imaginary-offset: 0
2734  * c-brace-offset: -4
2735  * c-argdecl-indent: 4
2736  * c-label-offset: -4
2737  * c-continued-statement-offset: 4
2738  * c-continued-brace-offset: 0
2739  * indent-tabs-mode: 1
2740  * tab-width: 8
2741  * End:
2742  */