1 /*++ 2 3 Copyright (c) Microsoft Corporation 4 5 Module Name: 6 7 FxDeviceInitApi.cpp 8 9 Abstract: 10 11 This module exposes the "C" interface to the FxDevice object. 12 13 Author: 14 15 16 17 Environment: 18 19 Both kernel and user mode 20 21 Revision History: 22 23 --*/ 24 25 #include "coreprivshared.hpp" 26 27 extern "C" { 28 // #include "FxDeviceInitApi.tmh" 29 } 30 31 typedef struct _WDF_PNPPOWER_EVENT_CALLBACKS_V1_9 { 32 // 33 // Size of this structure in bytes 34 // 35 ULONG Size; 36 37 PFN_WDF_DEVICE_D0_ENTRY EvtDeviceD0Entry; 38 39 PFN_WDF_DEVICE_D0_ENTRY_POST_INTERRUPTS_ENABLED EvtDeviceD0EntryPostInterruptsEnabled; 40 41 PFN_WDF_DEVICE_D0_EXIT EvtDeviceD0Exit; 42 43 PFN_WDF_DEVICE_D0_EXIT_PRE_INTERRUPTS_DISABLED EvtDeviceD0ExitPreInterruptsDisabled; 44 45 PFN_WDF_DEVICE_PREPARE_HARDWARE EvtDevicePrepareHardware; 46 47 PFN_WDF_DEVICE_RELEASE_HARDWARE EvtDeviceReleaseHardware; 48 49 PFN_WDF_DEVICE_SELF_MANAGED_IO_CLEANUP EvtDeviceSelfManagedIoCleanup; 50 51 PFN_WDF_DEVICE_SELF_MANAGED_IO_FLUSH EvtDeviceSelfManagedIoFlush; 52 53 PFN_WDF_DEVICE_SELF_MANAGED_IO_INIT EvtDeviceSelfManagedIoInit; 54 55 PFN_WDF_DEVICE_SELF_MANAGED_IO_SUSPEND EvtDeviceSelfManagedIoSuspend; 56 57 PFN_WDF_DEVICE_SELF_MANAGED_IO_RESTART EvtDeviceSelfManagedIoRestart; 58 59 PFN_WDF_DEVICE_SURPRISE_REMOVAL EvtDeviceSurpriseRemoval; 60 61 PFN_WDF_DEVICE_QUERY_REMOVE EvtDeviceQueryRemove; 62 63 PFN_WDF_DEVICE_QUERY_STOP EvtDeviceQueryStop; 64 65 PFN_WDF_DEVICE_USAGE_NOTIFICATION EvtDeviceUsageNotification; 66 67 PFN_WDF_DEVICE_RELATIONS_QUERY EvtDeviceRelationsQuery; 68 69 } WDF_PNPPOWER_EVENT_CALLBACKS_V1_9, *PWDF_PNPPOWER_EVENT_CALLBACKS_V1_9; 70 71 72 typedef struct _WDF_POWER_POLICY_EVENT_CALLBACKS_V1_5 { 73 // 74 // Size of this structure in bytes 75 // 76 ULONG Size; 77 78 PFN_WDF_DEVICE_ARM_WAKE_FROM_S0 EvtDeviceArmWakeFromS0; 79 80 PFN_WDF_DEVICE_DISARM_WAKE_FROM_S0 EvtDeviceDisarmWakeFromS0; 81 82 PFN_WDF_DEVICE_WAKE_FROM_S0_TRIGGERED EvtDeviceWakeFromS0Triggered; 83 84 PFN_WDF_DEVICE_ARM_WAKE_FROM_SX EvtDeviceArmWakeFromSx; 85 86 PFN_WDF_DEVICE_DISARM_WAKE_FROM_SX EvtDeviceDisarmWakeFromSx; 87 88 PFN_WDF_DEVICE_WAKE_FROM_SX_TRIGGERED EvtDeviceWakeFromSxTriggered; 89 90 } WDF_POWER_POLICY_EVENT_CALLBACKS_V1_5, *PWDF_POWER_POLICY_EVENT_CALLBACKS_V1_5; 91 92 typedef struct _WDF_PDO_EVENT_CALLBACKS_V1_9 { 93 // 94 // The size of this structure in bytes 95 // 96 ULONG Size; 97 98 // 99 // Called in response to IRP_MN_QUERY_RESOURCES 100 // 101 PFN_WDF_DEVICE_RESOURCES_QUERY EvtDeviceResourcesQuery; 102 103 // 104 // Called in response to IRP_MN_QUERY_RESOURCE_REQUIREMENTS 105 // 106 PFN_WDF_DEVICE_RESOURCE_REQUIREMENTS_QUERY EvtDeviceResourceRequirementsQuery; 107 108 // 109 // Called in response to IRP_MN_EJECT 110 // 111 PFN_WDF_DEVICE_EJECT EvtDeviceEject; 112 113 // 114 // Called in response to IRP_MN_SET_LOCK 115 // 116 PFN_WDF_DEVICE_SET_LOCK EvtDeviceSetLock; 117 118 // 119 // Called in response to the power policy owner sending a wait wake to the 120 // PDO. Bus generic arming shoulding occur here. 121 // 122 PFN_WDF_DEVICE_ENABLE_WAKE_AT_BUS EvtDeviceEnableWakeAtBus; 123 124 // 125 // Called in response to the power policy owner sending a wait wake to the 126 // PDO. Bus generic disarming shoulding occur here. 127 // 128 PFN_WDF_DEVICE_DISABLE_WAKE_AT_BUS EvtDeviceDisableWakeAtBus; 129 130 } WDF_PDO_EVENT_CALLBACKS_V1_9, *PWDF_PDO_EVENT_CALLBACKS_V1_9; 131 132 133 // 134 // Extern "C" the entire file 135 // 136 extern "C" { 137 138 __drv_maxIRQL(DISPATCH_LEVEL) 139 VOID 140 STDCALL 141 WDFEXPORT(WdfDeviceInitFree)( 142 __in 143 PWDF_DRIVER_GLOBALS DriverGlobals, 144 __in 145 PWDFDEVICE_INIT DeviceInit 146 ) 147 { 148 DDI_ENTRY(); 149 150 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 151 152 if (DeviceInit->CreatedOnStack == FALSE) { 153 delete DeviceInit; 154 } 155 } 156 157 __drv_maxIRQL(DISPATCH_LEVEL) 158 VOID 159 STDCALL 160 WDFEXPORT(WdfDeviceInitSetIoType)( 161 __in 162 PWDF_DRIVER_GLOBALS DriverGlobals, 163 __in 164 PWDFDEVICE_INIT DeviceInit, 165 __in 166 WDF_DEVICE_IO_TYPE IoType 167 ) 168 { 169 DDI_ENTRY(); 170 171 WDF_IO_TYPE_CONFIG ioTypeConfig; 172 173 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 174 175 WDF_IO_TYPE_CONFIG_INIT(&ioTypeConfig); 176 ioTypeConfig.ReadWriteIoType = IoType; 177 178 DeviceInit->AssignIoType(&ioTypeConfig); 179 } 180 181 _IRQL_requires_max_(PASSIVE_LEVEL) 182 WDFAPI 183 VOID 184 STDCALL 185 WDFEXPORT(WdfDeviceInitSetIoTypeEx)( 186 _In_ 187 PWDF_DRIVER_GLOBALS DriverGlobals, 188 _In_ 189 PWDFDEVICE_INIT DeviceInit, 190 _In_ 191 PWDF_IO_TYPE_CONFIG IoTypeConfig 192 ) 193 { 194 DDI_ENTRY(); 195 196 NTSTATUS status; 197 PFX_DRIVER_GLOBALS pFxDriverGlobals; 198 199 pFxDriverGlobals = GetFxDriverGlobals(DriverGlobals); 200 201 FxPointerNotNull(pFxDriverGlobals, DeviceInit); 202 203 if (IoTypeConfig->Size != sizeof(WDF_IO_TYPE_CONFIG)) { 204 status = STATUS_INFO_LENGTH_MISMATCH; 205 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGPNP, 206 "IoTypeConfig size (%d) incorrect, expected %d, %!STATUS!", 207 IoTypeConfig->Size, 208 sizeof(WDF_IO_TYPE_CONFIG), status); 209 return; 210 } 211 212 DeviceInit->AssignIoType(IoTypeConfig); 213 } 214 215 __drv_maxIRQL(DISPATCH_LEVEL) 216 VOID 217 STDCALL 218 WDFEXPORT(WdfDeviceInitSetExclusive)( 219 __in 220 PWDF_DRIVER_GLOBALS DriverGlobals, 221 __in 222 PWDFDEVICE_INIT DeviceInit, 223 __in 224 BOOLEAN Exclusive 225 ) 226 { 227 DDI_ENTRY(); 228 229 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 230 231 DeviceInit->Exclusive = Exclusive; 232 } 233 234 __drv_maxIRQL(DISPATCH_LEVEL) 235 VOID 236 STDCALL 237 WDFEXPORT(WdfDeviceInitSetDeviceType)( 238 __in 239 PWDF_DRIVER_GLOBALS DriverGlobals, 240 __in 241 PWDFDEVICE_INIT DeviceInit, 242 __in 243 DEVICE_TYPE DeviceType 244 ) 245 { 246 DDI_ENTRY(); 247 248 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 249 250 DeviceInit->DeviceType = DeviceType; 251 } 252 253 __drv_maxIRQL(DISPATCH_LEVEL) 254 VOID 255 STDCALL 256 WDFEXPORT(WdfDeviceInitSetPowerNotPageable)( 257 __in 258 PWDF_DRIVER_GLOBALS DriverGlobals, 259 __in 260 PWDFDEVICE_INIT DeviceInit 261 ) 262 { 263 DDI_ENTRY(); 264 265 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 266 267 DeviceInit->PowerPageable = FALSE; 268 } 269 270 __drv_maxIRQL(DISPATCH_LEVEL) 271 VOID 272 STDCALL 273 WDFEXPORT(WdfDeviceInitSetPowerPageable)( 274 __in 275 PWDF_DRIVER_GLOBALS DriverGlobals, 276 __in 277 PWDFDEVICE_INIT DeviceInit 278 ) 279 { 280 DDI_ENTRY(); 281 282 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 283 284 DeviceInit->PowerPageable = TRUE; 285 } 286 287 __drv_maxIRQL(DISPATCH_LEVEL) 288 VOID 289 STDCALL 290 WDFEXPORT(WdfDeviceInitSetPowerInrush)( 291 __in 292 PWDF_DRIVER_GLOBALS DriverGlobals, 293 __in 294 PWDFDEVICE_INIT DeviceInit 295 ) 296 { 297 DDI_ENTRY(); 298 299 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 300 301 // 302 // If you are inrush, there is no way you can be power pageable 303 // 304 DeviceInit->Inrush = TRUE; 305 DeviceInit->PowerPageable = FALSE; 306 } 307 308 _Must_inspect_result_ 309 __drv_maxIRQL(PASSIVE_LEVEL) 310 NTSTATUS 311 STDCALL 312 WDFEXPORT(WdfDeviceInitAssignName)( 313 __in 314 PWDF_DRIVER_GLOBALS DriverGlobals, 315 __in 316 PWDFDEVICE_INIT DeviceInit, 317 __in_opt 318 PCUNICODE_STRING DeviceName 319 ) 320 { 321 DDI_ENTRY(); 322 323 NTSTATUS status; 324 325 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 326 327 status = FxVerifierCheckIrqlLevel(DeviceInit->DriverGlobals, 328 PASSIVE_LEVEL); 329 if (!NT_SUCCESS(status)) { 330 return status; 331 } 332 333 if (DeviceName != NULL) { 334 status = FxValidateUnicodeString(DeviceInit->DriverGlobals, 335 DeviceName); 336 if (!NT_SUCCESS(status)) { 337 return status; 338 } 339 } 340 341 if (DeviceName == NULL) { 342 if (DeviceInit->DeviceName != NULL) { 343 DeviceInit->DeviceName->RELEASE(NULL); 344 DeviceInit->DeviceName = NULL; 345 } 346 347 if (DeviceInit->IsPdoInit()) { 348 // 349 // Make sure a PDO has a name 350 // 351 DeviceInit->Characteristics |= FILE_AUTOGENERATED_DEVICE_NAME; 352 } 353 354 return STATUS_SUCCESS; 355 } 356 357 return DeviceInit->AssignName(DeviceInit->DriverGlobals, DeviceName); 358 359 } 360 361 __drv_maxIRQL(DISPATCH_LEVEL) 362 VOID 363 STDCALL 364 WDFEXPORT(WdfDeviceInitSetCharacteristics)( 365 __in 366 PWDF_DRIVER_GLOBALS DriverGlobals, 367 __in 368 PWDFDEVICE_INIT DeviceInit, 369 __in 370 ULONG DeviceCharacteristics, 371 __in 372 BOOLEAN OrInValues 373 ) 374 { 375 DDI_ENTRY(); 376 377 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 378 379 if (OrInValues) { 380 DeviceInit->Characteristics |= DeviceCharacteristics | FILE_DEVICE_SECURE_OPEN; 381 } 382 else { 383 DeviceInit->Characteristics = DeviceCharacteristics | FILE_DEVICE_SECURE_OPEN; 384 } 385 386 // 387 // If the autogenerate flag is on, clear out the device name 388 // 389 if ((DeviceCharacteristics & FILE_AUTOGENERATED_DEVICE_NAME) && 390 DeviceInit->DeviceName != NULL) { 391 DeviceInit->DeviceName->RELEASE(NULL); 392 DeviceInit->DeviceName = NULL; 393 } 394 } 395 396 __drv_maxIRQL(DISPATCH_LEVEL) 397 VOID 398 STDCALL 399 WDFEXPORT(WdfDeviceInitSetFileObjectConfig)( 400 __in 401 PWDF_DRIVER_GLOBALS DriverGlobals, 402 __in 403 PWDFDEVICE_INIT DeviceInit, 404 __in 405 PWDF_FILEOBJECT_CONFIG FileObjectConfig, 406 __in_opt 407 PWDF_OBJECT_ATTRIBUTES FileObjectAttributes 408 ) 409 410 /*++ 411 412 Routine Description: 413 414 Registers callbacks for file object support. 415 416 Defaults to WdfDeviceFileObjectNoFsContext. 417 418 Arguments: 419 420 Returns: 421 422 --*/ 423 424 { 425 DDI_ENTRY(); 426 427 NTSTATUS status; 428 PFX_DRIVER_GLOBALS pFxDriverGlobals; 429 WDF_FILEOBJECT_CLASS normalizedFileClass; 430 WDF_FILEOBJECT_CLASS fileClass; 431 432 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 433 pFxDriverGlobals = DeviceInit->DriverGlobals; 434 435 FxPointerNotNull(pFxDriverGlobals, FileObjectConfig); 436 437 if (FileObjectConfig->Size != sizeof(WDF_FILEOBJECT_CONFIG)) { 438 DoTraceLevelMessage( 439 pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 440 "Invalid FileObjectConfig Size %d, expected %d", 441 FileObjectConfig->Size, sizeof(WDF_FILEOBJECT_CONFIG)); 442 443 FxVerifierDbgBreakPoint(pFxDriverGlobals); 444 return; 445 } 446 447 status = FxValidateObjectAttributes( 448 pFxDriverGlobals, 449 FileObjectAttributes, 450 FX_VALIDATE_OPTION_PARENT_NOT_ALLOWED | 451 FX_VALIDATE_OPTION_EXECUTION_LEVEL_ALLOWED | 452 FX_VALIDATE_OPTION_SYNCHRONIZATION_SCOPE_ALLOWED 453 ); 454 455 if (!NT_SUCCESS(status)) { 456 FxVerifierDbgBreakPoint(pFxDriverGlobals); 457 return; 458 } 459 460 // 461 // Validate AutoForwardCleanupClose 462 // 463 switch (FileObjectConfig->AutoForwardCleanupClose) { 464 case WdfTrue: 465 case WdfFalse: 466 case WdfUseDefault: 467 break; 468 469 default: 470 DoTraceLevelMessage( 471 pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 472 "Invalid FileObjectConfig->AutoForwardCleanupClose value 0x%x, " 473 "expected WDF_TRI_STATE value", FileObjectConfig->AutoForwardCleanupClose); 474 475 FxVerifierDbgBreakPoint(pFxDriverGlobals); 476 return; 477 } 478 479 DeviceInit->FileObject.Set = TRUE; 480 481 DeviceInit->FileObject.AutoForwardCleanupClose = 482 FileObjectConfig->AutoForwardCleanupClose; 483 484 fileClass = FileObjectConfig->FileObjectClass; 485 486 // 487 // Remove bit flags and validate file object class value. 488 // 489 normalizedFileClass = FxFileObjectClassNormalize(fileClass); 490 491 if (normalizedFileClass == WdfFileObjectInvalid || 492 normalizedFileClass > WdfFileObjectWdfCannotUseFsContexts) { 493 DoTraceLevelMessage( 494 pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 495 "Out of range FileObjectConfig->FileObjectClass %d", 496 fileClass); 497 FxVerifierDbgBreakPoint(pFxDriverGlobals); 498 return; 499 } 500 501 // 502 // UMDF doesn't support storing object handle at FsContext or FxContxt2. 503 // Update the class to WdfFileObjectWdfCannotUseFsContexts for UMDF. 504 // 505 if (pFxDriverGlobals->IsUserModeDriver && 506 (normalizedFileClass == WdfFileObjectWdfCanUseFsContext || 507 normalizedFileClass == WdfFileObjectWdfCanUseFsContext2)) { 508 509 // 510 // update the FileObjectClass value 511 // 512 BOOLEAN canBeOptional = 513 (fileClass & WdfFileObjectCanBeOptional) ? TRUE : FALSE; 514 515 fileClass = WdfFileObjectWdfCannotUseFsContexts; 516 if (canBeOptional) { 517 fileClass = (WDF_FILEOBJECT_CLASS) 518 (fileClass | WdfFileObjectCanBeOptional); 519 } 520 521 DoTraceLevelMessage( 522 pFxDriverGlobals, TRACE_LEVEL_VERBOSE, TRACINGDEVICE, 523 "FileObjectConfig->FileObjectClass value (%d) has been updated" 524 " to a UMDF-supported value %d", normalizedFileClass, 525 WdfFileObjectWdfCannotUseFsContexts); 526 527 // 528 // re-obtain the normalized class 529 // 530 normalizedFileClass = FxFileObjectClassNormalize(fileClass); 531 } 532 533 // 534 // The optional flag can only be combined with a subset of values. 535 // 536 if (FxIsFileObjectOptional(fileClass)) { 537 switch(normalizedFileClass) { 538 case WdfFileObjectWdfCanUseFsContext: 539 case WdfFileObjectWdfCanUseFsContext2: 540 case WdfFileObjectWdfCannotUseFsContexts: 541 break; 542 543 default: 544 DoTraceLevelMessage( 545 pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 546 "Invalid FileObjectConfig->FileObjectClass %d", 547 fileClass); 548 FxVerifierDbgBreakPoint(pFxDriverGlobals); 549 return; 550 break; // just in case static verification tools complain. 551 } 552 } 553 554 DeviceInit->FileObject.Class = fileClass; 555 556 RtlCopyMemory(&DeviceInit->FileObject.Callbacks, 557 FileObjectConfig, 558 sizeof(DeviceInit->FileObject.Callbacks)); 559 560 if (FileObjectAttributes != NULL) { 561 RtlCopyMemory(&DeviceInit->FileObject.Attributes, 562 FileObjectAttributes, 563 sizeof(DeviceInit->FileObject.Attributes)); 564 } 565 } 566 567 __drv_maxIRQL(DISPATCH_LEVEL) 568 VOID 569 STDCALL 570 WDFEXPORT(WdfDeviceInitSetRequestAttributes)( 571 __in 572 PWDF_DRIVER_GLOBALS DriverGlobals, 573 __in 574 PWDFDEVICE_INIT DeviceInit, 575 __in 576 PWDF_OBJECT_ATTRIBUTES RequestAttributes 577 ) 578 { 579 DDI_ENTRY(); 580 581 PFX_DRIVER_GLOBALS pFxDriverGlobals; 582 NTSTATUS status; 583 584 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 585 pFxDriverGlobals = DeviceInit->DriverGlobals; 586 587 FxPointerNotNull(pFxDriverGlobals, RequestAttributes); 588 589 // 590 // Parent of all requests created from WDFDEVICE are parented by the 591 // WDFDEVICE. 592 // 593 status = FxValidateObjectAttributes(pFxDriverGlobals, 594 RequestAttributes, 595 FX_VALIDATE_OPTION_PARENT_NOT_ALLOWED); 596 597 if (!NT_SUCCESS(status)) { 598 FxVerifierDbgBreakPoint(pFxDriverGlobals); 599 return; 600 } 601 602 RtlCopyMemory(&DeviceInit->RequestAttributes, 603 RequestAttributes, 604 sizeof(WDF_OBJECT_ATTRIBUTES)); 605 } 606 607 _Must_inspect_result_ 608 __drv_maxIRQL(PASSIVE_LEVEL) 609 NTSTATUS 610 STDCALL 611 WDFEXPORT(WdfDeviceInitAssignSDDLString)( 612 __in 613 PWDF_DRIVER_GLOBALS DriverGlobals, 614 __in 615 PWDFDEVICE_INIT DeviceInit, 616 __in_opt 617 PCUNICODE_STRING SDDLString 618 ) 619 { 620 DDI_ENTRY(); 621 622 PFX_DRIVER_GLOBALS pFxDriverGlobals; 623 NTSTATUS status; 624 625 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 626 pFxDriverGlobals = DeviceInit->DriverGlobals; 627 628 status = FxVerifierCheckIrqlLevel(pFxDriverGlobals, PASSIVE_LEVEL); 629 if (!NT_SUCCESS(status)) { 630 return status; 631 } 632 633 if (SDDLString == NULL) { 634 // 635 // Since we require the SDDL on control device creation, you can't 636 // clear it! 637 // 638 if (DeviceInit->IsControlDeviceInit()) { 639 return STATUS_INVALID_DEVICE_REQUEST; 640 } 641 642 if (DeviceInit->Security.Sddl != NULL) { 643 DeviceInit->Security.Sddl->RELEASE(NULL); 644 DeviceInit->Security.Sddl = NULL; 645 } 646 647 return STATUS_SUCCESS; 648 } 649 650 status = FxValidateUnicodeString(pFxDriverGlobals, SDDLString); 651 if (!NT_SUCCESS(status)) { 652 return status; 653 } 654 655 if (DeviceInit->Security.Sddl == NULL) { 656 DeviceInit->Security.Sddl = new(pFxDriverGlobals, 657 WDF_NO_OBJECT_ATTRIBUTES) 658 FxString(pFxDriverGlobals); 659 660 if (DeviceInit->Security.Sddl == NULL) { 661 DoTraceLevelMessage( 662 pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 663 "Couldn't create Security descriptor" 664 " STATUS_INSUFFICIENT_RESOURCES "); 665 666 return STATUS_INSUFFICIENT_RESOURCES; 667 } 668 } 669 670 return DeviceInit->Security.Sddl->Assign(SDDLString); 671 } 672 673 __drv_maxIRQL(DISPATCH_LEVEL) 674 VOID 675 STDCALL 676 WDFEXPORT(WdfDeviceInitSetDeviceClass)( 677 __in 678 PWDF_DRIVER_GLOBALS DriverGlobals, 679 __in 680 PWDFDEVICE_INIT DeviceInit, 681 __in 682 CONST GUID* DeviceClassGuid 683 ) 684 { 685 DDI_ENTRY(); 686 687 PFX_DRIVER_GLOBALS pFxDriverGlobals; 688 689 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 690 pFxDriverGlobals = DeviceInit->DriverGlobals; 691 692 FxPointerNotNull(pFxDriverGlobals, DeviceClassGuid); 693 694 DeviceInit->Security.DeviceClassSet = TRUE; 695 RtlCopyMemory(&DeviceInit->Security.DeviceClass, 696 DeviceClassGuid, 697 sizeof(GUID)); 698 } 699 700 __drv_maxIRQL(DISPATCH_LEVEL) 701 VOID 702 STDCALL 703 WDFEXPORT(WdfDeviceInitSetPnpPowerEventCallbacks)( 704 __in 705 PWDF_DRIVER_GLOBALS DriverGlobals, 706 __in 707 PWDFDEVICE_INIT DeviceInit, 708 __in 709 PWDF_PNPPOWER_EVENT_CALLBACKS PnpPowerEventCallbacks 710 ) 711 { 712 DDI_ENTRY(); 713 714 PFX_DRIVER_GLOBALS pFxDriverGlobals; 715 716 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 717 pFxDriverGlobals = DeviceInit->DriverGlobals; 718 719 FxPointerNotNull(pFxDriverGlobals, PnpPowerEventCallbacks); 720 721 if (PnpPowerEventCallbacks->Size != sizeof(WDF_PNPPOWER_EVENT_CALLBACKS) && 722 PnpPowerEventCallbacks->Size != sizeof(_WDF_PNPPOWER_EVENT_CALLBACKS_V1_9)) { 723 724 DoTraceLevelMessage( 725 pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 726 "PnpPowerEventCallbacks size %d is invalid, exptected %d", 727 PnpPowerEventCallbacks->Size, sizeof(WDF_PNPPOWER_EVENT_CALLBACKS) 728 ); 729 730 FxVerifierDbgBreakPoint(pFxDriverGlobals); 731 732 return; 733 } 734 735 // 736 // Make sure only one of the callbacks EvtDeviceUsageNotification or 737 // EvtDeviceUsageNotificationEx is provided by driver for >V1.9. 738 // 739 if (PnpPowerEventCallbacks->Size > sizeof(WDF_PNPPOWER_EVENT_CALLBACKS_V1_9) && 740 PnpPowerEventCallbacks->EvtDeviceUsageNotification != NULL && 741 PnpPowerEventCallbacks->EvtDeviceUsageNotificationEx != NULL) { 742 743 DoTraceLevelMessage( 744 pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 745 "Driver can provide either EvtDeviceUsageNotification or " 746 "EvtDeviceUsageNotificationEx callback but not both"); 747 748 FxVerifierDbgBreakPoint(pFxDriverGlobals); 749 750 return; 751 } 752 753 // 754 // Driver's PnpPowerEventCallbacks structure may be from a previous 755 // version and therefore may be different in size than the current version 756 // that framework is using. Therefore, copy only PnpPowerEventCallbacks->Size 757 // bytes and not sizeof(PnpPowerEventCallbacks) bytes. 758 // 759 RtlCopyMemory(&DeviceInit->PnpPower.PnpPowerEventCallbacks, 760 PnpPowerEventCallbacks, 761 PnpPowerEventCallbacks->Size); 762 } 763 764 __drv_maxIRQL(DISPATCH_LEVEL) 765 VOID 766 STDCALL 767 WDFEXPORT(WdfDeviceInitSetPowerPolicyEventCallbacks)( 768 __in 769 PWDF_DRIVER_GLOBALS DriverGlobals, 770 __in 771 PWDFDEVICE_INIT DeviceInit, 772 __in 773 PWDF_POWER_POLICY_EVENT_CALLBACKS PowerPolicyEventCallbacks 774 ) 775 { 776 DDI_ENTRY(); 777 778 PFX_DRIVER_GLOBALS pFxDriverGlobals; 779 780 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 781 pFxDriverGlobals = DeviceInit->DriverGlobals; 782 783 FxPointerNotNull(pFxDriverGlobals, PowerPolicyEventCallbacks); 784 785 // 786 // The WDF_POWER_POLICY_EVENT_CALLBACKS structure size increased after v1.5. 787 // Since this api is backwards compatible, it can accept either the current 788 // structure or the older version. Validate the size of the structure here 789 // so that it is one of the two supported sizes. 790 // 791 if (PowerPolicyEventCallbacks->Size != sizeof(WDF_POWER_POLICY_EVENT_CALLBACKS) && 792 PowerPolicyEventCallbacks->Size != sizeof(WDF_POWER_POLICY_EVENT_CALLBACKS_V1_5)) { 793 DoTraceLevelMessage( 794 pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 795 "PowerPolicyEventCallbacks size %d is invalid, expected %d", 796 PowerPolicyEventCallbacks->Size, sizeof(WDF_POWER_POLICY_EVENT_CALLBACKS) 797 ); 798 799 FxVerifierDbgBreakPoint(pFxDriverGlobals); 800 return; 801 } 802 803 // 804 // Only one of EvtDeviceArmWakeFromSx and EvtDeviceArmWakeFromSxWithReason 805 // callbacks should be specified if the given power policy callbacks structure 806 // is from a version after v1.5 807 // 808 if (PowerPolicyEventCallbacks->Size > sizeof(WDF_POWER_POLICY_EVENT_CALLBACKS_V1_5) && 809 PowerPolicyEventCallbacks->EvtDeviceArmWakeFromSx != NULL && 810 PowerPolicyEventCallbacks->EvtDeviceArmWakeFromSxWithReason != NULL) { 811 DoTraceLevelMessage( 812 pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 813 "PowerPolicyEventCallbacks can have either EvtDeviceArmWakeFromSx " 814 "or EvtDeviceArmWakeFromSxWithReason callback pointer, but not both" 815 ); 816 817 FxVerifierDbgBreakPoint(pFxDriverGlobals); 818 return; 819 } 820 821 RtlCopyMemory(&DeviceInit->PnpPower.PolicyEventCallbacks, 822 PowerPolicyEventCallbacks, 823 PowerPolicyEventCallbacks->Size); 824 } 825 826 __drv_maxIRQL(DISPATCH_LEVEL) 827 VOID 828 STDCALL 829 WDFEXPORT(WdfDeviceInitSetPowerPolicyOwnership)( 830 __in 831 PWDF_DRIVER_GLOBALS DriverGlobals, 832 __in 833 PWDFDEVICE_INIT DeviceInit, 834 __in 835 BOOLEAN IsPowerPolicyOwner 836 ) 837 { 838 DDI_ENTRY(); 839 840 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 841 842 DeviceInit->PnpPower.PowerPolicyOwner = IsPowerPolicyOwner ? WdfTrue : WdfFalse; 843 } 844 845 _Must_inspect_result_ 846 __drv_maxIRQL(PASSIVE_LEVEL) 847 NTSTATUS 848 STDCALL 849 WDFEXPORT(WdfDeviceInitRegisterPnpStateChangeCallback)( 850 __in 851 PWDF_DRIVER_GLOBALS DriverGlobals, 852 __in 853 PWDFDEVICE_INIT DeviceInit, 854 __in 855 WDF_DEVICE_PNP_STATE PnpState, 856 __in 857 PFN_WDF_DEVICE_PNP_STATE_CHANGE_NOTIFICATION EvtDevicePnpStateChange, 858 __in 859 ULONG CallbackTypes 860 ) 861 { 862 DDI_ENTRY(); 863 864 FxPnpStateCallbackInfo* pCallback; 865 PFX_DRIVER_GLOBALS pFxDriverGlobals; 866 ULONG normalizedState; 867 NTSTATUS status; 868 869 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 870 pFxDriverGlobals = DeviceInit->DriverGlobals; 871 872 FxPointerNotNull(pFxDriverGlobals, EvtDevicePnpStateChange); 873 874 normalizedState = WdfDevStateNormalize(PnpState); 875 876 status = FxVerifierCheckIrqlLevel(pFxDriverGlobals, PASSIVE_LEVEL); 877 if (!NT_SUCCESS(status)) { 878 return status; 879 } 880 881 if (normalizedState < WdfDevStatePnpObjectCreated || normalizedState > WdfDevStatePnpNull) { 882 status = STATUS_INVALID_PARAMETER; 883 884 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 885 "Pnp State is invalid %!STATUS!", status); 886 887 return status; 888 } 889 890 if ((CallbackTypes & ~StateNotificationAllStates) != 0 || 891 CallbackTypes == 0x0) { 892 status = STATUS_INVALID_PARAMETER; 893 894 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 895 "CallbackTypes is invalid %!STATUS!", status); 896 897 return status; 898 } 899 900 if (DeviceInit->PnpPower.PnpStateCallbacks == NULL) { 901 902 DeviceInit->PnpPower.PnpStateCallbacks = 903 new (pFxDriverGlobals) FxPnpStateCallback(); 904 905 if (DeviceInit->PnpPower.PnpStateCallbacks == NULL) { 906 status = STATUS_INVALID_PARAMETER; 907 908 DoTraceLevelMessage( 909 pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 910 "Couldn't create object PnpStateCallbacks %!STATUS!", status); 911 912 return status; 913 } 914 } 915 916 pCallback = &DeviceInit->PnpPower.PnpStateCallbacks->m_Methods[ 917 normalizedState - WdfDevStatePnpObjectCreated]; 918 919 pCallback->Callback = EvtDevicePnpStateChange; 920 pCallback->Types = CallbackTypes; 921 922 return STATUS_SUCCESS; 923 } 924 925 _Must_inspect_result_ 926 __drv_maxIRQL(PASSIVE_LEVEL) 927 NTSTATUS 928 STDCALL 929 WDFEXPORT(WdfDeviceInitRegisterPowerStateChangeCallback)( 930 __in 931 PWDF_DRIVER_GLOBALS DriverGlobals, 932 __in 933 PWDFDEVICE_INIT DeviceInit, 934 __in 935 WDF_DEVICE_POWER_STATE PowerState, 936 __in 937 PFN_WDF_DEVICE_POWER_STATE_CHANGE_NOTIFICATION EvtDevicePowerStateChange, 938 __in 939 ULONG CallbackTypes 940 ) 941 { 942 DDI_ENTRY(); 943 944 FxPowerStateCallbackInfo* pCallback; 945 PFX_DRIVER_GLOBALS pFxDriverGlobals; 946 ULONG normalizedState; 947 NTSTATUS status; 948 949 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 950 pFxDriverGlobals = DeviceInit->DriverGlobals; 951 952 FxPointerNotNull(pFxDriverGlobals, EvtDevicePowerStateChange); 953 954 normalizedState = WdfDevStateNormalize(PowerState); 955 956 status = FxVerifierCheckIrqlLevel(pFxDriverGlobals, PASSIVE_LEVEL); 957 if (!NT_SUCCESS(status)) { 958 return status; 959 } 960 961 if (normalizedState < WdfDevStatePowerObjectCreated || 962 normalizedState >= WdfDevStatePowerNull) { 963 status = STATUS_INVALID_PARAMETER; 964 965 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 966 "PowerState State is invalid %!STATUS!", status); 967 968 return status; 969 } 970 971 if ((CallbackTypes & ~StateNotificationAllStates) != 0 || 972 CallbackTypes == 0x0) { 973 status = STATUS_INVALID_PARAMETER; 974 975 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 976 "CallbackTypes is invalid %!STATUS!" 977 "STATUS_INVALID_PARAMETER", status); 978 979 return status; 980 } 981 982 if (DeviceInit->PnpPower.PowerStateCallbacks == NULL) { 983 DeviceInit->PnpPower.PowerStateCallbacks = 984 new (pFxDriverGlobals) FxPowerStateCallback(); 985 986 if (DeviceInit->PnpPower.PowerStateCallbacks == NULL) { 987 status = STATUS_INVALID_PARAMETER; 988 989 DoTraceLevelMessage( 990 pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 991 "Couldn't create object PowerStateCallbacks %!STATUS!", status); 992 993 return status; 994 } 995 } 996 997 pCallback = &DeviceInit->PnpPower.PowerStateCallbacks->m_Methods[ 998 normalizedState - WdfDevStatePowerObjectCreated]; 999 1000 pCallback->Callback = EvtDevicePowerStateChange; 1001 pCallback->Types = CallbackTypes; 1002 1003 return STATUS_SUCCESS; 1004 } 1005 1006 _Must_inspect_result_ 1007 __drv_maxIRQL(PASSIVE_LEVEL) 1008 NTSTATUS 1009 STDCALL 1010 WDFEXPORT(WdfDeviceInitRegisterPowerPolicyStateChangeCallback)( 1011 __in 1012 PWDF_DRIVER_GLOBALS DriverGlobals, 1013 __in 1014 PWDFDEVICE_INIT DeviceInit, 1015 __in 1016 WDF_DEVICE_POWER_POLICY_STATE PowerPolicyState, 1017 __in 1018 PFN_WDF_DEVICE_POWER_POLICY_STATE_CHANGE_NOTIFICATION EvtDevicePowerPolicyStateChange, 1019 __in 1020 ULONG CallbackTypes 1021 ) 1022 { 1023 DDI_ENTRY(); 1024 1025 FxPowerPolicyStateCallbackInfo* pCallback; 1026 PFX_DRIVER_GLOBALS pFxDriverGlobals; 1027 ULONG normalizedState; 1028 NTSTATUS status; 1029 1030 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 1031 pFxDriverGlobals = DeviceInit->DriverGlobals; 1032 1033 FxPointerNotNull(pFxDriverGlobals, EvtDevicePowerPolicyStateChange); 1034 1035 normalizedState = WdfDevStateNormalize(PowerPolicyState); 1036 1037 status = FxVerifierCheckIrqlLevel(pFxDriverGlobals, PASSIVE_LEVEL); 1038 if (!NT_SUCCESS(status)) { 1039 return status; 1040 } 1041 1042 if (normalizedState < WdfDevStatePwrPolObjectCreated || 1043 normalizedState >= WdfDevStatePwrPolNull) { 1044 status = STATUS_INVALID_PARAMETER; 1045 1046 DoTraceLevelMessage( 1047 pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 1048 "PowerPolicyState State is invalid %!STATUS!", status); 1049 1050 return status; 1051 } 1052 1053 if ((CallbackTypes & ~StateNotificationAllStates) != 0 || 1054 CallbackTypes == 0x0) { 1055 status = STATUS_INVALID_PARAMETER; 1056 1057 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 1058 "CallbackTypes is invalid %!STATUS!", status); 1059 1060 return status; 1061 } 1062 1063 if (DeviceInit->PnpPower.PowerPolicyStateCallbacks == NULL) { 1064 DeviceInit->PnpPower.PowerPolicyStateCallbacks = 1065 new (pFxDriverGlobals) FxPowerPolicyStateCallback(); 1066 1067 if (DeviceInit->PnpPower.PowerPolicyStateCallbacks == NULL) { 1068 status = STATUS_INVALID_PARAMETER; 1069 1070 DoTraceLevelMessage( 1071 pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 1072 "Couldn't create object PowerPolicyStateCallbacks %!STATUS!", status); 1073 1074 return status; 1075 } 1076 } 1077 1078 pCallback = &DeviceInit->PnpPower.PowerPolicyStateCallbacks->m_Methods[ 1079 normalizedState - WdfDevStatePwrPolObjectCreated]; 1080 1081 pCallback->Callback = EvtDevicePowerPolicyStateChange; 1082 pCallback->Types = CallbackTypes; 1083 1084 return STATUS_SUCCESS; 1085 } 1086 1087 _Must_inspect_result_ 1088 __drv_maxIRQL(DISPATCH_LEVEL) 1089 WDFAPI 1090 NTSTATUS 1091 STDCALL 1092 WDFEXPORT(WdfDeviceInitAssignWdmIrpPreprocessCallback)( 1093 __in 1094 PWDF_DRIVER_GLOBALS DriverGlobals, 1095 __in 1096 PWDFDEVICE_INIT DeviceInit, 1097 __in 1098 PFN_WDFDEVICE_WDM_IRP_PREPROCESS EvtDeviceWdmIrpPreprocess, 1099 __in 1100 UCHAR MajorFunction, 1101 __drv_when(NumMinorFunctions > 0, __in_bcount(NumMinorFunctions)) 1102 __drv_when(NumMinorFunctions == 0, __in_opt) 1103 PUCHAR MinorFunctions, 1104 __in 1105 ULONG NumMinorFunctions 1106 ) 1107 { 1108 DDI_ENTRY(); 1109 1110 PFX_DRIVER_GLOBALS pFxDriverGlobals; 1111 1112 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 1113 pFxDriverGlobals = DeviceInit->DriverGlobals; 1114 1115 FxPointerNotNull(pFxDriverGlobals, EvtDeviceWdmIrpPreprocess); 1116 1117 if (NumMinorFunctions > 0) { 1118 FxPointerNotNull(pFxDriverGlobals, MinorFunctions); 1119 } 1120 1121 // 1122 // ARRAY_SIZE(DeviceInit->PreprocessInfo->Dispatch) just returns a constant 1123 // size, it does not actually deref PreprocessInfo (which could be NULL) 1124 // 1125 if (MajorFunction >= ARRAY_SIZE(DeviceInit->PreprocessInfo->Dispatch)) { 1126 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 1127 "MajorFunction is invalid" 1128 "STATUS_INVALID_PARAMETER" 1129 ); 1130 1131 return STATUS_INVALID_PARAMETER; 1132 } 1133 1134 if (DeviceInit->PreprocessInfo == NULL) { 1135 DeviceInit->PreprocessInfo = new(pFxDriverGlobals) FxIrpPreprocessInfo(); 1136 1137 if (DeviceInit->PreprocessInfo == NULL) { 1138 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 1139 "Couldn't create object PreprocessInfo" 1140 "STATUS_INSUFFICIENT_RESOURCES" 1141 ); 1142 1143 1144 return STATUS_INSUFFICIENT_RESOURCES; 1145 } 1146 } 1147 1148 if (NumMinorFunctions > 0) { 1149 if (DeviceInit->PreprocessInfo->Dispatch[MajorFunction].NumMinorFunctions != 0) { 1150 1151 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 1152 "Already assigned Minorfunctions" 1153 "STATUS_INVALID_DEVICE_REQUEST" 1154 ); 1155 return STATUS_INVALID_DEVICE_REQUEST; 1156 } 1157 1158 DeviceInit->PreprocessInfo->Dispatch[MajorFunction].MinorFunctions = 1159 (PUCHAR) FxPoolAllocate(pFxDriverGlobals, 1160 NonPagedPool, 1161 sizeof(UCHAR) * NumMinorFunctions); 1162 1163 if (DeviceInit->PreprocessInfo->Dispatch[MajorFunction].MinorFunctions == NULL) { 1164 1165 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 1166 "Couldn't create object MinorFunctions" 1167 "STATUS_INSUFFICIENT_RESOURCES" 1168 ); 1169 1170 return STATUS_INSUFFICIENT_RESOURCES; 1171 } 1172 1173 RtlCopyMemory( 1174 &DeviceInit->PreprocessInfo->Dispatch[MajorFunction].MinorFunctions[0], 1175 &MinorFunctions[0], 1176 NumMinorFunctions 1177 ); 1178 1179 DeviceInit->PreprocessInfo->Dispatch[MajorFunction].NumMinorFunctions = 1180 NumMinorFunctions; 1181 } 1182 1183 DeviceInit->PreprocessInfo->Dispatch[MajorFunction].EvtDevicePreprocess = 1184 EvtDeviceWdmIrpPreprocess; 1185 1186 return STATUS_SUCCESS; 1187 } 1188 1189 1190 __drv_maxIRQL(DISPATCH_LEVEL) 1191 VOID 1192 STDCALL 1193 WDFEXPORT(WdfDeviceInitSetIoInCallerContextCallback)( 1194 __in 1195 PWDF_DRIVER_GLOBALS DriverGlobals, 1196 __in 1197 PWDFDEVICE_INIT DeviceInit, 1198 __in 1199 PFN_WDF_IO_IN_CALLER_CONTEXT EvtIoInCallerContext 1200 ) 1201 1202 /*++ 1203 1204 Routine Description: 1205 1206 Registers an I/O pre-processing callback for the device. 1207 1208 If registered, any I/O for the device is first presented to this 1209 callback function before being placed in any I/O Queue's. 1210 1211 The callback is invoked in the thread and/or DPC context of the 1212 original WDM caller as presented to the I/O package. No framework 1213 threading, locking, synchronization, or queuing occurs, and 1214 responsibility for synchronization is up to the device driver. 1215 1216 This API is intended to support METHOD_NEITHER IRP_MJ_DEVICE_CONTROL's 1217 which must access the user buffer in the original callers context. The 1218 driver would probe and lock the buffer pages from within this event 1219 handler using the functions supplied on the WDFREQUEST object, storing 1220 any required mapped buffers and/or pointers on the WDFREQUEST context 1221 whose size is set by the RequestContextSize of the WDF_DRIVER_CONFIG structure. 1222 1223 It is the responsibility of this routine to either complete the request, or 1224 pass it on to the I/O package through WdfDeviceEnqueueRequest(Device, Request). 1225 1226 Arguments: 1227 DeviceInit - Device initialization structure 1228 1229 EvtIoInCallerContext - Pointer to driver supplied callback function 1230 1231 Return Value: 1232 1233 --*/ 1234 { 1235 DDI_ENTRY(); 1236 1237 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 1238 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), EvtIoInCallerContext); 1239 1240 DeviceInit->IoInCallerContextCallback = EvtIoInCallerContext; 1241 1242 return; 1243 } 1244 1245 __drv_maxIRQL(DISPATCH_LEVEL) 1246 VOID 1247 STDCALL 1248 WDFEXPORT(WdfDeviceInitSetRemoveLockOptions)( 1249 __in 1250 PWDF_DRIVER_GLOBALS DriverGlobals, 1251 __in 1252 PWDFDEVICE_INIT DeviceInit, 1253 __in 1254 PWDF_REMOVE_LOCK_OPTIONS RemoveLockOptions 1255 ) 1256 { 1257 DDI_ENTRY(); 1258 1259 PFX_DRIVER_GLOBALS fxDriverGlobals = GetFxDriverGlobals(DriverGlobals); 1260 ULONG validFlags = WDF_REMOVE_LOCK_OPTION_ACQUIRE_FOR_IO; 1261 1262 FxPointerNotNull(fxDriverGlobals, DeviceInit); 1263 1264 FxPointerNotNull(fxDriverGlobals, RemoveLockOptions); 1265 1266 if (RemoveLockOptions->Size != sizeof(WDF_REMOVE_LOCK_OPTIONS)) { 1267 // 1268 // Size is wrong, bail out 1269 // 1270 DoTraceLevelMessage(fxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGAPIERROR, 1271 "RemoveLockOptions %p Size incorrect, expected %d, " 1272 "got %d", 1273 RemoveLockOptions, sizeof(WDF_REMOVE_LOCK_OPTIONS), 1274 RemoveLockOptions->Size); 1275 1276 FxVerifierDbgBreakPoint(fxDriverGlobals); 1277 goto Done; 1278 } 1279 1280 if ((RemoveLockOptions->Flags & ~validFlags) != 0) { 1281 // 1282 // Invalid flag 1283 // 1284 DoTraceLevelMessage(fxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGAPIERROR, 1285 "RemoveLockOptions %p Flags 0x%x invalid, " 1286 "valid mask is 0x%x", 1287 RemoveLockOptions, RemoveLockOptions->Flags, 1288 validFlags); 1289 1290 FxVerifierDbgBreakPoint(fxDriverGlobals); 1291 goto Done; 1292 } 1293 1294 if (FxDeviceInitTypeControlDevice == DeviceInit->InitType) { 1295 // 1296 // At this time this feature is not supported on control-devices. 1297 // 1298 DoTraceLevelMessage(fxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGAPIERROR, 1299 "WdfDeviceInitSetRemoveLockOptions is not " 1300 "supported on control devices"); 1301 1302 FxVerifierDbgBreakPoint(fxDriverGlobals); 1303 goto Done; 1304 } 1305 1306 DeviceInit->RemoveLockOptionFlags = RemoveLockOptions->Flags; 1307 Done: 1308 return; 1309 } 1310 1311 __drv_maxIRQL(DISPATCH_LEVEL) 1312 VOID 1313 STDCALL 1314 WDFEXPORT(WdfDeviceInitSetReleaseHardwareOrderOnFailure)( 1315 __in 1316 PWDF_DRIVER_GLOBALS DriverGlobals, 1317 __in 1318 PWDFDEVICE_INIT DeviceInit, 1319 __in 1320 WDF_RELEASE_HARDWARE_ORDER_ON_FAILURE ReleaseHardwareOrderOnFailure 1321 ) 1322 { 1323 DDI_ENTRY(); 1324 1325 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 1326 1327 if ((ReleaseHardwareOrderOnFailure == 1328 WdfReleaseHardwareOrderOnFailureInvalid) || 1329 (ReleaseHardwareOrderOnFailure > 1330 WdfReleaseHardwareOrderOnFailureAfterDescendants)) { 1331 DoTraceLevelMessage( 1332 DeviceInit->DriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 1333 "Out of range WDF_RELEASE_HARDWARE_ORDER_ON_FAILURE %d", 1334 ReleaseHardwareOrderOnFailure); 1335 FxVerifierDbgBreakPoint(DeviceInit->DriverGlobals); 1336 return; 1337 } 1338 1339 DeviceInit->ReleaseHardwareOrderOnFailure = ReleaseHardwareOrderOnFailure; 1340 } 1341 1342 _IRQL_requires_max_(DISPATCH_LEVEL) 1343 VOID 1344 STDCALL 1345 WDFEXPORT(WdfDeviceInitAllowSelfIoTarget)( 1346 _In_ 1347 PWDF_DRIVER_GLOBALS DriverGlobals, 1348 _In_ 1349 PWDFDEVICE_INIT DeviceInit 1350 ) 1351 /*++ 1352 1353 Routine Description: 1354 1355 A client or Cx calls this API to indicate that it would like to leverage an 1356 Self IO target. 1357 1358 For now the Self targets are not supported for PDOs, Miniport Device, 1359 or non pnp Devices. 1360 1361 Arguments: 1362 1363 DeviceInit - Pointer to the WDFDEVICE_INIT structure 1364 1365 Returns: 1366 1367 VOID 1368 1369 --*/ 1370 { 1371 DDI_ENTRY(); 1372 1373 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 1374 1375 DeviceInit->RequiresSelfIoTarget = TRUE; 1376 } 1377 1378 1379 1380 // 1381 // BEGIN FDO specific functions 1382 // 1383 1384 __drv_maxIRQL(DISPATCH_LEVEL) 1385 PDEVICE_OBJECT 1386 STDCALL 1387 WDFEXPORT(WdfFdoInitWdmGetPhysicalDevice)( 1388 __in 1389 PWDF_DRIVER_GLOBALS DriverGlobals, 1390 __in 1391 PWDFDEVICE_INIT DeviceInit 1392 ) 1393 { 1394 DDI_ENTRY(); 1395 1396 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 1397 1398 if (DeviceInit->IsNotFdoInit()) { 1399 DoTraceLevelMessage( 1400 DeviceInit->DriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 1401 "Not a PWDFDEVICE_INIT for an FDO" 1402 ); 1403 1404 return NULL; 1405 } 1406 1407 return reinterpret_cast<PDEVICE_OBJECT>(DeviceInit->Fdo.PhysicalDevice); 1408 } 1409 1410 _Must_inspect_result_ 1411 __drv_maxIRQL(PASSIVE_LEVEL) 1412 NTSTATUS 1413 STDCALL 1414 WDFEXPORT(WdfFdoInitOpenRegistryKey)( 1415 __in 1416 PWDF_DRIVER_GLOBALS DriverGlobals, 1417 __in 1418 PWDFDEVICE_INIT DeviceInit, 1419 __in 1420 ULONG DeviceInstanceKeyType, 1421 __in 1422 ACCESS_MASK DesiredAccess, 1423 __in_opt 1424 PWDF_OBJECT_ATTRIBUTES KeyAttributes, 1425 __out 1426 WDFKEY* Key 1427 ) 1428 { 1429 DDI_ENTRY(); 1430 1431 PFX_DRIVER_GLOBALS pFxDriverGlobals; 1432 NTSTATUS status; 1433 1434 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 1435 pFxDriverGlobals = DeviceInit->DriverGlobals; 1436 1437 FxPointerNotNull(pFxDriverGlobals, Key); 1438 1439 *Key = NULL; 1440 1441 if (DeviceInit->IsNotFdoInit()) { 1442 status = STATUS_INVALID_PARAMETER; 1443 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 1444 "Not a PWDFDEVICE_INIT for an FDO, %!STATUS!", 1445 status); 1446 return status; 1447 } 1448 1449 status = FxValidateObjectAttributes(pFxDriverGlobals, KeyAttributes); 1450 if (!NT_SUCCESS(status)) { 1451 return status; 1452 } 1453 1454 return FxDevice::_OpenKey(pFxDriverGlobals, 1455 DeviceInit, 1456 NULL, 1457 DeviceInstanceKeyType, 1458 DesiredAccess, 1459 KeyAttributes, 1460 Key); 1461 } 1462 1463 __drv_maxIRQL(PASSIVE_LEVEL) 1464 VOID 1465 STDCALL 1466 WDFEXPORT(WdfFdoInitSetFilter)( 1467 __in 1468 PWDF_DRIVER_GLOBALS DriverGlobals, 1469 __in 1470 PWDFDEVICE_INIT DeviceInit 1471 ) 1472 { 1473 DDI_ENTRY(); 1474 1475 PFX_DRIVER_GLOBALS pFxDriverGlobals; 1476 1477 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 1478 pFxDriverGlobals = DeviceInit->DriverGlobals; 1479 1480 if (!NT_SUCCESS(FxVerifierCheckIrqlLevel(pFxDriverGlobals, 1481 PASSIVE_LEVEL))) { 1482 return; 1483 } 1484 if (DeviceInit->IsNotFdoInit()) { 1485 DoTraceLevelMessage( 1486 pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 1487 "Not a PWDFDEVICE_INIT for an FDO"); 1488 1489 FxVerifierDbgBreakPoint(pFxDriverGlobals); 1490 return; 1491 } 1492 1493 DeviceInit->Fdo.Filter = TRUE; 1494 } 1495 1496 _Must_inspect_result_ 1497 __drv_maxIRQL(PASSIVE_LEVEL) 1498 NTSTATUS 1499 STDCALL 1500 WDFEXPORT(WdfFdoInitQueryProperty)( 1501 __in 1502 PWDF_DRIVER_GLOBALS DriverGlobals, 1503 __in 1504 PWDFDEVICE_INIT DeviceInit, 1505 __in 1506 DEVICE_REGISTRY_PROPERTY DeviceProperty, 1507 __in 1508 ULONG BufferLength, 1509 __out_bcount_full_opt(BufferLength) 1510 PVOID PropertyBuffer, 1511 __out 1512 PULONG ResultLength 1513 ) 1514 /*++ 1515 1516 Routine Description: 1517 Retrieves the requested device property for the given device 1518 1519 Arguments: 1520 DeviceInit - Device initialization structure 1521 1522 DeviceProperty - the property being queried 1523 1524 BufferLength - length of PropertyBuffer in bytes 1525 1526 PropertyBuffer - Buffer which will receive the property being queried 1527 1528 ResultLength - if STATUS_BUFFER_TOO_SMALL is returned, then this will contain 1529 the required length 1530 1531 Return Value: 1532 NTSTATUS 1533 1534 --*/ 1535 { 1536 DDI_ENTRY(); 1537 1538 PFX_DRIVER_GLOBALS pFxDriverGlobals; 1539 NTSTATUS status; 1540 1541 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 1542 pFxDriverGlobals = DeviceInit->DriverGlobals; 1543 1544 FxPointerNotNull(pFxDriverGlobals, ResultLength); 1545 if (BufferLength > 0) { 1546 FxPointerNotNull(pFxDriverGlobals, PropertyBuffer); 1547 } 1548 1549 status = FxVerifierCheckIrqlLevel(pFxDriverGlobals, PASSIVE_LEVEL); 1550 if (!NT_SUCCESS(status)) { 1551 return status; 1552 } 1553 1554 if (DeviceInit->IsNotFdoInit()) { 1555 status = STATUS_INVALID_DEVICE_REQUEST; 1556 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 1557 "Not a PWDFDEVICE_INIT for an FDO, %!STATUS!", 1558 status); 1559 return status; 1560 } 1561 1562 status = FxDevice::_QueryProperty(pFxDriverGlobals, 1563 DeviceInit, 1564 NULL, 1565 NULL, 1566 DeviceProperty, 1567 BufferLength, 1568 PropertyBuffer, 1569 ResultLength); 1570 return status; 1571 } 1572 1573 _Must_inspect_result_ 1574 __drv_maxIRQL(PASSIVE_LEVEL) 1575 NTSTATUS 1576 STDCALL 1577 WDFEXPORT(WdfFdoInitAllocAndQueryProperty)( 1578 __in 1579 PWDF_DRIVER_GLOBALS DriverGlobals, 1580 __in 1581 PWDFDEVICE_INIT DeviceInit, 1582 __in 1583 DEVICE_REGISTRY_PROPERTY DeviceProperty, 1584 __in 1585 __drv_strictTypeMatch(__drv_typeExpr) 1586 POOL_TYPE PoolType, 1587 __in_opt 1588 PWDF_OBJECT_ATTRIBUTES PropertyMemoryAttributes, 1589 __out 1590 WDFMEMORY* PropertyMemory 1591 ) 1592 /*++ 1593 1594 Routine Description: 1595 Allocates and retrieves the requested device property for the given device init 1596 1597 Arguments: 1598 DeviceInit - Device initialization structure 1599 1600 DeviceProperty - the property being queried 1601 1602 PoolType - what type of pool to allocate 1603 1604 PropertyMemoryAttributes - attributes to associate with PropertyMemory 1605 1606 PropertyMemory - handle which will receive the property buffer 1607 1608 Return Value: 1609 NTSTATUS 1610 1611 --*/ 1612 { 1613 DDI_ENTRY(); 1614 1615 PFX_DRIVER_GLOBALS pFxDriverGlobals; 1616 NTSTATUS status; 1617 1618 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 1619 pFxDriverGlobals = DeviceInit->DriverGlobals; 1620 1621 FxPointerNotNull(pFxDriverGlobals, PropertyMemory); 1622 1623 *PropertyMemory = NULL; 1624 1625 status = FxVerifierCheckIrqlLevel(pFxDriverGlobals, PASSIVE_LEVEL); 1626 if (!NT_SUCCESS(status)) { 1627 return status; 1628 } 1629 1630 FxVerifierCheckNxPoolType(pFxDriverGlobals, PoolType, pFxDriverGlobals->Tag); 1631 1632 status = FxValidateObjectAttributes(pFxDriverGlobals, PropertyMemoryAttributes); 1633 if (!NT_SUCCESS(status)) { 1634 return status; 1635 } 1636 1637 if (DeviceInit->IsNotFdoInit()) { 1638 status = STATUS_INVALID_DEVICE_REQUEST; 1639 1640 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 1641 "Not a PWDFDEVICE_INIT for an FDO, %!STATUS!", 1642 status); 1643 1644 return status; 1645 } 1646 1647 status = FxDevice::_AllocAndQueryProperty(pFxDriverGlobals, 1648 DeviceInit, 1649 NULL, 1650 NULL, 1651 DeviceProperty, 1652 PoolType, 1653 PropertyMemoryAttributes, 1654 PropertyMemory); 1655 return status; 1656 } 1657 1658 __drv_maxIRQL(PASSIVE_LEVEL) 1659 VOID 1660 STDCALL 1661 WDFEXPORT(WdfFdoInitSetEventCallbacks)( 1662 __in 1663 PWDF_DRIVER_GLOBALS DriverGlobals, 1664 __in 1665 PWDFDEVICE_INIT DeviceInit, 1666 __in 1667 PWDF_FDO_EVENT_CALLBACKS FdoEventCallbacks 1668 ) 1669 { 1670 DDI_ENTRY(); 1671 1672 PFX_DRIVER_GLOBALS pFxDriverGlobals; 1673 1674 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 1675 pFxDriverGlobals = DeviceInit->DriverGlobals; 1676 1677 FxPointerNotNull(pFxDriverGlobals, FdoEventCallbacks); 1678 1679 if (!NT_SUCCESS(FxVerifierCheckIrqlLevel(pFxDriverGlobals, PASSIVE_LEVEL))) { 1680 return; 1681 } 1682 1683 if (DeviceInit->IsNotFdoInit()) { 1684 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 1685 "Not a PWDFDEVICE_INIT for an FDO"); 1686 FxVerifierDbgBreakPoint(pFxDriverGlobals); 1687 return; 1688 } 1689 1690 if (FdoEventCallbacks->Size != sizeof(WDF_FDO_EVENT_CALLBACKS)) { 1691 DoTraceLevelMessage( 1692 pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 1693 "FdoEventCallbacks size %d is invalid, expected %d", 1694 FdoEventCallbacks->Size, sizeof(WDF_FDO_EVENT_CALLBACKS) 1695 ); 1696 FxVerifierDbgBreakPoint(pFxDriverGlobals); 1697 return; 1698 } 1699 1700 if (FdoEventCallbacks->EvtDeviceFilterAddResourceRequirements != NULL && 1701 FdoEventCallbacks->EvtDeviceRemoveAddedResources == NULL) { 1702 // 1703 // Not allowed to add resources without filtering them out later 1704 // 1705 DoTraceLevelMessage( 1706 GetFxDriverGlobals(DriverGlobals), TRACE_LEVEL_ERROR, TRACINGPNP, 1707 "Must set EvtDeviceRemoveAddedResources if " 1708 "EvtDeviceFilterAddResourceRequirements (%p) is set", 1709 FdoEventCallbacks->EvtDeviceFilterAddResourceRequirements); 1710 1711 FxVerifierDbgBreakPoint(GetFxDriverGlobals(DriverGlobals)); 1712 return; 1713 } 1714 1715 RtlCopyMemory(&DeviceInit->Fdo.EventCallbacks, 1716 FdoEventCallbacks, 1717 sizeof(DeviceInit->Fdo.EventCallbacks)); 1718 } 1719 1720 __drv_maxIRQL(PASSIVE_LEVEL) 1721 VOID 1722 STDCALL 1723 WDFEXPORT(WdfFdoInitSetDefaultChildListConfig)( 1724 __in 1725 PWDF_DRIVER_GLOBALS DriverGlobals, 1726 __inout 1727 PWDFDEVICE_INIT DeviceInit, 1728 __in 1729 PWDF_CHILD_LIST_CONFIG Config, 1730 __in_opt 1731 PWDF_OBJECT_ATTRIBUTES DefaultDeviceListAttributes 1732 ) 1733 { 1734 DDI_ENTRY(); 1735 1736 PFX_DRIVER_GLOBALS pFxDriverGlobals; 1737 NTSTATUS status; 1738 size_t totalDescriptionSize; 1739 1740 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 1741 pFxDriverGlobals = DeviceInit->DriverGlobals; 1742 totalDescriptionSize = 0; 1743 1744 FxPointerNotNull(pFxDriverGlobals, Config); 1745 1746 status = FxVerifierCheckIrqlLevel(pFxDriverGlobals, PASSIVE_LEVEL); 1747 if (!NT_SUCCESS(status)) { 1748 return; 1749 } 1750 1751 if (DeviceInit->IsNotFdoInit()) { 1752 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 1753 "Not a PWDFDEVICE_INIT for an FDO"); 1754 FxVerifierDbgBreakPoint(pFxDriverGlobals); 1755 return; 1756 } 1757 1758 status = FxChildList::_ValidateConfig(pFxDriverGlobals, 1759 Config, 1760 &totalDescriptionSize); 1761 if (!NT_SUCCESS(status)) { 1762 FxVerifierDbgBreakPoint(pFxDriverGlobals); 1763 return; 1764 } 1765 1766 if (DefaultDeviceListAttributes != NULL) { 1767 status = FxValidateObjectAttributes(pFxDriverGlobals, 1768 DefaultDeviceListAttributes, 1769 FX_VALIDATE_OPTION_PARENT_NOT_ALLOWED); 1770 if (!NT_SUCCESS(status)) { 1771 FxVerifierDbgBreakPoint(pFxDriverGlobals); 1772 return; 1773 } 1774 1775 RtlCopyMemory(&DeviceInit->Fdo.ListConfigAttributes, 1776 DefaultDeviceListAttributes, 1777 sizeof(DeviceInit->Fdo.ListConfigAttributes)); 1778 } 1779 1780 RtlCopyMemory(&DeviceInit->Fdo.ListConfig, 1781 Config, 1782 sizeof(WDF_CHILD_LIST_CONFIG)); 1783 } 1784 1785 _Must_inspect_result_ 1786 _IRQL_requires_max_(PASSIVE_LEVEL) 1787 WDFAPI 1788 NTSTATUS 1789 STDCALL 1790 WDFEXPORT(WdfFdoInitQueryPropertyEx)( 1791 _In_ 1792 PWDF_DRIVER_GLOBALS DriverGlobals, 1793 _In_ 1794 PWDFDEVICE_INIT DeviceInit, 1795 _In_ 1796 PWDF_DEVICE_PROPERTY_DATA DeviceProperty, 1797 _In_ 1798 ULONG BufferLength, 1799 _Out_ 1800 PVOID PropertyBuffer, 1801 _Out_ 1802 PULONG ResultLength, 1803 _Out_ 1804 PDEVPROPTYPE Type 1805 ) 1806 /*++ 1807 1808 Routine Description: 1809 1810 This routine queries device property. 1811 1812 Arguments: 1813 1814 DriverGlobals - DriverGlobals pointer 1815 1816 DeviceInit - WDF DeviceInit structure pointer. 1817 1818 DeviceProperty - A pointer to WDF_DEVICE_PROPERTY_DATA structure. 1819 1820 BufferLength - The size, in bytes, of the buffer that is pointed to by 1821 PropertyBuffer. 1822 1823 PropertyBuffer - A caller-supplied pointer to a caller-allocated buffer that 1824 receives the requested information. The pointer can be NULL 1825 if the BufferLength parameter is zero. 1826 1827 ResultLength - A caller-supplied location that, on return, contains the 1828 size, in bytes, of the information that the method stored in 1829 PropertyBuffer. If the function's return value is 1830 STATUS_BUFFER_TOO_SMALL, this location receives the required 1831 buffer size. 1832 1833 Type - A pointer to a DEVPROPTYPE variable. If method successfully retrieves 1834 the property data, the routine writes the property type value 1835 to this variable. This value indicates the type of property 1836 data that is in the Data buffer. 1837 1838 Return Value: 1839 1840 Method returns an NTSTATUS value. This routine might return one of the 1841 following values. 1842 1843 STATUS_BUFFER_TOO_SMALL - The supplied buffer is too small to receive the 1844 information. The ResultLength member receives the 1845 size of buffer required. 1846 STATUS_SUCCESS - The operation succeeded. 1847 STATUS_INVALID_PARAMETER - One of the parameters is incorrect. 1848 1849 The method might return other NTSTATUS values. 1850 1851 --*/ 1852 1853 { 1854 DDI_ENTRY(); 1855 1856 PFX_DRIVER_GLOBALS pFxDriverGlobals; 1857 NTSTATUS status; 1858 1859 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 1860 pFxDriverGlobals = DeviceInit->DriverGlobals; 1861 1862 FxPointerNotNull(pFxDriverGlobals, DeviceProperty); 1863 1864 if (DeviceProperty->Size != sizeof(WDF_DEVICE_PROPERTY_DATA)) { 1865 status = STATUS_INFO_LENGTH_MISMATCH; 1866 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGPNP, 1867 "PropertyData size (%d) incorrect, expected %d, %!STATUS!", 1868 DeviceProperty->Size, 1869 sizeof(WDF_DEVICE_PROPERTY_DATA), status); 1870 return status; 1871 } 1872 1873 FxPointerNotNull(pFxDriverGlobals, ResultLength); 1874 if (BufferLength > 0) { 1875 FxPointerNotNull(pFxDriverGlobals, PropertyBuffer); 1876 } 1877 1878 status = FxVerifierCheckIrqlLevel(pFxDriverGlobals, PASSIVE_LEVEL); 1879 if (!NT_SUCCESS(status)) { 1880 return status; 1881 } 1882 1883 if (DeviceInit->IsNotFdoInit()) { 1884 status = STATUS_INVALID_DEVICE_REQUEST; 1885 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 1886 "Not a PWDFDEVICE_INIT for an FDO, %!STATUS!", 1887 status); 1888 return status; 1889 } 1890 1891 status = FxDevice::_QueryPropertyEx(pFxDriverGlobals, 1892 DeviceInit, 1893 NULL, 1894 DeviceProperty, 1895 FxDeviceProperty, 1896 BufferLength, 1897 PropertyBuffer, 1898 ResultLength, 1899 Type); 1900 return status; 1901 } 1902 1903 _Must_inspect_result_ 1904 _IRQL_requires_max_(PASSIVE_LEVEL) 1905 WDFAPI 1906 NTSTATUS 1907 STDCALL 1908 WDFEXPORT(WdfFdoInitAllocAndQueryPropertyEx)( 1909 _In_ 1910 PWDF_DRIVER_GLOBALS DriverGlobals, 1911 _In_ 1912 PWDFDEVICE_INIT DeviceInit, 1913 _In_ 1914 PWDF_DEVICE_PROPERTY_DATA DeviceProperty, 1915 _In_ 1916 _Strict_type_match_ 1917 POOL_TYPE PoolType, 1918 _In_opt_ 1919 PWDF_OBJECT_ATTRIBUTES PropertyMemoryAttributes, 1920 _Out_ 1921 WDFMEMORY* PropertyMemory, 1922 _Out_ 1923 PDEVPROPTYPE Type 1924 ) 1925 /*++ 1926 1927 Routine Description: 1928 1929 This routine queries device property. 1930 1931 Arguments: 1932 1933 DriverGlobals - DriverGlobals pointer 1934 1935 DeviceInit - WDF DeviceInit pointer. 1936 1937 PropertyData - A pointer to WDF_DEVICE_PROPERTY_ DATA structure. 1938 1939 PoolType - A POOL_TYPE-typed enumerator that specifies the type of memory 1940 to be allocated. 1941 1942 PropertyMemoryAttributes - optional, A pointer to a caller-allocated 1943 WDF_OBJECT_ATTRIBUTES structure that describes object attributes 1944 for the memory object that the function will allocate. This 1945 parameter is optional and can be WDF_NO_OBJECT_ATTRIBUTES. 1946 1947 PropertyMemory - A pointer to a WDFMEMORY-typed location that receives a 1948 handle to a framework memory object. 1949 1950 Type - A pointer to a DEVPROPTYPE variable. If method successfully retrieves 1951 the property data, the routine writes the property type value to 1952 this variable. This value indicates the type of property data 1953 that is in the Data buffer. 1954 1955 Return Value: 1956 1957 Method returns an NTSTATUS value. This routine might return one of the 1958 following values. It might return other NTSTATUS-codes as well. 1959 1960 STATUS_SUCCESS The operation succeeded. 1961 STATUS_INVALID_PARAMETER One of the parameters is incorrect. 1962 1963 --*/ 1964 { 1965 DDI_ENTRY(); 1966 1967 PFX_DRIVER_GLOBALS pFxDriverGlobals; 1968 NTSTATUS status; 1969 1970 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 1971 pFxDriverGlobals = DeviceInit->DriverGlobals; 1972 1973 FxPointerNotNull(pFxDriverGlobals, DeviceProperty); 1974 1975 if (DeviceProperty->Size != sizeof(WDF_DEVICE_PROPERTY_DATA)) { 1976 status = STATUS_INFO_LENGTH_MISMATCH; 1977 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGPNP, 1978 "PropertyData size (%d) incorrect, expected %d, %!STATUS!", 1979 DeviceProperty->Size, 1980 sizeof(WDF_DEVICE_PROPERTY_DATA), status); 1981 return status; 1982 } 1983 1984 FxPointerNotNull(pFxDriverGlobals, PropertyMemory); 1985 1986 *PropertyMemory = NULL; 1987 1988 status = FxVerifierCheckIrqlLevel(pFxDriverGlobals, PASSIVE_LEVEL); 1989 if (!NT_SUCCESS(status)) { 1990 return status; 1991 } 1992 1993 FxVerifierCheckNxPoolType(pFxDriverGlobals, PoolType, pFxDriverGlobals->Tag); 1994 1995 status = FxValidateObjectAttributes(pFxDriverGlobals, PropertyMemoryAttributes); 1996 if (!NT_SUCCESS(status)) { 1997 return status; 1998 } 1999 2000 if (DeviceInit->IsNotFdoInit()) { 2001 status = STATUS_INVALID_DEVICE_REQUEST; 2002 2003 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2004 "Not a PWDFDEVICE_INIT for an FDO, %!STATUS!", 2005 status); 2006 2007 return status; 2008 } 2009 2010 status = FxDevice::_AllocAndQueryPropertyEx(pFxDriverGlobals, 2011 DeviceInit, 2012 NULL, 2013 DeviceProperty, 2014 FxDeviceProperty, 2015 PoolType, 2016 PropertyMemoryAttributes, 2017 PropertyMemory, 2018 Type); 2019 return status; 2020 } 2021 2022 // 2023 // END FDO specific functions 2024 // 2025 2026 // 2027 // BEGIN PDO specific functions 2028 // 2029 _Must_inspect_result_ 2030 __drv_maxIRQL(PASSIVE_LEVEL) 2031 PWDFDEVICE_INIT 2032 STDCALL 2033 WDFEXPORT(WdfPdoInitAllocate)( 2034 __in 2035 PWDF_DRIVER_GLOBALS DriverGlobals, 2036 __in 2037 WDFDEVICE ParentDevice 2038 ) 2039 { 2040 DDI_ENTRY(); 2041 2042 PFX_DRIVER_GLOBALS pFxDriverGlobals; 2043 PWDFDEVICE_INIT pInit; 2044 FxDevice* pDevice; 2045 NTSTATUS status; 2046 2047 FxObjectHandleGetPtrAndGlobals(GetFxDriverGlobals(DriverGlobals), 2048 ParentDevice, 2049 FX_TYPE_DEVICE, 2050 (PVOID*) &pDevice, 2051 &pFxDriverGlobals); 2052 2053 status = FxVerifierCheckIrqlLevel(pFxDriverGlobals, PASSIVE_LEVEL); 2054 if (!NT_SUCCESS(status)) { 2055 return NULL; 2056 } 2057 2058 if (pDevice->IsFdo() == FALSE) { 2059 DoTraceLevelMessage( 2060 pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2061 "Parent device is not a FDO (must use WDFCHILDLIST to use a PDO as a parent)" 2062 ); 2063 2064 return NULL; 2065 } 2066 2067 pInit = new(pFxDriverGlobals) WDFDEVICE_INIT(pDevice->GetDriver()); 2068 if (pInit == NULL) { 2069 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2070 "Couldn't create WDFDEVICE_INIT object"); 2071 2072 return NULL; 2073 } 2074 2075 pInit->SetPdo(pDevice); 2076 2077 // 2078 // Dynamically created PDOs are not created with this API, rather they go 2079 // through WDFCHILDLIST's callback. 2080 // 2081 pInit->Pdo.Static = TRUE; 2082 2083 return pInit; 2084 } 2085 2086 __drv_maxIRQL(PASSIVE_LEVEL) 2087 VOID 2088 STDCALL 2089 WDFEXPORT(WdfPdoInitSetEventCallbacks)( 2090 __in 2091 PWDF_DRIVER_GLOBALS DriverGlobals, 2092 __in 2093 PWDFDEVICE_INIT DeviceInit, 2094 __in 2095 PWDF_PDO_EVENT_CALLBACKS DispatchTable 2096 ) 2097 { 2098 DDI_ENTRY(); 2099 2100 PFX_DRIVER_GLOBALS pFxDriverGlobals; 2101 2102 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 2103 pFxDriverGlobals = DeviceInit->DriverGlobals; 2104 2105 FxPointerNotNull(pFxDriverGlobals, DispatchTable); 2106 2107 if (!NT_SUCCESS(FxVerifierCheckIrqlLevel(pFxDriverGlobals, PASSIVE_LEVEL))) { 2108 return; 2109 } 2110 2111 if (DeviceInit->IsNotPdoInit()) { 2112 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2113 "Not a PWDFDEVICE_INIT for a PDO"); 2114 FxVerifierDbgBreakPoint(pFxDriverGlobals); 2115 return; 2116 } 2117 2118 if (DispatchTable->Size != sizeof(WDF_PDO_EVENT_CALLBACKS) && 2119 DispatchTable->Size != sizeof(WDF_PDO_EVENT_CALLBACKS_V1_9)) { 2120 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2121 "DispatchTable size %d is invalid, expected %d", 2122 DispatchTable->Size, sizeof(WDF_PDO_EVENT_CALLBACKS)); 2123 FxVerifierDbgBreakPoint(pFxDriverGlobals); 2124 return; // STATUS_INFO_LENGTH_MISMATCH; 2125 } 2126 2127 RtlCopyMemory(&DeviceInit->Pdo.EventCallbacks, 2128 DispatchTable, 2129 sizeof(WDF_PDO_EVENT_CALLBACKS)); 2130 } 2131 2132 _Must_inspect_result_ 2133 __drv_maxIRQL(PASSIVE_LEVEL) 2134 NTSTATUS 2135 STDCALL 2136 WDFEXPORT(WdfPdoInitAssignDeviceID)( 2137 __in 2138 PWDF_DRIVER_GLOBALS DriverGlobals, 2139 __in 2140 PWDFDEVICE_INIT DeviceInit, 2141 __in 2142 PCUNICODE_STRING DeviceID 2143 ) 2144 { 2145 DDI_ENTRY(); 2146 2147 PFX_DRIVER_GLOBALS pFxDriverGlobals; 2148 NTSTATUS status; 2149 2150 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 2151 pFxDriverGlobals = DeviceInit->DriverGlobals; 2152 2153 FxPointerNotNull(pFxDriverGlobals, DeviceID); 2154 2155 status = FxVerifierCheckIrqlLevel(pFxDriverGlobals, PASSIVE_LEVEL); 2156 if (!NT_SUCCESS(status)) { 2157 return status; 2158 } 2159 2160 status = FxValidateUnicodeString(pFxDriverGlobals, DeviceID); 2161 if (!NT_SUCCESS(status)) { 2162 return status; 2163 } 2164 2165 if (DeviceInit->IsNotPdoInit()) { 2166 status = STATUS_INVALID_DEVICE_REQUEST; 2167 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2168 "Not a PWDFDEVICE_INIT for a PDO, %!STATUS!", 2169 status); 2170 return status; 2171 } 2172 2173 if (DeviceInit->Pdo.DeviceID == NULL) { 2174 DeviceInit->Pdo.DeviceID = new(pFxDriverGlobals, WDF_NO_OBJECT_ATTRIBUTES) 2175 FxString(pFxDriverGlobals); 2176 2177 if (DeviceInit->Pdo.DeviceID == NULL) { 2178 status = STATUS_INSUFFICIENT_RESOURCES; 2179 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2180 "Couldn't allocate DeviceID object, %!STATUS!", 2181 status); 2182 return status; 2183 } 2184 } 2185 2186 status = DeviceInit->Pdo.DeviceID->Assign(DeviceID); 2187 2188 return status; 2189 } 2190 2191 _Must_inspect_result_ 2192 __drv_maxIRQL(PASSIVE_LEVEL) 2193 NTSTATUS 2194 STDCALL 2195 WDFEXPORT(WdfPdoInitAssignInstanceID)( 2196 __in 2197 PWDF_DRIVER_GLOBALS DriverGlobals, 2198 __in 2199 PWDFDEVICE_INIT DeviceInit, 2200 __in 2201 PCUNICODE_STRING InstanceID 2202 ) 2203 { 2204 DDI_ENTRY(); 2205 2206 PFX_DRIVER_GLOBALS pFxDriverGlobals; 2207 NTSTATUS status; 2208 2209 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 2210 pFxDriverGlobals = DeviceInit->DriverGlobals; 2211 2212 FxPointerNotNull(pFxDriverGlobals, InstanceID); 2213 2214 status = FxVerifierCheckIrqlLevel(pFxDriverGlobals, PASSIVE_LEVEL); 2215 if (!NT_SUCCESS(status)) { 2216 return status; 2217 } 2218 2219 status = FxValidateUnicodeString(pFxDriverGlobals, InstanceID); 2220 if (!NT_SUCCESS(status)) { 2221 return status; 2222 } 2223 2224 if (DeviceInit->IsNotPdoInit()) { 2225 status = STATUS_INVALID_DEVICE_REQUEST ; 2226 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2227 "Not a PWDFDEVICE_INIT for a PDO, %!STATUS!", 2228 status); 2229 return status; 2230 } 2231 2232 if (DeviceInit->Pdo.InstanceID == NULL) { 2233 DeviceInit->Pdo.InstanceID = new(pFxDriverGlobals, WDF_NO_OBJECT_ATTRIBUTES) 2234 FxString(pFxDriverGlobals); 2235 2236 if (DeviceInit->Pdo.InstanceID == NULL) { 2237 status = STATUS_INSUFFICIENT_RESOURCES; 2238 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2239 "Couldn't allocate InstanceID object, %!STATUS!", 2240 status); 2241 return status; 2242 } 2243 } 2244 2245 status = DeviceInit->Pdo.InstanceID->Assign(InstanceID); 2246 2247 return status; 2248 } 2249 2250 _Must_inspect_result_ 2251 __drv_maxIRQL(PASSIVE_LEVEL) 2252 NTSTATUS 2253 STDCALL 2254 WDFEXPORT(WdfPdoInitAddHardwareID)( 2255 __in 2256 PWDF_DRIVER_GLOBALS DriverGlobals, 2257 __in 2258 PWDFDEVICE_INIT DeviceInit, 2259 __in 2260 PCUNICODE_STRING HardwareID 2261 ) 2262 { 2263 DDI_ENTRY(); 2264 2265 PFX_DRIVER_GLOBALS pFxDriverGlobals; 2266 FxString* pID; 2267 NTSTATUS status; 2268 2269 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 2270 pFxDriverGlobals = DeviceInit->DriverGlobals; 2271 2272 FxPointerNotNull(pFxDriverGlobals, HardwareID); 2273 2274 status = FxVerifierCheckIrqlLevel(pFxDriverGlobals, PASSIVE_LEVEL); 2275 if (!NT_SUCCESS(status)) { 2276 return status; 2277 } 2278 2279 status = FxValidateUnicodeString(pFxDriverGlobals, HardwareID); 2280 if (!NT_SUCCESS(status)) { 2281 return status; 2282 } 2283 2284 if (DeviceInit->IsNotPdoInit()) { 2285 status = STATUS_INVALID_DEVICE_REQUEST ; 2286 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2287 "Not a PWDFDEVICE_INIT for a PDO, %!STATUS!", 2288 status); 2289 return status; 2290 } 2291 2292 pID = new(pFxDriverGlobals, WDF_NO_OBJECT_ATTRIBUTES) FxString(pFxDriverGlobals); 2293 if (pID == NULL) { 2294 status = STATUS_INSUFFICIENT_RESOURCES; 2295 DoTraceLevelMessage( 2296 pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2297 "Couldn't allocate String object %!STATUS!", status); 2298 return status; 2299 } 2300 2301 status = pID->Assign(HardwareID); 2302 if (NT_SUCCESS(status)) { 2303 status = (DeviceInit->Pdo.HardwareIDs.Add(pFxDriverGlobals, pID)) ? 2304 STATUS_SUCCESS : STATUS_UNSUCCESSFUL; 2305 } 2306 2307 // 2308 // Upon success, the FxCollection will have taken a reference. 2309 // Upon failure, this is object cleanup. 2310 // 2311 pID->Release(); 2312 2313 return status; 2314 } 2315 2316 _Must_inspect_result_ 2317 __drv_maxIRQL(PASSIVE_LEVEL) 2318 NTSTATUS 2319 STDCALL 2320 WDFEXPORT(WdfPdoInitAddCompatibleID)( 2321 __in 2322 PWDF_DRIVER_GLOBALS DriverGlobals, 2323 __in 2324 PWDFDEVICE_INIT DeviceInit, 2325 __in 2326 PCUNICODE_STRING CompatibleID 2327 ) 2328 { 2329 DDI_ENTRY(); 2330 2331 PFX_DRIVER_GLOBALS pFxDriverGlobals; 2332 FxString* pID; 2333 NTSTATUS status; 2334 2335 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 2336 pFxDriverGlobals = DeviceInit->DriverGlobals; 2337 2338 FxPointerNotNull(pFxDriverGlobals, CompatibleID); 2339 2340 status = FxVerifierCheckIrqlLevel(pFxDriverGlobals, PASSIVE_LEVEL); 2341 if (!NT_SUCCESS(status)) { 2342 return status; 2343 } 2344 2345 status = FxValidateUnicodeString(pFxDriverGlobals, CompatibleID); 2346 if (!NT_SUCCESS(status)) { 2347 return status; 2348 } 2349 2350 if (DeviceInit->IsNotPdoInit()) { 2351 status = STATUS_INVALID_DEVICE_REQUEST; 2352 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2353 "Not a PWDFDEVICE_INIT for a PDO, %!STATUS!", 2354 status); 2355 return status; 2356 } 2357 2358 pID = new(pFxDriverGlobals, WDF_NO_OBJECT_ATTRIBUTES) FxString(pFxDriverGlobals); 2359 if (pID == NULL) { 2360 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2361 "Couldn't allocate String object" 2362 "STATUS_INSUFFICIENT_RESOURCES " 2363 ); 2364 return STATUS_INSUFFICIENT_RESOURCES; 2365 } 2366 2367 status = pID->Assign(CompatibleID); 2368 if (NT_SUCCESS(status)) { 2369 status = (DeviceInit->Pdo.CompatibleIDs.Add(pFxDriverGlobals, pID)) ? 2370 STATUS_SUCCESS : STATUS_UNSUCCESSFUL; 2371 } 2372 2373 // 2374 // Upon success, the FxCollection will have taken a reference. Upon failure, 2375 // this is object cleanup. 2376 // 2377 pID->Release(); 2378 2379 return status; 2380 } 2381 2382 _Must_inspect_result_ 2383 __drv_maxIRQL(PASSIVE_LEVEL) 2384 NTSTATUS 2385 STDCALL 2386 WDFEXPORT(WdfPdoInitAssignContainerID)( 2387 __in 2388 PWDF_DRIVER_GLOBALS DriverGlobals, 2389 __in 2390 PWDFDEVICE_INIT DeviceInit, 2391 __in 2392 PCUNICODE_STRING ContainerID 2393 ) 2394 { 2395 DDI_ENTRY(); 2396 2397 PFX_DRIVER_GLOBALS pFxDriverGlobals; 2398 NTSTATUS status; 2399 2400 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 2401 pFxDriverGlobals = DeviceInit->DriverGlobals; 2402 2403 FxPointerNotNull(pFxDriverGlobals, ContainerID); 2404 2405 status = FxVerifierCheckIrqlLevel(pFxDriverGlobals, PASSIVE_LEVEL); 2406 if (!NT_SUCCESS(status)) { 2407 return status; 2408 } 2409 2410 status = FxValidateUnicodeString(pFxDriverGlobals, ContainerID); 2411 if (!NT_SUCCESS(status)) { 2412 return status; 2413 } 2414 2415 if (DeviceInit->IsNotPdoInit()) { 2416 status = STATUS_INVALID_DEVICE_REQUEST ; 2417 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2418 "Not a PWDFDEVICE_INIT for a PDO, %!STATUS!", 2419 status); 2420 return status; 2421 } 2422 2423 if (DeviceInit->Pdo.ContainerID == NULL) { 2424 DeviceInit->Pdo.ContainerID = new(pFxDriverGlobals, 2425 WDF_NO_OBJECT_ATTRIBUTES) 2426 FxString(pFxDriverGlobals); 2427 2428 if (DeviceInit->Pdo.ContainerID == NULL) { 2429 status = STATUS_INSUFFICIENT_RESOURCES; 2430 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2431 "Couldn't allocate ContainerID object, %!STATUS!", 2432 status); 2433 2434 return status; 2435 } 2436 } 2437 2438 status = DeviceInit->Pdo.ContainerID->Assign(ContainerID); 2439 2440 return status; 2441 } 2442 2443 _Must_inspect_result_ 2444 __drv_maxIRQL(PASSIVE_LEVEL) 2445 NTSTATUS 2446 STDCALL 2447 WDFEXPORT(WdfPdoInitAddDeviceText)( 2448 __in 2449 PWDF_DRIVER_GLOBALS DriverGlobals, 2450 __in 2451 PWDFDEVICE_INIT DeviceInit, 2452 __in 2453 PCUNICODE_STRING DeviceDescription, 2454 __in 2455 PCUNICODE_STRING DeviceLocation, 2456 __in 2457 LCID LocaleId 2458 ) 2459 { 2460 DDI_ENTRY(); 2461 2462 PFX_DRIVER_GLOBALS pFxDriverGlobals; 2463 FxDeviceText *pDeviceText; 2464 NTSTATUS status; 2465 2466 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 2467 pFxDriverGlobals = DeviceInit->DriverGlobals; 2468 2469 FxPointerNotNull(pFxDriverGlobals, DeviceDescription); 2470 FxPointerNotNull(pFxDriverGlobals, DeviceLocation); 2471 2472 status = FxVerifierCheckIrqlLevel(pFxDriverGlobals, PASSIVE_LEVEL); 2473 if (!NT_SUCCESS(status)) { 2474 return status; 2475 } 2476 2477 status = FxValidateUnicodeString(pFxDriverGlobals, DeviceDescription); 2478 if (!NT_SUCCESS(status)) { 2479 return status; 2480 } 2481 2482 status = FxValidateUnicodeString(pFxDriverGlobals, DeviceLocation); 2483 if (!NT_SUCCESS(status)) { 2484 return status; 2485 } 2486 2487 if (DeviceInit->IsNotPdoInit()) { 2488 status = STATUS_INVALID_DEVICE_REQUEST; 2489 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2490 "Not a PWDFDEVICE_INIT for a PDO, %!STATUS!", status); 2491 return status; 2492 } 2493 2494 pDeviceText = new(pFxDriverGlobals, PagedPool) FxDeviceText(); 2495 2496 if (pDeviceText == NULL) { 2497 status = STATUS_INSUFFICIENT_RESOURCES; 2498 2499 DoTraceLevelMessage( 2500 pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2501 "Couldn't allocate DeviceText object, %!STATUS!", status); 2502 2503 return status; 2504 } 2505 2506 pDeviceText->m_LocaleId = LocaleId; 2507 2508 pDeviceText->m_Description = FxDuplicateUnicodeStringToString( 2509 pFxDriverGlobals, DeviceDescription); 2510 2511 if (pDeviceText->m_Description == NULL) { 2512 status = STATUS_INSUFFICIENT_RESOURCES; 2513 2514 DoTraceLevelMessage( 2515 pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2516 "Couldn't allocate DeviceDescription string, %!STATUS!", status); 2517 2518 goto Done; 2519 } 2520 2521 pDeviceText->m_LocationInformation = FxDuplicateUnicodeStringToString( 2522 pFxDriverGlobals, DeviceLocation); 2523 2524 if (pDeviceText->m_LocationInformation == NULL) { 2525 status = STATUS_INSUFFICIENT_RESOURCES; 2526 2527 DoTraceLevelMessage( 2528 pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2529 "Couldn't allocate DeviceLocation string, %!STATUS!", status); 2530 2531 goto Done; 2532 } 2533 2534 // 2535 // Insert at the end of the list and update end of the list 2536 // 2537 *DeviceInit->Pdo.LastDeviceTextEntry = &pDeviceText->m_Entry; 2538 DeviceInit->Pdo.LastDeviceTextEntry = &pDeviceText->m_Entry.Next; 2539 2540 Done: 2541 if (!NT_SUCCESS(status)) { 2542 delete pDeviceText; 2543 } 2544 2545 return status; 2546 } 2547 2548 __drv_maxIRQL(PASSIVE_LEVEL) 2549 VOID 2550 STDCALL 2551 WDFEXPORT(WdfPdoInitSetDefaultLocale)( 2552 __in 2553 PWDF_DRIVER_GLOBALS DriverGlobals, 2554 __in 2555 PWDFDEVICE_INIT DeviceInit, 2556 __in 2557 LCID LocaleId 2558 ) 2559 { 2560 DDI_ENTRY(); 2561 2562 PFX_DRIVER_GLOBALS pFxDriverGlobals; 2563 2564 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 2565 pFxDriverGlobals = DeviceInit->DriverGlobals; 2566 2567 if (!NT_SUCCESS(FxVerifierCheckIrqlLevel(pFxDriverGlobals, 2568 PASSIVE_LEVEL))) { 2569 return; 2570 } 2571 2572 if (DeviceInit->IsNotPdoInit()) { 2573 DoTraceLevelMessage( 2574 pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2575 "Not a PWDFDEVICE_INIT for a PDO"); 2576 FxVerifierDbgBreakPoint(pFxDriverGlobals); 2577 return; 2578 } 2579 2580 DeviceInit->Pdo.DefaultLocale = LocaleId; 2581 } 2582 2583 _Must_inspect_result_ 2584 __drv_maxIRQL(PASSIVE_LEVEL) 2585 NTSTATUS 2586 STDCALL 2587 WDFEXPORT(WdfPdoInitAssignRawDevice)( 2588 __in 2589 PWDF_DRIVER_GLOBALS DriverGlobals, 2590 __in 2591 PWDFDEVICE_INIT DeviceInit, 2592 __in 2593 CONST GUID* DeviceClassGuid 2594 ) 2595 { 2596 DDI_ENTRY(); 2597 2598 PFX_DRIVER_GLOBALS pFxDriverGlobals; 2599 NTSTATUS status; 2600 2601 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 2602 pFxDriverGlobals = DeviceInit->DriverGlobals; 2603 2604 FxPointerNotNull(pFxDriverGlobals, DeviceClassGuid); 2605 2606 status = FxVerifierCheckIrqlLevel(pFxDriverGlobals, PASSIVE_LEVEL); 2607 if (!NT_SUCCESS(status)) { 2608 return status; 2609 } 2610 2611 if (DeviceInit->IsNotPdoInit()) { 2612 status = STATUS_INVALID_PARAMETER; 2613 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2614 "Not a PWDFDEVICE_INIT for a PDO, %!STATUS!", 2615 status); 2616 return status; 2617 } 2618 2619 DeviceInit->Pdo.Raw = TRUE; 2620 DeviceInit->Security.DeviceClassSet = TRUE; 2621 RtlCopyMemory(&DeviceInit->Security.DeviceClass, 2622 DeviceClassGuid, 2623 sizeof(GUID)); 2624 2625 return STATUS_SUCCESS; 2626 } 2627 2628 __drv_maxIRQL(PASSIVE_LEVEL) 2629 VOID 2630 STDCALL 2631 WDFEXPORT(WdfPdoInitAllowForwardingRequestToParent)( 2632 __in 2633 PWDF_DRIVER_GLOBALS DriverGlobals, 2634 __in 2635 PWDFDEVICE_INIT DeviceInit 2636 ) 2637 { 2638 DDI_ENTRY(); 2639 2640 PFX_DRIVER_GLOBALS pFxDriverGlobals; 2641 NTSTATUS status; 2642 2643 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 2644 pFxDriverGlobals = DeviceInit->DriverGlobals; 2645 2646 status = FxVerifierCheckIrqlLevel(pFxDriverGlobals, PASSIVE_LEVEL); 2647 if (!NT_SUCCESS(status)) { 2648 return; 2649 } 2650 2651 if (DeviceInit->IsNotPdoInit()) { 2652 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2653 "Not a PWDFDEVICE_INIT for a PDO, %!STATUS!", 2654 status); 2655 FxVerifierDbgBreakPoint(pFxDriverGlobals); 2656 return; 2657 } 2658 2659 DeviceInit->Pdo.ForwardRequestToParent = TRUE; 2660 return ; 2661 } 2662 2663 2664 2665 // 2666 // END PDO specific functions 2667 // 2668 2669 // 2670 // BEGIN CONTROL DEVICE specific functions 2671 // 2672 2673 _Must_inspect_result_ 2674 __drv_maxIRQL(PASSIVE_LEVEL) 2675 PWDFDEVICE_INIT 2676 STDCALL 2677 WDFEXPORT(WdfControlDeviceInitAllocate)( 2678 __in 2679 PWDF_DRIVER_GLOBALS DriverGlobals, 2680 __in 2681 WDFDRIVER Driver, 2682 __in 2683 CONST UNICODE_STRING* SDDLString 2684 ) 2685 { 2686 DDI_ENTRY(); 2687 2688 PFX_DRIVER_GLOBALS pFxDriverGlobals; 2689 FxDriver* pDriver; 2690 NTSTATUS status; 2691 2692 FxObjectHandleGetPtrAndGlobals(GetFxDriverGlobals(DriverGlobals), 2693 Driver, 2694 FX_TYPE_DRIVER, 2695 (PVOID*) &pDriver, 2696 &pFxDriverGlobals); 2697 2698 FxPointerNotNull(pFxDriverGlobals, SDDLString); 2699 2700 status = FxVerifierCheckIrqlLevel(pFxDriverGlobals, PASSIVE_LEVEL); 2701 if (!NT_SUCCESS(status)) { 2702 return NULL; 2703 } 2704 2705 status = FxValidateUnicodeString(pFxDriverGlobals, SDDLString); 2706 if (!NT_SUCCESS(status)) { 2707 return NULL; 2708 } 2709 2710 return WDFDEVICE_INIT::_AllocateControlDeviceInit(pDriver, SDDLString); 2711 } 2712 2713 __drv_maxIRQL(PASSIVE_LEVEL) 2714 VOID 2715 STDCALL 2716 WDFEXPORT(WdfControlDeviceInitSetShutdownNotification)( 2717 __in 2718 PWDF_DRIVER_GLOBALS DriverGlobals, 2719 __in 2720 PWDFDEVICE_INIT DeviceInit, 2721 __in 2722 PFN_WDF_DEVICE_SHUTDOWN_NOTIFICATION Notification, 2723 __in 2724 UCHAR Flags 2725 ) 2726 { 2727 DDI_ENTRY(); 2728 2729 PFX_DRIVER_GLOBALS pFxDriverGlobals; 2730 2731 FxPointerNotNull(GetFxDriverGlobals(DriverGlobals), DeviceInit); 2732 pFxDriverGlobals = DeviceInit->DriverGlobals; 2733 2734 FxPointerNotNull(pFxDriverGlobals, Notification); 2735 2736 if (DeviceInit->IsNotControlDeviceInit()) { 2737 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2738 "Not a PWDFDEVICE_INIT for a control device"); 2739 FxVerifierDbgBreakPoint(pFxDriverGlobals); 2740 return; 2741 } 2742 2743 if ((Flags & ~(WdfDeviceShutdown | WdfDeviceLastChanceShutdown)) != 0) { 2744 DoTraceLevelMessage(pFxDriverGlobals, TRACE_LEVEL_ERROR, TRACINGDEVICE, 2745 "WdfDeviceShutdown Flags 0x%x are invalid", Flags); 2746 FxVerifierDbgBreakPoint(pFxDriverGlobals); 2747 return; 2748 } 2749 2750 DeviceInit->Control.ShutdownNotification = Notification; 2751 DeviceInit->Control.Flags |= Flags; 2752 } 2753 2754 // 2755 // END CONTROL DEVICE specific functions 2756 // 2757 2758 } // extern "C" 2759