https://git.reactos.org/?p=reactos.git;a=commitdiff;h=c0ea1f96eff0fa8b90972bed306b2f480be29dfd
commit c0ea1f96eff0fa8b90972bed306b2f480be29dfd Author: George Bișoc <george.bi...@reactos.org> AuthorDate: Sat Aug 26 22:37:53 2023 +0200 Commit: George Bișoc <george.bi...@reactos.org> CommitDate: Sun Oct 1 20:06:03 2023 +0200 [NTOS:CM][DOCUMENTATION] Provide documentation for newly added functions --- ntoskrnl/config/cmkcbncb.c | 81 ++++++++++++++++++++ ntoskrnl/config/cmparse.c | 186 +++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 267 insertions(+) diff --git a/ntoskrnl/config/cmkcbncb.c b/ntoskrnl/config/cmkcbncb.c index 659aeea4ddb..9a69479c4b0 100644 --- a/ntoskrnl/config/cmkcbncb.c +++ b/ntoskrnl/config/cmkcbncb.c @@ -1134,6 +1134,13 @@ DelistKeyBodyFromKCB(IN PCM_KEY_BODY KeyBody, if (!LockHeld) CmpReleaseKcbLock(KeyBody->KeyControlBlock); } +/** + * @brief + * Unlocks a number of KCBs provided by a KCB array. + * + * @param[in] KcbArray + * A pointer to an array of KCBs to be unlocked. + */ VOID CmpUnLockKcbArray( _In_ PULONG KcbArray) @@ -1147,6 +1154,24 @@ CmpUnLockKcbArray( } } +/** + * @brief + * Locks a given number of KCBs. + * + * @param[in] KcbArray + * A pointer to an array of KCBs to be locked. + * The count of KCBs to be locked is defined by the + * first element in the array. + * + * @param[in] KcbLockFlags + * Define a lock flag to lock the KCBs. + * + * CMP_LOCK_KCB_ARRAY_EXCLUSIVE -- indicates the KCBs are locked + * exclusively and owned by the calling thread. + * + * CMP_LOCK_KCB_ARRAY_SHARED -- indicates the KCBs are locked + * in shared mode by the owning threads. + */ static VOID CmpLockKcbArray( @@ -1169,6 +1194,18 @@ CmpLockKcbArray( } } +/** + * @brief + * Sorts an array of KCB hashes in ascending order + * and removes any key indices that are duplicates. + * The purpose of sorting the KCB elements is to + * ensure consistent and proper locking order, so + * that we can prevent a deadlock. + * + * @param[in,out] KcbArray + * A pointer to an array of KCBs of which the key + * indices are to be sorted. + */ static VOID CmpSortKcbArray( @@ -1216,6 +1253,50 @@ CmpSortKcbArray( KcbArray[0] = KcbCount; } +/** + * @brief + * Builds an array of KCBs and locks them. Whether these + * KCBs are locked exclusively or in shared mode by the calling + * thread, is specified by the KcbLockFlags parameter. The array + * is sorted. + * + * @param[in] HashCacheStack + * A pointer to a hash cache stack. This stack parameter + * stores the convkey hashes of interested KCBs of a + * key path name that need to be locked. + * + * @param[in] KcbLockFlags + * Define a lock flag to lock the KCBs. Consult the + * CmpLockKcbArray documentation for more information. + * + * @param[in] Kcb + * A pointer to a key control block to be given. This + * KCB is included in the array for locking, that is, + * given by the CmpParseKey from the parser object. + * + * @param[in,out] OuterStackArray + * A pointer to an array that lives on the caller's + * stack. It acts like an auxiliary array used by + * the function to store the KCB elements for locking. + * The expected size of the array is up to 32 elements, + * which is the imposed limit by CMP_HASH_STACK_LIMIT. + * This limit also corresponds to the maximum depth of + * subkey levels. + * + * @param[in] TotalRemainingSubkeys + * The number of total remaining subkey levels. + * + * @param[in] MatchRemainSubkeyLevel + * The number of remaining subkey levels that match. + * + * @return + * Returns a pointer to an array of KCBs that have been + * locked. + * + * @remarks + * The caller HAS THE RESPONSIBILITY to unlock the KCBs + * after the necessary operations are done! + */ PULONG NTAPI CmpBuildAndLockKcbArray( diff --git a/ntoskrnl/config/cmparse.c b/ntoskrnl/config/cmparse.c index dec2fd72cda..b9bc5c7e596 100644 --- a/ntoskrnl/config/cmparse.c +++ b/ntoskrnl/config/cmparse.c @@ -1111,6 +1111,31 @@ CmpHandleExitNode(IN OUT PHHIVE *Hive, } } +/** + * @brief + * Computes the hashes of each subkey in key path name + * and stores them in a hash stack for cache lookup. + * + * @param[in] RemainingName + * A Unicode string structure consisting of the remaining + * registry key path name. + * + * @param[in] ConvKey + * The hash convkey of the current KCB to be supplied. + * + * @param[in,out] HashCacheStack + * An array stack. This function uses this array to store + * all the computed hashes of a key pathname. + * + * @param[out] TotalSubKeys + * The number of total subkeys that have been found, returned + * by this function to the caller. If no subkey levels are found + * the function returns 0. + * + * @return + * Returns the number of remaining subkey levels to caller. + * If no subkey levels are found then this function returns 0. + */ static ULONG CmpComputeHashValue( @@ -1229,6 +1254,31 @@ CmpComputeHashValue( return RemainingSubkeysInTotal; } +/** + * @brief + * Compares each subkey's hash and name with those + * captured in the hash cache stack. + * + * @param[in] HashCacheStack + * A pointer to a hash cache stack array filled with + * subkey hashes and names for comparison. + * + * @param[in] CurrentKcb + * A pointer to the currently given KCB. + * + * @param[in] RemainingSubkeys + * The remaining subkey levels to be supplied. + * + * @param[out] ParentKcb + * A pointer to the parent KCB returned to the caller. + * This parameter points to the parent of the current + * KCB if all the subkeys match, otherwise it points + * to the actual current KCB. + * + * @return + * Returns TRUE if all the subkey levels match, otherwise + * FALSE is returned. + */ static BOOLEAN CmpCompareSubkeys( @@ -1290,6 +1340,22 @@ CmpCompareSubkeys( return TRUE; } +/** + * @brief + * Removes the subkeys on a remaining key pathname. + * + * @param[in] HashCacheStack + * A pointer to a hash cache stack array filled with + * subkey hashes and names. + * + * @param[in] RemainingSubkeys + * The remaining subkey levels to be supplied. + * + * @param[in,out] RemainingName + * A Unicode string structure consisting of the remaining + * registry key path name, where the subkeys of such path + * are to be removed. + */ static VOID CmpRemoveSubkeysInRemainingName( @@ -1326,6 +1392,69 @@ CmpRemoveSubkeysInRemainingName( } } +/** + * @brief + * Looks up in the pool cache for key pathname that matches + * with one in the said cache and returns a KCB pointing + * to that name. This function performs locking of KCBs + * during cache lookup. + * + * @param[in] HashCacheStack + * A pointer to a hash cache stack array filled with + * subkey hashes and names. + * + * @param[in] LockKcbsExclusive + * If set to TRUE, the KCBs are locked exclusively by the + * calling thread, otherwise they are locked in shared mode. + * See Remarks for further information. + * + * @param[in] TotalRemainingSubkeys + * The total remaining subkey levels to be supplied. + * + * @param[in,out] RemainingName + * A Unicode string structure consisting of the remaining + * registry key path name. The remaining name is updated + * by the function if a key pathname is found in cache. + * + * @param[in,out] OuterStackArray + * A pointer to an array that lives on the caller's stack. + * The expected size of the array is up to 32 elements, + * which is the imposed limit by CMP_HASH_STACK_LIMIT. + * This limit also corresponds to the maximum depth of + * subkey levels. + * + * @param[in,out] Kcb + * A pointer to a KCB, this KCB is changed if the key pathname + * is found in cache. + * + * @param[out] Hive + * A pointer to a hive, this hive is changed if the key pathname + * is found in cache. + * + * @param[out] Cell + * A pointer to a cell, this cell is changed if the key pathname + * is found in cache. + * + * @param[out] MatchRemainSubkeyLevel + * A pointer to match subkey levels returned by the function. + * If no match levels are found, this is 0. + * + * @return + * Returns STATUS_SUCCESS if cache lookup has completed successfully. + * STATUS_OBJECT_NAME_NOT_FOUND is returned if the current KCB of + * the key pathname has been deleted. STATUS_RETRY is returned if + * at least the current KCB or its parent have been deleted + * and a cache lookup must be retried again. STATUS_UNSUCCESSFUL is + * returned if a KCB is referenced too many times. + * + * @remarks + * The function attempts to do a cache lookup with a shared lock + * on KCBs so that other threads can simultaneously get access + * to these KCBs. When the captured KCB is being deleted on us + * we have to retry a lookup with exclusive look so that no other + * threads will mess with the KCBs and perform appropriate actions + * if a KCB is deleted. + */ static NTSTATUS CmpLookInCache( @@ -1505,6 +1634,63 @@ CmpLookInCache( return STATUS_SUCCESS; } +/** + * @brief + * Builds a hash stack cache and looks up in the + * pool cache for a matching key pathname. + * + * @param[in] ParseObject + * A pointer to a parse object, acting as a key + * body. This parameter is unused. + * + * @param[in,out] Kcb + * A pointer to a KCB. This KCB is used by the + * registry parser after hash stack and cache + * lookup are done. This KCB might change if the + * key is found to be cached in the cache pool. + * + * @param[in] Current + * The current remaining key pathname. + * + * @param[out] Hive + * A pointer to a registry hive, returned by the caller. + * + * @param[out] Cell + * A pointer to a hive cell, returned by the caller. + * + * @param[out] TotalRemainingSubkeys + * A pointer to a number of total remaining subkey levels, + * returned by the caller. This can be 0 if no subkey levels + * have been found. + * + * @param[out] MatchRemainSubkeyLevel + * A pointer to a number of remaining subkey levels that match, + * returned by the caller. This can be 0 if no matching levels + * are found. + * + * @param[out] TotalSubkeys + * A pointer to a number of total subkeys. This can be 0 if no + * subkey levels are found. By definition, both MatchRemainSubkeyLevel + * and TotalRemainingSubkeys are 0 as well. + * + * @param[in,out] OuterStackArray + * A pointer to an array that lives on the caller's stack. + * The expected size of the array is up to 32 elements, + * which is the imposed limit by CMP_HASH_STACK_LIMIT. + * This limit also corresponds to the maximum depth of + * subkey levels. + * + * @param[out] LockedKcbs + * A pointer to an array of locked KCBs, returned by the caller. + * + * @return + * Returns STATUS_SUCCESS if all the operations have succeeded without + * problems. STATUS_NAME_TOO_LONG is returned if the key pathname has + * too many subkey levels (more than 32 levels deep). A failure NTSTATUS + * code is returned otherwise. Refer to CmpLookInCache documentation + * for more information about other returned status codes. + * STATUS_UNSUCCESSFUL is returned if a KCB is referenced too many times. + */ NTSTATUS NTAPI CmpBuildHashStackAndLookupCache(