00001 /* 00002 * Copyright (c) 1999 - 2005 NetGroup, Politecnico di Torino (Italy) 00003 * Copyright (c) 2005 - 2010 CACE Technologies, Davis (California) 00004 * All rights reserved. 00005 * 00006 * Redistribution and use in source and binary forms, with or without 00007 * modification, are permitted provided that the following conditions 00008 * are met: 00009 * 00010 * 1. Redistributions of source code must retain the above copyright 00011 * notice, this list of conditions and the following disclaimer. 00012 * 2. Redistributions in binary form must reproduce the above copyright 00013 * notice, this list of conditions and the following disclaimer in the 00014 * documentation and/or other materials provided with the distribution. 00015 * 3. Neither the name of the Politecnico di Torino, CACE Technologies 00016 * nor the names of its contributors may be used to endorse or promote 00017 * products derived from this software without specific prior written 00018 * permission. 00019 * 00020 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 00021 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 00022 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 00023 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 00024 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 00025 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 00026 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 00027 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 00028 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 00029 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 00030 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 00031 * 00032 */ 00033 00042 #ifndef __PACKET_INCLUDE______ 00043 #define __PACKET_INCLUDE______ 00044 00045 #if !defined(NDIS30) && !defined(NDIS50) 00046 #error NDIS30 or NDIS50 should be defined 00047 #endif 00048 00049 #ifdef _X86_ 00050 #define NTKERNEL 00051 #include "jitter.h" 00052 #endif 00053 00054 #ifdef HAVE_BUGGY_TME_SUPPORT 00055 #ifndef _X86_ 00056 #error TME support is available only on x86 architectures 00057 #endif // _X86_ 00058 #endif //HAVE_BUGGY_TME_SUPPORT 00059 00060 00061 // 00062 // Needed to disable a warning due to the #pragma prefast directives, 00063 // that are ignored by the normal DDK compiler 00064 // 00065 #ifndef _PREFAST_ 00066 #pragma warning(disable:4068) 00067 #endif 00068 00069 #include "win_bpf.h" 00070 00071 #define MAX_REQUESTS 32 00072 00073 #define Packet_ALIGNMENT sizeof(int) 00074 #define Packet_WORDALIGN(x) (((x)+(Packet_ALIGNMENT-1))&~(Packet_ALIGNMENT-1)) 00075 00076 00077 #define KERNEL_EVENT_NAMESPACE L"\\BaseNamedObjects\\" 00078 00079 00080 // Working modes 00081 #define MODE_CAPT 0x0 00082 #define MODE_STAT 0x1 00083 #define MODE_MON 0x2 00084 #define MODE_DUMP 0x10 00085 00086 00087 #define IMMEDIATE 1 00088 00089 #define NDIS_FLAGS_SKIP_LOOPBACK_W2K 0x400 00090 00091 // The following definitions are used to provide compatibility 00092 // of the dump files with the ones of libpcap 00093 #define TCPDUMP_MAGIC 0xa1b2c3d4 00094 #define PCAP_VERSION_MAJOR 2 00095 #define PCAP_VERSION_MINOR 4 00096 00097 // Loopback behaviour definitions 00098 #define NPF_DISABLE_LOOPBACK 1 00099 #define NPF_ENABLE_LOOPBACK 2 00100 00101 00106 struct packet_file_header 00107 { 00108 UINT magic; 00109 USHORT version_major; 00110 USHORT version_minor; 00111 UINT thiszone; 00112 UINT sigfigs; 00113 UINT snaplen; 00114 UINT linktype; 00115 }; 00116 00121 struct sf_pkthdr { 00122 struct timeval ts; 00123 UINT caplen; 00124 00125 00126 UINT len; 00127 }; 00128 00129 // 00130 // NT4 DDK doesn't have C_ASSERT 00131 // 00132 #ifndef C_ASSERT 00133 #define C_ASSERT(a) 00134 #endif 00135 00143 typedef struct _PACKET_OID_DATA { 00144 ULONG Oid; 00145 00146 ULONG Length; 00147 UCHAR Data[1]; 00148 00149 } 00150 PACKET_OID_DATA, *PPACKET_OID_DATA; 00151 00152 C_ASSERT(sizeof(PACKET_OID_DATA) == 12); 00153 00163 typedef struct _INTERNAL_REQUEST { 00164 LIST_ENTRY ListElement; 00165 // PIRP Irp; ///< Irp that performed the request 00166 // BOOLEAN Internal; ///< True if the request is for internal use of npf.sys. False if the request is performed by the user through an IOCTL. 00167 NDIS_EVENT InternalRequestCompletedEvent; 00168 NDIS_REQUEST Request; 00169 NDIS_STATUS RequestStatus; 00170 00171 } INTERNAL_REQUEST, *PINTERNAL_REQUEST; 00172 00180 typedef struct _PACKET_RESERVED { 00181 LIST_ENTRY ListElement; 00182 PIRP Irp; 00183 PMDL pMdl; 00184 BOOLEAN FreeBufAfterWrite; 00185 00186 ULONG Cpu; 00187 } PACKET_RESERVED, *PPACKET_RESERVED; 00188 00189 #define RESERVED(_p) ((PPACKET_RESERVED)((_p)->ProtocolReserved)) 00190 00191 00196 typedef struct _DEVICE_EXTENSION { 00197 NDIS_STRING AdapterName; 00198 PWSTR ExportString; 00199 00200 } DEVICE_EXTENSION, *PDEVICE_EXTENSION; 00201 00207 typedef struct __CPU_Private_Data 00208 { 00209 ULONG P; 00210 ULONG C; 00211 ULONG Free; 00212 PUCHAR Buffer; 00213 ULONG Accepted; 00214 00215 00216 00217 ULONG Received; 00218 00219 00220 00221 ULONG Dropped; 00222 00223 00224 00225 NDIS_SPIN_LOCK BufferLock; 00226 PMDL TransferMdl1; 00227 PMDL TransferMdl2; 00228 ULONG NewP; 00229 } 00230 CpuPrivateData; 00231 00232 00240 typedef struct _OPEN_INSTANCE 00241 { 00242 PDEVICE_EXTENSION DeviceExtension; 00243 00244 NDIS_HANDLE AdapterHandle; 00245 UINT Medium; 00246 00247 NDIS_HANDLE PacketPool; 00248 KSPIN_LOCK RequestSpinLock; 00249 LIST_ENTRY RequestList; 00250 LIST_ENTRY ResetIrpList; 00251 INTERNAL_REQUEST Requests[MAX_REQUESTS]; 00252 PMDL BufferMdl; 00253 PKEVENT ReadEvent; 00254 PUCHAR bpfprogram; 00255 00256 00257 00258 00259 #ifdef _X86_ 00260 JIT_BPF_Filter *Filter; 00261 00262 #endif //_X86_ 00263 UINT MinToCopy; 00264 00265 LARGE_INTEGER TimeOut; 00266 00267 00268 int mode; 00269 LARGE_INTEGER Nbytes; 00270 LARGE_INTEGER Npackets; 00271 NDIS_SPIN_LOCK CountersLock; 00272 UINT Nwrites; 00273 00274 ULONG Multiple_Write_Counter; 00275 NDIS_EVENT WriteEvent; 00276 BOOLEAN WriteInProgress; 00277 00278 NDIS_SPIN_LOCK WriteLock; 00279 NDIS_EVENT NdisRequestEvent; 00280 BOOLEAN SkipSentPackets; 00281 NDIS_STATUS IOStatus; 00282 HANDLE DumpFileHandle; 00283 PFILE_OBJECT DumpFileObject; 00284 PKTHREAD DumpThreadObject; 00285 HANDLE DumpThreadHandle; 00286 NDIS_EVENT DumpEvent; 00287 LARGE_INTEGER DumpOffset; 00288 UNICODE_STRING DumpFileName; 00289 UINT MaxDumpBytes; 00290 00291 UINT MaxDumpPacks; 00292 00293 00294 BOOLEAN DumpLimitReached; 00295 00296 #ifdef HAVE_BUGGY_TME_SUPPORT 00297 MEM_TYPE mem_ex; 00298 TME_CORE tme; 00299 #endif //HAVE_BUGGY_TME_SUPPORT 00300 00301 NDIS_SPIN_LOCK MachineLock; 00302 UINT MaxFrameSize; 00303 00304 // 00305 // KAFFINITY is used as a bit mask for the affinity in the system. So on every supported OS is big enough for all the CPUs on the system (32 bits on x86, 64 on x64?). 00306 // We use its size to compute the max number of CPUs. 00307 // 00308 CpuPrivateData CpuData[sizeof(KAFFINITY) * 8]; 00309 ULONG ReaderSN; 00310 ULONG WriterSN; 00311 00312 ULONG Size; 00313 ULONG AdapterHandleUsageCounter; 00314 NDIS_SPIN_LOCK AdapterHandleLock; 00315 ULONG AdapterBindingStatus; 00316 00317 NDIS_EVENT NdisOpenCloseCompleteEvent; 00318 NDIS_EVENT NdisWriteCompleteEvent; 00319 NTSTATUS OpenCloseStatus; 00320 ULONG TransmitPendingPackets; 00321 ULONG NumPendingIrps; 00322 BOOLEAN ClosePending; 00323 NDIS_SPIN_LOCK OpenInUseLock; 00324 } 00325 OPEN_INSTANCE, *POPEN_INSTANCE; 00326 00327 enum ADAPTER_BINDING_STATUS 00328 { 00329 ADAPTER_UNBOUND, 00330 ADAPTER_BOUND, 00331 ADAPTER_UNBINDING, 00332 }; 00333 00341 struct PacketHeader 00342 { 00343 ULONG SN; 00344 struct bpf_hdr header; 00345 }; 00346 00347 extern ULONG g_NCpu; 00348 extern NDIS_HANDLE g_NdisProtocolHandle; 00349 extern struct time_conv G_Start_Time; // from openclos.c 00350 extern UINT g_SendPacketFlags; 00351 00352 #define TRANSMIT_PACKETS 256 00353 00354 00355 00357 #define EXIT_SUCCESS(quantity) Irp->IoStatus.Information=quantity;\ 00358 Irp->IoStatus.Status = STATUS_SUCCESS;\ 00359 IoCompleteRequest(Irp, IO_NO_INCREMENT);\ 00360 return STATUS_SUCCESS;\ 00361 00363 #define EXIT_FAILURE(quantity) Irp->IoStatus.Information=quantity;\ 00364 Irp->IoStatus.Status = STATUS_UNSUCCESSFUL;\ 00365 IoCompleteRequest(Irp, IO_NO_INCREMENT);\ 00366 return STATUS_UNSUCCESSFUL;\ 00367 00368 00373 /***************************/ 00374 /* Prototypes */ 00375 /***************************/ 00376 00393 NTSTATUS 00394 DriverEntry( 00395 IN PDRIVER_OBJECT DriverObject, 00396 IN PUNICODE_STRING RegistryPath 00397 ); 00398 00408 PWCHAR getAdaptersList(VOID); 00409 00416 PKEY_VALUE_PARTIAL_INFORMATION getTcpBindings(VOID); 00417 00428 BOOLEAN NPF_CreateDevice( 00429 IN OUT PDRIVER_OBJECT adriverObjectP, 00430 IN PUNICODE_STRING amacNameP 00431 ); 00443 NTSTATUS 00444 NPF_Open( 00445 IN PDEVICE_OBJECT DeviceObject, 00446 IN PIRP Irp 00447 ); 00448 00458 VOID 00459 NPF_OpenAdapterComplete( 00460 IN NDIS_HANDLE ProtocolBindingContext, 00461 IN NDIS_STATUS Status, 00462 IN NDIS_STATUS OpenErrorStatus 00463 ); 00464 00475 NTSTATUS 00476 NPF_Cleanup( 00477 IN PDEVICE_OBJECT DeviceObject, 00478 IN PIRP Irp 00479 ); 00480 00481 NTSTATUS 00482 NPF_Close( 00483 IN PDEVICE_OBJECT DeviceObject, 00484 IN PIRP Irp 00485 ); 00486 00487 00488 00497 VOID 00498 NPF_CloseAdapterComplete( 00499 IN NDIS_HANDLE ProtocolBindingContext, 00500 IN NDIS_STATUS Status 00501 ); 00502 00525 NDIS_STATUS 00526 NPF_tap( 00527 IN NDIS_HANDLE ProtocolBindingContext, 00528 IN NDIS_HANDLE MacReceiveContext, 00529 IN PVOID HeaderBuffer, 00530 IN UINT HeaderBufferSize, 00531 IN PVOID LookAheadBuffer, 00532 IN UINT LookaheadBufferSize, 00533 IN UINT PacketSize 00534 ); 00535 00546 VOID 00547 NPF_TransferDataComplete( 00548 IN NDIS_HANDLE ProtocolBindingContext, 00549 IN PNDIS_PACKET Packet, 00550 IN NDIS_STATUS Status, 00551 IN UINT BytesTransferred 00552 ); 00553 00560 VOID 00561 NPF_ReceiveComplete(IN NDIS_HANDLE ProtocolBindingContext); 00562 00586 NTSTATUS 00587 NPF_IoControl( 00588 IN PDEVICE_OBJECT DeviceObject, 00589 IN PIRP Irp 00590 ); 00591 00592 VOID 00593 00603 NPF_RequestComplete( 00604 IN NDIS_HANDLE ProtocolBindingContext, 00605 IN PNDIS_REQUEST pRequest, 00606 IN NDIS_STATUS Status 00607 ); 00608 00621 NTSTATUS 00622 NPF_Write( 00623 IN PDEVICE_OBJECT DeviceObject, 00624 IN PIRP Irp 00625 ); 00626 00627 00647 INT NPF_BufferedWrite(IN PIRP Irp, 00648 IN PCHAR UserBuff, 00649 IN ULONG UserBuffSize, 00650 BOOLEAN sync); 00651 00659 VOID NPF_WaitEndOfBufferedWrite(POPEN_INSTANCE Open); 00660 00670 VOID 00671 NPF_SendComplete( 00672 IN NDIS_HANDLE ProtocolBindingContext, 00673 IN PNDIS_PACKET pPacket, 00674 IN NDIS_STATUS Status 00675 ); 00676 00686 VOID 00687 NPF_ResetComplete( 00688 IN NDIS_HANDLE ProtocolBindingContext, 00689 IN NDIS_STATUS Status 00690 ); 00691 00695 VOID 00696 NPF_Status( 00697 IN NDIS_HANDLE ProtocolBindingContext, 00698 IN NDIS_STATUS Status, 00699 IN PVOID StatusBuffer, 00700 IN UINT StatusBufferSize 00701 ); 00702 00703 00707 VOID 00708 NPF_StatusComplete(IN NDIS_HANDLE ProtocolBindingContext); 00709 00718 VOID 00719 NPF_Unload(IN PDRIVER_OBJECT DriverObject); 00720 00721 00740 NTSTATUS 00741 NPF_Read( 00742 IN PDEVICE_OBJECT DeviceObject, 00743 IN PIRP Irp 00744 ); 00745 00751 NTSTATUS 00752 NPF_ReadRegistry( 00753 IN PWSTR *MacDriverName, 00754 IN PWSTR *PacketDriverName, 00755 IN PUNICODE_STRING RegistryPath 00756 ); 00757 00764 NTSTATUS 00765 NPF_QueryRegistryRoutine( 00766 IN PWSTR ValueName, 00767 IN ULONG ValueType, 00768 IN PVOID ValueData, 00769 IN ULONG ValueLength, 00770 IN PVOID Context, 00771 IN PVOID EntryContext 00772 ); 00773 00779 VOID NPF_BindAdapter( 00780 OUT PNDIS_STATUS Status, 00781 IN NDIS_HANDLE BindContext, 00782 IN PNDIS_STRING DeviceName, 00783 IN PVOID SystemSpecific1, 00784 IN PVOID SystemSpecific2 00785 ); 00786 00798 VOID 00799 NPF_UnbindAdapter( 00800 OUT PNDIS_STATUS Status, 00801 IN NDIS_HANDLE ProtocolBindingContext, 00802 IN NDIS_HANDLE UnbindContext 00803 ); 00804 00805 00813 NTSTATUS NPF_OpenDumpFile(POPEN_INSTANCE Open , PUNICODE_STRING fileName, BOOLEAN append); 00814 00823 NTSTATUS NPF_StartDump(POPEN_INSTANCE Open); 00824 00832 VOID NPF_DumpThread(PVOID Open); 00833 00840 NTSTATUS NPF_SaveCurrentBuffer(POPEN_INSTANCE Open); 00841 00854 VOID NPF_WriteDumpFile(PFILE_OBJECT FileObject, 00855 PLARGE_INTEGER Offset, 00856 ULONG Length, 00857 PMDL Mdl, 00858 PIO_STATUS_BLOCK IoStatusBlock); 00859 00860 00861 00867 NTSTATUS NPF_CloseDumpFile(POPEN_INSTANCE Open); 00868 00869 BOOLEAN 00870 NPF_StartUsingBinding( 00871 IN POPEN_INSTANCE pOpen); 00872 00873 VOID 00874 NPF_StopUsingBinding( 00875 IN POPEN_INSTANCE pOpen); 00876 00877 VOID 00878 NPF_CloseBinding( 00879 IN POPEN_INSTANCE pOpen); 00880 00881 BOOLEAN 00882 NPF_StartUsingOpenInstance( 00883 IN POPEN_INSTANCE pOpen); 00884 00885 VOID 00886 NPF_StopUsingOpenInstance( 00887 IN POPEN_INSTANCE pOpen); 00888 00889 VOID 00890 NPF_CloseOpenInstance( 00891 IN POPEN_INSTANCE pOpen); 00892 00893 NTSTATUS 00894 NPF_GetDeviceMTU( 00895 IN POPEN_INSTANCE pOpen, 00896 IN PIRP pIrp, 00897 OUT PUINT pMtu); 00898 00903 UINT GetBuffOccupation(POPEN_INSTANCE Open); 00904 00916 #ifdef NDIS50 00917 NDIS_STATUS NPF_PowerChange(IN NDIS_HANDLE ProtocolBindingContext, IN PNET_PNP_EVENT pNetPnPEvent); 00918 #endif 00919 00920 // 00921 // Old registry based WinPcap names 00922 // 00924 // \brief Helper function to query a value from the global WinPcap registry key 00925 //*/ 00926 //VOID NPF_QueryWinpcapRegistryString(PWSTR SubKeyName, 00927 // WCHAR *Value, 00928 // UINT ValueLen, 00929 // WCHAR *DefaultValue); 00930 // 00931 00932 00941 #endif /*main ifndef/define*/
documentation. Copyright (c) 2002-2005 Politecnico di Torino. Copyright (c) 2005-2009 CACE Technologies. All rights reserved.