?? ch375hft.c
字號(hào):
mDelaymS( 1 ); /* 寫(xiě)后延時(shí),可選的,大多數(shù)U盤(pán)不需要 */
memcpy( FILE_DATA_BUF+0, FILE_DATA_BUF+(total & ~ 511), total & 511 ); /* 將剛才已寫(xiě)入U(xiǎn)盤(pán)的零頭數(shù)據(jù)復(fù)制到緩沖區(qū)的頭部 */
total &= 511; /* 緩沖區(qū)中只剩下剛才已寫(xiě)入U(xiǎn)盤(pán)的零頭數(shù)據(jù),繼續(xù)保留在緩沖區(qū)中是為了方便以后在其后面追加數(shù)據(jù) */
if ( total ) NewSize = CH375vFileSize - 512 + total; /* 以扇區(qū)為單位,有零頭數(shù)據(jù),計(jì)算出真正的文件長(zhǎng)度(有效數(shù)據(jù)的長(zhǎng)度) */
else NewSize = CH375vFileSize; /* 以扇區(qū)為單位,沒(méi)有零頭數(shù)據(jù),文件長(zhǎng)度是512的倍數(shù) */
mCmdParam.Modify.mFileSize = NewSize; /* 輸入?yún)?shù): 新的文件長(zhǎng)度,扇區(qū)模式下涉及到零頭數(shù)據(jù)不便自動(dòng)更新長(zhǎng)度 */
mCmdParam.Modify.mFileAttr = 0xff; /* 輸入?yún)?shù): 新的文件屬性,為0FFH則不修改 */
mCmdParam.Modify.mFileTime = 0xffff; /* 輸入?yún)?shù): 新的文件時(shí)間,為0FFH則不修改 */
mCmdParam.Modify.mFileDate = 0xffff; /* 輸入?yún)?shù): 新的文件日期,為0FFH則不修改 */
i = CH375FileModify( ); /* 修改當(dāng)前文件的信息,修改文件長(zhǎng)度 */
mStopIfError( i );
printf( "Current file size is %ld\n", CH375vFileSize );
mCmdParam.Locate.mSectorOffset = 0xffffffff; /* 移到文件的尾部,以扇區(qū)為單位,所以會(huì)忽略文件尾部的零頭數(shù)據(jù) */
i = CH375FileLocate( ); /* 重新回到原文件的尾部,下面如果再寫(xiě)入數(shù)據(jù)將覆蓋尾部零頭數(shù)據(jù),不過(guò)該零頭數(shù)據(jù)有一份副本保留在緩沖區(qū)中,所以請(qǐng)放心 */
mStopIfError( i );
}
else if ( total >= FILE_DATA_BUF_LEN - 512 ) { /* 緩沖區(qū)中的數(shù)據(jù)快要滿了,所以應(yīng)該先將緩沖區(qū)中的原有數(shù)據(jù)寫(xiě)入U(xiǎn)盤(pán) */
mCmdParam.Write.mSectorCount = total >> 9; /* 將緩沖區(qū)中的字節(jié)數(shù)轉(zhuǎn)換為扇區(qū)數(shù)(除以512),最后的零頭數(shù)據(jù)先不管 */
i = CH375FileWrite( ); /* 以扇區(qū)為單位向文件寫(xiě)入數(shù)據(jù),寫(xiě)入緩沖區(qū)中的所有數(shù)據(jù),不含最后的零頭 */
mStopIfError( i );
memcpy( FILE_DATA_BUF+0, FILE_DATA_BUF+(total & ~ 511), total & 511 ); /* 將剛才未寫(xiě)入U(xiǎn)盤(pán)的零頭數(shù)據(jù)復(fù)制到緩沖區(qū)的頭部 */
total &= 511; /* 緩沖區(qū)中只剩下剛才未寫(xiě)入U(xiǎn)盤(pán)的零頭數(shù)據(jù) */
/* mCmdParam.Write.mSectorCount = 0; 如果全局變量CH375LibConfig的位4為0,可以指定寫(xiě)入0扇區(qū),用于刷新文件的長(zhǎng)度
CH375FileWrite( ); 以扇區(qū)為單位向文件寫(xiě)入數(shù)據(jù),因?yàn)槭?扇區(qū)寫(xiě)入,所以只用于更新文件的長(zhǎng)度,當(dāng)階段性寫(xiě)入數(shù)據(jù)后,可以用這種辦法更新文件長(zhǎng)度 */
}
}
main( ) {
UINT8 i, month, date, hour;
UINT16 year, adc;
LED_OUT_INIT( );
LED_OUT_ACT( ); /* 開(kāi)機(jī)后LED亮一下以示工作 */
mDelaymS( 100 ); /* 延時(shí)100毫秒 */
LED_OUT_INACT( );
mInitSTDIO( ); /* 為了讓計(jì)算機(jī)通過(guò)串口監(jiān)控演示過(guò)程 */
printf( "Start\n" );
i = CH375LibInit( ); /* 初始化CH375程序庫(kù)和CH375芯片,操作成功返回0 */
mStopIfError( i );
/* 其它電路初始化 */
while ( 1 ) {
printf( "Wait Udisk\n" );
while ( CH375DiskStatus != DISK_CONNECT ) xQueryInterrupt( ); /* 查詢CH375中斷并更新中斷狀態(tài),等待U盤(pán)插入 */
LED_OUT_ACT( ); /* LED亮 */
mDelaymS( 200 ); /* 延時(shí),可選操作,有的USB存儲(chǔ)器需要幾十毫秒的延時(shí) */
/* 檢查U盤(pán)是否準(zhǔn)備好,有些U盤(pán)不需要這一步,但是某些U盤(pán)必須要執(zhí)行這一步才能工作 */
for ( i = 0; i < 10; i ++ ) { /* 有的U盤(pán)總是返回未準(zhǔn)備好,不過(guò)可以被忽略 */
mDelaymS( 100 );
printf( "Ready ?\n" );
if ( CH375DiskReady( ) == ERR_SUCCESS ) break; /* 查詢磁盤(pán)是否準(zhǔn)備好 */
}
/* 查詢磁盤(pán)物理容量 */
printf( "DiskSize\n" );
i = CH375DiskSize( );
mStopIfError( i );
printf( "TotalSize = %u MB \n", (unsigned int)( mCmdParam.DiskSize.mDiskSizeSec >> 11 ) ); /* 顯示為以MB為單位的容量 */
LED_RUN_ACT( ); /* 開(kāi)始操作U盤(pán) */
/* 如果MY_ADC.TXT文件已經(jīng)存在則添加數(shù)據(jù)到尾部,如果不存在則新建文件 */
printf( "Open\n" );
mCopyCodeStringToIRAM( mCmdParam.Open.mPathName, "/MY_ADC.TXT" ); /* 文件名,該文件在根目錄下 */
i = CH375FileOpen( ); /* 打開(kāi)文件 */
if ( i == ERR_SUCCESS ) { /* 文件存在并且已經(jīng)被打開(kāi),移動(dòng)文件指針到尾部以便添加數(shù)據(jù) */
printf( "File size = %ld\n", CH375vFileSize ); /* V1.5以上子程序庫(kù)在成功打開(kāi)文件后,全局變量CH375vFileSize中是文件當(dāng)前長(zhǎng)度 */
printf( "Locate tail\n" );
mCmdParam.Locate.mSectorOffset = 0xffffffff; /* 移到文件的尾部,CH375子程序庫(kù)內(nèi)部是將文件長(zhǎng)度按扇區(qū)長(zhǎng)度512進(jìn)行取整處理 */
i = CH375FileLocate( ); /* 以扇區(qū)為單位移到文件尾部,如果文件尾部有不足一個(gè)扇區(qū)的零頭數(shù)據(jù)則被忽略,如果不做處理那么零頭數(shù)據(jù)將可能被寫(xiě)入數(shù)據(jù)覆蓋 */
mStopIfError( i );
total = CH375vFileSize & 511; /* 上次保存文件時(shí)如果尾部有零頭數(shù)據(jù),那么先取得零頭字節(jié)數(shù),不滿扇區(qū)長(zhǎng)度的零碎數(shù)據(jù) */
printf( "Read last tail = %d Bytes\n", total );
CH375vFileSize += 511; /* 人為地將文件長(zhǎng)度增加一個(gè)扇區(qū)減1,以便讀出最后一個(gè)扇區(qū)中的零頭數(shù)據(jù) */
mCmdParam.Read.mSectorCount = 1; /* 讀取文件尾部的零頭數(shù)據(jù),如果不人為增加文件長(zhǎng)度,那么由于文件長(zhǎng)度按512取整,導(dǎo)致尾部零頭數(shù)據(jù)無(wú)法讀出 */
i = CH375FileRead( ); /* 從文件讀取尾部零頭數(shù)據(jù),如果原尾部沒(méi)有零頭數(shù)據(jù),那么什么也讀不到,返回時(shí)mCmdParam.Read.mSectorCount為實(shí)際讀出扇區(qū)數(shù) */
mStopIfError( i );
CH375vFileSize -= 511; /* 恢復(fù)真正的文件長(zhǎng)度 */
mCmdParam.Locate.mSectorOffset = 0xffffffff; /* 移到文件的尾部,以扇區(qū)為單位,所以會(huì)忽略文件尾部的零頭數(shù)據(jù) */
i = CH375FileLocate( ); /* 重新回到原文件的尾部,下面如果寫(xiě)入數(shù)據(jù)將覆蓋原尾部零頭數(shù)據(jù),不過(guò)原零頭數(shù)據(jù)剛才已經(jīng)被讀入內(nèi)存,所以請(qǐng)放心 */
mStopIfError( i );
}
else if ( i == ERR_MISS_FILE ) { /* 沒(méi)有找到文件,必須新建文件 */
LED_WR_ACT( ); /* 寫(xiě)操作 */
printf( "Create\n" );
// mCopyCodeStringToIRAM( mCmdParam.Create.mPathName, "/MY_ADC.TXT" ); /* 文件名,該文件在根目錄下,剛才已經(jīng)提供給CH375FileOpen */
i = CH375FileCreate( ); /* 新建文件并打開(kāi),如果文件已經(jīng)存在則先刪除后再新建 */
mStopIfError( i );
total = 0; /* 此前沒(méi)有零頭數(shù)據(jù) */
}
else mStopIfError( i ); /* 打開(kāi)文件時(shí)出錯(cuò) */
LED_WR_ACT( ); /* 寫(xiě)操作 */
printf( "Write begin\n" );
total += sprintf( FILE_DATA_BUF + total, "在本次添加數(shù)據(jù)之前,該文件已有數(shù)據(jù)的長(zhǎng)度是 %ld 字節(jié)\xd\xa", CH375vFileSize ); /* 將新數(shù)據(jù)添加到緩沖區(qū)的尾部,累計(jì)緩沖區(qū)內(nèi)的數(shù)據(jù)長(zhǎng)度 */
mFlushBufferToDisk( 0 ); /* 自動(dòng)刷新緩沖區(qū),檢查緩沖區(qū)是否已滿,滿則寫(xiě)盤(pán) */
printf( "Write ADC data\n" );
TR0=1; /* 用定時(shí)器0的計(jì)數(shù)值代替ADC數(shù)據(jù) */
for ( month = 1; month != 12; month ++ ) { /* 因?yàn)闇y(cè)試板上沒(méi)有實(shí)時(shí)時(shí)鐘芯片,所以用循環(huán)方式模擬月份 */
for ( date = 1; date != 30; date ++ ) { /* 因?yàn)闇y(cè)試板上沒(méi)有實(shí)時(shí)時(shí)鐘芯片,所以用循環(huán)方式模擬日期 */
year = 2004; /* 假定為2004年 */
hour = TL1 & 0x1F; /* 因?yàn)闇y(cè)試板上沒(méi)有實(shí)時(shí)時(shí)鐘芯片,所以用定時(shí)器1的計(jì)數(shù)代替進(jìn)行演示 */
/* adc = get_adc_data( ); */
adc = ( (UINT16)TH0 << 8 ) | TL0; /* 因?yàn)闇y(cè)試板上沒(méi)有ADC,所以用定時(shí)器0的計(jì)數(shù)代替ADC數(shù)據(jù)演示 */
total += sprintf( FILE_DATA_BUF + total, "Year=%04d, Month=%02d, Date=%02d, Hour=%02d, ADC_data=%u\xd\xa", year, (UINT16)month, (UINT16)date, (UINT16)hour, adc ); /* 將二制制數(shù)據(jù)格式為一行字符串 */
if ( month == 6 && ( date & 0x0F ) == 0 ) mFlushBufferToDisk( 1 ); /* 強(qiáng)制刷新緩沖區(qū),定期強(qiáng)制刷新緩沖區(qū),這樣在突然斷電后可以減少數(shù)據(jù)丟失 */
else mFlushBufferToDisk( 0 ); /* 自動(dòng)刷新緩沖區(qū),檢查緩沖區(qū)是否已滿,滿則寫(xiě)盤(pán) */
printf( "Current total is %d\n", total ); /* 用于監(jiān)控檢查 */
}
}
printf( "Write end\n" );
total += sprintf( FILE_DATA_BUF + total, " ********************************* " ); /* 將新數(shù)據(jù)添加到緩沖區(qū)的尾部,累計(jì)緩沖區(qū)內(nèi)的數(shù)據(jù)長(zhǎng)度 */
total += sprintf( FILE_DATA_BUF + total, "這次的ADC數(shù)據(jù)到此結(jié)束,程序即將退出\xd\xa" ); /* 將新數(shù)據(jù)添加到緩沖區(qū)的尾部,累計(jì)緩沖區(qū)內(nèi)的數(shù)據(jù)長(zhǎng)度 */
mFlushBufferToDisk( 1 ); /* 強(qiáng)制刷新緩沖區(qū),因?yàn)橄到y(tǒng)要退出了,所以必須強(qiáng)制刷新 */
printf( "Close\n" );
mCmdParam.Close.mUpdateLen = 0; /* 因?yàn)閺?qiáng)制刷新緩沖區(qū)時(shí)已經(jīng)更新了文件長(zhǎng)度,所以這里不需要自動(dòng)更新文件長(zhǎng)度 */
i = CH375FileClose( ); /* 關(guān)閉文件 */
mStopIfError( i );
LED_WR_INACT( );
LED_RUN_INACT( );
printf( "Take out\n" );
while ( CH375DiskStatus != DISK_DISCONNECT ) xQueryInterrupt( ); /* 查詢CH375中斷并更新中斷狀態(tài),等待U盤(pán)拔出 */
LED_OUT_INACT( ); /* LED滅 */
mDelaymS( 200 );
}
}
?? 快捷鍵說(shuō)明
復(fù)制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號(hào)
Ctrl + =
減小字號(hào)
Ctrl + -