Windows NT 4.0 source code leak
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.

382 lines
8.5 KiB

4 years ago
  1. #include <nt.h>
  2. #include <ntrtl.h>
  3. #include <nturtl.h>
  4. #include <windows.h>
  5. #include "psapi.h"
  6. #include <stddef.h>
  7. BOOL
  8. FindDeviceDriver(
  9. LPVOID ImageBase,
  10. PRTL_PROCESS_MODULE_INFORMATION Module
  11. )
  12. /*++
  13. Routine Description:
  14. This function retrieves the full pathname of the executable file
  15. from which the specified module was loaded. The function copies the
  16. null-terminated filename into the buffer pointed to by the
  17. lpFilename parameter.
  18. Routine Description:
  19. ImageBase - Identifies the driver whose executable file name is being
  20. requested.
  21. Return Value:
  22. The return value specifies the actual length of the string copied to
  23. the buffer. A return value of zero indicates an error and extended
  24. error status is available using the GetLastError function.
  25. Arguments:
  26. --*/
  27. {
  28. RTL_PROCESS_MODULES ModuleInformation;
  29. NTSTATUS Status;
  30. DWORD cbModuleInformation;
  31. PRTL_PROCESS_MODULES pModuleInformation;
  32. DWORD i, ReturnedLength;
  33. Status = NtQuerySystemInformation(
  34. SystemModuleInformation,
  35. &ModuleInformation,
  36. sizeof(ModuleInformation),
  37. &ReturnedLength
  38. );
  39. if ( !NT_SUCCESS(Status) && (Status != STATUS_INFO_LENGTH_MISMATCH) ) {
  40. SetLastError( RtlNtStatusToDosError( Status ) );
  41. return(FALSE);
  42. }
  43. cbModuleInformation = offsetof(RTL_PROCESS_MODULES, Modules);
  44. cbModuleInformation += ModuleInformation.NumberOfModules * sizeof(RTL_PROCESS_MODULE_INFORMATION);
  45. pModuleInformation = (PRTL_PROCESS_MODULES) LocalAlloc(LMEM_FIXED, cbModuleInformation);
  46. if (pModuleInformation == NULL) {
  47. return(FALSE);
  48. }
  49. Status = NtQuerySystemInformation(
  50. SystemModuleInformation,
  51. pModuleInformation,
  52. cbModuleInformation,
  53. &ReturnedLength
  54. );
  55. if ( !NT_SUCCESS(Status) ) {
  56. LocalFree((HLOCAL) pModuleInformation);
  57. SetLastError( RtlNtStatusToDosError( Status ) );
  58. return(FALSE);
  59. }
  60. for (i = 0; i < ModuleInformation.NumberOfModules; i++) {
  61. if (pModuleInformation->Modules[i].ImageBase == ImageBase) {
  62. *Module = pModuleInformation->Modules[i];
  63. LocalFree((HLOCAL) pModuleInformation);
  64. return(TRUE);
  65. }
  66. }
  67. LocalFree((HLOCAL) pModuleInformation);
  68. SetLastError(ERROR_INVALID_HANDLE);
  69. return(FALSE);
  70. }
  71. BOOL
  72. WINAPI
  73. EnumDeviceDrivers(
  74. LPVOID *lpImageBase,
  75. DWORD cb,
  76. LPDWORD lpcbNeeded
  77. )
  78. {
  79. RTL_PROCESS_MODULES ModuleInformation;
  80. NTSTATUS Status;
  81. DWORD cbModuleInformation;
  82. PRTL_PROCESS_MODULES pModuleInformation;
  83. DWORD cpvMax;
  84. DWORD i, ReturnedLength;
  85. Status = NtQuerySystemInformation(
  86. SystemModuleInformation,
  87. &ModuleInformation,
  88. sizeof(ModuleInformation),
  89. &ReturnedLength
  90. );
  91. if ( !NT_SUCCESS(Status) && (Status != STATUS_INFO_LENGTH_MISMATCH) ) {
  92. SetLastError( RtlNtStatusToDosError( Status ) );
  93. return(FALSE);
  94. }
  95. cbModuleInformation = offsetof(RTL_PROCESS_MODULES, Modules);
  96. cbModuleInformation += ModuleInformation.NumberOfModules * sizeof(RTL_PROCESS_MODULE_INFORMATION);
  97. pModuleInformation = (PRTL_PROCESS_MODULES) LocalAlloc(LMEM_FIXED, cbModuleInformation);
  98. if (pModuleInformation == NULL) {
  99. return(FALSE);
  100. }
  101. Status = NtQuerySystemInformation(
  102. SystemModuleInformation,
  103. pModuleInformation,
  104. cbModuleInformation,
  105. &ReturnedLength
  106. );
  107. if ( !NT_SUCCESS(Status) ) {
  108. LocalFree((HLOCAL) pModuleInformation);
  109. SetLastError( RtlNtStatusToDosError( Status ) );
  110. return(FALSE);
  111. }
  112. cpvMax = cb / sizeof(LPVOID);
  113. for (i = 0; i < ModuleInformation.NumberOfModules; i++) {
  114. if (i == cpvMax) {
  115. break;
  116. }
  117. try {
  118. lpImageBase[i] = pModuleInformation->Modules[i].ImageBase;
  119. }
  120. except (EXCEPTION_EXECUTE_HANDLER) {
  121. LocalFree((HLOCAL) pModuleInformation);
  122. SetLastError( RtlNtStatusToDosError( GetExceptionCode() ) );
  123. return(FALSE);
  124. }
  125. }
  126. try {
  127. *lpcbNeeded = ModuleInformation.NumberOfModules * sizeof(LPVOID);
  128. }
  129. except (EXCEPTION_EXECUTE_HANDLER) {
  130. LocalFree((HLOCAL) pModuleInformation);
  131. SetLastError( RtlNtStatusToDosError( GetExceptionCode() ) );
  132. return(FALSE);
  133. }
  134. LocalFree((HLOCAL) pModuleInformation);
  135. return(TRUE);
  136. }
  137. DWORD
  138. WINAPI
  139. GetDeviceDriverFileNameW(
  140. LPVOID ImageBase,
  141. LPWSTR lpFilename,
  142. DWORD nSize
  143. )
  144. /*++
  145. Routine Description:
  146. This function retrieves the full pathname of the executable file
  147. from which the specified module was loaded. The function copies the
  148. null-terminated filename into the buffer pointed to by the
  149. lpFilename parameter.
  150. Routine Description:
  151. ImageBase - Identifies the driver whose executable file name is being
  152. requested.
  153. lpFilename - Points to the buffer that is to receive the filename.
  154. nSize - Specifies the maximum number of characters to copy. If the
  155. filename is longer than the maximum number of characters
  156. specified by the nSize parameter, it is truncated.
  157. Return Value:
  158. The return value specifies the actual length of the string copied to
  159. the buffer. A return value of zero indicates an error and extended
  160. error status is available using the GetLastError function.
  161. Arguments:
  162. --*/
  163. {
  164. LPSTR lpstr;
  165. DWORD cch;
  166. DWORD cchT;
  167. lpstr = (LPSTR) LocalAlloc(LMEM_FIXED, nSize);
  168. if (lpstr == NULL) {
  169. return(0);
  170. }
  171. cchT = cch = GetDeviceDriverFileNameA(ImageBase, lpstr, nSize);
  172. if (cchT < nSize) {
  173. //
  174. // Include NULL terminator
  175. //
  176. cchT++;
  177. }
  178. if (!MultiByteToWideChar(CP_ACP, 0, lpstr, cchT, lpFilename, nSize)) {
  179. cch = 0;
  180. }
  181. LocalFree((HLOCAL) lpstr);
  182. return(cch);
  183. }
  184. DWORD
  185. WINAPI
  186. GetDeviceDriverFileNameA(
  187. LPVOID ImageBase,
  188. LPSTR lpFilename,
  189. DWORD nSize
  190. )
  191. {
  192. RTL_PROCESS_MODULE_INFORMATION Module;
  193. DWORD cchT;
  194. DWORD cch;
  195. if (!FindDeviceDriver(ImageBase, &Module)) {
  196. return(0);
  197. }
  198. cch = cchT = (DWORD) (strlen(Module.FullPathName) + 1);
  199. if ( nSize < cch ) {
  200. cch = nSize;
  201. }
  202. CopyMemory(lpFilename, Module.FullPathName, cch);
  203. if (cch == cchT) {
  204. cch--;
  205. }
  206. return(cch);
  207. }
  208. DWORD
  209. WINAPI
  210. GetDeviceDriverBaseNameW(
  211. LPVOID ImageBase,
  212. LPWSTR lpFilename,
  213. DWORD nSize
  214. )
  215. /*++
  216. Routine Description:
  217. This function retrieves the full pathname of the executable file
  218. from which the specified module was loaded. The function copies the
  219. null-terminated filename into the buffer pointed to by the
  220. lpFilename parameter.
  221. Routine Description:
  222. ImageBase - Identifies the driver whose executable file name is being
  223. requested.
  224. lpFilename - Points to the buffer that is to receive the filename.
  225. nSize - Specifies the maximum number of characters to copy. If the
  226. filename is longer than the maximum number of characters
  227. specified by the nSize parameter, it is truncated.
  228. Return Value:
  229. The return value specifies the actual length of the string copied to
  230. the buffer. A return value of zero indicates an error and extended
  231. error status is available using the GetLastError function.
  232. Arguments:
  233. --*/
  234. {
  235. LPSTR lpstr;
  236. DWORD cch;
  237. DWORD cchT;
  238. lpstr = (LPSTR) LocalAlloc(LMEM_FIXED, nSize);
  239. if (lpstr == NULL) {
  240. return(0);
  241. }
  242. cchT = cch = GetDeviceDriverBaseNameA(ImageBase, lpstr, nSize);
  243. if (cchT < nSize) {
  244. //
  245. // Include NULL terminator
  246. //
  247. cchT++;
  248. }
  249. if (!MultiByteToWideChar(CP_ACP, 0, lpstr, cchT, lpFilename, nSize)) {
  250. cch = 0;
  251. }
  252. LocalFree((HLOCAL) lpstr);
  253. return(cch);
  254. }
  255. DWORD
  256. WINAPI
  257. GetDeviceDriverBaseNameA(
  258. LPVOID ImageBase,
  259. LPSTR lpFilename,
  260. DWORD nSize
  261. )
  262. {
  263. RTL_PROCESS_MODULE_INFORMATION Module;
  264. DWORD cchT;
  265. DWORD cch;
  266. if (!FindDeviceDriver(ImageBase, &Module)) {
  267. return(0);
  268. }
  269. cch = cchT = (DWORD) (strlen(Module.FullPathName + Module.OffsetToFileName) + 1);
  270. if ( nSize < cch ) {
  271. cch = nSize;
  272. }
  273. CopyMemory(lpFilename, Module.FullPathName + Module.OffsetToFileName, cch);
  274. if (cch == cchT) {
  275. cch--;
  276. }
  277. return(cch);
  278. }