ReactOS Fundraising Campaign 2012
 
€ 4,410 / € 30,000

Information | Donate

Home | Info | Community | Development | myReactOS | Contact Us

  1. Home
  2. Community
  3. Development
  4. myReactOS
  5. Fundraiser 2012

  1. Main Page
  2. Alphabetical List
  3. Data Structures
  4. Directories
  5. File List
  6. Data Fields
  7. Globals
  8. Related Pages

ReactOS Development > Doxygen

VALUE_SEARCH_RETURN_TYPE NTAPI CmpCompareNewValueDataAgainstKCBCache ( IN PCM_KEY_CONTROL_BLOCK  Kcb,
IN PUNICODE_STRING  ValueName,
IN ULONG  Type,
IN PVOID  Data,
IN ULONG  DataSize 
)

Definition at line 676 of file cmvalche.c.

Referenced by CmSetValueKey().

{
    VALUE_SEARCH_RETURN_TYPE SearchResult;
    PCM_KEY_NODE KeyNode;
    PCM_CACHED_VALUE *CachedValue;
    ULONG Index;
    PCM_KEY_VALUE Value;
    BOOLEAN ValueCached, BufferAllocated = FALSE;
    PVOID Buffer;
    HCELL_INDEX ValueCellToRelease = HCELL_NIL, CellToRelease = HCELL_NIL;
    BOOLEAN IsSmall;
    ULONG_PTR CompareResult;
    PAGED_CODE();

    /* Check if this is a symlink */
    if (Kcb->Flags & KEY_SYM_LINK)
    {
        /* We need the exclusive lock */
        if (!(CmpIsKcbLockedExclusive(Kcb)) &&
            !(CmpTryToConvertKcbSharedToExclusive(Kcb)))
        {
            /* We need the exclusive lock */
            return SearchNeedExclusiveLock;
        }
        
        /* Otherwise, get the key node */
        KeyNode = (PCM_KEY_NODE)HvGetCell(Kcb->KeyHive, Kcb->KeyCell);
        if (!KeyNode) return SearchFail;
        
        /* Cleanup the KCB cache */
        CmpCleanUpKcbValueCache(Kcb);
        
        /* Sanity checks */
        ASSERT(!(CMP_IS_CELL_CACHED(Kcb->ValueCache.ValueList)));
        ASSERT(!(Kcb->ExtFlags & CM_KCB_SYM_LINK_FOUND));
        
        /* Set the value cache */
        Kcb->ValueCache.Count = KeyNode->ValueList.Count;
        Kcb->ValueCache.ValueList = KeyNode->ValueList.List;
        
        /* Release the cell */
        HvReleaseCell(Kcb->KeyHive, Kcb->KeyCell);
    }
    
    /* Do the search */
    SearchResult = CmpFindValueByNameFromCache(Kcb,
                                               ValueName,
                                               &CachedValue,
                                               &Index,
                                               &Value,
                                               &ValueCached,
                                               &ValueCellToRelease);
    if (SearchResult == SearchNeedExclusiveLock)
    {
        /* We need the exclusive lock */
        ASSERT(!CmpIsKcbLockedExclusive(Kcb));
        ASSERT(ValueCellToRelease == HCELL_NIL);
        ASSERT(Value == NULL);
        goto Quickie;
    }
    else if (SearchResult == SearchSuccess)
    {
        /* Sanity check */
        ASSERT(Value);
        
        /* First of all, check if the key size and type matches */
        if ((Type == Value->Type) &&
            (DataSize == (Value->DataLength & ~CM_KEY_VALUE_SPECIAL_SIZE)))
        {
            /* Check if this is a small key */
            IsSmall = (DataSize <= CM_KEY_VALUE_SMALL) ? TRUE: FALSE;
            if (IsSmall)
            {
                /* Compare against the data directly */
                Buffer = &Value->Data;
            }
            else
            {
                /* Do a search */
                SearchResult = CmpGetValueDataFromCache(Kcb,
                                                        CachedValue,
                                                        (PCELL_DATA)Value,
                                                        ValueCached,
                                                        &Buffer,
                                                        &BufferAllocated,
                                                        &CellToRelease);
                if (SearchResult != SearchSuccess)
                {
                    /* Sanity checks */
                    ASSERT(Buffer == NULL);
                    ASSERT(BufferAllocated == FALSE);
                    goto Quickie;
                }
            }
            
            /* Now check the data size */
            if (DataSize)
            {
                /* Do the compare */
                CompareResult = RtlCompareMemory(Buffer,
                                                 Data,
                                                 DataSize &
                                                 ~CM_KEY_VALUE_SPECIAL_SIZE);
            }
            else
            {
                /* It's equal */
                CompareResult = 0;
            }
            
            /* Now check if the compare wasn't equal */
            if (CompareResult != DataSize) SearchResult = SearchFail;
        }
        else
        {
            /* The length or type isn't equal */
            SearchResult = SearchFail;
        }
    }

Quickie:
    /* Release the value cell */
    if (ValueCellToRelease) HvReleaseCell(Kcb->KeyHive, ValueCellToRelease);
    
    /* Free the buffer */
    if (BufferAllocated) CmpFree(Buffer, 0);
    
    /* Free the cell */
    if (CellToRelease) HvReleaseCell(Kcb->KeyHive, CellToRelease);

    /* Return the search result */
    return SearchResult;
}

Generated on Sat May 26 2012 06:05:49 for ReactOS by doxygen 1.7.6.1

ReactOS is a registered trademark or a trademark of ReactOS Foundation in the United States and other countries.