用FPGA在SD卡上新建一個TXT文件,并定義一個大小500的數(shù)組,并將數(shù)組里的數(shù)寫入文件的時候,會出現(xiàn)幾種如下錯誤然后一直不往下工作:
當(dāng)把數(shù)組大小設(shè)為400,可運行成功:
AD采的數(shù)是我在前面產(chǎn)生的,0到99循環(huán)輸入。
用FPGA在SD卡上新建一個TXT文件,并定義一個大小500的數(shù)組,并將數(shù)組里的數(shù)寫入文件的時候,會出現(xiàn)幾種如下錯誤然后一直不往下工作:
當(dāng)把數(shù)組大小設(shè)為400,可運行成功:
AD采的數(shù)是我在前面產(chǎn)生的,0到99循環(huán)輸入。
代碼如下(可能表達方法跟論壇提供的例程不一樣,但內(nèi)容應(yīng)該差不多):
#include "alt_types.h"
#include "altera_avalon_pio_regs.h"
#include "sys/alt_irq.h"
#include "system.h"
#include
#include
#include
#include "sys/unistd.h"
?
//函數(shù)申明
void init_usb(void); //CH376初始化
void init_Udisk(void);???? //U盤初始化
void set_usb_mode(alt_u8 mode);? //設(shè)置USB工作模式
void send_string_to_usb(alt_8 *str,alt_8 str_len);???? //向USB寫入數(shù)據(jù)塊
void write_command_to_usb(alt_u8 command);????? //寫命令到CH376
void write_data_to_usb(alt_u8 data);???? //寫數(shù)據(jù)到CH376
alt_u8 read_data_from_usb(void);?? //從CH376讀出數(shù)據(jù)
void delayus(alt_u32 cnt);?? //短延時函數(shù)
?
?
alt_u8 ch376_intflag;??? //CH376中斷標志位,1表示產(chǎn)生中斷
alt_u8 ch376_status;???? //CH376中斷狀態(tài)數(shù)據(jù)
?
//////////////////////////////////////////////////////////////////////
//函數(shù)名:handle_usbirq_interrupts
//功 ? ? 能:ch376中斷函數(shù)
//輸 ? ? 入:無
//返 ? ? 回:無
//////////////////////////////////////////////////////////////////////
static void handle_usbirq_interrupts(void* nirq_isr_context)
{
? ? //獲取中斷狀態(tài)并取消請求
? ? write_command_to_usb(GET_STATUS);????? //發(fā)送命令
? ? ch376_status = read_data_from_usb();? //讀取當(dāng)前狀態(tài)
? ? ch376_intflag = 1;??? //中斷標志位置位
}
?
//////////////////////////////////////////////////////////////////////
//函數(shù)名:main
//功 ? ? 能:主函數(shù)
//輸 ? ? 入:無
//返 ? ? 回:alt_u8
//////////////////////////////////////////////////////////////////////
alt_u8 main()
{
?????? alt_u16 ad_dis[400]; //給500的時候不行,只有小于等于400的時候程序可以運行成功
?????? alt_u8 num1;
?????? alt_u8 num2;
?????? alt_u8 num3;
?????? alt_u8 num4;
?????? alt_u16 cnt;
?????? cnt=0;
?
?????? init_usb();????????? //CH376初始化
?????? init_Udisk();?????? //U盤初始化
?
?????? while(IORD_ALTERA_AVALON_PIO_DATA(PIO_BASE)==0);
?????? printf("開始數(shù)據(jù)采集\n");
?????? for(cnt=0;cnt<400;cnt++)
?????? {
????????????? ad_dis[cnt]=IORD_16DIRECT(DATA_BASE,0);
?????? }
?????? cnt=0;
?????? printf("數(shù)據(jù)采集完成\n");
?
?????? //新建一個名為TEST.TXT的文件
?????? printf("\n創(chuàng)建一個TXT文件……%d",cnt1);
?????? write_command_to_usb(SET_FILE_NAME);//送“設(shè)置文件名”命令
?????? send_string_to_usb("/",1);
?????? write_data_to_usb(cnt1+0x30);
?????? send_string_to_usb(".TXT\0",6);????? //送文件名“TEST.TXT”
?????? write_command_to_usb(FILE_CREATE);?? //送“新建文件”命令
?????? while(ch376_intflag != 1);??? //等待中斷產(chǎn)生
?????? ch376_intflag = 0;?? //清除CH376中斷標志位
?????? if(ch376_status == USB_INT_SUCCESS)? //請求繼續(xù)寫入
?????? {
????????????? printf("成功!\n");
?????? }
?????? else
?????? {
????????????? printf("失敗--%d\n",ch376_status);
????????????? while(1);
?????? }
?
?????? write_command_to_usb(FILE_CLOSE);????? //關(guān)閉當(dāng)前已經(jīng)打開的文件或目錄
?????? write_data_to_usb(1);?? //允許自動更新文件長度
?????? printf("TXT文本創(chuàng)建完成!\n");
?
? ??? write_command_to_usb(SET_FILE_NAME);//送“設(shè)置文件名”命令
? ??? send_string_to_usb("/",1);
?????? write_data_to_usb(cnt1+0x30);
?????? send_string_to_usb(".TXT\0",8);????? //送文件名“TEST.TXT”
?
?????? write_command_to_usb(FILE_OPEN); //送“打開文件或目錄,枚舉文件和目錄”命令
?????? while(ch376_intflag != 1);??? //等待中斷產(chǎn)生
?????? ch376_intflag = 0;?? //清除CH376中斷標志位
?????? if(ch376_status == USB_INT_SUCCESS)? //請求繼續(xù)寫入
?????? {
?????? ???printf("文件打開成功!\n");
?????? ?}
????????else
????????{
????????????printf("文件打開失敗--%d\n",ch376_status);
????????????while(1);
?????? }
?
? ? while(cnt<400)
? ? {
? ??? //往已有文件添加一串?dāng)?shù)據(jù)
?????? write_command_to_usb(BYTE_WRITE);???? //以字節(jié)為單位從當(dāng)前位置寫入數(shù)據(jù)塊
?????? write_data_to_usb(8);?? //頭兩個字節(jié)是以低字節(jié)在前的16bit指示后續(xù)寫入的數(shù)據(jù)個數(shù)
?????? write_data_to_usb(0);
?????? ch376_intflag = 0;?? //清除CH375中斷標志位
?????? while(ch376_intflag != 1);??? //等待中斷產(chǎn)生
?????? ch376_intflag = 0;?? //清除CH375中斷標志位
?????? if(ch376_status == USB_INT_DISK_WRITE)???? //請求繼續(xù)寫入
?????? {
????????????? write_command_to_usb(WR_REQ_DATA);?????? //向內(nèi)部指定緩沖區(qū)寫入請求的數(shù)據(jù)塊
????????????? read_data_from_usb();
????????????? printf("需要寫入TXT的數(shù)據(jù)量為:%d\n",cnt);
?????? }
?????? else
?????? {
????????????? printf("\nTXT文本數(shù)據(jù)寫入失敗--%d\n",ch376_status);
????????????? while(1);
?????? }
?????? printf("ad_dis=%d\n",ad_dis[cnt] );
?
?????? num1=ad_dis[cnt]/4096;
?????? num2=ad_dis[cnt]%4096/256;
?????? num3=ad_dis[cnt]%4096%256/16;
?????? num4=ad_dis[cnt]%4096%256%16;
?????? if(num1<10)
?????? {
????????????? write_data_to_usb(num1+0x30);
?????? }
?????? else
?????? {
????????????? num1=num1%10;
????????????? write_data_to_usb(num1+0x61);
?????? }
?????? if(num2<10)
?????? {
????????????? write_data_to_usb(num2+0x30);
?????? }
?????? else
?????? {
????????????? num2=num2%10;
????????????? write_data_to_usb(num2+0x61);
?????? }
?????? if(num3<10)
?????? {
????????????? write_data_to_usb(num3+0x30);
?????? }
?????? else
?????? {
????????????? num3=num3%10;
????????????? write_data_to_usb(num3+0x61);
?????? }
?????? if(num4<10)
?????? {
????????????? write_data_to_usb(num4+0x30);
?????? }
?????? else
?????? {
????????????? num4=num4%10;
????????????? write_data_to_usb(num4+0x61);
?????? }
?????? send_string_to_usb("\r\n",4);???? //回車換行
?????? write_command_to_usb(BYTE_WR_GO);?? //繼續(xù)字節(jié)寫
?????? while(ch376_intflag != 1);??? //等待中斷產(chǎn)生
?????? ch376_intflag = 0;?? //清除CH375中斷標志位
?????? if(ch376_status == USB_INT_SUCCESS)? //請求繼續(xù)寫入
?????? {
????????????? printf("TXT文本數(shù)據(jù)寫入成功!\n");
?????? }
?????? else
?????? {
????????????? printf("TXT文本數(shù)據(jù)寫入失敗--%d\n",ch376_status);
?????? ?????? while(1);
?????? }
?????? cnt++;
? ? }
?????? write_command_to_usb(FILE_CLOSE);????? //關(guān)閉當(dāng)前已經(jīng)打開的文件或目錄
?????? write_data_to_usb(1);?? //允許自動更新文件長度
?????? printf("TXT文本創(chuàng)建并寫入完成!\n");
?????? cnt=0;
?????? while(1);
?????? return 0;
}
?
//////////////////////////////////////////////////////////////////////
//函數(shù)名:init_usb
//功 ? ? 能:CH376初始化
//輸 ? ? 入:無
//返 ? ? 回:無
//////////////////////////////////////////////////////////////////////
void init_usb(void)
{
?????? alt_u8 temp = 0;?????? //臨時變量
?
?????? //初始化全局變量
?????? ch376_intflag = 0;?? //清除CH376中斷標志位
?????? ch376_status = 0;?? //清除 CH376中斷寄存器
?
?????? //注冊中斷函數(shù)
? ? alt_ic_isr_register(CH376_CONTROLLER_0_IRQ_INTERRUPT_CONTROLLER_ID,
? ??????????????????????????????? CH376_CONTROLLER_0_IRQ,
? ??????????????????????????????? handle_usbirq_interrupts,
? ? ? ? ? ? ? ? ? ? ? ? NULL,
? ? ? ? ? ? ? ? ? ? ? ? NULL);
?
?????? //設(shè)置USB工作模式
?????? write_command_to_usb(SET_USB_MODE);???? //送命令
?????? write_data_to_usb(0x03);??? //切換到SD卡主機模式,管理和存取SD卡中的文件
?????? /*
????????????? 模式代碼為04H時切換到未啟用的USB主機方式;
????????????? 模式代碼為05H時切換到已啟用的USB主機方式,不產(chǎn)生SOF包;
????????????? 模式代碼為06H時切換到已啟用的USB主機方式,自動產(chǎn)生SOF包;
????????????? 模式代碼為07H時切換到已啟用的USB主機方式,復(fù)位USB總線;
?????? */
?????? ch376_intflag = 0;?? //清除CH376中斷標志位
?????? delayus(100);
?
?????? //CH376芯片工作狀態(tài)測試
?????? write_command_to_usb(CHECK_EXIST);? //發(fā)送命令
?????? write_data_to_usb(0xaa);????????????????? //寫入數(shù)據(jù)0xaa
?????? temp = read_data_from_usb();???????? //讀取寫入數(shù)據(jù)取反結(jié)果,即0xaa取反應(yīng)為0x55
?????? if(temp == 0x55) printf("CH376芯片工作正常\n");??? //打印測試結(jié)果
?????? else
?????? {
????????????? printf("CH376芯片初始化失敗\n");
????????????? while(1);
?????? }
}
?
//////////////////////////////////////////////////////////////////////
//函數(shù)名:init_Udisk
//功 ? ? 能:U盤初始化
//輸 ? ? 入:無
//返 ? ? 回:無
//////////////////////////////////////////////////////////////////////
void init_Udisk(void)
{
?????? alt_u8 i;
//???? alt_u8 temp = 0;?????? //臨時變量
?????? alt_u8 mem[9];???????? //U盤存儲量
?????? //初始化USB存儲設(shè)備
?????? printf("初始化USB存儲設(shè)備……"); //打印事件
?????? ch376_intflag = 0;?? //清除CH376中斷標志位
?????? write_command_to_usb(DISK_MOUNT);??? //發(fā)送命令
?????? while(ch376_intflag != 1);??? //等待中斷產(chǎn)生
?????? ch376_intflag = 0;?? //清除CH376中斷標志位
?????? if(ch376_status == USB_INT_SUCCESS) printf("成功\n");
?????? else
?????? {
????????????? printf("失敗——0x%x\n",ch376_status);
????????????? while(1);
?????? }
?
?????? //獲取USB存儲設(shè)備的磁盤物理容量
?????? printf("獲取USB存儲設(shè)備的磁盤物理容量……");???? //打印事件
?????? write_command_to_usb(DISK_CAPACITY);????? //發(fā)送命令
?????? while(ch376_intflag != 1);??? //等待中斷產(chǎn)生
?????? ch376_intflag = 0;?? //清除CH376中斷標志位
?????? if(ch376_status == USB_INT_SUCCESS)
?????? {
????????????? printf("成功\n");
????????????? write_command_to_usb(RD_USB_DATA0);????? //發(fā)送命令
????????????? //讀取并打印USB存儲設(shè)備容量
????????????? read_data_from_usb();//讀取第一個字節(jié),即后續(xù)數(shù)據(jù)長度,為8
????????????? for(i=0;i<4;i++)? //連續(xù)讀取8個字節(jié)數(shù)據(jù)
????????????? {
???????????????????? mem[i] = read_data_from_usb();
????????????? }
????????????? printf("\t總扇區(qū)數(shù)為:%d\n",((mem[3]<<24)+(mem[2]<<16)+(mem[1]<<8)+mem[0]));
????????????? printf("\t每個扇區(qū)字節(jié)數(shù)為:%d\n",512);
????????????? printf("\t總存儲量為:%dMB\n",((mem[3]<<24)+(mem[2]<<16)+(mem[1]<<8)+mem[0])*512/1024/1024);
?????? }
?????? else
?????? {
????????????? printf("失敗——0x%x\n",ch376_status);
????????????? while(1);
?????? }
}
?
//////////////////////////////////////////////////////////////////////
//函數(shù)名:send_string_to_usb
//功 ? ? 能:向USB主機端點的輸出緩沖區(qū)寫入數(shù)據(jù)塊
//輸 ? ? 入:alt_8 *str----寫入字符串,alt_8 str_len----字符串長度
//返 ? ? 回:無
//////////////////////////////////////////////////////////////////////
void send_string_to_usb(alt_8 *str,alt_8 str_len)
{
?????? alt_u8 i;
?????? //寫入固定長度數(shù)據(jù)字節(jié)
?????? for(i=0;i
?????? {
????????????? //寫入數(shù)據(jù)
????????????? write_data_to_usb(str[i]);
?????? }
}
?
//////////////////////////////////////////////////////////////////////
//函數(shù)名:write_command_to_usb
//功 ? ? 能:寫命令到CH376
//輸 ? ? 入:alt_u8 command----寫入命令
//返 ? ? 回:無
//////////////////////////////////////////////////////////////////////
void write_command_to_usb(alt_u8 command)
{
?????? //延時>1.5us
?????? delayus(1);
?????? IOWR_8DIRECT(CH376_CONTROLLER_0_BASE,1,command);
?????? //命令操作 A0=1
}
?
//////////////////////////////////////////////////////////////////////
//函數(shù)名:write_data_to_usb
//功 ? ? 能:寫數(shù)據(jù)到CH376
//輸 ? ? 入:alt_u8 data----寫入數(shù)據(jù)
//返 ? ? 回:無
//////////////////////////////////////////////////////////////////////
void write_data_to_usb(alt_u8 data)
{
?????? //延時>1.5us
?????? delayus(1);
?????? IOWR_8DIRECT(CH376_CONTROLLER_0_BASE,0,data);
}
?
//////////////////////////////////////////////////////////////////////
//函數(shù)名:read_data_from_usb
//功 ? ? 能:從CH376讀出數(shù)據(jù)
//輸 ? ? 入:無
//返 ? ? 回:alt_u8----讀出數(shù)據(jù)
//////////////////////////////////////////////////////////////////////
alt_u8 read_data_from_usb(void)
{
?????? //延時>1.5us
?????? delayus(1);
?????? return IORD_8DIRECT(CH376_CONTROLLER_0_BASE,0);
}
//////////////////////////////////////////////////////////////////////
//函數(shù)名:delayus
//功 ? ? 能:短延時函數(shù)
//輸 ? ? 入:alt_u32 cnt----延時值
//返 ? ? 回:void
//////////////////////////////////////////////////////////////////////
void delayus(alt_u32 cnt)
{
?????? int i;
?????? for(i=0;i
}
用的芯片是CH376