1 /* 2 * 3 * COPYRIGHT: See COPYING in the top level directory 4 * PROJECT: ReactOS devmgr.dll 5 * FILE: dll/win32/devmgr/api.cpp 6 * PURPOSE: devmgr.dll interface 7 * PROGRAMMER: Thomas Weidenmueller (w3seek@users.sourceforge.net) 8 * Ged Murphy (gedmurphy@reactos.org) 9 * NOTES: 10 * Some helpful resources: 11 * http://support.microsoft.com/default.aspx?scid=kb;%5BLN%5D;815320 12 * http://www.jsiinc.com/SUBO/tip7400/rh7482.htm 13 * http://www.jsiinc.com/SUBM/tip6400/rh6490.htm 14 * 15 * UPDATE HISTORY: 16 * 04-04-2004 Created 17 */ 18 19 #include "precomp.h" 20 #include "devmgmt/MainWindow.h" 21 #include "properties/properties.h" 22 23 HINSTANCE hDllInstance = NULL; 24 25 26 27 /*************************************************************************** 28 * NAME EXPORTED 29 * DeviceAdvancedPropertiesW 30 * 31 * DESCRIPTION 32 * Invokes the device properties dialog, this version may add some property pages 33 * for some devices 34 * 35 * ARGUMENTS 36 * hWndParent: Handle to the parent window 37 * lpMachineName: Machine Name, NULL is the local machine 38 * lpDeviceID: Specifies the device whose properties are to be shown 39 * 40 * RETURN VALUE 41 * Always returns -1, a call to GetLastError returns 0 if successful 42 * 43 * @implemented 44 */ 45 INT_PTR 46 WINAPI 47 DeviceAdvancedPropertiesW(IN HWND hWndParent OPTIONAL, 48 IN LPCWSTR lpMachineName OPTIONAL, 49 IN LPCWSTR lpDeviceID) 50 { 51 HDEVINFO hDevInfo; 52 SP_DEVINFO_DATA DevInfoData; 53 HINSTANCE hComCtl32; 54 INT_PTR Ret = -1; 55 56 if (lpDeviceID == NULL) 57 { 58 SetLastError(ERROR_INVALID_PARAMETER); 59 return FALSE; 60 } 61 62 /* dynamically load comctl32 */ 63 hComCtl32 = LoadAndInitComctl32(); 64 if (hComCtl32 != NULL) 65 { 66 hDevInfo = SetupDiCreateDeviceInfoListEx(NULL, 67 hWndParent, 68 lpMachineName, 69 NULL); 70 if (hDevInfo != INVALID_HANDLE_VALUE) 71 { 72 DevInfoData.cbSize = sizeof(SP_DEVINFO_DATA); 73 if (SetupDiOpenDeviceInfo(hDevInfo, 74 lpDeviceID, 75 hWndParent, 76 0, 77 &DevInfoData)) 78 { 79 Ret = DisplayDeviceAdvancedProperties(hWndParent, 80 lpDeviceID, 81 hDevInfo, 82 &DevInfoData, 83 hComCtl32, 84 lpMachineName, 85 0); 86 } 87 88 SetupDiDestroyDeviceInfoList(hDevInfo); 89 } 90 91 FreeLibrary(hComCtl32); 92 } 93 94 return Ret; 95 } 96 97 98 /*************************************************************************** 99 * NAME EXPORTED 100 * DeviceAdvancedPropertiesA 101 * 102 * DESCRIPTION 103 * Invokes the device properties dialog, this version may add some property pages 104 * for some devices 105 * 106 * ARGUMENTS 107 * hWndParent: Handle to the parent window 108 * lpMachineName: Machine Name, NULL is the local machine 109 * lpDeviceID: Specifies the device whose properties are to be shown 110 * 111 * RETURN VALUE 112 * Always returns -1, a call to GetLastError returns 0 if successful 113 * 114 * @implemented 115 */ 116 INT_PTR 117 WINAPI 118 DeviceAdvancedPropertiesA(IN HWND hWndParent OPTIONAL, 119 IN LPCSTR lpMachineName OPTIONAL, 120 IN LPCSTR lpDeviceID) 121 { 122 LPWSTR lpMachineNameW = NULL; 123 LPWSTR lpDeviceIDW = NULL; 124 INT_PTR Ret = -1; 125 126 if (lpMachineName != NULL) 127 { 128 if (!(lpMachineNameW = ConvertMultiByteToUnicode(lpMachineName, 129 CP_ACP))) 130 { 131 goto Cleanup; 132 } 133 } 134 if (lpDeviceID != NULL) 135 { 136 if (!(lpDeviceIDW = ConvertMultiByteToUnicode(lpDeviceID, 137 CP_ACP))) 138 { 139 goto Cleanup; 140 } 141 } 142 143 Ret = DeviceAdvancedPropertiesW(hWndParent, 144 lpMachineNameW, 145 lpDeviceIDW); 146 147 Cleanup: 148 if (lpMachineNameW != NULL) 149 { 150 HeapFree(GetProcessHeap(), 151 0, 152 lpMachineNameW); 153 } 154 if (lpDeviceIDW != NULL) 155 { 156 HeapFree(GetProcessHeap(), 157 0, 158 lpDeviceIDW); 159 } 160 161 return Ret; 162 } 163 164 165 /*************************************************************************** 166 * NAME EXPORTED 167 * DevicePropertiesExA 168 * 169 * DESCRIPTION 170 * Invokes the extended device properties dialog 171 * 172 * ARGUMENTS 173 * hWndParent: Handle to the parent window 174 * lpMachineName: Machine Name, NULL is the local machine 175 * lpDeviceID: Specifies the device whose properties are to be shown, optional if 176 * bShowDevMgr is nonzero 177 * dwFlags: This parameter can be a combination of the following flags: 178 * * DPF_DEVICE_STATUS_ACTION: Only valid if bShowDevMgr, causes 179 * the default device status action button 180 * to be clicked (Troubleshoot, Enable 181 * Device, etc) 182 * bShowDevMgr: If non-zero it displays the device manager instead of 183 * the advanced device property dialog 184 * 185 * RETURN VALUE 186 * 1: if bShowDevMgr is non-zero and no error occured 187 * -1: a call to GetLastError returns 0 if successful 188 * 189 * @implemented 190 */ 191 INT_PTR 192 WINAPI 193 DevicePropertiesExA(IN HWND hWndParent OPTIONAL, 194 IN LPCSTR lpMachineName OPTIONAL, 195 IN LPCSTR lpDeviceID OPTIONAL, 196 IN DWORD dwFlags OPTIONAL, 197 IN BOOL bShowDevMgr) 198 { 199 LPWSTR lpMachineNameW = NULL; 200 LPWSTR lpDeviceIDW = NULL; 201 INT_PTR Ret = -1; 202 203 if (lpMachineName != NULL) 204 { 205 if (!(lpMachineNameW = ConvertMultiByteToUnicode(lpMachineName, 206 CP_ACP))) 207 { 208 goto Cleanup; 209 } 210 } 211 if (lpDeviceID != NULL) 212 { 213 if (!(lpDeviceIDW = ConvertMultiByteToUnicode(lpDeviceID, 214 CP_ACP))) 215 { 216 goto Cleanup; 217 } 218 } 219 220 Ret = DevicePropertiesExW(hWndParent, 221 lpMachineNameW, 222 lpDeviceIDW, 223 dwFlags, 224 bShowDevMgr); 225 226 Cleanup: 227 if (lpMachineNameW != NULL) 228 { 229 HeapFree(GetProcessHeap(), 230 0, 231 lpMachineNameW); 232 } 233 if (lpDeviceIDW != NULL) 234 { 235 HeapFree(GetProcessHeap(), 236 0, 237 lpDeviceIDW); 238 } 239 240 return Ret; 241 } 242 243 244 /*************************************************************************** 245 * NAME EXPORTED 246 * DevicePropertiesExW 247 * 248 * DESCRIPTION 249 * Invokes the extended device properties dialog 250 * 251 * ARGUMENTS 252 * hWndParent: Handle to the parent window 253 * lpMachineName: Machine Name, NULL is the local machine 254 * lpDeviceID: Specifies the device whose properties are to be shown, optional if 255 * bShowDevMgr is nonzero 256 * dwFlags: This parameter can be a combination of the following flags: 257 * * DPF_DEVICE_STATUS_ACTION: Only valid if bShowDevMgr, causes 258 * the default device status action button 259 * to be clicked (Troubleshoot, Enable 260 * Device, etc) 261 * bShowDevMgr: If non-zero it displays the device manager instead of 262 * the advanced device property dialog 263 * 264 * RETURN VALUE 265 * 1: if bShowDevMgr is non-zero and no error occured 266 * -1: a call to GetLastError returns 0 if successful 267 * 268 * @implemented 269 */ 270 INT_PTR 271 WINAPI 272 DevicePropertiesExW(IN HWND hWndParent OPTIONAL, 273 IN LPCWSTR lpMachineName OPTIONAL, 274 IN LPCWSTR lpDeviceID OPTIONAL, 275 IN DWORD dwFlags OPTIONAL, 276 IN BOOL bShowDevMgr) 277 { 278 INT_PTR Ret = -1; 279 280 if (dwFlags & ~(DPF_EXTENDED | DPF_DEVICE_STATUS_ACTION)) 281 { 282 FIXME("DevPropertiesExW: Invalid flags: 0x%x\n", 283 dwFlags & ~(DPF_EXTENDED | DPF_DEVICE_STATUS_ACTION)); 284 SetLastError(ERROR_INVALID_FLAGS); 285 return -1; 286 } 287 288 if (bShowDevMgr) 289 { 290 FIXME("DevPropertiesExW doesn't support bShowDevMgr!\n"); 291 SetLastError(ERROR_CALL_NOT_IMPLEMENTED); 292 } 293 else 294 { 295 HDEVINFO hDevInfo; 296 SP_DEVINFO_DATA DevInfoData; 297 HINSTANCE hComCtl32; 298 299 if (lpDeviceID == NULL) 300 { 301 SetLastError(ERROR_INVALID_PARAMETER); 302 return -1; 303 } 304 305 /* dynamically load comctl32 */ 306 hComCtl32 = LoadAndInitComctl32(); 307 if (hComCtl32 != NULL) 308 { 309 hDevInfo = SetupDiCreateDeviceInfoListEx(NULL, 310 hWndParent, 311 lpMachineName, 312 NULL); 313 if (hDevInfo != INVALID_HANDLE_VALUE) 314 { 315 DevInfoData.cbSize = sizeof(SP_DEVINFO_DATA); 316 if (SetupDiOpenDeviceInfo(hDevInfo, 317 lpDeviceID, 318 hWndParent, 319 0, 320 &DevInfoData)) 321 { 322 Ret = DisplayDeviceAdvancedProperties(hWndParent, 323 lpDeviceID, 324 hDevInfo, 325 &DevInfoData, 326 hComCtl32, 327 lpMachineName, 328 dwFlags); 329 } 330 331 SetupDiDestroyDeviceInfoList(hDevInfo); 332 } 333 334 FreeLibrary(hComCtl32); 335 } 336 } 337 338 return Ret; 339 } 340 341 342 /*************************************************************************** 343 * NAME EXPORTED 344 * DevicePropertiesA 345 * 346 * DESCRIPTION 347 * Invokes the device properties dialog directly 348 * 349 * ARGUMENTS 350 * hWndParent: Handle to the parent window 351 * lpMachineName: Machine Name, NULL is the local machine 352 * lpDeviceID: Specifies the device whose properties are to be shown 353 * bShowDevMgr: If non-zero it displays the device manager instead of 354 * the device property dialog 355 * 356 * RETURN VALUE 357 * >=0: if no errors occured 358 * -1: if errors occured 359 * 360 * REVISIONS 361 * 362 * @implemented 363 */ 364 int 365 WINAPI 366 DevicePropertiesA(HWND hWndParent, 367 LPCSTR lpMachineName, 368 LPCSTR lpDeviceID, 369 BOOL bShowDevMgr) 370 { 371 return DevicePropertiesExA(hWndParent, 372 lpMachineName, 373 lpDeviceID, 374 DPF_EXTENDED, 375 bShowDevMgr); 376 } 377 378 379 /*************************************************************************** 380 * NAME EXPORTED 381 * DevicePropertiesW 382 * 383 * DESCRIPTION 384 * Invokes the device properties dialog directly 385 * 386 * ARGUMENTS 387 * hWndParent: Handle to the parent window 388 * lpMachineName: Machine Name, NULL is the local machine 389 * lpDeviceID: Specifies the device whose properties are to be shown 390 * bShowDevMgr: If non-zero it displays the device manager instead of 391 * the device property dialog 392 * 393 * RETURN VALUE 394 * >=0: if no errors occured 395 * -1: if errors occured 396 * 397 * REVISIONS 398 * 399 * @implemented 400 */ 401 int 402 WINAPI 403 DevicePropertiesW(HWND hWndParent, 404 LPCWSTR lpMachineName, 405 LPCWSTR lpDeviceID, 406 BOOL bShowDevMgr) 407 { 408 return DevicePropertiesExW(hWndParent, 409 lpMachineName, 410 lpDeviceID, 411 DPF_EXTENDED, 412 bShowDevMgr); 413 } 414 415 416 /*************************************************************************** 417 * NAME EXPORTED 418 * DeviceProperties_RunDLLA 419 * 420 * DESCRIPTION 421 * Invokes the device properties dialog 422 * 423 * ARGUMENTS 424 * hWndParent: Handle to the parent window 425 * hInst: Handle to the application instance 426 * lpDeviceCmd: A command that includes the DeviceID of the properties to be shown, 427 * also see NOTEs 428 * nCmdShow: Specifies how the window should be shown 429 * 430 * RETURN VALUE 431 * 432 * REVISIONS 433 * 434 * NOTE 435 * - lpDeviceCmd is a string in the form of "/MachineName MACHINE /DeviceID DEVICEPATH" 436 * (/MachineName is optional). This function only parses this string and eventually 437 * calls DeviceProperties(). 438 * 439 * @implemented 440 */ 441 VOID 442 WINAPI 443 DeviceProperties_RunDLLA(HWND hWndParent, 444 HINSTANCE hInst, 445 LPCSTR lpDeviceCmd, 446 int nCmdShow) 447 { 448 LPWSTR lpDeviceCmdW = NULL; 449 450 if (lpDeviceCmd != NULL) 451 { 452 if ((lpDeviceCmdW = ConvertMultiByteToUnicode(lpDeviceCmd, 453 CP_ACP))) 454 { 455 DeviceProperties_RunDLLW(hWndParent, 456 hInst, 457 lpDeviceCmdW, 458 nCmdShow); 459 } 460 } 461 462 if (lpDeviceCmdW != NULL) 463 { 464 HeapFree(GetProcessHeap(), 465 0, 466 lpDeviceCmdW); 467 } 468 } 469 470 471 /*************************************************************************** 472 * NAME EXPORTED 473 * DeviceProperties_RunDLLW 474 * 475 * DESCRIPTION 476 * Invokes the device properties dialog 477 * 478 * ARGUMENTS 479 * hWndParent: Handle to the parent window 480 * hInst: Handle to the application instance 481 * lpDeviceCmd: A command that includes the DeviceID of the properties to be shown, 482 * also see NOTEs 483 * nCmdShow: Specifies how the window should be shown 484 * 485 * RETURN VALUE 486 * 487 * REVISIONS 488 * 489 * NOTE 490 * - lpDeviceCmd is a string in the form of "/MachineName MACHINE /DeviceID DEVICEPATH" 491 * (/MachineName is optional). This function only parses this string and eventually 492 * calls DeviceProperties(). 493 * 494 * @implemented 495 */ 496 VOID 497 WINAPI 498 DeviceProperties_RunDLLW(HWND hWndParent, 499 HINSTANCE hInst, 500 LPCWSTR lpDeviceCmd, 501 int nCmdShow) 502 { 503 WCHAR szDeviceID[MAX_DEVICE_ID_LEN + 1]; 504 WCHAR szMachineName[MAX_COMPUTERNAME_LENGTH + 1]; 505 LPWSTR lpString = (LPWSTR)lpDeviceCmd; 506 507 if (!GetDeviceAndComputerName(lpString, 508 szDeviceID, 509 szMachineName)) 510 { 511 ERR("DeviceProperties_RunDLLW DeviceID: %S, MachineName: %S\n", szDeviceID, szMachineName); 512 return; 513 } 514 515 DevicePropertiesW(hWndParent, 516 szMachineName, 517 szDeviceID, 518 FALSE); 519 } 520 521 522 523 /*************************************************************************** 524 * NAME EXPORTED 525 * DeviceManager_ExecuteA 526 * 527 * DESCRIPTION 528 * Starts the Device Manager 529 * 530 * ARGUMENTS 531 * hWndParent: Handle to the parent window 532 * hInst: Handle to the application instance 533 * lpMachineName: Machine Name, NULL is the local machine 534 * nCmdShow: Specifies how the window should be shown 535 * 536 * RETURN VALUE 537 * TRUE: if no errors occured 538 * FALSE: if the device manager could not be executed 539 * 540 * REVISIONS 541 * 542 * NOTE 543 * - Win runs the device manager in a separate process, so hWndParent is somehow 544 * obsolete. 545 * 546 * @implemented 547 */ 548 BOOL 549 WINAPI 550 DeviceManager_ExecuteA(HWND hWndParent, 551 HINSTANCE hInst, 552 LPCSTR lpMachineName, 553 int nCmdShow) 554 { 555 LPWSTR lpMachineNameW = NULL; 556 BOOL Ret; 557 558 if (lpMachineName != NULL) 559 { 560 if (!(lpMachineNameW = ConvertMultiByteToUnicode(lpMachineName, 561 CP_ACP))) 562 { 563 return FALSE; 564 } 565 } 566 567 Ret = DeviceManager_ExecuteW(hWndParent, 568 hInst, 569 lpMachineNameW, 570 nCmdShow); 571 572 if (lpMachineNameW != NULL) 573 { 574 HeapFree(GetProcessHeap(), 575 0, 576 lpMachineNameW); 577 } 578 579 580 return Ret; 581 } 582 583 584 /*************************************************************************** 585 * NAME EXPORTED 586 * DeviceManager_ExecuteW 587 * 588 * DESCRIPTION 589 * Starts the Device Manager 590 * 591 * ARGUMENTS 592 * hWndParent: Handle to the parent window 593 * hInst: Handle to the application instance 594 * lpMachineName: Machine Name, NULL is the local machine 595 * nCmdShow: Specifies how the window should be shown 596 * 597 * RETURN VALUE 598 * TRUE: if no errors occured 599 * FALSE: if the device manager could not be executed 600 * 601 * REVISIONS 602 * 603 * NOTE 604 * - Win runs the device manager in a separate process, so hWndParent is somehow 605 * obsolete. 606 * 607 * @implemented 608 */ 609 BOOL 610 WINAPI 611 DeviceManager_ExecuteW(HWND hWndParent, 612 HINSTANCE hInst, 613 LPCWSTR lpMachineName, 614 int nCmdShow) 615 { 616 // FIXME: Call mmc with devmgmt.msc 617 618 CDeviceManager DevMgr; 619 return DevMgr.Create(hWndParent, hInst, lpMachineName, nCmdShow); 620 } 621 622 623 /*************************************************************************** 624 * NAME EXPORTED 625 * DeviceProblemWizard_RunDLLA 626 * 627 * DESCRIPTION 628 * Calls the device problem wizard 629 * 630 * ARGUMENTS 631 * hWndParent: Handle to the parent window 632 * hInst: Handle to the application instance 633 * lpDeviceCmd: A command that includes the DeviceID of the properties to be shown, 634 * also see NOTEs 635 * nCmdShow: Specifies how the window should be shown 636 * 637 * RETURN VALUE 638 * 639 * REVISIONS 640 * 641 * NOTE 642 * - Win XP exports this function as DeviceProblenWizard_RunDLLA, apparently it's 643 * a typo so we additionally export an alias function 644 * - lpDeviceCmd is a string in the form of "/MachineName MACHINE /DeviceID DEVICEPATH" 645 * (/MachineName is optional). This function only parses this string and eventually 646 * calls DeviceProperties(). 647 * 648 * @unimplemented 649 */ 650 VOID 651 WINAPI 652 DeviceProblemWizard_RunDLLA(HWND hWndParent, 653 HINSTANCE hInst, 654 LPCSTR lpDeviceCmd, 655 int nCmdShow) 656 { 657 UNIMPLEMENTED; 658 } 659 660 661 /*************************************************************************** 662 * NAME EXPORTED 663 * DeviceProblemWizard_RunDLLW 664 * 665 * DESCRIPTION 666 * Calls the device problem wizard 667 * 668 * ARGUMENTS 669 * hWndParent: Handle to the parent window 670 * hInst: Handle to the application instance 671 * lpDeviceCmd: A command that includes the DeviceID of the properties to be shown, 672 * also see NOTEs 673 * nCmdShow: Specifies how the window should be shown 674 * 675 * RETURN VALUE 676 * 677 * REVISIONS 678 * 679 * NOTE 680 * - Win XP exports this function as DeviceProblenWizard_RunDLLA, apparently it's 681 * a typo so we additionally export an alias function 682 * - lpDeviceCmd is a string in the form of "/MachineName MACHINE /DeviceID DEVICEPATH" 683 * (/MachineName is optional). This function only parses this string and eventually 684 * calls DeviceProperties(). 685 * 686 * @unimplemented 687 */ 688 VOID 689 WINAPI 690 DeviceProblemWizard_RunDLLW(HWND hWndParent, 691 HINSTANCE hInst, 692 LPCWSTR lpDeviceCmd, 693 int nCmdShow) 694 { 695 UNIMPLEMENTED; 696 } 697 698 699 /*************************************************************************** 700 * NAME EXPORTED 701 * DeviceManagerPrintA 702 * 703 * DESCRIPTION 704 * Calls the device problem wizard 705 * 706 * ARGUMENTS 707 * lpMachineName: Machine Name, NULL is the local machine 708 * lpPrinter: Filename of the printer where it should be printed on 709 * nPrintMode: Specifies what kind of information is to be printed 710 * DEV_PRINT_ABSTRACT: Prints an abstract of system information, the parameters 711 * uNumberOfGuids, Guids are ignored 712 * DEV_PRINT_SELECTED: Prints information about the devices listed in Guids 713 * DEV_PRINT_ALL: Prints an abstract of system information and all 714 * system devices 715 * uNumberOfGuids: Numbers of guids in the Guids array, this parameter is ignored unless 716 * nPrintMode is DEV_PRINT_SELECTED 717 * lpGuids: Array of device guids, this parameter is ignored unless 718 * nPrintMode is DEV_PRINT_SELECTED 719 * 720 * RETURN VALUE 721 * TRUE: if no errors occured 722 * FALSE: if errors occured 723 * 724 * REVISIONS 725 * 726 * NOTE 727 * 728 * @unimplemented 729 */ 730 BOOL 731 WINAPI 732 DeviceManagerPrintA(LPCSTR lpMachineName, 733 LPCSTR lpPrinter, 734 int nPrintMode, 735 UINT uNumberOfGuids, 736 LPGUID lpGuids) 737 { 738 UNIMPLEMENTED; 739 return FALSE; 740 } 741 742 743 /*************************************************************************** 744 * NAME EXPORTED 745 * DeviceManagerPrintW 746 * 747 * DESCRIPTION 748 * Calls the device problem wizard 749 * 750 * ARGUMENTS 751 * lpMachineName: Machine Name, NULL is the local machine 752 * lpPrinter: Filename of the printer where it should be printed on 753 * nPrintMode: Specifies what kind of information is to be printed 754 * DEV_PRINT_ABSTRACT: Prints an abstract of system information, the parameters 755 * uNumberOfGuids, Guids are ignored 756 * DEV_PRINT_SELECTED: Prints information about the devices listed in Guids 757 * DEV_PRINT_ALL: Prints an abstract of system information and all 758 * system devices 759 * uNumberOfGuids: Numbers of guids in the Guids array, this parameter is ignored unless 760 * nPrintMode is DEV_PRINT_SELECTED 761 * lpGuids: Array of device guids, this parameter is ignored unless 762 * nPrintMode is DEV_PRINT_SELECTED 763 * 764 * RETURN VALUE 765 * TRUE: if no errors occured 766 * FALSE: if errors occured 767 * 768 * REVISIONS 769 * 770 * NOTE 771 * 772 * @unimplemented 773 */ 774 BOOL 775 WINAPI 776 DeviceManagerPrintW(LPCWSTR lpMachineName, 777 LPCWSTR lpPrinter, 778 int nPrintMode, 779 UINT uNumberOfGuids, 780 LPGUID lpGuids) 781 { 782 UNIMPLEMENTED; 783 return FALSE; 784 } 785 786 class CDevMgrUIModule : public CComModule 787 { 788 public: 789 }; 790 791 CDevMgrUIModule gModule; 792 793 STDAPI DllCanUnloadNow() 794 { 795 return gModule.DllCanUnloadNow(); 796 } 797 798 STDAPI DllGetClassObject(REFCLSID rclsid, REFIID riid, LPVOID *ppv) 799 { 800 return gModule.DllGetClassObject(rclsid, riid, ppv); 801 } 802 803 STDAPI DllRegisterServer() 804 { 805 return gModule.DllRegisterServer(FALSE); 806 } 807 808 STDAPI DllUnregisterServer() 809 { 810 return gModule.DllUnregisterServer(FALSE); 811 } 812 813 extern "C" { 814 815 BOOL 816 WINAPI 817 DllMain(_In_ HINSTANCE hinstDLL, 818 _In_ DWORD dwReason, 819 _In_ LPVOID lpvReserved) 820 { 821 switch (dwReason) 822 { 823 case DLL_PROCESS_ATTACH: 824 DisableThreadLibraryCalls(hinstDLL); 825 hDllInstance = hinstDLL; 826 break; 827 } 828 829 return TRUE; 830 } 831 }