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.

201 lines
5.2 KiB

  1. /*++
  2. Copyright (c) 1990, 1991 Microsoft Corporation
  3. Module Name:
  4. hwpbiosc.c
  5. Abstract:
  6. This modules contains PnP BIOS C supporting routines
  7. Author:
  8. Shie-Lin Tzong (shielint) 20-Apr-1995
  9. Environment:
  10. Real mode.
  11. Revision History:
  12. --*/
  13. #include "hwdetect.h"
  14. #include <string.h>
  15. #if !defined(_GAMBIT_)
  16. #include "pnpbios.h"
  17. #endif
  18. BOOLEAN
  19. HwGetPnpBiosSystemData(
  20. IN FPUCHAR *Configuration,
  21. OUT PUSHORT Length
  22. )
  23. /*++
  24. Routine Description:
  25. This routine checks if PNP BIOS is present in the machine. If yes, it
  26. also create a registry descriptor to collect the BIOS data.
  27. Arguments:
  28. Configuration - Supplies a variable to receive the PNP BIOS data.
  29. Length - Supplies a variable to receive the size of the data + HEADER
  30. Return Value:
  31. A value of TRUE is returned if success. Otherwise, a value of
  32. FALSE is returned.
  33. --*/
  34. {
  35. #if defined(_GAMBIT_)
  36. return FALSE;
  37. #else
  38. ULONG romAddr, romEnd;
  39. FPUCHAR current;
  40. FPPNP_BIOS_INSTALLATION_CHECK header;
  41. UCHAR sum, node = 0;
  42. USHORT i, totalSize = 0, nodeSize, numberNodes, retCode;
  43. ENTRY_POINT biosEntry;
  44. FPPNP_BIOS_DEVICE_NODE deviceNode;
  45. USHORT control = GET_CURRENT_CONFIGURATION;
  46. //
  47. // Perform PNP BIOS installation Check
  48. //
  49. MAKE_FP(current, PNP_BIOS_START);
  50. romAddr = PNP_BIOS_START;
  51. romEnd = PNP_BIOS_END;
  52. while (romAddr < romEnd) {
  53. header = (FPPNP_BIOS_INSTALLATION_CHECK)current;
  54. if (header->Signature[0] == '$' && header->Signature[1] == 'P' &&
  55. header->Signature[2] == 'n' && header->Signature[3] == 'P' &&
  56. header->Length >= sizeof(PNP_BIOS_INSTALLATION_CHECK)) {
  57. #if DBG
  58. BlPrint("GetPnpBiosData: find Pnp installation\n");
  59. #endif
  60. sum = 0;
  61. for (i = 0; i < header->Length; i++) {
  62. sum += current[i];
  63. }
  64. if (sum == 0) {
  65. break;
  66. }
  67. #if DBG
  68. BlPrint("GetPnpBiosData: Checksum fails\n");
  69. #endif
  70. }
  71. romAddr += PNP_BIOS_HEADER_INCREMENT;
  72. MAKE_FP(current, romAddr);
  73. }
  74. if (romAddr >= romEnd) {
  75. return FALSE;
  76. }
  77. #if DBG
  78. BlPrint("PnP installation check at %lx\n", romAddr);
  79. #endif
  80. //
  81. // Determine how much space we will need and allocate heap space
  82. //
  83. totalSize += sizeof(PNP_BIOS_INSTALLATION_CHECK) + DATA_HEADER_SIZE;
  84. biosEntry = *(ENTRY_POINT far *)&header->RealModeEntryOffset;
  85. retCode = biosEntry(PNP_BIOS_GET_NUMBER_DEVICE_NODES,
  86. (FPUSHORT)&numberNodes,
  87. (FPUSHORT)&nodeSize,
  88. header->RealModeDataBaseAddress
  89. );
  90. if (retCode != 0) {
  91. #if DBG
  92. BlPrint("GetPnpBiosData: PnP Bios GetNumberNodes func returns failure %x.\n", retCode);
  93. #endif
  94. return FALSE;
  95. }
  96. #if DBG
  97. BlPrint("GetPnpBiosData: Pnp Bios GetNumberNodes returns %x nodes\n", numberNodes);
  98. #endif
  99. deviceNode = (FPPNP_BIOS_DEVICE_NODE) HwAllocateHeap(nodeSize, FALSE);
  100. if (!deviceNode) {
  101. #if DBG
  102. BlPrint("GetPnpBiosData: Out of heap space.\n");
  103. #endif
  104. return FALSE;
  105. }
  106. while (node != 0xFF) {
  107. retCode = biosEntry(PNP_BIOS_GET_DEVICE_NODE,
  108. (FPUCHAR)&node,
  109. deviceNode,
  110. control,
  111. header->RealModeDataBaseAddress
  112. );
  113. if (retCode != 0) {
  114. #if DBG
  115. BlPrint("GetPnpBiosData: PnP Bios GetDeviceNode func returns failure = %x.\n", retCode);
  116. #endif
  117. HwFreeHeap((ULONG)nodeSize);
  118. return FALSE;
  119. }
  120. #if DBG
  121. BlPrint("GetPnpBiosData: PnpBios GetDeviceNode returns nodesize %x for node %x\n", deviceNode->Size, node);
  122. #endif
  123. totalSize += deviceNode->Size;
  124. }
  125. #if DBG
  126. BlPrint("GetPnpBiosData: PnpBios total size of nodes %lx\n", totalSize);
  127. #endif
  128. HwFreeHeap((ULONG)nodeSize); // Free temporary buffer
  129. current = (FPUCHAR) HwAllocateHeap(totalSize, FALSE);
  130. if (!current) {
  131. #if DBG
  132. BlPrint("GetPnpBiosData: Out of heap space.\n");
  133. #endif
  134. return FALSE;
  135. }
  136. //
  137. // Collect PnP Bios installation check data and device node data.
  138. //
  139. _fmemcpy (current + DATA_HEADER_SIZE,
  140. (FPUCHAR)header,
  141. sizeof(PNP_BIOS_INSTALLATION_CHECK)
  142. );
  143. deviceNode = (FPPNP_BIOS_DEVICE_NODE)(current + DATA_HEADER_SIZE +
  144. sizeof(PNP_BIOS_INSTALLATION_CHECK));
  145. node = 0;
  146. while (node != 0xFF) {
  147. retCode = biosEntry(PNP_BIOS_GET_DEVICE_NODE,
  148. (FPUCHAR)&node,
  149. deviceNode,
  150. control,
  151. header->RealModeDataBaseAddress
  152. );
  153. if (retCode != 0) {
  154. #if DBG
  155. BlPrint("GetPnpBiosData: PnP Bios func 1 returns failure = %x.\n", retCode);
  156. #endif
  157. HwFreeHeap((ULONG)totalSize);
  158. return FALSE;
  159. }
  160. deviceNode = (FPPNP_BIOS_DEVICE_NODE)((FPUCHAR)deviceNode + deviceNode->Size);
  161. }
  162. *Configuration = current;
  163. *Length = totalSize;
  164. return TRUE;
  165. #endif // _GAMBIT_
  166. }