예제 #1
0
        private static LLSD DeserializeNotationInteger(StringReader reader)
        {
            int           character;
            StringBuilder s = new StringBuilder();

            if (((character = reader.Peek()) > 0) && ((char)character == '-'))
            {
                s.Append((char)character);
                reader.Read();
            }

            while ((character = reader.Peek()) > 0 &&
                   Char.IsDigit((char)character))
            {
                s.Append((char)character);
                reader.Read();
            }
            int integer;

            if (!Helpers.TryParse(s.ToString(), out integer))
            {
                throw new LLSDException("Notation LLSD parsing: Can't parse integer value." + s.ToString());
            }

            return(LLSD.FromInteger(integer));
        }
예제 #2
0
        private static LLSD ParseNotationElement(string notationData, out int endPos)
        {
            if (notationData.Length == 0)
            {
                endPos = 0;
                return(null);
            }

            // Identify what type of object this is
            switch (notationData[0])
            {
            case '!':
                endPos = 1;
                return(new LLSD());

            case '1':
                endPos = 1;
                return(LLSD.FromBoolean(true));

            case '0':
                endPos = 1;
                return(LLSD.FromBoolean(false));

            case 'i':
            {
                if (notationData.Length < 2)
                {
                    endPos = notationData.Length;
                    return(LLSD.FromInteger(0));
                }

                int value;
                endPos = FindEnd(notationData, 1);

                if (Helpers.TryParse(notationData.Substring(1, endPos - 1), out value))
                {
                    return(LLSD.FromInteger(value));
                }
                else
                {
                    return(LLSD.FromInteger(0));
                }
            }

            case 'r':
            {
                if (notationData.Length < 2)
                {
                    endPos = notationData.Length;
                    return(LLSD.FromReal(0d));
                }

                double value;
                endPos = FindEnd(notationData, 1);

                if (Helpers.TryParse(notationData.Substring(1, endPos - 1), out value))
                {
                    return(LLSD.FromReal(value));
                }
                else
                {
                    return(LLSD.FromReal(0d));
                }
            }

            case 'u':
            {
                if (notationData.Length < 17)
                {
                    endPos = notationData.Length;
                    return(LLSD.FromUUID(LLUUID.Zero));
                }

                LLUUID value;
                endPos = FindEnd(notationData, 1);

                if (Helpers.TryParse(notationData.Substring(1, endPos - 1), out value))
                {
                    return(LLSD.FromUUID(value));
                }
                else
                {
                    return(LLSD.FromUUID(LLUUID.Zero));
                }
            }

            case 'b':
                throw new NotImplementedException("Notation binary type is unimplemented");

            case 's':
            case '"':
            case '\'':
                if (notationData.Length < 2)
                {
                    endPos = notationData.Length;
                    return(LLSD.FromString(String.Empty));
                }

                endPos = FindEnd(notationData, 1);
                return(LLSD.FromString(notationData.Substring(1, endPos - 1).Trim(new char[] { '"', '\'' })));

            case 'l':
                throw new NotImplementedException("Notation URI type is unimplemented");

            case 'd':
                throw new NotImplementedException("Notation date type is unimplemented");

            case '[':
            {
                if (notationData.IndexOf(']') == -1)
                {
                    throw new LLSDException("Invalid notation array");
                }

                int       pos   = 0;
                LLSDArray array = new LLSDArray();

                while (notationData[pos] != ']')
                {
                    ++pos;

                    // Advance past comma if need be
                    if (notationData[pos] == ',')
                    {
                        ++pos;
                    }

                    // Allow a single whitespace character
                    if (pos < notationData.Length && notationData[pos] == ' ')
                    {
                        ++pos;
                    }

                    int end;
                    array.Add(ParseNotationElement(notationData.Substring(pos), out end));
                    pos += end;
                }

                endPos = pos + 1;
                return(array);
            }

            case '{':
            {
                if (notationData.IndexOf('}') == -1)
                {
                    throw new LLSDException("Invalid notation map");
                }

                int     pos       = 0;
                LLSDMap hashtable = new LLSDMap();

                while (notationData[pos] != '}')
                {
                    ++pos;

                    // Advance past comma if need be
                    if (notationData[pos] == ',')
                    {
                        ++pos;
                    }

                    // Allow a single whitespace character
                    if (pos < notationData.Length && notationData[pos] == ' ')
                    {
                        ++pos;
                    }

                    if (notationData[pos] != '\'')
                    {
                        throw new LLSDException("Expected a map key");
                    }

                    int endquote = notationData.IndexOf('\'', pos + 1);
                    if (endquote == -1 || (endquote + 1) >= notationData.Length || notationData[endquote + 1] != ':')
                    {
                        throw new LLSDException("Invalid map format");
                    }

                    string key = notationData.Substring(pos, endquote - pos);
                    key  = key.Trim(new char[] { '"', '\'' });    //key.Replace("'", String.Empty);
                    pos += (endquote - pos) + 2;

                    int end;
                    hashtable[key] = ParseNotationElement(notationData.Substring(pos), out end);
                    pos           += end;
                }

                endPos = pos + 1;
                return(hashtable);
            }

            default:
                throw new LLSDException("Unknown notation value type");
            }
        }
