Source code of Windows XP (NT5)
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

219 lines
5.4 KiB

  1. /*++
  2. Copyright (c) 1995-2001 Microsoft Corporation
  3. Module Name:
  4. rconflist.c
  5. Abstract:
  6. This module contains the server-side conflict list reporting APIs.
  7. PNP_QueryResConfList
  8. Author:
  9. Paula Tomlinson (paulat) 9-27-1995
  10. Environment:
  11. User-mode only.
  12. Revision History:
  13. 27-Sept-1995 paulat
  14. Creation and initial implementation.
  15. --*/
  16. //
  17. // includes
  18. //
  19. #include "precomp.h"
  20. #include "umpnpi.h"
  21. //
  22. // private prototypes
  23. //
  24. CONFIGRET
  25. ResDesToNtResource(
  26. IN PCVOID ResourceData,
  27. IN RESOURCEID ResourceID,
  28. IN ULONG ResourceLen,
  29. IN PCM_PARTIAL_RESOURCE_DESCRIPTOR pResDes,
  30. IN ULONG ulTag,
  31. IN ULONG ulFlags
  32. );
  33. ULONG
  34. GetResDesSize(
  35. IN ULONG ResourceID,
  36. IN ULONG ulFlags
  37. );
  38. CONFIGRET
  39. PNP_QueryResConfList(
  40. IN handle_t hBinding,
  41. IN LPWSTR pDeviceID,
  42. IN RESOURCEID ResourceID,
  43. IN LPBYTE ResourceData,
  44. IN ULONG ResourceLen,
  45. OUT LPBYTE clBuffer,
  46. IN ULONG clBufferLen,
  47. IN ULONG ulFlags
  48. )
  49. /*++
  50. Routine Description:
  51. This the server-side of an RPC remote call. This routine retrieves
  52. conflict information for a specified resource.
  53. Arguments:
  54. hBinding RPC binding handle, not used.
  55. pDeviceID Null-terminated device instance id string.
  56. ResourceID Type of resource, ResType_xxxx
  57. ResourceData Resource specific data
  58. ResourceLen length of ResourceData
  59. clBuffer Buffer filled with conflict list
  60. clBufferLen Size of clBuffer
  61. ulFlags Specifies the width of certain variable-size resource
  62. descriptor structure fields, where applicable.
  63. Currently, the following flags are defined:
  64. CM_RESDES_WIDTH_32 or
  65. CM_RESDES_WIDTH_64
  66. If no flags are specified, the width of the variable-sized
  67. resource data supplied is assumed to be that native to the
  68. platform of the caller.
  69. Return Value:
  70. If the specified device instance is valid, it returns CR_SUCCESS,
  71. otherwise it returns CR_ error code.
  72. --*/
  73. {
  74. CONFIGRET Status = CR_SUCCESS;
  75. NTSTATUS NtStatus = STATUS_SUCCESS;
  76. PLUGPLAY_CONTROL_CONFLICT_DATA ControlData;
  77. PPLUGPLAY_CONTROL_CONFLICT_LIST pConflicts;
  78. CM_RESOURCE_LIST NtResourceList;
  79. ULONG Index;
  80. UNREFERENCED_PARAMETER(hBinding);
  81. try {
  82. //
  83. // validate parameters
  84. //
  85. if (INVALID_FLAGS(ulFlags, CM_RESDES_WIDTH_BITS)) {
  86. Status = CR_INVALID_FLAG;
  87. goto Clean0;
  88. }
  89. //
  90. // validate res des size
  91. //
  92. if (ResourceLen < GetResDesSize(ResourceID, ulFlags)) {
  93. Status = CR_INVALID_DATA;
  94. goto Clean0;
  95. }
  96. if (!IsLegalDeviceId(pDeviceID)) {
  97. Status = CR_INVALID_DEVNODE;
  98. goto Clean0;
  99. }
  100. //
  101. // make sure original caller didn't specify root devnode
  102. //
  103. if (IsRootDeviceID(pDeviceID)) {
  104. Status = CR_INVALID_LOG_CONF;
  105. goto Clean0;
  106. }
  107. //
  108. // look at buffer we need to fill in
  109. // validate parameters passed in buffer
  110. // buffer should always be big enough to hold header
  111. //
  112. if(clBufferLen < sizeof(PPLUGPLAY_CONTROL_CONFLICT_LIST)) {
  113. Status = CR_INVALID_STRUCTURE_SIZE;
  114. goto Clean0;
  115. }
  116. pConflicts = (PPLUGPLAY_CONTROL_CONFLICT_LIST)clBuffer;
  117. //
  118. // Convert the user-mode version of the resource list to an
  119. // NT CM_RESOURCE_LIST structure.
  120. //
  121. // we'll sort out InterfaceType and BusNumber in kernel
  122. //
  123. NtResourceList.Count = 1;
  124. NtResourceList.List[0].InterfaceType = InterfaceTypeUndefined;
  125. NtResourceList.List[0].BusNumber = 0;
  126. NtResourceList.List[0].PartialResourceList.Version = NT_RESLIST_VERSION;
  127. NtResourceList.List[0].PartialResourceList.Revision = NT_RESLIST_REVISION;
  128. NtResourceList.List[0].PartialResourceList.Count = 1;
  129. Status = ResDesToNtResource(ResourceData, ResourceID, ResourceLen,
  130. &NtResourceList.List[0].PartialResourceList.PartialDescriptors[0], 0, ulFlags);
  131. if (Status != CR_SUCCESS) {
  132. goto Clean0;
  133. }
  134. //
  135. // now fill in ControlData
  136. //
  137. RtlInitUnicodeString(&ControlData.DeviceInstance, pDeviceID);
  138. ControlData.ResourceList = &NtResourceList;
  139. ControlData.ResourceListSize = sizeof(NtResourceList);
  140. ControlData.ConflictBuffer = pConflicts;
  141. ControlData.ConflictBufferSize = clBufferLen;
  142. ControlData.Flags = ulFlags;
  143. ControlData.Status = STATUS_SUCCESS;
  144. NtStatus = NtPlugPlayControl(PlugPlayControlQueryConflictList,
  145. &ControlData,
  146. sizeof(ControlData));
  147. if (NtStatus == STATUS_SUCCESS) {
  148. Status = CR_SUCCESS;
  149. } else {
  150. Status = MapNtStatusToCmError(NtStatus);
  151. }
  152. Clean0:
  153. NOTHING;
  154. } except(EXCEPTION_EXECUTE_HANDLER) {
  155. //
  156. // unspecified failure
  157. //
  158. Status = CR_FAILURE;
  159. }
  160. return Status;
  161. } // PNP_QueryResConfList