阅读:950回复:0
driverworks 3.0中的NmInt例子在win2003下蓝屏Bug
DDK版本是2600。
修正的地方: 在Program Files\\Compuware\\SoftICE Driver Suite\\DriverNetworks\\include目录下 KNdisMedium.h和kndisprotocolwrapper.h 前者的内存访问有错误, 后者是个小毛病,bind()函数中SelectedMedium应该在调用OpenComplete()前设置好。 其他: netNmIntMP.inf中Characteristics原来是29(隐藏), 改为21,虚拟网卡才会在网络邻居属性里出现。 以下是那两个头文件的补丁文件的内容,存成文件在linux下用patch或手工修改。 diff -aur org/KNdisMedium.h my/KNdisMedium.h --- org/KNdisMedium.h 2003-07-15 18:18:36.000000000 +0800 +++ my/KNdisMedium.h 2003-12-24 23:20:24.000000000 +0800 @@ -52,7 +52,7 @@ operator PNDIS_MEDIUM() const { return (PNDIS_MEDIUM) m_Medium; } // Return selected medium - NDIS_MEDIUM SelectedMedium() const { return *this[m_Index]; } + NDIS_MEDIUM SelectedMedium() const { return (*this)[m_Index]; } // Returns the size in bytes of the medium array UINT Size() const { return m_MediumSize; } @@ -73,7 +73,7 @@ protected: UINT m_MediumSize; UINT m_Index; - NDIS_MEDIUM m_Medium[NdisMediumMax]; + NDIS_MEDIUM m_Medium[NdisMediumMax * 2]; public: @@ -126,7 +126,15 @@ KNdisMedium::KNdisMedium(PNDIS_MEDIUM MediumArray, UINT MediumArraySize) : m_MediumSize(MediumArraySize), m_Index(UINT(-1)) { - NdisMoveMemory(&m_Medium, MediumArray, MediumArraySize*sizeof(NDIS_MEDIUM)); + //2k&xp NdisMediumMax == 14 but 2003 called with MediumArraySize = 15 + if (sizeof(m_Medium)/sizeof(m_Medium[0]) < MediumArraySize) + { +#if defined(NDIS50) && NDIS50 == 1 + DbgPrint(\"KNdisMedium::KNdisMedium():too large MediumArraySize\\n\"); +#endif + m_MediumSize = sizeof(m_Medium)/sizeof(m_Medium[0]); + } + NdisMoveMemory(&m_Medium, MediumArray, m_MediumSize*sizeof(NDIS_MEDIUM)); } diff -aur org/KNdisProtocolWrapper.h my/KNdisProtocolWrapper.h --- org/KNdisProtocolWrapper.h 2003-07-15 18:18:36.000000000 +0800 +++ my/KNdisProtocolWrapper.h 2003-12-25 09:26:22.000000000 +0800 @@ -424,11 +424,11 @@ // Construct protocol config and empty medium objects. Note SystemSpecific1 is // a \"protocol section\" name in the Registry. Then pass control to client\'s Open() KNdisConfig Config( reinterpret_cast<PNDIS_STRING> (SystemSpecific1) ); - KNdisMedium Medium; + KNdisMedium SupportedMedium; PSTRING AddressInfo=NULL; NDIS_STATUS sts_ex; - NDIS_STATUS sts = b->Open(DeviceName, Config, Medium, &AddressInfo); + NDIS_STATUS sts = b->Open(DeviceName, Config, SupportedMedium, &AddressInfo); if (sts != NDIS_STATUS_SUCCESS) { *Status = sts; // protocol decided not to bind, bail out delete b; @@ -439,12 +439,14 @@ // Note that \'B\' must provide GetContainerHandle() method, which returns // protocol handle assigned on NdisRegisterProtocol(). + UINT mediaSelectedIndex = -1; NdisOpenAdapter(&sts, &sts_ex, // extended err code if any b->HandlePTR(), // cached handle value to be assigned - (PUINT)PNDIS_MEDIUM(*b), // cached medium index to be selected - Medium, - Medium.Size(), + //(PUINT)PNDIS_MEDIUM(*b), // cached medium index to be selected + &mediaSelectedIndex, + SupportedMedium, + SupportedMedium.Size(), b->GetContainerHandle(), // protocol handle b, // \'this\' we want to get in all consequitive callbacks DeviceName, @@ -460,12 +462,23 @@ *PNDIS_STATUS(*b) = sts; // save status in the object if (sts == NDIS_STATUS_SUCCESS) { + if (mediaSelectedIndex == -1) + { + *Status = NDIS_STATUS_FAILURE; + TRACE(\"no supported medium selected.\\n\"); + b->CloseAdapter(true); + delete b; + return; + } // Now, cache the adapter\'s friendly name, if we\'re set to do so if (KNdisProtocolTraits<B>::CacheFriendlyAdapterName()) b->GetAdapterName(); b->SetBound(true); } + + // OK. Turn medium index into medium type + *PNDIS_MEDIUM(*b) = SupportedMedium [mediaSelectedIndex]; // Inform the client on completion. If it was unsuccessful the binding object is destroyed. b->OpenComplete(); *Status = sts = *PNDIS_STATUS(*b); // retrieve the status of open complete operation @@ -476,8 +489,6 @@ return; } - // OK. Turn medium index into medium type - *PNDIS_MEDIUM(*b) = Medium [*(PUINT)PNDIS_MEDIUM(*b)]; UNREFERENCED_PARAMETER(SystemSpecific2); } |
|