WINCE6.0+SLC NAND FLASH实现U盘功能

备注:选择ROM-only文件系统

 

1.      WINCE6.0FLASH映射为PC磁盘

WINCE6.0实现把FLASH映射为PC磁盘的实现主要由mass storage实现,其代码在

\WINCE600\PUBLIC\COMMON\OAK\DRIVERS\USBFN\CLASS\STORAGE中,此部分代码编译生成usbmsfn.dll,在连接USB线时,USB功能驱动,比如s3c2450_usbfn.dll会通过调用代码pContext->pfnNotify(pContext->pvMddContext, UFN_MSG_BUS_EVENTS, UFN_ATTACH);

来通知usbmsfn.dll,然后usbmsfn.dll读取下面的注册表:

[HKEY_LOCAL_MACHINE\Drivers\USB\FunctionDrivers\Mass_Storage_Class]下的注册表信息,"DeviceName"="DSK3:"

Usbmsfn根据"DeviceName"="DSK3:",把DSK3对应的FLASH分区映射为PC磁盘,同时这个盘符在pc上看到后,在wince下就会消失,在wince下不能同时访问这个盘符。这里的DSK3可以根据自己的具体指来定。

 

对于三星的MLCSLC NAND FLASH,把FLASHFAT分区映射到PC作为磁盘有两种思路:

MLC

根据三星的MLC NAND驱动,一个FLASH被分成多个DSK加载,这个可以通过修改NAND驱动的注册表信息来实现,比如MLC FLASH,分为三个分区,分别为一个BINFS分区,两个FAT分区,其中BINFS只是是用于保存NK的,两个FAT分区对应两个不同的DSK驱动被加载,比如DSK2DSK3,这样就只需要把上面注册表DeviceName的值改为对应的DSK,这样usbmsfn就可以把DSK对应的分区映射到PC端了。

WINCE6.0+SLC NAND FLASH实现U盘功能_第1张图片

1

MLC实现为PC磁盘的相关部分见我之前的博客:

http://blog.csdn.net/loongembedded/article/details/7536193

 

SLC

SLC驱动一般不管把FLASH分为几个分区都只有一个DSK,其中包含至少两个partition,前边的是BINFS,后边的是FAT,比如SLC驱动把FLASH分为三个分区,如下图:

WINCE6.0+SLC NAND FLASH实现U盘功能_第2张图片

2

其中part00BINFS,对一个binfs.dllpart01part02dFAT分区,对应exfat.dll,有图2可以看出只有一个DSK,就是DSK3。可是微软usbmsfn.dll的实现是Unmount整个DISK的,所以需要修改usbmsfn.dll的代码,对于SLC来说,只需要Unmount这个DSK的对应的分区就可以,把这个partition映射到PC,同时WINCE端这个FAT区消失。

 

是指定哪个盘符,"Removable"=dword:0是在PC端显示成本地磁盘还是移动磁盘。

2.      三星SLC实现映射为PC磁盘的实现

 

2.1  移植STORAGE代码

因为STORAGE代码是在public中,修改和调试所需要的编译时间太长,所以就移植到我们BSPdrivers目录下作为一个单独的驱动的实现,编译生成的还是usbmsfn.dll,把\WINCE600\PUBLIC\COMMON\OAK\DRIVERS\USBFN\CLASS\STORAGE代码拷贝到drivers目录下,所需要做的工作就是让我们drivers下的STORAGE文件下能够单独编译生成usbmsfn.dll,我在这里是通过修改STORAGE\TRANSPORT\BOT\sources的文件来实现的,修改之前:

TARGETDEFNAME=USBMSFN

DEFFILE=$(TARGETDEFNAME).DEF

PREPROCESSDEFFILE=1

 

TARGETNAME=USBMSFN_LIB

TARGETTYPE=LIBRARY

WINCETARGETFILE0=$(_COMMONOAKROOT)\lib\$(_CPUINDPATH)\$(DEFFILE)

 

INCLUDES= \

   ..\inc; \

   ..\..\inc; \

 

SOURCES= \

bot.cpp \

修改之后:

TARGETNAME=usbmsfn

 

TARGETTYPE=DYNLINK

RELEASETYPE=PLATFORM

SYNCHRONIZE_DRAIN=1

 

DLLENTRY=_DllEntryCRTStartup

 

DEFFILE=$(_PUBLICROOT)\common\oak\lib\$(_CPUINDPATH)\usbmsfn.def

 

SOURCELIBS=

 

TARGETLIBS=\

   $(_TARGETPLATROOT)\lib\$(_CPUINDPATH)\scsi2dad.lib \

   $(_SYSGENOAKROOT)\lib\$(_CPUINDPATH)\ufnclientlib.lib \

   $(_PUBLICROOT)\common\oak\lib\$(_CPUINDPATH)\storeapi.lib \

   $(_SYSGENSDKROOT)\lib\$(_CPUINDPATH)\coredll.lib

 