예제 #3
0
        private static LLSD ParseXmlElement(XmlTextReader reader)
        {
            SkipWhitespace(reader);

            if (reader.NodeType != XmlNodeType.Element)
            {
                throw new LLSDException("Expected an element");
            }

            string type = reader.LocalName;
            LLSD   ret;

            switch (type)
            {
            case "undef":
                if (reader.IsEmptyElement)
                {
                    reader.Read();
                    return(new LLSD());
                }

                reader.Read();
                SkipWhitespace(reader);
                ret = new LLSD();
                break;

            case "boolean":
                if (reader.IsEmptyElement)
                {
                    reader.Read();
                    return(LLSD.FromBoolean(false));
                }

                if (reader.Read())
                {
                    string s = reader.ReadString().Trim();

                    if (!String.IsNullOrEmpty(s) && (s == "true" || s == "1"))
                    {
                        ret = LLSD.FromBoolean(true);
                        break;
                    }
                }

                ret = LLSD.FromBoolean(false);
                break;

            case "integer":
                if (reader.IsEmptyElement)
                {
                    reader.Read();
                    return(LLSD.FromInteger(0));
                }

                if (reader.Read())
                {
                    int value = 0;
                    Helpers.TryParse(reader.ReadString().Trim(), out value);
                    ret = LLSD.FromInteger(value);
                    break;
                }

                ret = LLSD.FromInteger(0);
                break;

            case "real":
                if (reader.IsEmptyElement)
                {
                    reader.Read();
                    return(LLSD.FromReal(0d));
                }

                if (reader.Read())
                {
                    double value = 0d;
                    string str   = reader.ReadString().Trim().ToLower();

                    if (str == "nan")
                    {
                        value = Double.NaN;
                    }
                    else
                    {
                        Helpers.TryParse(str, out value);
                    }

                    ret = LLSD.FromReal(value);
                    break;
                }

                ret = LLSD.FromReal(0d);
                break;

            case "uuid":
                if (reader.IsEmptyElement)
                {
                    reader.Read();
                    return(LLSD.FromUUID(LLUUID.Zero));
                }

                if (reader.Read())
                {
                    LLUUID value = LLUUID.Zero;
                    LLUUID.TryParse(reader.ReadString().Trim(), out value);
                    ret = LLSD.FromUUID(value);
                    break;
                }

                ret = LLSD.FromUUID(LLUUID.Zero);
                break;

            case "date":
                if (reader.IsEmptyElement)
                {
                    reader.Read();
                    return(LLSD.FromDate(Helpers.Epoch));
                }

                if (reader.Read())
                {
                    DateTime value = Helpers.Epoch;
                    Helpers.TryParse(reader.ReadString().Trim(), out value);
                    ret = LLSD.FromDate(value);
                    break;
                }

                ret = LLSD.FromDate(Helpers.Epoch);
                break;

            case "string":
                if (reader.IsEmptyElement)
                {
                    reader.Read();
                    return(LLSD.FromString(String.Empty));
                }

                if (reader.Read())
                {
                    ret = LLSD.FromString(reader.ReadString());
                    break;
                }

                ret = LLSD.FromString(String.Empty);
                break;

            case "binary":
                if (reader.IsEmptyElement)
                {
                    reader.Read();
                    return(LLSD.FromBinary(new byte[0]));
                }

                if (reader.GetAttribute("encoding") != null && reader.GetAttribute("encoding") != "base64")
                {
                    throw new LLSDException("Unsupported binary encoding: " + reader.GetAttribute("encoding"));
                }

                if (reader.Read())
                {
                    try
                    {
                        ret = LLSD.FromBinary(Convert.FromBase64String(reader.ReadString().Trim()));
                        break;
                    }
                    catch (FormatException ex)
                    {
                        throw new LLSDException("Binary decoding exception: " + ex.Message);
                    }
                }

                ret = LLSD.FromBinary(new byte[0]);
                break;

            case "uri":
                if (reader.IsEmptyElement)
                {
                    reader.Read();
                    return(LLSD.FromUri(new Uri(String.Empty, UriKind.RelativeOrAbsolute)));
                }

                if (reader.Read())
                {
                    ret = LLSD.FromUri(new Uri(reader.ReadString(), UriKind.RelativeOrAbsolute));
                    break;
                }

                ret = LLSD.FromUri(new Uri(String.Empty, UriKind.RelativeOrAbsolute));
                break;

            case "map":
                return(ParseXmlMap(reader));

            case "array":
                return(ParseXmlArray(reader));

            default:
                reader.Read();
                ret = null;
                break;
            }

            if (reader.NodeType != XmlNodeType.EndElement || reader.LocalName != type)
            {
                throw new LLSDException("Expected </" + type + ">");
            }
            else
            {
                reader.Read();
                return(ret);
            }
        }
