




版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請進(jìn)行舉報或認(rèn)領(lǐng)
文檔簡介
淘寶店鋪:技術(shù)論壇《手把手教你學(xué)STM32》主講人:正點(diǎn)原子團(tuán)隊(duì)硬件平臺:正點(diǎn)原子STM32開發(fā)板:廣州市星翼電子科技有限公司淘寶店鋪:技術(shù)論壇:開源電子網(wǎng)公眾平臺:“正點(diǎn)原子”官方網(wǎng)站:聯(lián)系電話:ALIENTEK《手把手教你學(xué)STM32》USB鼠標(biāo)鍵盤實(shí)驗(yàn)(M4)淘寶店鋪:技術(shù)論壇STM32F1xx開發(fā)板(正點(diǎn)原子)STM32F4xx開發(fā)板(正點(diǎn)原子)適用平臺本視頻重點(diǎn)參考資料淘寶店鋪:技術(shù)論壇參考資料:1,探索者STM32F407開發(fā)板《STM32F4開發(fā)指南-庫函數(shù)版本》——USB鼠標(biāo)鍵盤(Host)實(shí)驗(yàn)2,USB參考資料①《STM32F4xx中文參考手冊》-第30章全速USBon-the-go(OTG_FS)
②光盤:STM32參考資料STM32USB學(xué)習(xí)資料CD00289278.pdf(UM1021)③光盤:STM32參考資料STM32USB學(xué)習(xí)資料USB培訓(xùn).pdf(分為Part1~3,三個部分,是ST官方USB培訓(xùn)資料)3,USB參考代碼光盤:STM32參考資料STM32USB學(xué)習(xí)資料stm32_f105-07_f2_f4_usb-host-device_lib.zip目錄淘寶店鋪:技術(shù)論壇USB鼠標(biāo)鍵盤簡介1
硬件連接2
代碼移植&例程測試31、USB鼠標(biāo)鍵盤簡介淘寶店鋪:技術(shù)論壇傳統(tǒng)的鼠標(biāo)和鍵盤是采用PS/2接口和電腦通信的,但是現(xiàn)在PS/2接口在電腦上逐漸消失,所以現(xiàn)在越來越多的鼠標(biāo)鍵盤采用的是USB接口,而不是PS/2接口的了。USB鼠標(biāo)鍵盤屬于USBHID設(shè)備。USBHID即:HumanInterfaceDevice(人機(jī)交互設(shè)備)的縮寫,鍵盤、鼠標(biāo)與游戲桿等都屬于此類設(shè)備。不過HID設(shè)備并不一定要有人機(jī)接口,只要符合HID類別規(guī)范的設(shè)備都是HID設(shè)備。關(guān)于USBHID的知識,我們這里就不詳細(xì)介紹了,請大家自行百度學(xué)習(xí)。1、USB鼠標(biāo)鍵盤簡介淘寶店鋪:技術(shù)論壇STM32F4的USBOTGFS支持USBHID設(shè)備,并且ST官方提供了USBHID例程(支持USB鼠標(biāo)和USB鍵盤),官方例程路徑:光盤STM32參考資料STM32USB學(xué)習(xí)資料stm32_f105-07_f2_f4_usb-host-device_lib.zip(解壓)ProjectUSB_Host_ExamplesHID。
本視頻,我們將移植該例程到探索者STM32F4開發(fā)板上,以通過STM32F4的USBHOST接口,實(shí)現(xiàn)USB鼠標(biāo)和USB鍵盤的驅(qū)動。2、硬件連接-STM32F4硬件連接淘寶店鋪:技術(shù)論壇探索者STM32F407開發(fā)板,自帶了USBHOST功能,并板載了一個USBA座,可以插U盤、USB鼠標(biāo)、USB鍵盤、USB手柄等設(shè)備,硬件連接原理圖如下:特別注意:USB_SLAVE和USB_HOST共用D-和D+,所以,他們不能同時連接!!3、代碼移植&例程測試-源碼說明淘寶店鋪:技術(shù)論壇光盤程序源碼標(biāo)準(zhǔn)例程(庫函數(shù)/寄存器)實(shí)驗(yàn)54USB鼠標(biāo)鍵盤(Host)實(shí)驗(yàn)探索者STM32F4開發(fā)板源碼本例程,我們是在標(biāo)準(zhǔn)例程-庫函數(shù)版本:TFTLCD顯示實(shí)驗(yàn)的基礎(chǔ)上,移植ST官方的主機(jī)HID例程而來。3、代碼移植&例程測試-代碼移植過程淘寶店鋪:技術(shù)論壇1,打開ST官方的主機(jī)HID例程,如下圖所示:這3個文件用戶可配置,包括:板級支持代碼、用戶應(yīng)用層代碼、LCD鼠標(biāo)數(shù)據(jù)顯示代碼(本例程不用)。USB底層驅(qū)動代碼,包括通用部分和主機(jī)(Host)部分的代碼。USB主機(jī)庫驅(qū)動代碼,包括主機(jī)內(nèi)核驅(qū)動和主機(jī)HID類驅(qū)動代碼。根據(jù)此例程,我們知道了與USB相關(guān)的代碼,方便移植。USB驅(qū)動代碼說明,詳見:CD00289278.pdf3、代碼移植&例程測試-代碼移植過程淘寶店鋪:技術(shù)論壇2,STM32F4USB通信需要用的庫,如下圖所示:1,USB從機(jī)驅(qū)動庫2,USB主機(jī)驅(qū)動庫3,USB_OTG內(nèi)核驅(qū)動代碼有了ST提供的這兩個庫和USB_OTG驅(qū)動,我們可以很方便的實(shí)現(xiàn)各種USB功能,本例程,我們將使用:2+3,實(shí)現(xiàn)USB鼠標(biāo)鍵盤例程。3、代碼移植&例程測試-代碼移植過程淘寶店鋪:技術(shù)論壇3,打開TFTLCD顯示實(shí)驗(yàn),拷貝USB驅(qū)動庫,如下圖所示:在工程目錄下,新建USB文件夾,然后拷貝ST官方USB驅(qū)動庫代碼進(jìn)來。新建USB_APP文件夾,拷貝主機(jī)HID相關(guān)代碼3、代碼移植&例程測試-代碼移植過程淘寶店鋪:技術(shù)論壇4,打開TFTLCD顯示實(shí)驗(yàn)工程,添加USB相關(guān)代碼,如下圖所示:根據(jù)ST官方的主機(jī)HID例程,新建USB_OTG組,存放USB_OTG內(nèi)核驅(qū)動代碼,新建USB_HOST組,存放USB主機(jī)與HID相關(guān)代碼,新建USB_APP存放用戶配置相關(guān)驅(qū)動代碼。頭文件包含路徑記得添加!!3、代碼移植&例程測試-代碼移植過程淘寶店鋪:技術(shù)論壇5,編譯代碼,根據(jù)報錯提示,修改相關(guān)內(nèi)容。①,usb_conf.h,include部分,使用如下代碼替代:#include"stm32f4xx.h"②,在C/C++選項(xiàng)卡,定義全局宏:USE_USB_OTG_FS,選擇使用USBOTGFS,如圖所示:3、代碼移植&例程測試-代碼移植過程淘寶店鋪:技術(shù)論壇③,修改usbh_usr.c。3.1,刪除lcd_log.h等頭文件,并添加usb_hcd_int.h等頭文件,如下所示:3.2,定義bDeviceState變量,用于記錄連接狀態(tài)。然后,去掉一些用不到的變量和宏定義,并添加USB中斷處理函數(shù)(官方例程在stm32fxxx_it.c里面處理)到本.c文件,如下所示://表示USB連接狀態(tài):0,沒連接;1,已連接vu8bDeviceState=0; //默認(rèn)沒有連接externUSB_OTG_CORE_HANDLEUSB_OTG_Core_dev;//在main函數(shù)定義externvoidUSBH_Msg_Show(u8msgx); //在main函數(shù)定義u8USB_FIRST_PLUGIN_FLAG=0; //USB第一次插入標(biāo)志,如果為1,說明是第一次插入//USBOTG中斷服務(wù)函數(shù),處理所有USB中斷voidOTG_FS_IRQHandler(void){ USBH_OTG_ISR_Handler(&USB_OTG_Core_dev);}#include"usbh_usr.h"#include"usb_hcd_int.h"#include"usbh_hid_mouse.h"#include"usbh_hid_keybd.h"#include"delay.h"#include"lcd.h"#include"string.h"3、代碼移植&例程測試-代碼移植過程淘寶店鋪:技術(shù)論壇voidUSBH_USR_Init(void){ printf("USBOTGHSMSCHost\r\n"); printf(">USBHostlibrarystarted.\r\n"); printf("USBHostLibraryv2.1.0\r\n\r\n");
}3.3,修改USBH_USR_Init函數(shù)為:voidUSBH_USR_DeviceAttached(void)//U盤插入{ printf("檢測到USB設(shè)備插入!\r\n");}3.4,修改USBH_USR_DeviceAttached函數(shù)為:voidUSBH_USR_UnrecoveredError(void){ printf("無法恢復(fù)的錯誤!!!\r\n\r\n"); }3.5,修改USBH_USR_UnrecoveredError函數(shù)為:3、代碼移植&例程測試-代碼移植過程淘寶店鋪:技術(shù)論壇voidUSBH_USR_DeviceDisconnected(void)//U盤移除{ printf("USB設(shè)備拔出!\r\n"); bDeviceState=0; //USB設(shè)備拔出了
USBH_Msg_Show(0);}3.6,修改USBH_USR_DeviceDisconnected函數(shù)為:voidUSBH_USR_ResetDevice(void){ printf("復(fù)位設(shè)備...\r\n");}3.7,修改USBH_USR_ResetDevice函數(shù)為:3、代碼移植&例程測試-代碼移植過程淘寶店鋪:技術(shù)論壇voidUSBH_USR_DeviceSpeedDetected(uint8_tDeviceSpeed){ if(DeviceSpeed==HPRT0_PRTSPD_HIGH_SPEED) { printf("高速(HS)USB設(shè)備!\r\n"); } elseif(DeviceSpeed==HPRT0_PRTSPD_FULL_SPEED) { printf("全速(FS)USB設(shè)備!\r\n"); } elseif(DeviceSpeed==HPRT0_PRTSPD_LOW_SPEED) { printf("低速(LS)USB設(shè)備!\r\n"); } else { printf("設(shè)備錯誤!\r\n"); }}3.8,修改USBH_USR_DeviceSpeedDetected函數(shù)為:3、代碼移植&例程測試-代碼移植過程淘寶店鋪:技術(shù)論壇voidUSBH_USR_Device_DescAvailable(void*DeviceDesc){ USBH_DevDesc_TypeDef*hs; hs=DeviceDesc; printf("VID:%04Xh\r\n",(uint32_t)(*hs).idVendor); printf("PID:%04Xh\r\n",(uint32_t)(*hs).idProduct);}3.9,修改USBH_USR_Device_DescAvailable函數(shù)為:voidUSBH_USR_DeviceAddressAssigned(void){ printf("從機(jī)地址分配成功!\r\n");}3.10,修改USBH_USR_DeviceAddressAssigned函數(shù)為:3、代碼移植&例程測試-代碼移植過程淘寶店鋪:技術(shù)論壇voidUSBH_USR_Configuration_DescAvailable(USBH_CfgDesc_TypeDef*cfgDesc,USBH_InterfaceDesc_TypeDef*itfDesc,USBH_EpDesc_TypeDef*epDesc){ USBH_InterfaceDesc_TypeDef*id; id=itfDesc; if((*id).bInterfaceClass==0x08) { printf("可移動存儲器設(shè)備!\r\n"); }elseif((*id).bInterfaceClass==0x03) { printf("HID設(shè)備!\r\n"); }}3.11,修改USBH_USR_Configuration_DescAvailable函數(shù)為:voidUSBH_USR_Manufacturer_String(void*ManufacturerString){ printf("Manufacturer:%s\r\n",(char*)ManufacturerString);}3.12,修改USBH_USR_Manufacturer_String函數(shù)為:3、代碼移植&例程測試-代碼移植過程淘寶店鋪:技術(shù)論壇voidUSBH_USR_Product_String(void*ProductString){ printf("Product:%s\r\n",(char*)ProductString);}3.13,修改USBH_USR_Product_String函數(shù)為:voidUSBH_USR_SerialNum_String(void*SerialNumString){ printf("SerialNumber:%s\r\n",(char*)SerialNumString);}3.14,修改USBH_USR_SerialNum_String函數(shù)為:voidUSBH_USR_EnumerationDone(void){ printf("設(shè)備枚舉完成!\r\n\r\n");}3.15,修改USBH_USR_EnumerationDone函數(shù)為:3、代碼移植&例程測試-代碼移植過程淘寶店鋪:技術(shù)論壇voidUSBH_USR_DeviceNotSupported(void){ USBH_Msg_Show(3);//無法識別的USB設(shè)備
//printf("無法識別的USB設(shè)備!\r\n\r\n");}3.16,修改USBH_USR_DeviceNotSupported函數(shù)為:USBH_USR_StatusUSBH_USR_UserInput(void){ printf("跳過用戶確認(rèn)步驟!\r\n"); bDeviceState=1;//USB設(shè)備已經(jīng)連接成功
returnUSBH_USR_RESP_OK;}3.17,修改USBH_USR_UserInput函數(shù)為:voidUSBH_USR_OverCurrentDetected(void){ printf("端口電流過大!!!\r\n");}3.18,修改USBH_USR_OverCurrentDetected函數(shù)為:3、代碼移植&例程測試-代碼移植過程淘寶店鋪:技術(shù)論壇voidUSR_MOUSE_Init(void){ USBH_Msg_Show(2); //USB鼠標(biāo)
USB_FIRST_PLUGIN_FLAG=1;//標(biāo)記第一次插入}3.19,修改USR_MOUSE_Init函數(shù)為:3.21,定義數(shù)組tbuf,用于存儲鼠標(biāo)/鍵盤輸入的內(nèi)容,如下所示:voidUSR_KEYBRD_Init(void){ USBH_Msg_Show(1); //USB鍵盤
USB_FIRST_PLUGIN_FLAG=1;//標(biāo)記第一次插入}3.20,修改USR_KEYBRD_Init函數(shù)為://零時數(shù)組,用于存放鼠標(biāo)坐標(biāo)/鍵盤輸入內(nèi)容(4.3屏,最大可以輸入2016字節(jié))__align(4)u8tbuf[2017];3、代碼移植&例程測試-代碼移植過程淘寶店鋪:技術(shù)論壇3.22,修改USR_MOUSE_ProcessData函數(shù)為:voidUSR_MOUSE_ProcessData(HID_MOUSE_Data_TypeDef*data){ staticsignedshortx,y,z; if(USB_FIRST_PLUGIN_FLAG)//第一次插入,將數(shù)據(jù)清零
{ USB_FIRST_PLUGIN_FLAG=0;x=y=z=0; } x+=(signedchar)data->x; if(x>9999)x=9999;if(x<-9999)x=-9999; y+=(signedchar)data->y; if(y>9999)y=9999;if(y<-9999)y=-9999; z+=(signedchar)data->z; if(z>9999)z=9999;if(z<-9999)z=-9999; POINT_COLOR=BLUE; sprintf((char*)tbuf,"BUTTON:"); if(data->button&0X01)strcat((char*)tbuf,"LEFT"); if((data->button&0X03)==0X02)strcat((char*)tbuf,"RIGHT"); elseif((data->button&0X03)==0X03)strcat((char*)tbuf,"+RIGHT"); if((data->button&0X07)==0X04)strcat((char*)tbuf,"MID"); elseif((data->button&0X07)>0X04)strcat((char*)tbuf,"+MID"); LCD_Fill(30+56,180,lcddev.width,180+16,WHITE);LCD_ShowString(30,180,210,16,16,tbuf); sprintf((char*)tbuf,"XPOS:%05d",x);LCD_ShowString(30,200,200,16,16,tbuf); sprintf((char*)tbuf,"YPOS:%05d",y);LCD_ShowString(30,220,200,16,16,tbuf); sprintf((char*)tbuf,"ZPOS:%05d",z);LCD_ShowString(30,240,200,16,16,tbuf);}3、代碼移植&例程測試-代碼移植過程淘寶店鋪:技術(shù)論壇3.23,修改USR_KEYBRD_ProcessData函數(shù)為:voidUSR_KEYBRD_ProcessData(uint8_tdata){ staticu16pos,endx,endy,maxinputchar; u8buf[4]; if(USB_FIRST_PLUGIN_FLAG)//第一次插入,將數(shù)據(jù)清零
{ USB_FIRST_PLUGIN_FLAG=0;pos=0; endx=((lcddev.width-30)/8)*8+30; //得到endx值
endy=((lcddev.height-220)/16)*16+220; //得到endy值
maxinputchar=((lcddev.width-30)/8); maxinputchar*=(lcddev.height-220)/16; //當(dāng)前LCD最大可以顯示的字符數(shù). } POINT_COLOR=BLUE; sprintf((char*)buf,"%02X",data);LCD_ShowString(30+56,180,200,16,16,buf);//顯示鍵值
if(data>=''&&data<='~') { tbuf[pos++]=data; tbuf[pos]=0; //添加結(jié)束符. if(pos>maxinputchar)pos=maxinputchar; //最大輸入這么多
}elseif(data==0X0D){if(pos)pos--;tbuf[pos]=0;} //退格鍵,添加結(jié)束符. if(pos<=maxinputchar) //沒有超過顯示區(qū)
{ LCD_Fill(30,220,endx,endy,WHITE);LCD_ShowString(30,220,endx-30,endy-220,16,tbuf); } }3、代碼移植&例程測試-代碼移植過程淘寶店鋪:技術(shù)論壇3.24,修改USBH_USR_DeInit函數(shù)為:voidUSBH_USR_DeInit(void){ printf("重新初始化!!!\r\n");}3.25,由于ST官方HID例程,某些時候會死機(jī)(通信死機(jī)/枚舉死機(jī)),所以,我們在usbh_usr.c里面,添加檢查USB死機(jī)的相關(guān)代碼,一旦發(fā)現(xiàn)死機(jī),立即重啟USB。新增:mDead,檢查通信死機(jī),代碼如下://USBHID通信死機(jī)檢測,防止USB通信死機(jī)(暫時僅針對:DTERR,即Datatoggleerror)//pcore:USB_OTG_Core_dev_HANDLE結(jié)構(gòu)體指針//phidm:HID_Machine_TypeDef結(jié)構(gòu)體指針//返回值:0,沒有死機(jī)//1,死機(jī)了,外部必須重新啟動USB連接.u8mDead(USB_OTG_CORE_HANDLE*pcore,HID_Machine_TypeDef*phidm){ if(pcore->host.HC_Status[phidm->hc_num_in]==HC_DATATGLERR)//檢測到DTERR錯誤,直接重啟USB. { return1; } return0;}3、代碼移植&例程測試-代碼移植過程淘寶店鋪:技術(shù)論壇3.26,新增:USBH_Check_EnumeDead,檢查枚舉死機(jī),代碼如下://USB枚舉狀態(tài)死機(jī)檢測,防止USB枚舉失敗導(dǎo)致的死機(jī)//phost:USB_HOST結(jié)構(gòu)體指針//返回值:0,沒有死機(jī)//1,死機(jī)了,外部必須重新啟動USB連接.u8USBH_Check_EnumeDead(USBH_HOST*phost){ staticu16errcnt=0; //這個狀態(tài),如果持續(xù)存在,則說明USB死機(jī)了. if(phost->gState==HOST_CTRL_XFER&&(phost->EnumState==ENUM_IDLE||phost->EnumState==ENUM_GET_FULL_DEV_DESC)) { errcnt++; if(errcnt>2000)//死機(jī)了
{ errcnt=0; RCC_AHB2PeriphClockCmd(RCC_AHB2Periph_OTG_FS,ENABLE);//USB復(fù)位
delay_ms(5); RCC_AHB2PeriphClockCmd(RCC_AHB2Periph_OTG_FS,DISABLE);//復(fù)位結(jié)束
return1; } }elseerrcnt=0; return0;}3、代碼移植&例程測試-代碼移植過程淘寶店鋪:技術(shù)論壇//表示USB連接狀態(tài)//0,沒有連接;//1,已經(jīng)連接;externvu8bDeviceState; //默認(rèn)沒有連接u8USBH_Check_EnumeDead(USBH_HOST*phost);u8mDead(USB_OTG_CORE_HANDLE*pcore,HID_Machine_TypeDef*phidm);3.28,最后,將bDeviceState變量的聲明和USBH_Check_EnumeDead與mDead這兩個函數(shù)的定義,加入usbh_usr.h,以便其他函數(shù)調(diào)用,如下:3.27,將usbh_usr.h里面的usbh_usr_lcd.h頭文件,用usbh_hid_core.h替代,如下所示:#include"usbh_core.h"#include"usbh_hid_core.h"#include"usb_conf.h"#include<stdio.h>3、代碼移植&例程測試-代碼移植過程淘寶店鋪:技術(shù)論壇④,修改usb_bsp.c。這個.c文件的代碼,完全同:USBU盤(HOST)實(shí)驗(yàn),所以,直接從這個例程拷貝過來即可。⑤,修改usbh_hid_mouse.c,修改MOUSE_Decode函數(shù)代碼,以支持5/6字節(jié)輸出的USB鼠標(biāo),如下所示:externHID_Machine_TypeDefHID_Machine; staticvoidMOUSE_Decode(uint8_t*data){ if(HID_Machine.length==5||HID_Machine.length==6)//5/6字節(jié)長度的USB鼠標(biāo)數(shù)據(jù)處理
{ HID_MOUSE_Data.button=data[0]; HID_MOUSE_Data.x=data[1]; HID_MOUSE_Data.y=data[3]<<4|data[2]>>4; HID_MOUSE_Data.z=data[4]; }elseif(HID_Machine.length==4) //4字節(jié)長度的USB鼠標(biāo)數(shù)據(jù)處理
{ HID_MOUSE_Data.button=data[0]; HID_MOUSE_Data.x=data[1]; HID_MOUSE_Data.y=data[2]; HID_MOUSE_Data
溫馨提示
- 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
- 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
- 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負(fù)責(zé)。
- 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請與我們聯(lián)系,我們立即糾正。
- 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時也不承擔(dān)用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。
最新文檔
- 企業(yè)出資合同范本
- 農(nóng)村廚子采購合同范本
- 勘察設(shè)計(jì)合同范本全國
- 2024年河南信陽一五四醫(yī)院招聘筆試真題
- 2024重慶鏡辰美科技有限公司招聘筆試參考題庫附帶答案詳解
- 出售養(yǎng)殖用地合同范本
- 人教版七年級歷史與社會上冊 3.3.1耕海牧漁教學(xué)設(shè)計(jì)
- 買窯洞合同范本
- 臨勤合同范本
- 助播商務(wù)合同范本
- 怎樣處理課堂突發(fā)事件
- 采礦學(xué)課程設(shè)計(jì)-隆德煤礦1.8Mta新井開拓設(shè)計(jì)
- 中藥藥劑學(xué)講義(英語).doc
- 【課件】Unit1ReadingforWriting課件高中英語人教版(2019)必修第二冊
- Q∕GDW 10799.6-2018 國家電網(wǎng)有限公司電力安全工作規(guī)程 第6部分:光伏電站部分
- 滴灌工程設(shè)計(jì)示例
- 配套模塊an9238用戶手冊rev
- 醫(yī)院室外管網(wǎng)景觀綠化施工組織設(shè)計(jì)
- 霍尼韋爾DDC編程軟件(CARE)簡介
- 論《說文解字》中的水文化
- 德龍自卸車合格證掃描件(原圖)
評論
0/150
提交評論