Ejemplo n.º 1
0
        private CtfPropertyBag GetPropertyBag(string str, int start, int stop)
        {
            Debug.Assert(str[start] == '{');
            CtfPropertyBag result = new CtfPropertyBag();

            foreach (string rawStatement in EnumerateStatements(str, start + 1, stop))
            {
                string statement = StripComments(rawStatement);

                int i = statement.IndexOf('=');
                if (i <= 0)
                {
                    continue;
                }

                if (statement[i - 1] == ':')
                {
                    string name = statement.Substring(0, i - 1).Trim();

                    int open  = statement.IndexOf('{', i + 1);
                    int close = FindCloseBrace(statement, open);

                    if (close > stop || close == -1)
                    {
                        string[] structNameParts = statement.Substring(i + 1).Trim().Split(' ');

                        if (structNameParts.Length != 2 || structNameParts[0] != "struct")
                        {
                            throw new InvalidOperationException();
                        }

                        CtfUnresolvedType unresolved = new CtfUnresolvedType(structNameParts[1]);
                        result.AddValue(name, unresolved);
                    }
                    else
                    {
                        CtfField[] fields = ParseStructFields(statement, open, close).ToArray();
                        result.AddValue(name, new CtfStruct(null, fields));
                    }
                }
                else
                {
                    string name  = statement.Substring(0, i).Trim();
                    string value = statement.Substring(i + 1).Trim();

                    if (value.Length > 2 && value[0] == '\"' && value[value.Length - 1] == '\"')
                    {
                        value = value.Substring(1, value.Length - 2);
                    }

                    result.AddValue(name, value);
                }
            }

            return(result);
        }
Ejemplo n.º 2
0
        private CtfMetadataType ParseOneType(string statement, out int index)
        {
            CtfMetadataType type = null;
            Match           match;

            if ((match = s_integer.Match(statement)).Success)
            {
                Group          group = match.Groups[1];
                CtfPropertyBag bag   = GetPropertyBag(group.ToString());

                type  = new CtfInteger(bag);
                index = group.Index + group.Length;
            }
            else if ((match = s_struct.Match(statement)).Success)
            {
                var group = match.Groups[1];

                if (group.ToString() != "{")
                {
                    throw new InvalidOperationException();
                }

                int open  = group.Index;
                int close = FindCloseBrace(statement, open);

                CtfField[] fields = ParseStructFields(statement, open, close).ToArray();

                type  = new CtfStruct(null, fields);
                index = close + 1;
            }
            else if ((match = s_float.Match(statement)).Success)
            {
                int open  = match.Index + match.Length - 1;
                int close = FindCloseBrace(statement, open);

                CtfPropertyBag bag = GetPropertyBag(statement, open, close);
                type  = new CtfFloat(bag);
                index = close + 1;
            }
            else if ((match = s_variant.Match(statement)).Success)
            {
                string switchVariable = match.Groups[1].ToString();

                int open  = statement.IndexOf('{');
                int close = FindCloseBrace(statement, open);

                if (close == -1)
                {
                    throw new InvalidOperationException();
                }


                CtfField[] fields = ParseStructFields(statement, open, close).ToArray();

                type  = new CtfVariant(switchVariable, fields);
                index = close + 1;
            }
            else if ((match = s_variable.Match(statement)).Success)
            {
                var typeGroup = match.Groups[1];

                string typeName = typeGroup.ToString().Trim();
                if (typeName == "string")
                {
                    type = new CtfString();
                }
                else
                {
                    type = new CtfUnresolvedType(typeName);
                }

                index = typeGroup.Index + typeGroup.Length;
            }
            else if ((match = s_enum.Match(statement)).Success)
            {
                var    groups   = match.Groups;
                string typeName = groups[1].ToString().Trim();

                int open  = statement.IndexOf('{');
                int close = FindCloseBrace(statement, open);
                if (close == -1)
                {
                    throw new InvalidOperationException();
                }

                CtfNamedRange[] ranges = ParseNamedRanges(statement, open + 1, close).ToArray();

                // TODO: Can enums just be an inline defined integer?
                type  = new CtfEnum(new CtfUnresolvedType(typeName), ranges);
                index = close + 1;
            }
            else
            {
                // TODO:  Floating point

                index = 0;
                return(null);
            }

            return(type);
        }