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.

483 lines
15 KiB

  1. //
  2. // PCH.H
  3. //
  4. // Copyright (C) Microsoft Corporation, 1995
  5. //
  6. #ifndef _REGPRIV_
  7. #define _REGPRIV_
  8. // Conditional enable registry "features" based on the target model.
  9. //
  10. // WANT_STATIC_KEYS: Allocates key handles from a memory pool allocated
  11. // during library initialization. Especially useful for real-mode to reduce
  12. // the memory fragmentation caused by allocating several small fixed objects.
  13. //
  14. // WANT_FULL_MEMORY_CLEANUP: When detaching, free every memory block. Not
  15. // necessary for the ring zero version where "detach" means system shutdown.
  16. //
  17. // WANT_HIVE_SUPPORT: RegLoadKey, RegUnLoadKey, RegSaveKey, RegReplaceKey
  18. // APIs plus support code.
  19. //
  20. // WANT_DYNKEY_SUPPORT: RegCreateDynKey plus HKEY_DYN_DATA support.
  21. //
  22. // WANT_NOTIFY_CHANGE_SUPPORT: RegNotifyChangeKeyValue plus support code.
  23. #ifndef IS_32
  24. #define WANT_STATIC_KEYS
  25. #endif
  26. #ifndef VXD
  27. #define WANT_FULL_MEMORY_CLEANUP
  28. #endif
  29. #ifndef REALMODE
  30. #define WANT_HIVE_SUPPORT
  31. #endif
  32. #ifdef VXD
  33. #define WANT_REGREPLACEKEY
  34. #define WANT_DYNKEY_SUPPORT
  35. #define WANT_NOTIFY_CHANGE_SUPPORT
  36. #endif
  37. // Map any other header's definitions of these to unused types.
  38. #define HKEY __UNUSED_HKEY
  39. #define LPHKEY __UNUSED_LPHKEY
  40. #ifndef WIN32_LEAN_AND_MEAN
  41. #define WIN32_LEAN_AND_MEAN
  42. #endif
  43. #define NORESOURCE // prevent RT_* definitions from vmmsys.h
  44. #include <windows.h>
  45. #include <string.h>
  46. #ifdef VXD
  47. #include <vmmsys.h>
  48. #include <thrdsys.h>
  49. #endif
  50. #ifndef UNALIGNED
  51. #define UNALIGNED // defined in standard headers for RISC
  52. #endif
  53. #ifndef ANYSIZE_ARRAY
  54. #define ANYSIZE_ARRAY 1
  55. #endif
  56. #ifdef VXD
  57. // By default, all registry code and data is pageable.
  58. #pragma VMM_PAGEABLE_CODE_SEG
  59. #pragma VMM_PAGEABLE_DATA_SEG
  60. #endif
  61. #define UNREFERENCED_PARAMETER(P) (P)
  62. #define INTERNAL PASCAL NEAR
  63. #define INTERNALV CDECL NEAR
  64. // Undefine any constants that we're about to define ourselves.
  65. #undef HKEY
  66. #undef LPHKEY
  67. #undef HKEY_CLASSES_ROOT
  68. #undef HKEY_CURRENT_USER
  69. #undef HKEY_LOCAL_MACHINE
  70. #undef HKEY_USERS
  71. #undef HKEY_PERFORMANCE_DATA
  72. #undef HKEY_CURRENT_CONFIG
  73. #undef HKEY_DYN_DATA
  74. typedef struct _KEY FAR* HKEY; // Forward reference
  75. #include "regdebug.h"
  76. #include "regffmt.h"
  77. #include "regfinfo.h"
  78. // Many file structures in the registry are declared as DWORDs, the HIWORD is
  79. // always zero. Use SmallDword to access such DWORDs for optimal access in
  80. // 16-bit or 32-bit code.
  81. #if defined(IS_32)
  82. #define SmallDword(dw) ((UINT) (dw))
  83. #else
  84. #define SmallDword(dw) ((UINT) LOWORD((dw)))
  85. #endif
  86. #if defined(WIN16)
  87. #define IsNullPtr(ptr) (SELECTOROF((ptr)) == NULL)
  88. #else
  89. #define IsNullPtr(ptr) ((ptr) == NULL)
  90. #endif
  91. // In either mode, the resulting code uses an instrinsic version of the memcmp
  92. // function.
  93. #if defined(IS_32)
  94. #define CompareMemory memcmp
  95. #else
  96. #define CompareMemory _fmemcmp
  97. #endif
  98. #if defined(WIN16) || defined(WIN32)
  99. #define StrCpy(lpd, lps) (lstrcpy((lpd), (lps)))
  100. #define StrCpyN(lpd, lps, cb) (lstrcpyn((lpd), (lps), (cb)))
  101. #define StrLen(lpstr) (lstrlen((lpstr)))
  102. #define ToUpper(ch) ((int) (DWORD) AnsiUpper((LPSTR)((BYTE)(ch))))
  103. #define RgCreateFile(lpfn) ((HFILE) _lcreat((lpfn), 0))
  104. #define RgOpenFile(lpfn, mode) ((HFILE) _lopen((lpfn), (mode)))
  105. #define RgCloseFile(h) ((VOID) _lclose(h))
  106. #if defined(WIN32)
  107. #define RgDeleteFile(lpv) (DeleteFile((lpv)))
  108. #define RgRenameFile(lpv1, lpv2) (MoveFile((lpv1), (lpv2)))
  109. #define RgGetFileAttributes(lpv) (GetFileAttributes((lpv)))
  110. #define RgSetFileAttributes(lpv, a) (SetFileAttributes((lpv), (a)))
  111. #ifdef USEHEAP
  112. extern HANDLE g_RgHeap; // Low memory heap for testing
  113. #define AllocBytes(cb) ((LPVOID) HeapAlloc(g_RgHeap, 0, (cb)))
  114. #define FreeBytes(lpv) ((VOID) HeapFree(g_RgHeap, 0, (lpv)))
  115. #define ReAllocBytes(lpv, cb) ((LPVOID) HeapReAlloc(g_RgHeap, 0, (lpv), (cb)))
  116. #define MemorySize(lpv) ((UINT) HeapSize(g_RgHeap, 0, (lpv)))
  117. #else
  118. #define AllocBytes(cb) ((LPVOID) LocalAlloc(LMEM_FIXED, (cb)))
  119. #define FreeBytes(lpv) ((VOID) LocalFree((HLOCAL) (lpv)))
  120. #define ReAllocBytes(lpv, cb) ((LPVOID) LocalReAlloc((HLOCAL) (lpv), (cb), LMEM_MOVEABLE))
  121. #define MemorySize(lpv) ((UINT) LocalSize((lpv)))
  122. #endif // USEHEAP
  123. #else
  124. #define AllocBytes(cb) ((LPVOID) MAKELP(GlobalAlloc(GMEM_FIXED, (cb)), 0))
  125. #define FreeBytes(lpv) ((VOID) GlobalFree((HGLOBAL) SELECTOROF((lpv))))
  126. #define ReAllocBytes(lpv, cb) ((LPVOID) MAKELP(GlobalReAlloc((HGLOBAL) SELECTOROF((lpv)), (cb), GMEM_MOVEABLE), 0))
  127. #define MemorySize(lpv) ((UINT) GlobalSize((HGLOBAL) SELECTOROF((lpv))))
  128. // WIN16's ZeroMemory/MoveMemory: SETUPX is the only target WIN16 environment
  129. // and they already use _fmemset and _fmemmove, so just use their versions.
  130. #define ZeroMemory(lpv, cb) (_fmemset((lpv), 0, (cb)))
  131. #define MoveMemory(lpd, lps, cb) (_fmemmove((lpd), (lps), (cb)))
  132. #endif // WIN16 || WIN32
  133. #elif defined(REALMODE)
  134. #define IsBadStringPtr(lpv, cb) (FALSE)
  135. #define IsBadHugeWritePtr(lpv, cb) (FALSE)
  136. #define IsBadHugeReadPtr(lpv, cb) (FALSE)
  137. #define StrCpy(lpd, lps) (_fstrcpy((lpd), (lps)))
  138. #define StrCpyN(lpd, lps, cb) (_fstrcpyn((lpd), (lps), (cb)))
  139. #define StrLen(lpstr) (_fstrlen((lpstr)))
  140. #define ToUpper(ch) ((int)(((ch>='a')&&(ch<='z'))?(ch-'a'+'A'):ch))
  141. LPVOID INTERNAL AllocBytes(UINT);
  142. VOID INTERNAL FreeBytes(LPVOID);
  143. LPVOID INTERNAL ReAllocBytes(LPVOID, UINT);
  144. UINT INTERNAL MemorySize(LPVOID);
  145. VOID INTERNAL ZeroMemory(LPVOID, UINT);
  146. VOID INTERNAL MoveMemory(LPVOID, const VOID FAR*, UINT);
  147. #elif defined(VXD)
  148. #undef IsBadStringPtr // Conflicts with windows.h
  149. #undef ZeroMemory // Conflicts with windows.h
  150. #undef MoveMemory // Conflicts with windows.h
  151. BOOL INTERNAL RgIsBadStringPtr(const VOID FAR*, UINT);
  152. BOOL INTERNAL RgIsBadOptionalStringPtr(const VOID FAR*, UINT);
  153. BOOL INTERNAL RgIsBadHugeWritePtr(const VOID FAR*, UINT);
  154. BOOL INTERNAL RgIsBadHugeOptionalWritePtr(const VOID FAR*, UINT);
  155. BOOL INTERNAL RgIsBadHugeReadPtr(const VOID FAR*, UINT);
  156. #define IsBadStringPtr(lpv, cb) (RgIsBadStringPtr((lpv), (cb)))
  157. #define IsBadOptionalStringPtr(lpv, cb) (RgIsBadOptionalStringPtr((lpv), (cb)))
  158. #define IsBadHugeWritePtr(lpv, cb) (RgIsBadHugeWritePtr((lpv), (cb)))
  159. #define IsBadHugeOptionalWritePtr(lpv, cb) (RgIsBadHugeOptionalWritePtr((lpv), (cb)))
  160. #define IsBadHugeReadPtr(lpv, cb) (RgIsBadHugeReadPtr((lpv), (cb)))
  161. #define StrCpy(lpd, lps) (_lstrcpyn((PCHAR)(lpd), (PCHAR)(lps), (ULONG)(-1)))
  162. #define StrCpyN(lpd, lps, cb) (_lstrcpyn((PCHAR)(lpd), (PCHAR)(lps), (ULONG)(cb)))
  163. #define StrLen(lpstr) (_lstrlen((PCHAR)(lpstr)))
  164. extern UCHAR UpperCaseTable[256];
  165. #define ToUpper(ch) ((int)(UpperCaseTable[(UCHAR)(ch)]))
  166. VOID INTERNAL RgSetAndReleaseEvent(HANDLE hEvent);
  167. #define RgGetCurrentThreadId() ((DWORD)pthcbCur)
  168. #define AllocBytes(cb) ((LPVOID) _HeapAllocate((cb), HEAPSWAP))
  169. #define FreeBytes(lpv) ((VOID) _HeapFree((lpv), 0))
  170. #define ReAllocBytes(lpv, cb) ((LPVOID) _HeapReAllocate((lpv), (cb), HEAPSWAP))
  171. #define MemorySize(lpv) ((UINT) _HeapGetSize((lpv), 0))
  172. #define AllocPages(cp) ((LPVOID) _PageAllocate((cp), PG_SYS, 0, 0, 0, 0, NULL, 0))
  173. #define FreePages(lpv) ((VOID) _PageFree((ULONG) (lpv), 0))
  174. #define ReAllocPages(lpv, cp) ((LPVOID) _PageReAllocate((ULONG) (lpv), (cp), 0))
  175. VOID INTERNAL RgZeroMemory(LPVOID, UINT);
  176. VOID INTERNAL RgMoveMemory(LPVOID, const VOID FAR*, UINT);
  177. #define ZeroMemory RgZeroMemory
  178. #define MoveMemory RgMoveMemory
  179. #else
  180. #error Must define REALMODE, VXD, WIN16, or WIN32.
  181. #endif
  182. // The IsBadHugeOptional*Ptr macros are used to validate pointers that may be
  183. // NULL. By wrapping this "predicate", we can generate smaller code in some
  184. // environments, specifically VMM...
  185. #if !defined(VXD)
  186. #define IsBadOptionalStringPtr(lpv, cb) \
  187. (!IsNullPtr((lpv)) && IsBadStringPtr((lpv), (cb)))
  188. #define IsBadHugeOptionalWritePtr(lpv, cb) \
  189. (!IsNullPtr((lpv)) && IsBadHugeWritePtr((lpv), (cb)))
  190. #endif
  191. // The IsEnumIndexTooBig macro is used to check if a DWORD sized index can fit
  192. // into a UINT sized variable. Only useful for validation of RegEnumKey or
  193. // RegEnumValue to make small code in both 16 and 32 bit environments.
  194. #if defined(IS_32)
  195. #define IsEnumIndexTooBig(index) (FALSE)
  196. #else
  197. #define IsEnumIndexTooBig(index) (HIWORD(index) > 0)
  198. #endif
  199. #if defined(VXD)
  200. BOOL INTERNAL RgLockRegistry(VOID);
  201. VOID INTERNAL RgUnlockRegistry(VOID);
  202. VOID INTERNAL RgDelayFlush(VOID);
  203. VOID INTERNAL RgYield(VOID);
  204. #else
  205. #define RgLockRegistry() (TRUE)
  206. #define RgUnlockRegistry() (TRUE)
  207. #define RgDelayFlush() (TRUE)
  208. #define RgYield() (TRUE)
  209. #endif
  210. // Eliminate the need for #ifdef DBCS by using macros and letting the compiler
  211. // optimize out the DBCS code on SBCS systems.
  212. #ifdef DBCS
  213. #if !defined(WIN16) && !defined(WIN32)
  214. BOOL INTERNAL RgIsDBCSLeadByte(BYTE TestChar);
  215. #define IsDBCSLeadByte(ch) RgIsDBCSLeadByte(ch)
  216. #endif
  217. #else
  218. #define IsDBCSLeadByte(ch) ((ch), FALSE)
  219. #endif // DBCS
  220. #ifdef WANT_DYNKEY_SUPPORT
  221. // Internally used for maintaining dynamic key information; only keeps the
  222. // fields that we actually need from the REG_PROVIDER structure given to
  223. // VMMRegCreateDynKey.
  224. typedef struct _INTERNAL_PROVIDER {
  225. PQUERYHANDLER ipi_R0_1val;
  226. PQUERYHANDLER ipi_R0_allvals;
  227. LPVOID ipi_key_context;
  228. } INTERNAL_PROVIDER, FAR* PINTERNAL_PROVIDER;
  229. #endif
  230. typedef struct _KEY {
  231. WORD Signature; // KEY_SIGNATURE
  232. WORD Flags; // KEYF_* bits
  233. UINT ReferenceCount;
  234. LPFILE_INFO lpFileInfo;
  235. DWORD KeynodeIndex;
  236. DWORD ChildKeynodeIndex;
  237. WORD BlockIndex;
  238. BYTE KeyRecordIndex;
  239. BYTE PredefinedKeyIndex;
  240. struct _KEY FAR* lpNext;
  241. struct _KEY FAR* lpPrev;
  242. UINT LastEnumKeyIndex;
  243. DWORD LastEnumKeyKeynodeIndex;
  244. #ifdef WANT_DYNKEY_SUPPORT
  245. PINTERNAL_PROVIDER pProvider;
  246. #endif
  247. } KEY;
  248. #define KEY_SIGNATURE 0x4B48 // "HK"
  249. #define KEYF_PREDEFINED 0x01 // Represents one of HKEY_*
  250. #define KEYF_DELETED 0x02 //
  251. #define KEYF_INVALID 0x04 //
  252. #define KEYF_STATIC 0x08 // Allocated from static pool
  253. #define KEYF_ENUMKEYCACHED 0x10 // LastEnumKey* values valid
  254. #define KEYF_HIVESALLOWED 0x20 //
  255. #define KEYF_PROVIDERHASVALUELENGTH 0x40 // PROVIDER_KEEPS_VALUE_LENGTH
  256. #define KEYF_NEVERDELETE 0x80 // Reference count overflow
  257. #define INDEX_CLASSES_ROOT 0
  258. #define INDEX_CURRENT_USER 1
  259. #define INDEX_LOCAL_MACHINE 2
  260. #define INDEX_USERS 3
  261. #define INDEX_PERFORMANCE_DATA 4
  262. #define INDEX_CURRENT_CONFIG 5
  263. #define INDEX_DYN_DATA 6
  264. // Returns TRUE if the KEY references the root of a hive, such as
  265. // HKEY_LOCAL_MACHINE, HKEY_USERS, or any hive loaded by RegLoadKey.
  266. #define IsKeyRootOfHive(hkey) \
  267. ((hkey)-> KeynodeIndex == (hkey)-> lpFileInfo-> KeynodeHeader.RootIndex)
  268. #include <regapix.h>
  269. #include "regkylst.h"
  270. #include "regdblk.h"
  271. #include "regknode.h"
  272. #include "regnckey.h"
  273. #include "regfsio.h"
  274. #include "regmem.h"
  275. #ifdef VXD
  276. extern BYTE g_RgPostCriticalInit;
  277. extern BYTE g_RgFileAccessDisabled;
  278. #define IsPostCriticalInit() (g_RgPostCriticalInit)
  279. #define IsFileAccessDisabled() (g_RgFileAccessDisabled)
  280. #else
  281. #define IsPostCriticalInit() (TRUE)
  282. #define IsFileAccessDisabled() (FALSE)
  283. #endif
  284. // g_RgWorkBuffer: one buffer is always available of size SIZEOF_WORK_BUFFER.
  285. // These macros wrap access to this buffer for to verify only one routine is
  286. // attempting to use it at any time.
  287. extern LPVOID g_RgWorkBuffer;
  288. #ifdef DEBUG
  289. extern BOOL g_RgWorkBufferBusy;
  290. #define RgLockWorkBuffer() \
  291. (ASSERT(!g_RgWorkBufferBusy), g_RgWorkBufferBusy = TRUE, (LPVOID) g_RgWorkBuffer)
  292. #define RgUnlockWorkBuffer(lpv) \
  293. (VOID) (ASSERT((lpv) == g_RgWorkBuffer), g_RgWorkBufferBusy = FALSE)
  294. #else
  295. #define RgLockWorkBuffer() ((LPVOID) g_RgWorkBuffer)
  296. #define RgUnlockWorkBuffer(lpv)
  297. #endif
  298. #define SIZEOF_WORK_BUFFER (sizeof(W95KEYNODE_BLOCK))
  299. #define IsKeyRecordFree(lpkr) \
  300. (((lpkr)-> DatablockAddress) == REG_NULL)
  301. BOOL
  302. INTERNAL
  303. RgIsBadSubKey(
  304. LPCSTR lpSubKey
  305. );
  306. UINT
  307. INTERNAL
  308. RgGetNextSubSubKey(
  309. LPCSTR lpSubKey,
  310. LPCSTR FAR* lplpSubSubKey,
  311. UINT FAR* lpSubSubKeyLength
  312. );
  313. #define LK_OPEN 0x0000 // Open key only
  314. #define LK_CREATE 0x0001 // Create or open key
  315. #define LK_CREATEDYNDATA 0x0002 // HKEY_DYN_DATA may create
  316. int
  317. INTERNAL
  318. RgLookupKey(
  319. HKEY hKey,
  320. LPCSTR lpSubKey,
  321. LPHKEY lphSubKey,
  322. UINT Flags
  323. );
  324. int
  325. INTERNAL
  326. RgCreateOrOpenKey(
  327. HKEY hKey,
  328. LPCSTR lpSubKey,
  329. LPHKEY lphKey,
  330. UINT Flags
  331. );
  332. int
  333. INTERNAL
  334. RgLookupKeyByIndex(
  335. HKEY hKey,
  336. UINT Index,
  337. LPSTR lpKeyName,
  338. LPDWORD lpcbKeyName
  339. );
  340. int
  341. INTERNAL
  342. RgLookupValueByName(
  343. HKEY hKey,
  344. LPCSTR lpValueName,
  345. LPKEY_RECORD FAR* lplpKeyRecord,
  346. LPVALUE_RECORD FAR* lplpValueRecord
  347. );
  348. int
  349. INTERNAL
  350. RgLookupValueByIndex(
  351. HKEY hKey,
  352. UINT Index,
  353. LPVALUE_RECORD FAR* lplpValueRecord
  354. );
  355. int
  356. INTERNAL
  357. RgCopyFromValueRecord(
  358. HKEY hKey,
  359. LPVALUE_RECORD lpValueRecord,
  360. LPSTR lpValueName,
  361. LPDWORD lpcbValueName,
  362. LPDWORD lpType,
  363. LPBYTE lpData,
  364. LPDWORD lpcbData
  365. );
  366. int
  367. INTERNAL
  368. RgReAllocKeyRecord(
  369. HKEY hKey,
  370. DWORD Length,
  371. LPKEY_RECORD FAR* lplpKeyRecord
  372. );
  373. int
  374. INTERNAL
  375. RgSetValue(
  376. HKEY hKey,
  377. LPCSTR lpValueName,
  378. DWORD Type,
  379. LPBYTE lpData,
  380. UINT cbData
  381. );
  382. int
  383. INTERNAL
  384. RgDeleteKey(
  385. HKEY hKey
  386. );
  387. DWORD
  388. INTERNAL
  389. RgChecksum(
  390. LPVOID lpBuffer,
  391. UINT ByteCount
  392. );
  393. DWORD
  394. INTERNAL
  395. RgHashString(
  396. LPCSTR lpString,
  397. UINT Length
  398. );
  399. int
  400. INTERNAL
  401. RgStrCmpNI(
  402. LPCSTR lpString1,
  403. LPCSTR lpString2,
  404. UINT Length
  405. );
  406. int
  407. INTERNAL
  408. RgCopyFileBytes(
  409. HFILE hSourceFile,
  410. LONG SourceOffset,
  411. HFILE hDestinationFile,
  412. LONG DestinationOffset,
  413. DWORD cbSize
  414. );
  415. BOOL
  416. INTERNAL
  417. RgGenerateAltFileName(
  418. LPCSTR lpFileName,
  419. LPSTR lpAltFileName,
  420. char ExtensionChar
  421. );
  422. int
  423. INTERNAL
  424. RgCopyFile(
  425. LPCSTR lpSourceFile,
  426. LPCSTR lpDestinationFile
  427. );
  428. int
  429. INTERNAL
  430. RgReplaceFileInfo(
  431. LPFILE_INFO lpFileInfo
  432. );
  433. #endif // _REGPRIV_