home *** CD-ROM | disk | FTP | other *** search
- *===================================================================*
- * *
- * Example program demonstrating the various methods of talking to *
- * the SCRAM 500 device driver. *
- * *
- * Both standard and SCSI-Direct methods are demonstrated. *
- * *
- * The code is verbosely commented to make it simple to understand *
- * but some knowledge of 68000 assembler programming on the part of *
- * the reader is assumed. *
- * *
- * All code by Will McGovern. (yes, I wrote the driver as well !!) *
- * *
- * BLATENT AD ==> For a custom written driver for your hardware, *
- * send inquiries to : *
- * *
- * Will McGovern *
- * PO Box 247, *
- * NEW LABTON, *
- * NSW 2289 *
- * AUSTRALIA *
- * *
- * The code is written to be assembled with Macro68 from DigiSoft *
- * but can be converted to other formats with ease. Any Macro68 *
- * specific directives are explained. *
- * *
- * The 2.0 include files are used for all symbols and equates. *
- * *
- * THIS CODE IS COMPLETELY PUBLIC DOMAIN. USE IT HOWEVER YOU WANT !! *
- *===================================================================*
-
- Macro68 assembler directives
-
- mc68000 ;68000 mode
- strict ;strict syntax mode
- exeobj ;executable object file
- objfile 'example' ;object filename
-
- SYS : Call system vector macro
-
- sys macro
- jsr(_LVO\1,a6)
- endm
-
- *------------------------------------------------------------------
-
- EXAMPLE_UNIT equ 0 ;scsi unit to talk to
- BLOCK_SIZE equ $200 ;size of 512 byte block
- MAXAUTO_SIZE equ $fe ;maximum autosense size
- MAXINQUIRY_SIZE equ $fe ;maximum # of inquiry bytes
-
- *------------------------------------------------------------------
-
- section excode,code
-
- Find this task and see if we started from workbench or from a CLI
-
- start movea.l (4).w,a6 ;exec library base
- suba.l a1,a1 ;this task
- sys FindTask ;find this task
- movea.l d0,a4 ;save task pointer
- tst.l (pr_CLI,a4) ;did we come from a CLI ?
- bne.s clistartup ;branch if CLI entry
-
- Discard the workbench startup msg
-
- lea (pr_MsgPort,a4),a0 ;this task's message port
- sys WaitPort ;wait for WB startup message
- lea (pr_MsgPort,a4),a0 ;this task's message port
- sys GetMsg ;fetch the startup message
-
- Initialise a message port (MP) for use with my IORequest structure
-
- clistartup movea.l #mymp,a2 ;my message port
- move.l a4,(MP_SIGTASK,a2) ;save pointer to this task
- moveq #-1,d0 ;any signal will do
- sys AllocSignal ;allocate a signal for MP
- move.b d0,(MP_SIGBIT,a2) ;save signal # in MP
- bmi nosignal ;branch if error
- movea.l a2,a1 ;copy MP pointer
- sys AddPort ;add my MP to the system
- Open scram.device for EXAMPLEUNIT
-
- movea.l #scramname,a0 ;scram.device name
- movea.l #myior,a1 ;my IORequest structure
- move.l a2,(MN_REPLYPORT,a1) ;init MP pointer in IOR
- moveq #EXAMPLE_UNIT,d0 ;scsi unit to talk to
- moveq #0,d1 ;no flags
- sys OpenDevice ;open scram.device
- tst.l d0 ;any errors ?
- bne.b noscramdevice ;branch if error
-
- * Now we can talk to the scram.device through the standard
- * device commands such as CMD_READ or use the HD_SCSICMD command
- * for SCSI-Direct mode.
-
- Here are some examples of normal and SCSI-Direct mode access.
-
-
- Read block 0 from the unit into blockbuffer using CMD_READ command
-
- movea.l #myior,a1 ;IORequest pointer
- move.w #CMD_READ,(IO_COMMAND,a1) ;CMD_READ command
- move.l #blockbuffer,(IO_DATA,a1) ;buffer for data
- clr.l (IO_OFFSET,a1) ;block 0
- move.l #BLOCK_SIZE,(IO_LENGTH,a1) ;one block to read
- sys DoIO ;read the block
- tst.b d0 ;any error ?
- bne.b cmdreaderror ;error if d0 not zero
-
- Now do the same as above in SCSI-Direct mode
-
- movea.l #myior,a1 ;IORequest pointer
- move.w #HD_SCSICMD,(IO_COMMAND,a1) ;CMD_READ command
- move.l #scsireadcmd,(IO_DATA,a1) ;pointer to SCSICmd
- sys DoIO ;read the block
- tst.b d0 ;any error ?
- bne.b scsireaderror ;error if d0 not zero
-
- Perform a SCSI INQUIRY command on the EXAMPLE_UNIT
-
- movea.l #myior,a1 ;IORequest pointer
- move.w #HD_SCSICMD,(IO_COMMAND,a1) ;HD_SCSICMD command
- move.l #scsiinquirycmd,(IO_DATA,a1) ;pointer to SCSICmd
- sys DoIO ;perform inquiry
- tst.b d0 ;any error ?
- beq.b exitexample ;error if d0 not zero
-
- This is where an error handler would be placed if this was serious code
-
- cmdreaderror:
- scsireaderror nop
-
- Clean up our mess and return to DOS
-
- exitexample movea.l #myior,a1 ;pointer to my IORequest
- sys CloseDevice ;close scram.device
- noscramdevice movea.l #mymp,a1 ;pointer to my MP
- sys RemPort ;remove my message port
- moveq #0,d0 ;prepare D0 for byte load
- move.b (mymp+MP_SIGBIT),d0 ;get signal # we allocated
- sys FreeSignal ;free the allocated signal
- nosignal moveq #0,d0 ;clear return code
- rts ;return to DOS
-
- *--------------------------------------------------------------------
-
- section exdata,data
-
-
- Note: The SCSICmd structure used in this example did not appear in the
- early 1.3 include files in its entirety. C= omitted the autosense
- information. See the 2.0 include file "devices/scsidisk.i" for a
- full description of the SCSI-Direct protocol.
-
- Also note that the SCSIF_AUTOSENSE (4 byte sense length) has
- become SCSIF_OLDAUTOSENSE in the 2.0 implementation.
-
- The new SCSIF_AUTOSENSE supports sense data lengths of 4 to 255
- bytes. The sense length is specified in scsi_SenseLength field.
-
- The SCSIF_READ/SCSIF_WRITE flags are NOT required by the scram.device as
- the data direction is determined automatically by the driver.
-
-
- SCSICmd structure for reading block 0
-
- scsireadcmd dc.l blockbuffer ;data buffer address
- dc.l BLOCK_SIZE ;number of bytes to read
- dc.l 0 ;actual bytes read
- dc.l readcmd ;pointer to scsi CDB
- dc.w 10 ;# of command bytes
- dc.w 0 ;actual cmd bytes sent
- dc.b SCSIF_AUTOSENSE ;automatic sense
- dc.b 0 ;status byte
- dc.l sensebuffer ;buffer for sense data
- dc.w MAXAUTO_SIZE ;size of my sense buffer
- dc.w 0 ;actual sense bytes read
-
- SCSICmd structure for an INQUIRY command
-
- scsiinquirycmd dc.l inquirybuffer ;data buffer address
- dc.l MAXINQUIRY_SIZE ;number of bytes to read
- dc.l 0 ;actual bytes read
- dc.l inquirycmd ;pointer to scsi CDB
- dc.w 6 ;# of command bytes
- dc.w 0 ;actual cmd bytes sent
- dc.b SCSIF_AUTOSENSE ;automatic sense
- dc.b 0 ;status byte
- dc.l sensebuffer ;buffer for sense data
- dc.w MAXAUTO_SIZE ;size of my sense buffer
- dc.w 0 ;actual sense bytes read
-
- * Here are the actual command desciptor blocks (CDB's) sent to the
- * selected scsi unit.
- *
- * For more information on these consult the SCSI specifications or the
- * manual for your scsi device.
-
- readcmd dc.w $2800,$0000,$0000,$0000,$0100 ;extended read
- inquirycmd dc.w $1200,$0000,MAXINQUIRY_SIZE<<8
-
- Text and byte data
-
- scramname cstr 'scram.device' ;null terminated name
- even
-
- *--------------------------------------------------------------------
-
- section exbss,data
-
- mymp ds.b MP_SIZE ;my message port structure
- even
- myior ds.b IOSTD_SIZE ;my IORequest structure
- even
- inquirybuffer ds.b MAXINQUIRY_SIZE ;inquiry data buffer
- even
- sensebuffer ds.b MAXAUTO_SIZE ;autosense data buffer
- even
- blockbuffer ds.b BLOCK_SIZE ;block data buffer
- even
-
- *--------------------------------------------------------------------
-
- end
-
-