完善资料让更多小伙伴认识你,还能领取20积分哦, 立即完善>
之前的文章中介绍过STM32读写SD卡和FatFS文件系统相关的知识。今天将在这基础上介绍STM32通过USB口虚拟U盘的知识。即插入USB接口后,电脑将SD卡识别为U盘,可以直接读写SD卡内的文件。
硬件环境:STM32F407ZGT6 软件环境:STM32CubeMX v5.5.0 HAL库版本:STM32CubeF4 Firmware Package V1.24.0 1.STM32CubeMX配置 首先SD卡为SDIO接口,时钟等基础配置、SDIO接口配置和FatFs文件系统的配置参考之前的文章《STM32CubeMX之SDIO+FatFS读写SD卡》。之后需要配置USB接口,F407有两个USB接口,这里使用USB_OTG_FS接口,模式选择为设备模式Device_Only,其它配置默认即可。 在中间件菜单下选择USB_DEVICE,选择大容量存储设备(Mass Storage Class),其它参数默认即可。 生成代码之前,系统堆栈配置大一些: 2.程序编写 SD卡和文件系统读写文件等操作,参考之前文章,也不在这里介绍。 需要用户实现的只有USB虚拟U盘相关的函数,都在u***d_storage_if.c文件中。需要实现以下几个函数,其中中文注释的四个为必须实现的,其它的可选。 USBD_StorageTypeDef USBD_Storage_Interface_fops_FS = { STORAGE_Init_FS, STORAGE_GetCapacity_FS, //获取U盘容量 STORAGE_IsReady_FS, //判断U盘状态 STORAGE_IsWriteProtected_FS, STORAGE_Read_FS, //读U盘数据 STORAGE_Write_FS, //写U盘数据 STORAGE_GetMaxLun_FS, (int8_t *)STORAGE_Inquirydata_FS }; 因为SD卡扇区读写等相关的驱动函数系统已经自动生成,这里只需要调用相关函数即可。四个函数的实现如下: 获取容量函数: int8_t STORAGE_GetCapacity_FS(uint8_t lun, uint32_t *block_num, uint16_t *block_size) { /* USER CODE BEGIN 3 */ *block_num = hsd.SdCard.BlockNbr; *block_size = hsd.SdCard.BlockSize; return (USBD_OK); /* USER CODE END 3 */ } 判断U盘状态函数: int8_t STORAGE_IsReady_FS(uint8_t lun) { /* USER CODE BEGIN 4 */ uint8_t state = 0; state = HAL_SD_GetState(&hsd) ; if(HAL_SD_STATE_READY != state) { return USBD_FAIL ; } return (USBD_OK); /* USER CODE END 4 */ } U盘读数据函数: int8_t STORAGE_Read_FS(uint8_t lun, uint8_t *buf, uint32_t blk_addr, uint16_t blk_len) { /* USER CODE BEGIN 6 */ if(HAL_OK != HAL_SD_ReadBlocks(&hsd,(uint8_t *)buf, blk_addr , blk_len, 1000)) { return USBD_FAIL ; } return (USBD_OK); /* USER CODE END 6 */ } U盘写数据函数: i int8_t STORAGE_Write_FS(uint8_t lun, uint8_t *buf, uint32_t blk_addr, uint16_t blk_len) { /* USER CODE BEGIN 7 */ if(HAL_OK != HAL_SD_WriteBlocks(&hsd, (uint8_t *)buf, blk_addr , blk_len, 1000)) { return USBD_FAIL ; } return (USBD_OK); /* USER CODE END 7 */ } 完成之后,在主函数中初始化后添加相关测试程序,在SD卡新建一个文件,并写入数据。 retSD = f_mount(&SDFatFS, (TCHAR const*)SDPath, 0);//挂载 retSD = f_open(&SDFile,(const char*)"测试.txt",FA_CREATE_ALWAYS|FA_WRITE); retSD = f_write(&SDFile,FileBuf,17,&bw); retSD = f_close(&SDFile); 运行程序后,将USB线插入电脑,电脑识别出一个U盘,打开后可看到U盘内的文件及内容与所以写程序一致,说明程序正确。 通过电脑在U盘中新建一个文件,123.txt,任意写入一些内容。同时将刚才的写文件的程序改为读文件,并重新运行程序。 retSD = f_open(&SDFile,(const char*)"123.txt",FA_OPEN_EXISTING|FA_READ);//打开文件 if(retSD==FR_OK) { retSD = f_read(&SDFile,FileBuf,17,&bw); } retSD = f_close(&SDFile); 可以看到程序读取的数据与电脑上新建并写入的内容一致,说明程序正确。 3.总结 USB虚拟U盘的接口有很多应用,比如,可以通过USB接口直接SD卡内的导出文件。也可以利用该功能实现IAP功能,将bin文件拷贝到SD卡,Boot程序读取SD卡进行程序升级。应用时需要注意USB接口操作SD卡和程序操作SD卡不能同时进行,以免发生冲突。 |
|
|
|
只有小组成员才能发言,加入小组>>
3263 浏览 9 评论
2944 浏览 16 评论
3443 浏览 1 评论
8955 浏览 16 评论
4036 浏览 18 评论
1078浏览 3评论
558浏览 2评论
const uint16_t Tab[10]={0}; const uint16_t *p; p = Tab;//报错是怎么回事?
551浏览 2评论
用NUC131单片机UART3作为打印口,但printf没有输出东西是什么原因?
2286浏览 2评论
NUC980DK61YC启动随机性出现Err-DDR是为什么?
1848浏览 2评论
小黑屋| 手机版| Archiver| 电子发烧友 ( 湘ICP备2023018690号 )
GMT+8, 2024-11-10 15:51 , Processed in 0.812692 second(s), Total 47, Slave 39 queries .
Powered by 电子发烧友网
© 2015 bbs.elecfans.com
关注我们的微信
下载发烧友APP
电子发烧友观察
版权所有 © 湖南华秋数字科技有限公司
电子发烧友 (电路图) 湘公网安备 43011202000918 号 电信与信息服务业务经营许可证:合字B2-20210191 工商网监 湘ICP备2023018690号