INCLUDES= \

   ..\inc; \

   ..\..\inc; \

 

SOURCES= \

bot.cpp \

这样我们drivers下的STORAGE文件下能够单独编译生成usbmsfn.dll,当然,public下也会编译生成这个dll,但是因为我们BSP包下的drivers编译时间在它后面,所以,我们的usbmsfn.dll会覆盖掉public下编译生成的。

 

2.2  修改STORAGE代码

 

STORE_Init函数

g_hStore = OpenStore(g_szDeviceName);的下面打开此DSK对应的分区:

g_hPartition = OpenPartition(g_hStore, _T("Part02"));

 

if (!DismountStore(g_hStore)) {

       dwError = GetLastError();

       goto EXIT;

}改为Unmount分区:

if (!DismountPartition(g_hPartition))

                   {

                dwError = GetLastError();

                goto EXIT;

             }

 

STORE_Close函数

DismountStore(g_hStore);改为DismountPartition(g_hPartition);

 

2.3  遇到的问题及解决办法

根据上面的修改就可以把SLC对应的分区映射为PC的磁盘,但在测试过程中发现一些问题,详见csdn帖子http://bbs.csdn.net/topics/390332837:

 

WINCE设备第一次把Flash Disk作为PC的可移动磁盘使用时,在PC端需要先格式化才能使用,我想要的效果是就算是第一次也不需要先格式化(WINCE设备下的TF卡作为PC的可移动磁盘使用时,就算是第一次也不需要在PC端对其格式化的),该怎么实现呢?


3

在格式化之前文件系统显示的是RAW,双击之后进行格式化的选择如下:

WINCE6.0+SLC NAND FLASH实现U盘功能_第3张图片

4

这是在xp系统下看到的,记得选择格式化为FAT32文件系统,如果格式化为FAT之后,重新启动WINCE设备,之前在我的设备中可见到的NAND盘符变成已装入的卷,接入USB线之后,已装入的卷盘符不会消失,在PC端也看不到此分区对应的磁盘,在WINCE的存储管理器中看到:

WINCE6.0+SLC NAND FLASH实现U盘功能_第4张图片

5

之前的part02变成*,应该是因为我们SLC驱动中用的是exfat.dll对应的是FAT32文件格式,但在PC端却格式化为FAT格式,所以存储管理器不能正常识别。

 

对于xp的系统也不能选择格式化为exfat,此时无法完成格式化,至于具体的原因目前还不清楚,如下图:

WINCE6.0+SLC NAND FLASH实现U盘功能_第5张图片

6

正常格式化为FAT32文件系统之后,右击磁盘属性,可以看到下图:

WINCE6.0+SLC NAND FLASH实现U盘功能_第6张图片

7

 

到此先回到怎么解决第一次不需要格式化的问题,刚开始以为是xp系统不能直接识别文件系统格式为FAT32FLASH分区

[HKEY_LOCAL_MACHINE\System\StorageManager\Profiles\NAND\FATFS]

        "FormatExfat"=dword:1

 就在上面的注册表基础上添加了"Dll"="exfat.dll",可以还是需要格式,不过xp系统识别到的文件系统由RAW变为FAT32

8

后来把上面的"FormatExfat"=dword:1改为"FormatFAT"=dword:1才解决了第一次不需要格式化的问题。

 


假设在我的设备界面下接入USB线,这时候Flash Disk会自动隐藏,当拔出USB线的时候,我的设备窗口会自动退出,直接回到桌面,这是一个问题,另外还有就是,这时我到桌面新建文件夹,但看不到新建的文件夹,如果到windows->桌面文件夹下确实可以看到刚才新建的文件夹的

 

后来经过调试发现是STORE_Close函数中的问题,在此函数中调用到MoveFile函数,其作用相当于在拔出USB线的时候重新mount DSK对应的分区,把此处理部分改为MountPartition(g_hPartition);就解决了这些问题

WINCE6.0+SLC NAND FLASH实现U盘功能_第7张图片

9

FLASHPC端显示为本地磁盘还是移动磁盘

[HKEY_LOCAL_MACHINE\Drivers\USB\FunctionDrivers\Mass_Storage_Class]

"Removable"=dword:1

这里其值为1表示在PC端是在PC端显示为移动磁盘,为0显示成本地磁盘,可是我改为0之后,虽然WINCE设备对应的盘符可以隐藏,但在PC端却看不到,具体的原因还不知很清楚,因为此问题不影响客户时候,后面再查,就先写到这里了,知道的朋友还望可以分享。


xp系统exfat补丁下载地址http://www.microsoft.com/zh-cn/download/confirmation.aspx?id=19364

 

你可能感兴趣的:(WINCE6.0+SLC NAND FLASH实现U盘功能)