?? bulkonly.c
字號:
/****************************************Copyright (c)**************************************************
** CH374做主機操作U盤讀寫程序
** Bulk-only傳輸協議層
** 接口函數
**
** VBeat 0.2
**
**--------------文件信息--------------------------------------------------------------------------------
**文 件 名: Bulkonly.C
**創 建 人: 徐亦朱
**最后修改日期: 2007年9月24日
**描 述: 增加部分UFI命令集支持
**
**--------------歷史版本信息----------------------------------------------------------------------------
** 創建人: 徐亦朱
** 版 本: VBeat 0.1
** 日 期: 2007年9月21日
** 描 述: 原始版本
**
**--------------當前版本修訂------------------------------------------------------------------------------
** 修改人: 徐亦朱
** 日 期: 2007年9月24日
** 描 述: 增加部分UFI命令集支持
**
**------------------------------------------------------------------------------------------------------
********************************************************************************************************/
#include <stdio.h>
#include <string.h>
#include "HAL.H"
#include "HAL_BASE2.C"
#include "PARA_HW2.C"
#include "Bulkonly.H"
/*********************************************************************************************************
** 函數名稱: IsDiskConnect
** 功能描述: 檢查磁盤是否連接
**
** 輸 入:
** 輸 出: 返回錯誤碼:
** USB_INT_SUCCESS: 已經連接
** USB_INT_CONNECT: 剛連接
** USB_INT_DISCONNECT: 斷開
**
** 全局變量: 無
** 調用模塊: 無
** 調試碼: 無
**
**
** 作 者: 徐亦朱
** 日 期: 2007年9月21日
**-------------------------------------------------------------------------------------------------------
** 修改人:
** 日 期:
**------------------------------------------------------------------------------------------------------
********************************************************************************************************/
UINT8 IsDiskConnect( void )
{
if ( Read374Byte( REG_INTER_FLAG ) & ( BIT_IF_DEV_DETECT ) ) //檢測到插拔事件
{
SetHostUsbAddr( 0x00 );
HostSetBusFree( ); //USB總線空閑
Write374Byte( REG_INTER_FLAG, BIT_IF_USB_PAUSE | BIT_IF_DEV_DETECT | BIT_IF_TRANSFER ); //清中斷標志
if( Read374Byte( REG_INTER_FLAG ) & BIT_IF_DEV_ATTACH ) //設備剛連接
return( USB_INT_CONNECT );
return( USB_INT_DISCONNECT ); //設備斷開
}
if ( Read374Byte( REG_INTER_FLAG ) & BIT_IF_DEV_ATTACH ) //設備已連接
{
return( USB_INT_SUCCESS );
}
return( USB_INT_DISCONNECT ) ;
}
/*********************************************************************************************************
** 函數名稱: mResetErrorBOC
** 功能描述: USB DISK重置
**
** 輸 入: LastError: 重置前的錯誤碼
** 輸 出: 返回重置前的錯誤碼,即Lastrror
**
** 全局變量: 無
** 調用模塊: 無
** 調試碼: 無
**
**
** 作 者: 徐亦朱
** 日 期: 2007年9月21日
**-------------------------------------------------------------------------------------------------------
** 修改人:
** 日 期:
**------------------------------------------------------------------------------------------------------
********************************************************************************************************/
UINT8 mResetErrorBOC( UINT8 LastError )
{
UINT8 s;
UINT8 ReqBuf[ sizeof( BoResetUsbDisk ) ] ;
s = IsDiskConnect( ); //檢查U盤是否連接
if ( s != USB_INT_SUCCESS ) //斷開或者剛連接
return( s );
memcpy( ReqBuf, BoResetUsbDisk, sizeof( BoResetUsbDisk ) );
( ( PUSB_SETUP_REQ )ReqBuf ) -> wIndexL = mDiskInterfNumber ;
s = HostCtrlTransfer374( ReqBuf, NULL, NULL ) ;
if ( s == USB_INT_DISCONNECT ) //檢測到USB設備斷開事件,磁盤已經斷開
return( s );
mClearEndpStall( mDiskBulkInEndp | 0x80 ) ; //清除IN端點錯誤
mClearEndpStall( mDiskBulkOutEndp ) ; //清除OUT端點錯誤
mSaveDevEndpTog &= ~ ( BIT_HOST_TRAN_TOG | BIT_HOST_RECV_TOG ) ;
return( LastError ) ; //返回原錯誤碼
}
/*********************************************************************************************************
** 函數名稱: mBulkOnlyCmd
** 功能描述: 執行基于Bulk-only協議的命令
**
** 輸 入: DataBuf: 指向數據緩沖區
** 輸 出:
**
** 全局變量: 無
** 調用模塊: 無
** 調試碼: 無
**
**
** 作 者: 徐亦朱
** 日 期: 2007年9月21日
**-------------------------------------------------------------------------------------------------------
** 修改人:
** 日 期:
**------------------------------------------------------------------------------------------------------
********************************************************************************************************/
UINT8 mBulkOnlyCmd( PUINT8 DataBuf )
{
UINT8 s ;
UINT8 len ;
UINT32 TotalLen ;
UINT32 DataLength ;
mBOC.mCBW.mCBW_Sig = USB_BO_CBW_SIG ;
mBOC.mCBW.mCBW_Tag = 0x03740374 ;
mBOC.mCBW.mCBW_LUN = 0;
//向CH374主機端點的發送緩沖區寫入CBW
Write374Block( RAM_HOST_TRAN, USB_BO_CBW_SIZE, ( PUINT8 )( & mBOC.mCBW ) ) ;
Write374Byte( REG_USB_LENGTH, USB_BO_CBW_SIZE );
mSetBulkOut( ) ;
s = HostTransactInter( ); //向USB盤的OUT端點輸出CBW
if ( s == USB_INT_DISCONNECT ) //檢測到USB設備斷開事件,磁盤已經斷開
{
return( s ) ;
printf ( " 檢測到USB設備斷開事件,磁盤已經斷開 \n " ) ;
}
if ( s != USB_INT_SUCCESS ) //發送CBW失敗
{
printf ( " 發送CBW失敗,準備復位重試 \n " ) ;
mResetErrorBOC( s ) ;
//向CH374主機端點的發送緩沖區寫入CBW
Write374Block( RAM_HOST_TRAN, USB_BO_CBW_SIZE, ( PUINT8 )( & mBOC.mCBW ) ) ;
Write374Byte( REG_USB_LENGTH, USB_BO_CBW_SIZE ) ;
mSetBulkOut( );
s = HostTransactInter( ); //向USB盤的OUT端點輸出CBW
if ( s != USB_INT_SUCCESS ) //發送CBW失敗
{
printf( " 重試失敗,復位并退出傳輸,返回錯誤碼.\n " ) ;
return( mResetErrorBOC( s ) ) ;
}
}
mSaveDevEndpTog ^= BIT_HOST_TRAN_TOG; //OUT端點的數據同步標志翻轉
if ( mBOC.mCBW.mCBW_DataLen )
{
TotalLen = mBOC.mCBW.mCBW_DataLen ;
DataLength = mBOC.mCBW.mCBW_DataLen ;
if ( mBOC.mCBW.mCBW_Flag & 0x80 ) //IN事務
{
//Write374Byte( REG_USB_SETUP, Read374Byte( REG_USB_SETUP ) | BIT_SETP_HOST_MODE | BIT_SETP_AUTO_SOF ) ;
while( TotalLen )
{
mDelayuS( 100 ) ;
mSetBulkIn( );
s = HostTransactInter( ); //接受數據
if ( s != USB_INT_SUCCESS ) //操作失敗
{
if ( s == ( DEF_USB_PID_STALL | 0x20 ) ) //清除端點錯誤
{
mClearEndpStall( mDiskBulkInEndp | 0x80 ) ;
printf ( " 接收數據時發生STALL錯誤.\n " ) ;
}
else
{
printf ( " 接收數據時發生未知錯誤!\n " ) ;
return( USB_INT_DISK_ERR ) ;
}
}
len = Read374Byte( REG_USB_LENGTH ) ;
Read374Block( RAM_HOST_RECV, len, DataBuf );
mSaveDevEndpTog ^= BIT_HOST_RECV_TOG ; //IN端點的數據同步標志翻轉
DataBuf += len ;
if ( TotalLen > len )
TotalLen -= len ;
else
TotalLen = 0 ;
if ( len < 64 )
break;
}
}
else //OUT事務
{
//Write374Byte( REG_USB_SETUP, Read374Byte( REG_USB_SETUP ) | BIT_SETP_HOST_MODE | BIT_SETP_AUTO_SOF ) ;
while( TotalLen )
{
mDelayuS( 100 ) ;
len = TotalLen >= 64 ? 64 : TotalLen ;
Write374Block( RAM_HOST_TRAN, len, DataBuf );
Write374Byte( REG_USB_LENGTH, len );
mSetBulkOut( );
s = HostTransactInter( ); //發送數據
if ( s != USB_INT_SUCCESS ) //操作失敗
{
if ( s == ( DEF_USB_PID_STALL | 0x20 ) ) //清除端點錯誤
{
mClearEndpStall( mDiskBulkOutEndp );
printf ( " 發送數據時發生STALL錯誤!\n " ) ;
break ;
}
else
{
printf ( " 發送數據時發生未知錯誤!\n " ) ;
return( USB_INT_DISK_ERR ) ;
}
}
DataBuf += len;
TotalLen -= len ;
mSaveDevEndpTog ^= BIT_HOST_TRAN_TOG ; //OUT端點的數據同步標志翻轉
}
}
}
//全速USB主機模式,USB總線空閑,發SOF
//Write374Byte( REG_USB_SETUP, M_SET_RAM_MODE_OFF( BIT_SETP_HOST_MODE | BIT_SETP_AUTO_SOF ) ) ;
//從USB盤的IN端點輸入CSW
mSetBulkIn( ); //輸入
s = HostTransactInter( ); //發送數據
if ( s != USB_INT_SUCCESS ) //接受CSW失敗
{
printf( "接收CSW失敗!\n" ) ;
if ( s == ( DEF_USB_PID_STALL | 0x20 ) ) //清除端點錯誤
{
mClearEndpStall( mDiskBulkInEndp | 0x80 );
printf ( " 接收數據時發生STALL錯誤!\n " ) ;
printf ( " 嘗試重試接收CSW.\n " ) ;
mSetBulkIn( );
s = HostTransactInter( );
if ( s != USB_INT_SUCCESS )
{
printf( " 重試失敗,復位并退出傳輸,返回錯誤碼.\n " ) ;
return( mResetErrorBOC( s ) ) ;
}
}
else
{
printf ( " 接收CSW時發生未知錯誤!\n " ) ;
return( s );
}
}
len = Read374Byte( REG_USB_LENGTH ) ;
Read374Block( RAM_HOST_RECV, len, ( PUINT8 )( & mBOC.mCSW ) );
mSaveDevEndpTog ^= BIT_HOST_RECV_TOG ; //IN端點的數據同步標志翻轉
//確認Valid
if ( len != USB_BO_CSW_SIZE || mBOC.mCSW.mCSW_Sig != USB_BO_CSW_SIG )
{
printf( " 收到的CSW: NON-Valid\n " ) ;
return( USB_INT_DISK_ERR ) ;
}
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -