デジタルフォトミニアルバム(仮2)解析

デジタルフォトミニアルバム(仮)解析 の続き

SPTIによる制御法
http://azuco.smallnews.net/fao/doc/spti.html
DeviceIoControl-SCSI_PASS_THROUGH_DIRECT keeps giving Error 87
http://social.microsoft.com/Forums/en-US/Offtopic/thread/56529bff-ef02-4b67-8dae-bef7a7be0dfd
SCSI read disc structure C++ help
http://cboard.cprogramming.com/cplusplus-programming/113878-scsi-read-disc-structure-cplusplus-help.html
アーカイブ: USB ストレージ – ドライバおよびハードウェア開発者向けの FAQ
http://www.microsoft.com/japan/whdc/archive/usbfaq.mspx
Japan WDK Support Blog : アプリケーションからSCSIコマンドを発行する方法
http://blogs.msdn.com/jpwdkblog/archive/2009/04/15/scsi.aspx

DeviceIoControl と IOCTL_SCSI_PASS_THROUGH_DIRECT をキーワードにして探していくと↑なところに行きつきました。

最初は、SPTIによる制御法を参考にして、直接組んでいたのですが、やっぱり Windows Device Kit(WDK)が必要なようです。つーか、そこにサンプルがあります。

WDKをインストールして、

C:WinDDK6001.18002srcstoragetoolsspti

を見ると、spti.c なソースに IOCTL_SCSI_PASS_THROUGH や IOCTL_SCSI_PASS_THROUGH_DIRECT を指定したサンプルがあります。ちなみに _DIRECT あり/なしの違いを簡単に言うと、読み書きするときのバッファの取り方が違います。_DIRECT なしの場合は、いったんドライバー内部のデータに読み込んだ後にユーザーの指定バッファに転送、_DIRECT ありの場合は、ドライバー内部を経由せずに直接ユーザー指定のバッファに転送します。ってのが、spti.htm に書いてあります。

WDKの入手先は、Microsoft Connect Web サイト か MSDN サブスクリプションとなっています。が、私の見た限り MSDN サブスクリプションには WDK が無い(?) ので、Microsoft Connect Web サイトのほうでダウンロードしました。

ci090527105535

Alcohol 52% でマウントしたCDを以下のソースで読み取ることができたみたいです(データの解析をしていないので、本当に読み込んだかどうかは後日)。

    printf("            *****       READ DATA BUFFER operation         *****n");
 if ( dataBuffer == NULL ) {
      dataBuffer = AllocateAlignedBuffer(sectorSize,alignmentMask, &pUnAlignedBuffer);
 }
    ZeroMemory(&sptdwb, sizeof(SCSI_PASS_THROUGH_DIRECT_WITH_BUFFER));
    ZeroMemory(dataBuffer,sectorSize);</pre>
    sptdwb.sptd.Length = sizeof(SCSI_PASS_THROUGH_DIRECT);
    sptdwb.sptd.PathId = 0;
    sptdwb.sptd.TargetId = 1;
    sptdwb.sptd.Lun = 0;
    sptdwb.sptd.CdbLength = CDB12GENERIC_LENGTH;
    sptdwb.sptd.DataIn = SCSI_IOCTL_DATA_IN;
    sptdwb.sptd.SenseInfoLength = SPT_SENSE_LENGTH;
    sptdwb.sptd.DataTransferLength = 2352; // SPT_SENSE_LENGTH;
    sptdwb.sptd.TimeOutValue = 2;
    sptdwb.sptd.DataBuffer = dataBuffer;
    sptdwb.sptd.SenseInfoOffset =
       offsetof(SCSI_PASS_THROUGH_DIRECT_WITH_BUFFER,ucSenseBuf);
//    sptdwb.sptd.Cdb[0] = SCSIOP_READ_DATA_BUFF;
//    sptdwb.sptd.Cdb[1] = 2;                         // Data mode
//    sptdwb.sptd.Cdb[7] = (UCHAR)(sectorSize >> 8);  // Parameter List length
//    sptdwb.sptd.Cdb[8] = 0;

    sptdwb.sptd.Cdb[0] = SCSIOP_READ_CD;
    sptdwb.sptd.Cdb[2] = 0;                        
    sptdwb.sptd.Cdb[3] = 0;                        
    sptdwb.sptd.Cdb[4] = 0;                        
    sptdwb.sptd.Cdb[5] = 0x10;    // どのセクタを読み込むか
    sptdwb.sptd.Cdb[8] = 1;   // 1セクタ分読み込む
    sptdwb.sptd.Cdb[9] = 0xF8;
    length = sizeof(SCSI_PASS_THROUGH_DIRECT_WITH_BUFFER);

    status = DeviceIoControl(fileHandle,
                             IOCTL_SCSI_PASS_THROUGH_DIRECT,
                             &sptdwb,
                             length,
                             &sptdwb,
                             length,
                             &returned,
                             FALSE);

肝心のデジタルフォトミニアルバムのほうは読み込めない。何故に?というか、CDB(Command Discripter Block)をきちんと設定していないので、まぁそりゃそうなんですが。このあたりのコマンド、どういうのを送るのかと言うのが良くわからん。「SPTIによる制御法」を読むとコマンド仕様については、以下を参照のこと、
Information Specification for ATAPI DVD Devices
ftp://ftp.seagate.com/sff/INF-8090.PDF

となるので、これを詳細に読むのかな?

カテゴリー: 開発 パーマリンク