ide-lib.c 3.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145
  1. #include <linux/types.h>
  2. #include <linux/string.h>
  3. #include <linux/kernel.h>
  4. #include <linux/export.h>
  5. #include <linux/interrupt.h>
  6. #include <linux/ide.h>
  7. #include <linux/bitops.h>
  8. u64 ide_get_lba_addr(struct ide_cmd *cmd, int lba48)
  9. {
  10. struct ide_taskfile *tf = &cmd->tf;
  11. u32 high, low;
  12. low = (tf->lbah << 16) | (tf->lbam << 8) | tf->lbal;
  13. if (lba48) {
  14. tf = &cmd->hob;
  15. high = (tf->lbah << 16) | (tf->lbam << 8) | tf->lbal;
  16. } else
  17. high = tf->device & 0xf;
  18. return ((u64)high << 24) | low;
  19. }
  20. EXPORT_SYMBOL_GPL(ide_get_lba_addr);
  21. static void ide_dump_sector(ide_drive_t *drive)
  22. {
  23. struct ide_cmd cmd;
  24. struct ide_taskfile *tf = &cmd.tf;
  25. u8 lba48 = !!(drive->dev_flags & IDE_DFLAG_LBA48);
  26. memset(&cmd, 0, sizeof(cmd));
  27. if (lba48) {
  28. cmd.valid.in.tf = IDE_VALID_LBA;
  29. cmd.valid.in.hob = IDE_VALID_LBA;
  30. cmd.tf_flags = IDE_TFLAG_LBA48;
  31. } else
  32. cmd.valid.in.tf = IDE_VALID_LBA | IDE_VALID_DEVICE;
  33. ide_tf_readback(drive, &cmd);
  34. if (lba48 || (tf->device & ATA_LBA))
  35. printk(KERN_CONT ", LBAsect=%llu",
  36. (unsigned long long)ide_get_lba_addr(&cmd, lba48));
  37. else
  38. printk(KERN_CONT ", CHS=%d/%d/%d", (tf->lbah << 8) + tf->lbam,
  39. tf->device & 0xf, tf->lbal);
  40. }
  41. static void ide_dump_ata_error(ide_drive_t *drive, u8 err)
  42. {
  43. printk(KERN_CONT "{ ");
  44. if (err & ATA_ABORTED)
  45. printk(KERN_CONT "DriveStatusError ");
  46. if (err & ATA_ICRC)
  47. printk(KERN_CONT "%s",
  48. (err & ATA_ABORTED) ? "BadCRC " : "BadSector ");
  49. if (err & ATA_UNC)
  50. printk(KERN_CONT "UncorrectableError ");
  51. if (err & ATA_IDNF)
  52. printk(KERN_CONT "SectorIdNotFound ");
  53. if (err & ATA_TRK0NF)
  54. printk(KERN_CONT "TrackZeroNotFound ");
  55. if (err & ATA_AMNF)
  56. printk(KERN_CONT "AddrMarkNotFound ");
  57. printk(KERN_CONT "}");
  58. if ((err & (ATA_BBK | ATA_ABORTED)) == ATA_BBK ||
  59. (err & (ATA_UNC | ATA_IDNF | ATA_AMNF))) {
  60. struct request *rq = drive->hwif->rq;
  61. ide_dump_sector(drive);
  62. if (rq)
  63. printk(KERN_CONT ", sector=%llu",
  64. (unsigned long long)blk_rq_pos(rq));
  65. }
  66. printk(KERN_CONT "\n");
  67. }
  68. static void ide_dump_atapi_error(ide_drive_t *drive, u8 err)
  69. {
  70. printk(KERN_CONT "{ ");
  71. if (err & ATAPI_ILI)
  72. printk(KERN_CONT "IllegalLengthIndication ");
  73. if (err & ATAPI_EOM)
  74. printk(KERN_CONT "EndOfMedia ");
  75. if (err & ATA_ABORTED)
  76. printk(KERN_CONT "AbortedCommand ");
  77. if (err & ATA_MCR)
  78. printk(KERN_CONT "MediaChangeRequested ");
  79. if (err & ATAPI_LFS)
  80. printk(KERN_CONT "LastFailedSense=0x%02x ",
  81. (err & ATAPI_LFS) >> 4);
  82. printk(KERN_CONT "}\n");
  83. }
  84. /**
  85. * ide_dump_status - translate ATA/ATAPI error
  86. * @drive: drive that status applies to
  87. * @msg: text message to print
  88. * @stat: status byte to decode
  89. *
  90. * Error reporting, in human readable form (luxurious, but a memory hog).
  91. * Combines the drive name, message and status byte to provide a
  92. * user understandable explanation of the device error.
  93. */
  94. u8 ide_dump_status(ide_drive_t *drive, const char *msg, u8 stat)
  95. {
  96. u8 err = 0;
  97. printk(KERN_ERR "%s: %s: status=0x%02x { ", drive->name, msg, stat);
  98. if (stat & ATA_BUSY)
  99. printk(KERN_CONT "Busy ");
  100. else {
  101. if (stat & ATA_DRDY)
  102. printk(KERN_CONT "DriveReady ");
  103. if (stat & ATA_DF)
  104. printk(KERN_CONT "DeviceFault ");
  105. if (stat & ATA_DSC)
  106. printk(KERN_CONT "SeekComplete ");
  107. if (stat & ATA_DRQ)
  108. printk(KERN_CONT "DataRequest ");
  109. if (stat & ATA_CORR)
  110. printk(KERN_CONT "CorrectedError ");
  111. if (stat & ATA_SENSE)
  112. printk(KERN_CONT "Sense ");
  113. if (stat & ATA_ERR)
  114. printk(KERN_CONT "Error ");
  115. }
  116. printk(KERN_CONT "}\n");
  117. if ((stat & (ATA_BUSY | ATA_ERR)) == ATA_ERR) {
  118. err = ide_read_error(drive);
  119. printk(KERN_ERR "%s: %s: error=0x%02x ", drive->name, msg, err);
  120. if (drive->media == ide_disk)
  121. ide_dump_ata_error(drive, err);
  122. else
  123. ide_dump_atapi_error(drive, err);
  124. }
  125. printk(KERN_ERR "%s: possibly failed opcode: 0x%02x\n",
  126. drive->name, drive->hwif->cmd.tf.command);
  127. return err;
  128. }
  129. EXPORT_SYMBOL(ide_dump_status);