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

Definition at line 21 of file name.c.

Referenced by FsRtlIsNameInExpression().

{
    SHORT StarFound = -1;
    PUSHORT BackTracking = NULL;
    UNICODE_STRING IntExpression;
    USHORT ExpressionPosition = 0, NamePosition = 0, MatchingChars;
    PAGED_CODE();

    /* Check if we were given strings at all */
    if (!Name->Length || !Expression->Length)
    {
        /* Return TRUE if both strings are empty, otherwise FALSE */
        if (Name->Length == 0 && Expression->Length == 0)
            return TRUE;
        else
            return FALSE;
    }

    /* Check for a shortcut: just one wildcard */
    if (Expression->Length == sizeof(WCHAR))
    {
        if (Expression->Buffer[0] == L'*')
            return TRUE;
    }

    ASSERT(!IgnoreCase || UpcaseTable);

    /* Another shortcut, wildcard followed by some string */
    if (Expression->Buffer[0] == L'*')
    {
        /* Copy Expression to our local variable */
        IntExpression = *Expression;

        /* Skip the first char */
        IntExpression.Buffer++;
        IntExpression.Length -= sizeof(WCHAR);

        /* Continue only if the rest of the expression does NOT contain
           any more wildcards */
        if (!FsRtlDoesNameContainWildCards(&IntExpression))
        {
            /* Check for a degenerate case */
            if (Name->Length < (Expression->Length - sizeof(WCHAR)))
                return FALSE;

            /* Calculate position */
            NamePosition = (Name->Length - IntExpression.Length) / sizeof(WCHAR);

            /* Compare */
            if (!IgnoreCase)
            {
                /* We can just do a byte compare */
                return RtlEqualMemory(IntExpression.Buffer,
                                      Name->Buffer + NamePosition,
                                      IntExpression.Length);
            }
            else
            {
                /* Not so easy, need to upcase and check char by char */
                for (ExpressionPosition = 0; ExpressionPosition < (IntExpression.Length / sizeof(WCHAR)); ExpressionPosition++)
                {
                    /* Assert that expression is already upcased! */
                    ASSERT(IntExpression.Buffer[ExpressionPosition] == UpcaseTable[IntExpression.Buffer[ExpressionPosition]]);

                    /* Now compare upcased name char with expression */
                    if (UpcaseTable[Name->Buffer[NamePosition + ExpressionPosition]] !=
                        IntExpression.Buffer[ExpressionPosition])
                    {
                        return FALSE;
                    }
                }

                /* It matches */
                return TRUE;
            }
        }
    }

    while (NamePosition < Name->Length / sizeof(WCHAR) && ExpressionPosition < Expression->Length / sizeof(WCHAR))
    {
        /* Basic check to test if chars are equal */
        if ((Expression->Buffer[ExpressionPosition] == (IgnoreCase ? UpcaseTable[Name->Buffer[NamePosition]] : Name->Buffer[NamePosition])))
        {
            NamePosition++;
            ExpressionPosition++;
        }
        /* Check cases that eat one char */
        else if (Expression->Buffer[ExpressionPosition] == L'?' || (Expression->Buffer[ExpressionPosition] == DOS_QM) ||
                 (Expression->Buffer[ExpressionPosition] == DOS_DOT && Name->Buffer[NamePosition] == L'.'))
        {
            NamePosition++;
            ExpressionPosition++;
        }
        /* Test star */
        else if (Expression->Buffer[ExpressionPosition] == L'*')
        {
            /* Skip contigous stars */
            while (ExpressionPosition + 1 < Expression->Length / sizeof(WCHAR) && Expression->Buffer[ExpressionPosition + 1] == L'*')
            {
                ExpressionPosition++;
            }

            /* Save star position */
            if (!BackTracking)
            {
                BackTracking = ExAllocatePoolWithTag(PagedPool | POOL_RAISE_IF_ALLOCATION_FAILURE,
                                                     (Expression->Length / sizeof(WCHAR)) * sizeof(USHORT),
                                                     'nrSF');
            }
            BackTracking[++StarFound] = ExpressionPosition++;

            /* If star is at the end, then eat all rest and leave */
            if (ExpressionPosition == Expression->Length / sizeof(WCHAR))
            {
                NamePosition = Name->Length / sizeof(WCHAR);
                break;
            }
            else if (Expression->Buffer[ExpressionPosition] != L'?')
            {
                NamePosition++;
            }
        }
        /* Check DOS_STAR */
        else if (Expression->Buffer[ExpressionPosition] == DOS_STAR)
        {
            MatchingChars = NamePosition;
            while (MatchingChars < Name->Length / sizeof(WCHAR))
            {
                if (Name->Buffer[MatchingChars] == L'.')
                {
                    NamePosition = MatchingChars;
                }
                MatchingChars++;
            }
            ExpressionPosition++;
        }
        /* If nothing match, try to backtrack */
        else if (StarFound >= 0)
        {
            ExpressionPosition = BackTracking[StarFound--];
        }
        /* Otherwise, fail */
        else
        {
            break;
        }

        /* Under certain circumstances, expression is over, but name isn't
         * and we can backtrack, then, backtrack */
        if (ExpressionPosition == Expression->Length / sizeof(WCHAR) &&
            NamePosition != Name->Length / sizeof(WCHAR) &&
            StarFound >= 0)
        {
            ExpressionPosition = BackTracking[StarFound--];
        }
    }
    if (ExpressionPosition + 1 == Expression->Length / sizeof(WCHAR) && NamePosition == Name->Length / sizeof(WCHAR) &&
        Expression->Buffer[ExpressionPosition] == DOS_DOT)
    {
        ExpressionPosition++;
    }

    if (BackTracking)
    {
        ExFreePoolWithTag(BackTracking, 'nrSF');
    }

    return (ExpressionPosition == Expression->Length / sizeof(WCHAR) && NamePosition == Name->Length / sizeof(WCHAR));
}

Generated on Sun May 27 2012 05:19:00 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.