⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 scsidirectlib.c

📁 VxWorks BSP框架源代码包含头文件和驱动
💻 C
📖 第 1 页 / 共 3 页
字号:
* transferred is greater than the maximum transfer length it breaks the* data into permissible sizes and loops until the transfer is done.** RETURNS: OK, or ERROR if the sector cannot be written, or if the numSecs* is zero.*/LOCAL STATUS scsi2WrtSecs    (    SCSI_BLK_DEV *pScsiBlkDev,  /* ptr to SCSI block device info */    int sector,                 /* sector number to be read */    int numSecs,                /* total sectors to be read */    char *buffer                /* ptr to input data buffer */    )    {    SCSI_PHYS_DEV *pScsiPhysDev = pScsiBlkDev->pScsiPhysDev;    int dataToXfer;             /* Total Transfer size */    int sectorNum;               /* sector number to be written */    int numbSecs;               /* total sectors to be written */    char *xferBuf;              /* ptr to input data buffer    */    STATUS xferStatus = OK;    dataToXfer = numSecs * pScsiPhysDev->blockSize;    xferBuf = buffer;    sectorNum = sector;    if (numSecs == 0)	return ERROR;    if (dataToXfer <= (pScsiPhysDev->pScsiCtrl->maxBytesPerXfer))	xferStatus = scsiSectorWrite (pScsiBlkDev,sector,numSecs,buffer);    else	{	while (dataToXfer > 0)	    {	    /* determine the number of sectors to written */	    	    if (dataToXfer > (pScsiPhysDev->pScsiCtrl->maxBytesPerXfer))		numbSecs = (pScsiPhysDev->pScsiCtrl->maxBytesPerXfer) / 			    pScsiPhysDev->blockSize;	    else		numbSecs = dataToXfer / pScsiPhysDev->blockSize;	    	    /* write the sectors */	    	    xferStatus = scsiSectorWrite (pScsiBlkDev,sectorNum,numbSecs,					  xferBuf);	    	    if (xferStatus == OK)		{		/* 		 * increment the sector no, buffer pointers & update the		 * bytes left to be transferred		 */				sectorNum += numbSecs;		xferBuf += (numbSecs * pScsiPhysDev->blockSize);		dataToXfer -= (numbSecs * pScsiPhysDev->blockSize);		}	    else		return (xferStatus);	    }	}    return (xferStatus);    }/********************************************************************************* scsiSectorWrite - write sector(s) to a SCSI block device** This routine writes the specified physical sector(s) to a specified physical* device.** RETURNS: OK, or ERROR if the sector cannot be written.*/LOCAL STATUS scsiSectorWrite    (    SCSI_BLK_DEV *pScsiBlkDev,  /* ptr to SCSI block device info */    int sector,                 /* sector number to be read */    int numSecs,                /* total sectors to be read */    char *buffer                /* ptr to input data buffer */    )    {    SCSI_COMMAND writeCommand;		/* SCSI command byte array */    SCSI_TRANSACTION scsiXaction;	/* info on a SCSI transaction */    SCSI_PHYS_DEV *pScsiPhysDev = pScsiBlkDev->pScsiPhysDev;    int startSec = sector + pScsiBlkDev->blockOffset;    SCSI_DEBUG_MSG ("scsiWrtSecs:\n", 0, 0, 0, 0, 0, 0);    if (startSec <= SCSI_BLOCK_ADDRESS_SIZE && numSecs <= 256)        {        /* build a 21 bit logical block address 'WRITE' command */	if (scsiCmdBuild (writeCommand, &scsiXaction.cmdLength,			  SCSI_OPCODE_WRITE, pScsiPhysDev->scsiDevLUN, FALSE,			  startSec, (numSecs == 256 ? 0 : numSecs), (UINT8) 0)	    == ERROR)	    {	    return (ERROR);	    }        }    else        {        /* build a 32 bit logical block address 'WRITE_EXTENDED' command */		if (scsiCmdBuild (writeCommand, &scsiXaction.cmdLength,			  SCSI_OPCODE_WRITE_EXT, pScsiPhysDev->scsiDevLUN,			  FALSE, startSec, numSecs, (UINT8) 0) == ERROR)	    return (ERROR);        }        scsiXaction.cmdAddress    = writeCommand;    scsiXaction.dataAddress   = (UINT8 *) buffer;    scsiXaction.dataDirection = O_WRONLY;    scsiXaction.dataLength    = numSecs * pScsiPhysDev->blockSize;    scsiXaction.addLengthByte = NONE;    scsiXaction.tagType       = SCSI_TAG_DEFAULT;    scsiXaction.priority      = SCSI_THREAD_TASK_PRIORITY;        if (numSecs < 2000)	scsiXaction.cmdTimeout = SCSI_TIMEOUT_5SEC +				 (SCSI_TIMEOUT_1SEC * numSecs);    else	scsiXaction.cmdTimeout = SCSI_TIMEOUT_FULL;        return ((*pScsiPhysDev->pScsiCtrl->scsiTransact)	    (pScsiPhysDev, &scsiXaction));    }/********************************************************************************* scsiStatusCheck - called by filesystems before doing open()'s or creat()'s** This routine issues a TEST_UNIT_READY command to a SCSI device to detect a* medium change.** RETURNS: OK or ERROR.*/LOCAL STATUS scsiStatusCheck    (    BLK_DEV *pBlkDev                    /* ptr to a block dev */    )    {    SCSI_PHYS_DEV *pScsiPhysDev;        /* ptr to SCSI physical device */    SCSI_COMMAND testUnitRdyCommand;    /* SCSI command byte array */    SCSI_TRANSACTION scsiXaction;       /* info on a SCSI transaction */    pScsiPhysDev = ((SCSI_BLK_DEV *) pBlkDev)->pScsiPhysDev;    if (scsiCmdBuild (testUnitRdyCommand, &scsiXaction.cmdLength,        SCSI_OPCODE_TEST_UNIT_READY, pScsiPhysDev->scsiDevLUN, FALSE,        0, 0, (UINT8) 0) == ERROR)        {        return (ERROR);        }    scsiXaction.cmdAddress    = testUnitRdyCommand;    scsiXaction.dataAddress   = NULL;    scsiXaction.dataDirection = NONE;    scsiXaction.dataLength    = 0;    scsiXaction.addLengthByte = NONE;    scsiXaction.cmdTimeout    = SCSI_TIMEOUT_5SEC;    scsiXaction.tagType       = SCSI_TAG_DEFAULT;    scsiXaction.priority      = SCSI_THREAD_TASK_PRIORITY;    (*pScsiPhysDev->pScsiCtrl->scsiTransact) (pScsiPhysDev, &scsiXaction);    if ((pScsiPhysDev->lastSenseKey != SCSI_SENSE_KEY_NO_SENSE) &&        (pScsiPhysDev->lastSenseKey != SCSI_SENSE_KEY_UNIT_ATTENTION))        {        SCSI_DEBUG_MSG ("scsiStatusCheck returning ERROR, last Sense = %x\n",                        pScsiPhysDev->lastSenseKey, 0, 0, 0, 0, 0);        return (ERROR);        }    else        return (OK);    }/********************************************************************************* scsiBlkDevIoctl - call scsiIoctl() with pointer to SCSI physical device*                   associated with the specified SCSI block device** RETURNS: Status of scsiIoctl call.*/LOCAL STATUS scsiBlkDevIoctl    (    SCSI_BLK_DEV *pScsiBlkDev,  /* ptr to SCSI block device info */    int function,               /* function code */    int arg                     /* argument to pass called function */    )    {    return (scsiIoctl (pScsiBlkDev->pScsiPhysDev, function, arg));    }/********************************************************************************* scsiStartStopUnit - issue a START_STOP_UNIT command to a SCSI device** This routine issues a START_STOP_UNIT command to a specified SCSI device.** RETURNS: OK, or ERROR if the command fails.*/STATUS scsiStartStopUnit    (    SCSI_PHYS_DEV *pScsiPhysDev,  /* ptr to SCSI physical device */    BOOL start                    /* TRUE == start, FALSE == stop */    )    {    SCSI_COMMAND startStopCommand;      /* SCSI command byte array */    SCSI_TRANSACTION scsiXaction;       /* info on a SCSI transaction */    SCSI_DEBUG_MSG ("scsiStartStopUnit:\n", 0, 0, 0, 0, 0, 0);    if (scsiCmdBuild (startStopCommand, &scsiXaction.cmdLength,        SCSI_OPCODE_START_STOP_UNIT, pScsiPhysDev->scsiDevLUN, FALSE,        0, 1, (UINT8) 0)        == ERROR)        {        return (ERROR);        }    scsiXaction.cmdAddress    = startStopCommand;    scsiXaction.dataDirection = O_RDONLY;    scsiXaction.dataLength    = 0;    scsiXaction.addLengthByte = NONE;    scsiXaction.cmdTimeout    = SCSI_TIMEOUT_5SEC;    scsiXaction.tagType       = SCSI_TAG_DEFAULT;    scsiXaction.priority      = SCSI_THREAD_TASK_PRIORITY;    return ((*pScsiPhysDev->pScsiCtrl->scsiTransact)            (pScsiPhysDev, &scsiXaction));    }/********************************************************************************* scsiReserve - issue a RESERVE command to a SCSI device** This routine issues a RESERVE command to a specified SCSI device.** RETURNS: OK, or ERROR if the command fails.*/STATUS scsiReserve    (    SCSI_PHYS_DEV *pScsiPhysDev         /* ptr to SCSI physical device */    )    {    SCSI_COMMAND reserveCommand;        /* SCSI command byte array */    SCSI_TRANSACTION scsiXaction;       /* info on a SCSI transaction */    SCSI_DEBUG_MSG ("scsiReserve:\n", 0, 0, 0, 0, 0, 0);    if (scsiCmdBuild (reserveCommand, &scsiXaction.cmdLength,        SCSI_OPCODE_RESERVE, pScsiPhysDev->scsiDevLUN, FALSE,        0, 0, (UINT8) 0)        == ERROR)        {        return (ERROR);        }    scsiXaction.cmdAddress    = reserveCommand;    scsiXaction.dataDirection = O_RDONLY;    scsiXaction.dataLength    = 0;    scsiXaction.addLengthByte = NONE;    scsiXaction.cmdTimeout    = SCSI_TIMEOUT_5SEC;    scsiXaction.tagType       = SCSI_TAG_DEFAULT;    scsiXaction.priority      = SCSI_THREAD_TASK_PRIORITY;    return ((*pScsiPhysDev->pScsiCtrl->scsiTransact)            (pScsiPhysDev, &scsiXaction));    }/********************************************************************************* scsiRelease - issue a RELEASE command to a SCSI device** This routine issues a RELEASE command to a specified SCSI device.** RETURNS: OK, or ERROR if the command fails.*/STATUS scsiRelease    (    SCSI_PHYS_DEV *pScsiPhysDev         /* ptr to SCSI physical device */    )    {    SCSI_COMMAND releaseCommand;        /* SCSI command byte array */    SCSI_TRANSACTION scsiXaction;       /* info on a SCSI transaction */    SCSI_DEBUG_MSG ("scsiRelease:\n", 0, 0, 0, 0, 0, 0);    if (scsiCmdBuild (releaseCommand, &scsiXaction.cmdLength,        SCSI_OPCODE_RELEASE, pScsiPhysDev->scsiDevLUN, FALSE,        0, 0, (UINT8) 0)        == ERROR)        {        return (ERROR);        }    scsiXaction.cmdAddress    = releaseCommand;    scsiXaction.dataDirection = O_RDONLY;    scsiXaction.dataLength    = 0;    scsiXaction.addLengthByte = NONE;    scsiXaction.cmdTimeout    = SCSI_TIMEOUT_5SEC;    scsiXaction.tagType       = SCSI_TAG_DEFAULT;    scsiXaction.priority      = SCSI_THREAD_TASK_PRIORITY;    return ((*pScsiPhysDev->pScsiCtrl->scsiTransact)            (pScsiPhysDev, &scsiXaction));    }

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -