一个最简单的问题:CreateFile()函数与COM_Open()函数的关系

  • 请教大家一个最基本的问:
      这两天研究了一下串口驱动程序(MDD,PDD),发现这么一个问题:CreateFile(L"COM1:",....)中的"COM1"的信息是怎样记录到COM_Open()的句柄中的。COM_init()(有DeviceArrayIndex和Priority256)和HWinit(有memorywindow,interrupt,physicalbase)中好像没有对COMindex的记录?有的话,麻烦指点下!,COM_Read()又是如何判断要读数据的口是COM1还是其他口的呢?我看了好几遍了都没看明白,请高手指点下!不胜感激!
L"COM1:"参数,就是用于COM_Read判断的
应该去研究CreateFile创建的句柄中,COM1:对应于什么信息,这个信息就是以后相关API判断操作那个文件或设备的依据。

不知道我有没有理解LZ的问题 HANDLE COM_Init(
  ULONG Identifier
);

这个吧二楼说的也对,但是就是不知道COM_Read是根据那个记录信息来判断的. COM_Read()代码开始是对参数检查,包括对存取权限,OpenCnt等。之后计算超时时间,如果设定了超时读取动作会在超时后返回,不管是否读到了足够长度的数据。随后就是简单对软件缓冲进行读取的操作了,读取的操作是在RX_CS中完成的。最后在读取的过程中需要处理流控制的成本了,包括软件流和硬件流. 那么它从软件缓冲读取数据时,怎么知道是哪个口的数据呢? 大家帮忙顶一下阿!你在 COM_Init(ULONG Identifier) 中, 應可透過 OpenDeviceKey 來得到其 registry setting (若不知如何使用, 請參考 %_WINCEROOT%/PUBLIC/COMMON/OAK/DRIVERS/SERIAL/COM_MDD2/mdd2.c 的程式). 如此即可得知其載入的 Index, 或是透過 RegOpenKeyEx(HKEY_LOCAL_MACHINE, Identifier, ...) 的方式, 來直接得到 "Activate" 的值, 將值記錄在 COM_Init 的回傳值 (return value) 中, 該值即為 COM_Open 的第一個 parameter, 而 COM_Open 的回傳值, 即為 COM_Read 的 first parameter.

Paul, Chao @ Techware
Paul,chao,我的两个真实串口的注册表如下:
[HKEY_LOCAL_MACHINE/Drivers/BuiltIn/Serial]
  "Order"=dword:0
  "InterfaceType"=dword:0
  "IoBase"=dword:10030000
  "IoLen"=dword:20
  "Irq"=dword:9
  "DeviceArrayIndex"=dword:0
  "Prefix"="COM"
  "Index"=dword:3
  "Dll"="Serial.dll"
[HKEY_LOCAL_MACHINE/Drivers/BuiltIn/Serial2]
  "Order"=dword:0
  "InterfaceType"=dword:0
  "IoBase"=dword:10031000
  "IoLen"=dword:20
  "Irq"=dword:8
  "DeviceArrayIndex"=dword:1
  "Prefix"="COM"
  "Index"=dword:2
  "Dll"="Serial.dll"
我研究了一下mdd.c中的COM_Init()发现没有对COM Index的记录呀
   DEBUGMSG (ZONE_INIT,(TEXT("Try to open %s/r/n"), (LPCTSTR)Identifier));
    hKey = OpenDeviceKey((LPCTSTR)Identifier);
    if ( !hKey ) {DEBUGMSG (ZONE_INIT | ZONE_ERROR,(TEXT("Failed to open devkeypath, COM_Init failed/r/n")));
           LocalFree(pSerialHead);
           return(NULL);
    }
    datasize = sizeof(DWORD);
    if ( RegQueryValueEx(hKey, L"[color=#FF0000]有这个DeviceArrayIndex
", NULL, &kvaluetype,(LPBYTE)&DevIndex, &datasize) ) {
        DEBUGMSG (ZONE_INIT | ZONE_ERROR,(TEXT("Failed to get DeviceArrayIndex value, COM_Init failed/r/n")));
        RegCloseKey (hKey);
        LocalFree(pSerialHead);
        return(NULL);
    }
    datasize = sizeof(DWORD);
    if ( RegQueryValueEx(hKey, L" 有这个Priority256", NULL, &kvaluetype,
                        (LPBYTE)&pSerialHead->Priority256, &datasize) ) {
        pSerialHead->Priority256 = DEFAULT_CE_THREAD_PRIORITY;
       DEBUGMSG (ZONE_INIT | ZONE_WARN,(TEXT("Failed to get Priority256 value, defaulting to %d/r/n"), pSerialHead->Priority256));
    }
    RegCloseKey (hKey);
    DEBUGMSG (ZONE_INIT,
              (TEXT("DevIndex %X/r/n"), DevIndex));
    // Initialize hardware dependent data.
    pSerialHead->pHWObj = GetSerialObject( DevIndex );
    if ( !pSerialHead->pHWObj ) {
        DEBUGMSG(ZONE_ERROR | ZONE_INIT,
                (TEXT("Error in GetSerialObject, COM_Init failed/n/r")));
        LocalFree(pSerialHead);
        return(NULL);
    }
    DEBUGMSG (ZONE_INIT, (TEXT("About to call HWInit(%s,0x%X)/r/n"),Identifier, pSerialHead));
    pHWHead = pSerialHead->pHWObj->pFuncTbl->HWInit(Identifier, pSerialHead, pSerialHead->pHWObj);
    pSerialHead->pHWHead = pHWHead;[/color]
只有DeviceArrayIndex和Priority256

况且即使有,按照流驱动的加载顺序:
1)加载驱动。在当系统启动时,设备管理器搜寻注册表的HKEY_LOCAL_MACHINE/Driver/BuiltIn键下面的子键,并逐一加载子键下的每个驱动,此过程叫BusEnum。
2)设备管理器从注册表的dll键值中获取驱动程序所在的DLL文件名。
3)设备管理器调用LoadDriver()函数把DLL加载到自己的虚拟地址空间内。
4)设备管理器在注册表的HKEY_LOCAL_MACHINE/Driver/Active下面,记录所有已经加载的驱动程序[2]。
5)设备管理器调用驱动中的XXX_Init()函数。
6)在XXX_Init()中,通常对硬件进行一些基本的初始化操作。通过以上6步,流接口驱动被成功加载。
7)应用程序使用该设备。首先它调用CreateFile()打开设备。CreateFile()是在FileSys.exe中实现的。但是FileSys.exe只作简单判断,如果发现打开的设备驱动程序而不是一个文件,那么就重新把主动权交还给设备管理器。
由此可见COM_Init()的执行要先于CreateFile(),那么COM_Init()执行完毕之后我注册表中的两个个串口的Index会同时被记录的呀 把驱动加载流程搞懂,这些都不是问题了
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值