Inhalt

8. Inquiry Kommandobeispiel

Eines der elementarsten SCSI-Kommandos ist das INQUIRY Kommando, das zur Identifikation des SCSI-Geräts verwendet wird. Hier ist die Definition aus der SCSI-2 Spezifikation (weitere Details sind dem SCSI-2 Standard zu entnehmen).

                            Tabelle 44: INQUIRY Command
+=====-========-========-========-========-========-========-========-========+
|  Bit|   7    |   6    |   5    |   4    |   3    |   2    |   1    |   0    |
|Byte |        |        |        |        |        |        |        |        |
|=====+=======================================================================|
| 0   |                           Operation Code (12h)                        |
|-----+-----------------------------------------------------------------------|
| 1   | Logical Unit Number      |                  Reserved         |  EVPD  |
|-----+-----------------------------------------------------------------------|
| 2   |                           Page Code                                   |
|-----+-----------------------------------------------------------------------|
| 3   |                           Reserved                                    |
|-----+-----------------------------------------------------------------------|
| 4   |                           Allocation Length                           |
|-----+-----------------------------------------------------------------------|
| 5   |                           Control                                     |
+=============================================================================+

Die Ausgabedaten sind dann wie folgt:

                     Tabelle 45: Standard INQUIRY Data Format
+=====-========-========-========-========-========-========-========-========+
|  Bit|   7    |   6    |   5    |   4    |   3    |   2    |   1    |   0    |
|Byte |        |        |        |        |        |        |        |        |
|=====+==========================+============================================|
| 0   | Peripheral Qualifier     |           Peripheral Device Type           |
|-----+-----------------------------------------------------------------------|
| 1   |  RMB   |                  Device-Type Modifier                        |
|-----+-----------------------------------------------------------------------|
| 2   |   ISO Version   |       ECMA Version       |  ANSI-Approved Version   |
|-----+-----------------+-----------------------------------------------------|
| 3   |  AENC  | TrmIOP |     Reserved    |         Response Data Format      |
|-----+-----------------------------------------------------------------------|
| 4   |                           Additional Length (n-4)                     |
|-----+-----------------------------------------------------------------------|
| 5   |                           Reserved                                    |
|-----+-----------------------------------------------------------------------|
| 6   |                           Reserved                                    |
|-----+-----------------------------------------------------------------------|
| 7   | RelAdr | WBus32 | WBus16 |  Sync  | Linked |Reserved| CmdQue | SftRe  |
|-----+-----------------------------------------------------------------------|
| 8   | (MSB)                                                                 |
|- - -+---                        Vendor Identification                    ---|
| 15  |                                                                 (LSB) |
|-----+-----------------------------------------------------------------------|
| 16  | (MSB)                                                                 |
|- - -+---                        Product Identification                   ---|
| 31  |                                                                 (LSB) |
|-----+-----------------------------------------------------------------------|
| 32  | (MSB)                                                                 |
|- - -+---                        Product Revision Level                   ---|
| 35  |                                                                 (LSB) |
|-----+-----------------------------------------------------------------------|
| 36  |                                                                       |
|- - -+---                        Vendor Specific                          ---|
| 55  |                                                                       |
|-----+-----------------------------------------------------------------------|
| 56  |                                                                       |
|- - -+---                        Reserved                                 ---|
| 95  |                                                                       |
|=====+=======================================================================|
|     |                       Vendor-Specific Parameters                      |
|=====+=======================================================================|
| 96  |                                                                       |
|- - -+---                        Vendor Specific                          ---|
| n   |                                                                       |
+=============================================================================+

Das folgende Beispiel benutzt die Lowlevel-Funktion handle_SCSI_cmd zum Abschicken des Inquiry SCSI Kommandos.

Zuerst hängen wir den Kommandoblock an den generischen Header, dann rufen wir handle_SCSI_cmd auf. Bitte beachte, daß der Parameter für die Größe des Ausgabepuffers die Kopfstrukturgröße nicht beinhaltet. Nach Abarbeitung des Kommandos enthält der Ausgabepuffer die angeforderte Information, falls kein Fehler vorlag.

#define INQUIRY_CMD     0x12
#define INQUIRY_CMDLEN  6
#define INQUIRY_REPLY_LEN 96
#define INQUIRY_VENDOR  8       /* Versatz zum Herstellernamen im Antwortblock */

/* Herstellernamen und Typ anfordern */
static unsigned char *Inquiry ( void )
{
  unsigned char Inqbuffer[ SCSI_OFF + INQUIRY_REPLY_LEN ];
  unsigned char cmdblk [ INQUIRY_CMDLEN ] = 
      { INQUIRY_CMD,  /* Kommando */
                  0,  /* lun/reserviert */
                  0,  /* page code */
                  0,  /* reserviert */
  INQUIRY_REPLY_LEN,  /* Allokationslänge */
                  0 };/* reserviert/flag/link */

  memcpy( cmd + SCSI_OFF, cmdblk, sizeof(cmdblk) );

  /*
   * +------------------+
   * | struct sg_header | <- cmd
   * +------------------+
   * | Kopie von cmdblk | <- cmd + SCSI_OFF
   * +------------------+
   */

  if (handle_SCSI_cmd(sizeof(cmdblk), 0, cmd, 
                      sizeof(Inqbuffer) - SCSI_OFF, Inqbuffer )) {
      fprintf( stderr, "Inquiry scheiterte\n" );
      exit(2);
  }
  return (Inqbuffer + SCSI_OFF);
}

Das oben angegebene Beispiel hält sich an diese Struktur. Die Inquiry-Funktion kopiert ihren Kommandoblock hinter den generischen Kopf (durch SCSI_OFF gegeben). Dieser Befehl hat keine weiteren Daten zu übergeben. Funktion Handle_SCSI_cmd erzeugt daraus die Kopfstruktur.

Um das Beispiel vollständig zu machen, implementieren wir nun noch die Funktion main.

int main( void )
{
  fd = open(DEVICE, O_RDWR);
  if (fd < 0) {
    fprintf( stderr, "Lese-Schreiberlaubnis erforderlich für "DEVICE".\n" 
);
    exit(1);
  }

  /* ein paar Felder des Inquiry-Ergebnisses ausgeben */
  printf( "%s\n", Inquiry() + INQUIRY_VENDOR );
  return 0;
}

Zuerst öffnen wir das Gerät, prüfen auf Fehler und rufen dann das Unterprogramm Inquiry auf. Die Ergebnisse Hersteller, Produkt und Version werden schließlich in lesbarer Form ausgegeben.

Hinweis: Der Inquiry-Befehl liefert noch weitere Informationen, mehr als diese kleine Programm ausgibt. Vielleicht möchtest Du es so erweitern, daß Gerätetyp, ANSI-Version usw. behandelt werden. Der Gerätetyp ist zum Beispiel von besonderer Bedeutung, da er für das Gerät den festen (minimalen) und erweiterten Befehlsumfang festlegt. Wenn Du das nicht selbst programmieren möchtest, gibt es auch noch das Programm scsiinfo von Eric Youngdale. Es liefert nahezu alle Angaben zu einem SCSI-Gerät. Du findest es per FTP unter:

tsx-11.mit.edu:/pub/Linux/ALPHA/scsi


Inhalt