예제 #4
0
        private static LLSD ParseBinaryElement(MemoryStream stream)
        {
            SkipWhiteSpace(stream);
            LLSD llsd;

            int marker = stream.ReadByte();

            if (marker < 0)
            {
                throw new LLSDException("Binary LLSD parsing:Unexpected end of stream.");
            }

            switch ((byte)marker)
            {
            case undefBinaryValue:
                llsd = new LLSD();
                break;

            case trueBinaryValue:
                llsd = LLSD.FromBoolean(true);
                break;

            case falseBinaryValue:
                llsd = LLSD.FromBoolean(false);
                break;

            case integerBinaryMarker:
                int integer = NetworkToHostInt(ConsumeBytes(stream, int32Length));
                llsd = LLSD.FromInteger(integer);
                break;

            case realBinaryMarker:
                double dbl = NetworkToHostDouble(ConsumeBytes(stream, doubleLength));
                llsd = LLSD.FromReal(dbl);
                break;

            case uuidBinaryMarker:
                llsd = LLSD.FromUUID(new LLUUID(ConsumeBytes(stream, 16), 0));
                break;

            case binaryBinaryMarker:
                int binaryLength = NetworkToHostInt(ConsumeBytes(stream, int32Length));
                llsd = LLSD.FromBinary(ConsumeBytes(stream, binaryLength));
                break;

            case stringBinaryMarker:
                int    stringLength = NetworkToHostInt(ConsumeBytes(stream, int32Length));
                string ss           = Encoding.UTF8.GetString(ConsumeBytes(stream, stringLength));
                llsd = LLSD.FromString(ss);
                break;

            case uriBinaryMarker:
                int    uriLength = NetworkToHostInt(ConsumeBytes(stream, int32Length));
                string sUri      = Encoding.UTF8.GetString(ConsumeBytes(stream, uriLength));
                Uri    uri;
                try
                {
                    uri = new Uri(sUri, UriKind.RelativeOrAbsolute);
                }
                catch
                {
                    throw new LLSDException("Binary LLSD parsing: Invalid Uri format detected.");
                }
                llsd = LLSD.FromUri(uri);
                break;

            case dateBinaryMarker:
                double   timestamp = NetworkToHostDouble(ConsumeBytes(stream, doubleLength));
                DateTime dateTime  = DateTime.SpecifyKind(Helpers.Epoch, DateTimeKind.Utc);
                dateTime = dateTime.AddSeconds(timestamp);
                llsd     = LLSD.FromDate(dateTime.ToLocalTime());
                break;

            case arrayBeginBinaryMarker:
                llsd = ParseBinaryArray(stream);
                break;

            case mapBeginBinaryMarker:
                llsd = ParseBinaryMap(stream);
                break;

            default:
                throw new LLSDException("Binary LLSD parsing: Unknown type marker.");
            }
            return(llsd);
        }