1 /*++ 2 3 Copyright (c) Microsoft Corporation 4 5 Module Name: 6 7 FxIrp.hpp 8 9 Abstract: 10 11 This module implements a class for handling irps. 12 13 Author: 14 15 16 17 Environment: 18 19 Both kernel and user mode 20 21 Revision History: 22 23 --*/ 24 25 #ifndef _FXIRP_HPP_ 26 #define _FXIRP_HPP_ 27 28 class FxIrp { 29 30 friend struct FxAutoIrp; 31 32 private: 33 MdIrp m_Irp; 34 35 public: 36 37 FxIrp() {} 38 39 FxIrp(MdIrp irp) : m_Irp(irp) 40 { 41 } 42 43 // A function for when not assigning 44 45 MdIrp 46 SetIrp( 47 MdIrp irp 48 ); 49 50 MdIrp 51 GetIrp( 52 VOID 53 ); 54 55 56 VOID 57 CompleteRequest( 58 __in_opt CCHAR PriorityBoost=IO_NO_INCREMENT 59 ); 60 61 62 NTSTATUS 63 CallDriver( 64 __in MdDeviceObject DeviceObject 65 ); 66 67 68 69 70 71 72 73 NTSTATUS 74 PoCallDriver( 75 __in MdDeviceObject DeviceObject 76 ); 77 78 79 VOID 80 StartNextPowerIrp( 81 ); 82 83 MdCompletionRoutine 84 GetNextCompletionRoutine( 85 VOID 86 ); 87 88 VOID 89 SetCompletionRoutine( 90 __in MdCompletionRoutine CompletionRoutine, 91 __in PVOID Context, 92 __in BOOLEAN InvokeOnSuccess = TRUE, 93 __in BOOLEAN InvokeOnError = TRUE, 94 __in BOOLEAN InvokeOnCancel = TRUE 95 ); 96 97 VOID 98 SetCompletionRoutineEx( 99 __in MdDeviceObject DeviceObject, 100 __in MdCompletionRoutine CompletionRoutine, 101 __in PVOID Context, 102 __in BOOLEAN InvokeOnSuccess = TRUE, 103 __in BOOLEAN InvokeOnError = TRUE, 104 __in BOOLEAN InvokeOnCancel = TRUE 105 ); 106 107 MdCancelRoutine 108 SetCancelRoutine( 109 __in_opt MdCancelRoutine CancelRoutine 110 ); 111 112 // 113 // SendIrpSynchronously achieves synchronous behavior by waiting on an 114 // event after submitting the IRP. The event creation can fail in UM, but 115 // not in KM. Hence, in UM the return code could either indicate event 116 // creation failure or it could indicate the status set on the IRP by the 117 // lower driver. In KM, the return code only indicates the status set on 118 // the IRP by the lower lower, because event creation cannot fail. 119 // 120 CHECK_RETURN_IF_USER_MODE 121 NTSTATUS 122 SendIrpSynchronously( 123 __in MdDeviceObject DeviceObject 124 ); 125 126 127 VOID 128 CopyCurrentIrpStackLocationToNext( 129 VOID 130 ); 131 132 VOID 133 CopyToNextIrpStackLocation( 134 __in PIO_STACK_LOCATION Stack 135 ); 136 137 VOID 138 SetNextIrpStackLocation( 139 VOID 140 ); 141 142 UCHAR 143 GetMajorFunction( 144 VOID 145 ); 146 147 UCHAR 148 GetMinorFunction( 149 VOID 150 ); 151 152 UCHAR 153 GetCurrentStackFlags( 154 VOID 155 ); 156 157 MdFileObject 158 GetCurrentStackFileObject( 159 VOID 160 ); 161 162 KPROCESSOR_MODE 163 GetRequestorMode( 164 VOID 165 ); 166 167 VOID 168 SetContext( 169 __in ULONG Index, 170 __in PVOID Value 171 ); 172 173 VOID 174 SetSystemBuffer( 175 __in PVOID Value 176 ); 177 178 VOID 179 SetUserBuffer( 180 __in PVOID Value 181 ); 182 183 VOID 184 SetMdlAddress( 185 __in PMDL Value 186 ); 187 188 VOID 189 SetFlags( 190 __in ULONG Flags 191 ); 192 193 PVOID 194 GetContext( 195 __in ULONG Index 196 ); 197 198 ULONG 199 GetFlags( 200 VOID 201 ); 202 203 PIO_STACK_LOCATION 204 GetCurrentIrpStackLocation( 205 VOID 206 ); 207 208 209 PIO_STACK_LOCATION 210 GetNextIrpStackLocation( 211 VOID 212 ); 213 214 static 215 PIO_STACK_LOCATION 216 _GetAndClearNextStackLocation( 217 __in MdIrp Irp 218 ); 219 220 221 VOID 222 SkipCurrentIrpStackLocation( 223 VOID 224 ); 225 226 227 VOID 228 MarkIrpPending( 229 ); 230 231 232 BOOLEAN 233 PendingReturned( 234 ); 235 236 237 VOID 238 PropagatePendingReturned( 239 VOID 240 ); 241 242 243 VOID 244 SetStatus( 245 __in NTSTATUS Status 246 ); 247 248 249 NTSTATUS 250 GetStatus( 251 ); 252 253 254 BOOLEAN 255 Cancel( 256 VOID 257 ); 258 259 VOID 260 SetCancel( 261 __in BOOLEAN Cancel 262 ); 263 264 265 BOOLEAN 266 IsCanceled( 267 ); 268 269 270 KIRQL 271 GetCancelIrql( 272 ); 273 274 275 VOID 276 SetInformation( 277 __in ULONG_PTR Information 278 ); 279 280 281 ULONG_PTR 282 GetInformation( 283 ); 284 285 286 CCHAR 287 GetCurrentIrpStackLocationIndex( 288 ); 289 290 CCHAR 291 GetStackCount( 292 ); 293 294 PLIST_ENTRY 295 ListEntry( 296 ); 297 298 299 PVOID 300 GetSystemBuffer( 301 ); 302 303 PVOID 304 GetOutputBuffer( 305 ); 306 307 PMDL 308 GetMdl( 309 ); 310 311 PMDL* 312 GetMdlAddressPointer( 313 ); 314 315 PVOID 316 GetUserBuffer( 317 ); 318 319 VOID 320 Reuse( 321 __in NTSTATUS Status = STATUS_SUCCESS 322 ); 323 324 // 325 // Methods for IO_STACK_LOCATION members 326 // 327 328 VOID 329 SetMajorFunction( 330 __in UCHAR MajorFunction 331 ); 332 333 334 VOID 335 SetMinorFunction( 336 __in UCHAR MinorFunction 337 ); 338 339 // 340 // Get Methods for IO_STACK_LOCATION.Parameters.Power 341 // 342 343 SYSTEM_POWER_STATE_CONTEXT 344 GetParameterPowerSystemPowerStateContext( 345 ); 346 347 348 POWER_STATE_TYPE 349 GetParameterPowerType( 350 ); 351 352 POWER_STATE 353 GetParameterPowerState( 354 ); 355 356 357 DEVICE_POWER_STATE 358 GetParameterPowerStateDeviceState( 359 ); 360 361 362 SYSTEM_POWER_STATE 363 GetParameterPowerStateSystemState( 364 ); 365 366 367 POWER_ACTION 368 GetParameterPowerShutdownType( 369 ); 370 371 372 MdFileObject 373 GetFileObject( 374 VOID 375 ); 376 377 378 // 379 // Get/Set Method for IO_STACK_LOCATION.Parameters.QueryDeviceRelations 380 // 381 382 DEVICE_RELATION_TYPE 383 GetParameterQDRType( 384 ); 385 386 VOID 387 SetParameterQDRType( 388 __in DEVICE_RELATION_TYPE DeviceRelation 389 ); 390 391 // 392 // Get/Set Methods for IO_STACK_LOCATION.Parameters.DeviceCapabilities 393 // 394 395 PDEVICE_CAPABILITIES 396 GetParameterDeviceCapabilities( 397 ); 398 399 VOID 400 SetCurrentDeviceObject( 401 __in MdDeviceObject DeviceObject 402 ); 403 404 MdDeviceObject 405 GetDeviceObject( 406 VOID 407 ); 408 409 VOID 410 SetParameterDeviceCapabilities( 411 __in PDEVICE_CAPABILITIES DeviceCapabilities 412 ); 413 414 415 // 416 // Get/Set Methods for IO_STACK_LOCATION.Parameters.Write.ByteOffset.QuadPart 417 // 418 419 LONGLONG 420 GetParameterWriteByteOffsetQuadPart( 421 ); 422 423 424 VOID 425 SetNextParameterWriteByteOffsetQuadPart( 426 __in LONGLONG DeviceOffset 427 ); 428 429 // 430 // Get/Set Methods for IO_STACK_LOCATION.Parameters.Write.Length 431 // 432 433 ULONG 434 GetCurrentParameterWriteLength( 435 ); 436 437 VOID 438 SetNextParameterWriteLength( 439 __in ULONG IoLength 440 ); 441 442 PVOID* 443 GetNextStackParameterOthersArgument1Pointer( 444 ); 445 446 VOID 447 SetNextStackParameterOthersArgument1( 448 __in PVOID Argument1 449 ); 450 451 PVOID* 452 GetNextStackParameterOthersArgument2Pointer( 453 ); 454 455 PVOID* 456 GetNextStackParameterOthersArgument4Pointer( 457 ); 458 459 // 460 // Get/Set Methods for IO_STACK_LOCATION.Parameters.StartDevice 461 // 462 463 PCM_RESOURCE_LIST 464 GetParameterAllocatedResources( 465 ); 466 467 468 VOID 469 SetParameterAllocatedResources( 470 __in PCM_RESOURCE_LIST AllocatedResources 471 ); 472 473 474 PCM_RESOURCE_LIST 475 GetParameterAllocatedResourcesTranslated( 476 ); 477 478 479 VOID 480 SetParameterAllocatedResourcesTranslated( 481 __in PCM_RESOURCE_LIST AllocatedResourcesTranslated 482 ); 483 484 // 485 // Get Method for IO_STACK_LOCATION.Parameters.QueryDeviceText 486 // 487 488 LCID 489 GetParameterQueryDeviceTextLocaleId( 490 ); 491 492 493 DEVICE_TEXT_TYPE 494 GetParameterQueryDeviceTextType( 495 ); 496 497 // 498 // Get Method for IO_STACK_LOCATION.Parameters.SetLock 499 // 500 501 BOOLEAN 502 GetParameterSetLockLock( 503 ); 504 505 // 506 // Get Method for IO_STACK_LOCATION.Parameters.QueryId 507 // 508 509 BUS_QUERY_ID_TYPE 510 GetParameterQueryIdType( 511 ); 512 513 // 514 // Get/Set Methods for IO_STACK_LOCATION.Parameters.QueryInterface 515 // 516 517 PINTERFACE 518 GetParameterQueryInterfaceInterface( 519 ); 520 521 522 const GUID* 523 GetParameterQueryInterfaceType( 524 ); 525 526 527 USHORT 528 GetParameterQueryInterfaceVersion( 529 ); 530 531 532 USHORT 533 GetParameterQueryInterfaceSize( 534 ); 535 536 537 PVOID 538 GetParameterQueryInterfaceInterfaceSpecificData( 539 ); 540 541 VOID 542 SetParameterQueryInterfaceInterface( 543 __in PINTERFACE Interface 544 ); 545 546 VOID 547 SetParameterQueryInterfaceType( 548 __in const GUID* InterfaceType 549 ); 550 551 VOID 552 SetParameterQueryInterfaceVersion( 553 __in USHORT Version 554 ); 555 556 VOID 557 SetParameterQueryInterfaceSize( 558 __in USHORT Size 559 ); 560 561 VOID 562 SetParameterQueryInterfaceInterfaceSpecificData( 563 __in PVOID InterfaceSpecificData 564 ); 565 566 // 567 // Get Method for IO_STACK_LOCATION.Parameters.UsageNotification 568 // 569 570 DEVICE_USAGE_NOTIFICATION_TYPE 571 GetParameterUsageNotificationType( 572 ); 573 574 575 BOOLEAN 576 GetParameterUsageNotificationInPath( 577 ); 578 579 580 VOID 581 SetParameterUsageNotificationInPath( 582 __in BOOLEAN InPath 583 ); 584 585 586 BOOLEAN 587 GetNextStackParameterUsageNotificationInPath( 588 ); 589 590 ULONG 591 GetParameterIoctlCode( 592 VOID 593 ); 594 595 ULONG 596 GetParameterIoctlCodeBufferMethod( 597 VOID 598 ); 599 600 ULONG 601 GetParameterIoctlInputBufferLength( 602 VOID 603 ); 604 605 ULONG 606 GetParameterIoctlOutputBufferLength( 607 VOID 608 ); 609 610 PVOID 611 GetParameterIoctlType3InputBuffer( 612 VOID 613 ); 614 615 // 616 // Set Methods for IO_STACK_LOCATION.Parameters.DeviceControl members 617 // 618 619 VOID 620 SetParameterIoctlCode( 621 __in ULONG DeviceIoControlCode 622 ); 623 624 VOID 625 SetParameterIoctlInputBufferLength( 626 __in ULONG InputBufferLength 627 ); 628 629 VOID 630 SetParameterIoctlOutputBufferLength( 631 __in ULONG OutputBufferLength 632 ); 633 634 VOID 635 SetParameterIoctlType3InputBuffer( 636 __in PVOID Type3InputBuffer 637 ); 638 639 ULONG 640 GetParameterReadLength( 641 VOID 642 ); 643 644 ULONG 645 GetParameterWriteLength( 646 VOID 647 ); 648 649 VOID 650 SetNextStackFlags( 651 __in UCHAR Flags 652 ); 653 654 VOID 655 SetNextStackFileObject( 656 _In_ MdFileObject FileObject 657 ); 658 659 PVOID 660 GetCurrentParametersPointer( 661 VOID 662 ); 663 664 // 665 // Methods for IO_STACK_LOCATION 666 // 667 668 VOID 669 ClearNextStack( 670 VOID 671 ); 672 673 VOID 674 ClearNextStackLocation( 675 VOID 676 ); 677 678 VOID 679 InitNextStackUsingStack( 680 __in FxIrp* Irp 681 ); 682 683 ULONG 684 GetCurrentFlags( 685 VOID 686 ); 687 688 VOID 689 FreeIrp( 690 VOID 691 ); 692 693 MdEThread 694 GetThread( 695 VOID 696 ); 697 698 BOOLEAN 699 Is32bitProcess( 700 VOID 701 ); 702 703 private: 704 705 static 706 NTSTATUS 707 STDCALL 708 _IrpSynchronousCompletion( 709 __in MdDeviceObject DeviceObject, 710 __in MdIrp OriginalIrp, 711 __in PVOID Context 712 ); 713 714 public: 715 716 _Must_inspect_result_ 717 static 718 MdIrp 719 AllocateIrp( 720 _In_ CCHAR StackSize, 721 _In_opt_ FxDevice* Device = NULL 722 ); 723 724 static 725 MdIrp 726 GetIrpFromListEntry( 727 __in PLIST_ENTRY Ple 728 ); 729 730 _Must_inspect_result_ 731 static 732 NTSTATUS 733 RequestPowerIrp( 734 __in MdDeviceObject DeviceObject, 735 __in UCHAR MinorFunction, 736 __in POWER_STATE PowerState, 737 __in MdRequestPowerComplete CompletionFunction, 738 __in PVOID Context 739 ); 740 741 PIO_STATUS_BLOCK 742 GetStatusBlock( 743 VOID 744 ); 745 746 PVOID 747 GetDriverContext( 748 ); 749 750 ULONG 751 GetDriverContextSize( 752 ); 753 754 VOID 755 CopyParameters( 756 _Out_ PWDF_REQUEST_PARAMETERS Parameters 757 ); 758 759 VOID 760 CopyStatus( 761 _Out_ PIO_STATUS_BLOCK StatusBlock 762 ); 763 764 BOOLEAN 765 HasStack( 766 _In_ UCHAR StackCount 767 ); 768 769 BOOLEAN 770 IsCurrentIrpStackLocationValid( 771 VOID 772 ); 773 774 #if (FX_CORE_MODE == FX_CORE_USER_MODE) 775 776 IWudfIoIrp* 777 GetIoIrp( 778 VOID 779 ); 780 781 IWudfPnpIrp* 782 GetPnpIrp( 783 VOID 784 ); 785 #endif 786 787 }; 788 789 // 790 // FxAutoIrp adds value to FxIrp by automatically freeing the associated MdIrp 791 // when it goes out of scope 792 // 793 struct FxAutoIrp : public FxIrp { 794 795 FxAutoIrp( 796 __in_opt MdIrp Irp = NULL 797 ) : 798 FxIrp(Irp) 799 { 800 } 801 802 803 ~FxAutoIrp(); 804 }; 805 806 #endif // _FXIRP_HPP_ 807