Пример #1
0
        private IASValue ReadArray()
        {
            int length = input.ReadInt();

            if (length < 0)
            {
                throw new AMFException(ExceptionPrefix + "Encountered negative Array length.");
            }

            // Important: Add the array to the cache before deserializing its properties!
            ASArray result = ASArray.CreateUninitializedInstance();

            AddObjectToCache(result);

            IASValue[] indexedValues;

            // Read indexed values, if any.
            if (length != 0)
            {
                indexedValues = new IASValue[length];
                for (int i = 0; i < length; i++)
                {
                    indexedValues[i] = ReadObject();
                }
            }
            else
            {
                indexedValues = EmptyArray <IASValue> .Instance;
            }

            result.SetProperties(indexedValues, EmptyDictionary <string, IASValue> .Instance);
            return(result);
        }
Пример #2
0
        public void ConstructorWithLength()
        {
            ASArray array = new ASArray(10);

            Assert.AreEqual(10, array.IndexedValues.Count);
            Assert.AreEqual(0, array.DynamicProperties.Count);
        }
Пример #3
0
        public void ReadObject_Objects_ReferenceCaching_AMF0()
        {
            // Read an array with multiple copies of each kind of object and including a self-reference
            SetStreamContents(new byte[] {
                (byte)AMF0ObjectTypeCode.MixedArray, 0x00, 0x00, 0x00, 0x04,
                0x00, 0x01, 0x61, (byte)AMF0ObjectTypeCode.Reference, 0x00, 0x01,                                    // mixed array by reference
                0x00, 0x01, 0x30, (byte)AMF0ObjectTypeCode.Object, 0x00, 0x00, (byte)AMF0ObjectTypeCode.EndOfObject, // obj
                0x00, 0x01, 0x31, (byte)AMF0ObjectTypeCode.Array, 0x00, 0x00, 0x00, 0x00,                            // regular array
                0x00, 0x01, 0x32, (byte)AMF0ObjectTypeCode.Reference, 0x00, 0x02,                                    // obj by reference
                0x00, 0x01, 0x33, (byte)AMF0ObjectTypeCode.Reference, 0x00, 0x03,                                    // regular array by reference
                0x00, 0x00, (byte)AMF0ObjectTypeCode.EndOfObject
            });

            input.BeginObjectStream();
            ASArray mixedArray = (ASArray)input.ReadObject();

            Assert.AreEqual(AMFObjectEncoding.AMF0, input.ObjectEncoding);
            input.EndObjectStream();

            Assert.AreEqual(4, mixedArray.IndexedValues.Count);
            Assert.AreEqual(1, mixedArray.DynamicProperties.Count);

            ASObject obj          = (ASObject)mixedArray.IndexedValues[0];
            ASArray  regularArray = (ASArray)mixedArray.IndexedValues[1];

            Assert.AreSame(obj, mixedArray.IndexedValues[2]);
            Assert.AreSame(regularArray, mixedArray.IndexedValues[3]);
            Assert.AreSame(mixedArray, mixedArray.DynamicProperties["a"]);
        }
Пример #4
0
        public void ReadObject_Objects_ReferenceCaching_AMF3()
        {
            // Read an array with multiple copies of each kind of object and including a self-reference
            SetStreamContents(new byte[] {
                (byte)AMF0ObjectTypeCode.AMF3Data, (byte)AMF3ObjectTypeCode.Array, 0x0d,
                0x03, 0x61, (byte)AMF3ObjectTypeCode.Array, 0x00,                  // array by reference
                0x01,                                                              // end of mixed values
                (byte)AMF3ObjectTypeCode.Object, 0x0b, 0x01, 0x01,                 // obj
                (byte)AMF3ObjectTypeCode.ByteArray, 0x01,                          // byte array
                (byte)AMF3ObjectTypeCode.Date, 0x01, 0x3f, 0xf0, 0, 0, 0, 0, 0, 0, // date
                (byte)AMF3ObjectTypeCode.Object, 0x02,                             // obj by reference
                (byte)AMF3ObjectTypeCode.ByteArray, 0x04,                          // byte array by reference
                (byte)AMF3ObjectTypeCode.Date, 0x06,                               // date by reference
            });

            input.BeginObjectStream();
            ASArray array = (ASArray)input.ReadObject();

            Assert.AreEqual(AMFObjectEncoding.AMF3, input.ObjectEncoding);
            input.EndObjectStream();

            Assert.AreEqual(6, array.IndexedValues.Count);
            Assert.AreEqual(1, array.DynamicProperties.Count);

            ASObject    obj       = (ASObject)array.IndexedValues[0];
            ASByteArray byteArray = (ASByteArray)array.IndexedValues[1];
            ASDate      date      = (ASDate)array.IndexedValues[2];

            Assert.AreSame(obj, array.IndexedValues[3]);
            Assert.AreSame(byteArray, array.IndexedValues[4]);
            Assert.AreSame(date, array.IndexedValues[5]);
            Assert.AreSame(array, array.DynamicProperties["a"]);
        }
Пример #5
0
        public void ConstructorWithLength()
        {
            ASArray array = new ASArray(10);

            Assert.AreEqual(10, array.IndexedValues.Count);
            Assert.AreEqual(0, array.DynamicProperties.Count);
        }
Пример #6
0
        public void ConstructorWithIndexedValues()
        {
            IASValue[] indexedValues = new IASValue[] { null, null, null };
            ASArray    array         = new ASArray(indexedValues);

            Assert.AreSame(indexedValues, array.IndexedValues);
            Assert.AreEqual(0, array.DynamicProperties.Count);
        }
Пример #7
0
        public void ConstructorWithIndexedValues()
        {
            IASValue[] indexedValues = new IASValue[] { null, null, null };
            ASArray array = new ASArray(indexedValues);

            Assert.AreSame(indexedValues, array.IndexedValues);
            Assert.AreEqual(0, array.DynamicProperties.Count);
        }
Пример #8
0
        public void IndexedValueIndexer()
        {
            ASArray array = new ASArray(new IASValue[] { null, new ASString("abc"), null });

            Assert.AreEqual(new ASString("abc"), array[1]);
            array[1] = new ASString("def");
            Assert.AreEqual(new ASString("def"), array[1]);
        }
Пример #9
0
        public void CreateUninitializedInstanceAndSetProperties()
        {
            ASArray array = ASArray.CreateUninitializedInstance();

            array.SetProperties(EmptyArray <IASValue> .Instance, EmptyDictionary <string, IASValue> .Instance);

            Assert.AreSame(EmptyArray <IASValue> .Instance, array.IndexedValues);
            Assert.AreSame(EmptyDictionary <string, IASValue> .Instance, array.DynamicProperties);
        }
Пример #10
0
        public void ConstructorWithIndexedAndMixedValues()
        {
            IASValue[] indexedValues = new IASValue[] { null, null, null };
            IDictionary<string, IASValue> mixedValues = new Dictionary<string, IASValue>();

            ASArray array = new ASArray(indexedValues, mixedValues);

            Assert.AreSame(indexedValues, array.IndexedValues);
            Assert.AreSame(mixedValues, array.DynamicProperties);
        }
Пример #11
0
        public void ConstructorWithIndexedAndMixedValues()
        {
            IASValue[] indexedValues = new IASValue[] { null, null, null };
            IDictionary <string, IASValue> mixedValues = new Dictionary <string, IASValue>();

            ASArray array = new ASArray(indexedValues, mixedValues);

            Assert.AreSame(indexedValues, array.IndexedValues);
            Assert.AreSame(mixedValues, array.DynamicProperties);
        }
Пример #12
0
        private IASValue ReadMixedArray()
        {
            int length = input.ReadInt();

            if (length < 0)
            {
                throw new AMFException(ExceptionPrefix + "Encountered negative MixedArray length.");
            }

            // Important: Add the array to the cache before deserializing its properties!
            ASArray result = ASArray.CreateUninitializedInstance();

            AddObjectToCache(result);

            IASValue[] indexedValues = length == 0 ? EmptyArray <IASValue> .Instance : new IASValue[length];
            IDictionary <string, IASValue> mixedValues = null;

            for (;;)
            {
                string key = input.ReadShortString();
                if (key.Length == 0)
                {
                    break;
                }

                IASValue value = input.ReadObject();

                // If the string looks like a valid index, then stuff it into the array.
                int index;
                if (int.TryParse(key, NumberStyles.None, CultureInfo.InvariantCulture, out index) && index >= 0 && index < length)
                {
                    indexedValues[index] = value;
                }
                else
                {
                    // Otherwise add it as a mixed value.
                    if (mixedValues == null)
                    {
                        mixedValues = new Dictionary <string, IASValue>();
                    }

                    mixedValues.Add(key, value);
                }
            }

            if (mixedValues == null)
            {
                mixedValues = EmptyDictionary <string, IASValue> .Instance;
            }

            ConsumeEndOfObject();

            result.SetProperties(indexedValues, mixedValues);
            return(result);
        }
Пример #13
0
        public void MixedValueIndexer()
        {
            ASArray array = new ASArray(0);

            array["abc"] = new ASInt29(1);
            Assert.AreEqual(new ASInt29(1), array["abc"]);

            // do it twice to be sure
            array["abc"] = new ASInt29(2);
            Assert.AreEqual(new ASInt29(2), array["abc"]);
        }
Пример #14
0
        public void WriteObject_Arrays(AMFObjectEncoding objectEncoding, byte[] expected, string[] values, string[] mixedKeysAndValues)
        {
            ASArray array = new ASArray(WrapStrings(values));

            for (int i = 0; i < mixedKeysAndValues.Length; i += 2)
            {
                array.DynamicProperties[mixedKeysAndValues[i]] = new ASString(mixedKeysAndValues[i + 1]);
            }

            output.ObjectEncoding = objectEncoding;
            output.BeginObjectStream();
            output.WriteObject(array);
            output.EndObjectStream();

            CollectionAssert.AreElementsEqual(expected, stream.ToArray());
        }
Пример #15
0
        public void ReadObject_Arrays(AMFObjectEncoding objectEncoding, byte[] bytes, string[] indexedValues, string[] mixedKeysAndValues)
        {
            SetStreamContents(bytes);

            input.BeginObjectStream();
            ASArray result = (ASArray)input.ReadObject();

            Assert.AreEqual(objectEncoding, input.ObjectEncoding);
            input.EndObjectStream();

            CollectionAssert.AreElementsEqual(WrapStrings(indexedValues), result.IndexedValues);

            Assert.AreEqual(mixedKeysAndValues.Length / 2, result.DynamicProperties.Count);
            for (int i = 0; i < mixedKeysAndValues.Length; i += 2)
            {
                Assert.AreEqual(new ASString(mixedKeysAndValues[i + 1]), result.DynamicProperties[mixedKeysAndValues[i]]);
            }
        }
Пример #16
0
        public void ReadObject_Strings_Caching_AMF3()
        {
            ASString empty  = new ASString("");
            ASString valueA = new ASString("a");
            ASString valueB = new ASString("b");
            ASString valueC = new ASString("c");

            byte[] bytes = new byte[] { (byte)AMF0ObjectTypeCode.AMF3Data,
                                        (byte)AMF3ObjectTypeCode.String, 0x01,                                                                                                                                 // ""
                                        (byte)AMF3ObjectTypeCode.String, 0x03, 0x61,                                                                                                                           // valueA
                                        (byte)AMF3ObjectTypeCode.String, 0x01,                                                                                                                                 // ""
                                        (byte)AMF3ObjectTypeCode.String, 0x03, 0x62,                                                                                                                           // valueB
                                        (byte)AMF3ObjectTypeCode.String, 0x00,                                                                                                                                 // valueA (by ref)
                                        (byte)AMF3ObjectTypeCode.Xml, 0x02,                                                                                                                                    // valueB (by ref)
                                        (byte)AMF3ObjectTypeCode.Array, 0x05, 0x02, (byte)AMF3ObjectTypeCode.String, 0x00, 0x01, (byte)AMF3ObjectTypeCode.String, 0x00, (byte)AMF3ObjectTypeCode.String, 0x02, // array
                                        (byte)AMF3ObjectTypeCode.Object, 0x1b, 0x02, 0x03, 0x63, (byte)AMF3ObjectTypeCode.String, 0x04, 0x00, (byte)AMF3ObjectTypeCode.String, 0x02, 0x01                      // object
            };
            SetStreamContents(bytes);

            input.BeginObjectStream();
            Assert.AreEqual(empty, input.ReadObject());  // empty strings are not cached
            Assert.AreEqual(valueA, input.ReadObject()); // will get string ref #0
            Assert.AreEqual(empty, input.ReadObject());  // empty strings are not cached
            Assert.AreEqual(valueB, input.ReadObject()); // will get string ref #1
            Assert.AreEqual(valueA, input.ReadObject()); // will use string ref #0
            ASXmlDocument xml = (ASXmlDocument)input.ReadObject();

            Assert.AreEqual(valueB.Value, xml.XmlString); // XML contents are same as valueB, will use ref #1
            ASArray array = (ASArray)input.ReadObject();  // Array contains valueA and valueB and mixed values with key valueB and value valueA

            CollectionAssert.AreElementsEqual(new object[] { valueA, valueB }, array.IndexedValues);
            Assert.AreEqual(valueA, array.DynamicProperties[valueB.Value]);
            ASObject obj = (ASObject)input.ReadObject();  // Object has class name valueB contains member with key valueC and value valueA dynamic property with key valueA and value valueB

            CollectionAssert.AreElementsEqual(new object[] { valueC }, obj.MemberValues);
            Assert.AreEqual(valueB, obj.DynamicProperties[valueA.Value]);
            Assert.AreEqual(valueB.Value, obj.Class.ClassAlias);
            Assert.AreEqual(ASClassLayout.Dynamic, obj.Class.Layout);
            CollectionAssert.AreElementsEqual(new string[] { valueC.Value }, obj.Class.MemberNames);

            Assert.AreEqual(AMFObjectEncoding.AMF3, input.ObjectEncoding);
            input.EndObjectStream();
        }
Пример #17
0
        public void WriteObject_Strings_Caching_AMF3()
        {
            ASString      empty  = new ASString("");
            ASString      valueA = new ASString("a");
            ASString      valueB = new ASString("b");
            ASString      valueC = new ASString("c");
            ASXmlDocument xml    = new ASXmlDocument(valueB.Value);
            ASArray       array  = new ASArray(new IASValue[] { valueA, valueB });

            array.DynamicProperties[valueB.Value] = valueA;
            ASClass  clazz = new ASClass(valueB.Value, ASClassLayout.Dynamic, new string[] { valueC.Value });
            ASObject obj   = new ASObject(clazz);

            obj.MemberValues[0] = valueC;
            obj.DynamicProperties[valueA.Value] = valueB;

            output.ObjectEncoding = AMFObjectEncoding.AMF3;
            output.BeginObjectStream();
            output.WriteObject(empty);  // empty strings are not cached
            output.WriteObject(valueA); // will get string ref #0
            output.WriteObject(empty);  // empty strings are not cached
            output.WriteObject(valueB); // will get string ref #1
            output.WriteObject(valueA); // will use string ref #0
            output.WriteObject(xml);    // XML contents are same as valueB, will use ref #1
            output.WriteObject(array);  // Array contains valueA and valueB and mixed values with key valueB and value valueA
            output.WriteObject(obj);    // Object has class name valueB contains member with key valueC and value valueA dynamic property with key valueA and value valueB
            output.EndObjectStream();

            CollectionAssert.AreElementsEqual(
                new byte[] { (byte)AMF0ObjectTypeCode.AMF3Data,
                             (byte)AMF3ObjectTypeCode.String, 0x01,                                                                                                                                 // ""
                             (byte)AMF3ObjectTypeCode.String, 0x03, 0x61,                                                                                                                           // valueA
                             (byte)AMF3ObjectTypeCode.String, 0x01,                                                                                                                                 // ""
                             (byte)AMF3ObjectTypeCode.String, 0x03, 0x62,                                                                                                                           // valueB
                             (byte)AMF3ObjectTypeCode.String, 0x00,                                                                                                                                 // valueA (by ref)
                             (byte)AMF3ObjectTypeCode.Xml, 0x02,                                                                                                                                    // valueB (by ref)
                             (byte)AMF3ObjectTypeCode.Array, 0x05, 0x02, (byte)AMF3ObjectTypeCode.String, 0x00, 0x01, (byte)AMF3ObjectTypeCode.String, 0x00, (byte)AMF3ObjectTypeCode.String, 0x02, // array
                             (byte)AMF3ObjectTypeCode.Object, 0x1b, 0x02, 0x03, 0x63, (byte)AMF3ObjectTypeCode.String, 0x04, 0x00, (byte)AMF3ObjectTypeCode.String, 0x02, 0x01                      // object
                }, stream.ToArray());
        }
Пример #18
0
        public void WriteObject_Objects_ReferenceCaching(AMFObjectEncoding objectEncoding, byte[] expected)
        {
            // Create an array with multiple copies of each kind of object and including a self-reference
            ASObject    obj       = new ASObject();
            ASByteArray byteArray = new ASByteArray(new byte[0]);
            ASDate      date      = new ASDate(1, 0);
            ASArray     array     = new ASArray(6);

            array.IndexedValues[0]       = obj;
            array.IndexedValues[1]       = byteArray;
            array.IndexedValues[2]       = date;
            array.IndexedValues[3]       = obj;
            array.IndexedValues[4]       = byteArray;
            array.IndexedValues[5]       = date;
            array.DynamicProperties["a"] = array;

            output.ObjectEncoding = objectEncoding;
            output.BeginObjectStream();
            output.WriteObject(array);
            output.EndObjectStream();

            CollectionAssert.AreElementsEqual(expected, stream.ToArray());
        }
Пример #19
0
        public void MixedValueIndexer()
        {
            ASArray array = new ASArray(0);

            array["abc"] = new ASInt29(1);
            Assert.AreEqual(new ASInt29(1), array["abc"]);

            // do it twice to be sure
            array["abc"] = new ASInt29(2);
            Assert.AreEqual(new ASInt29(2), array["abc"]);
        }
Пример #20
0
 public void SetPropertiesWithInitializedInstanceThrows()
 {
     ASArray array = new ASArray(1);
     array.SetProperties(EmptyArray<IASValue>.Instance, EmptyDictionary<string, IASValue>.Instance);
 }
Пример #21
0
 public void IndexedValueGetIndexerThrowsIfOutOfRange(int index)
 {
     ASArray array = new ASArray(new IASValue[] { null, null, null });
     GC.KeepAlive(array[index]);
 }
Пример #22
0
 public void IndexedValueSetIndexerThrowsIfOutOfRange(int index)
 {
     ASArray array = new ASArray(new IASValue[] { null, null, null });
     array[index] = new ASString("abc");
 }
Пример #23
0
        public void IndexedValueGetIndexerThrowsIfOutOfRange(int index)
        {
            ASArray array = new ASArray(new IASValue[] { null, null, null });

            GC.KeepAlive(array[index]);
        }
Пример #24
0
        public void IndexedValueSetIndexerThrowsIfOutOfRange(int index)
        {
            ASArray array = new ASArray(new IASValue[] { null, null, null });

            array[index] = new ASString("abc");
        }
Пример #25
0
        public void SetPropertiesWithInitializedInstanceThrows()
        {
            ASArray array = new ASArray(1);

            array.SetProperties(EmptyArray <IASValue> .Instance, EmptyDictionary <string, IASValue> .Instance);
        }
Пример #26
0
 internal ArrayWrapper(ASArray instance) => this.instance = instance;
Пример #27
0
        public void WriteObject_Objects_ReferenceCaching(AMFObjectEncoding objectEncoding, byte[] expected)
        {
            // Create an array with multiple copies of each kind of object and including a self-reference
            ASObject obj = new ASObject();
            ASByteArray byteArray = new ASByteArray(new byte[0]);
            ASDate date = new ASDate(1, 0);
            ASArray array = new ASArray(6);

            array.IndexedValues[0] = obj;
            array.IndexedValues[1] = byteArray;
            array.IndexedValues[2] = date;
            array.IndexedValues[3] = obj;
            array.IndexedValues[4] = byteArray;
            array.IndexedValues[5] = date;
            array.DynamicProperties["a"] = array;

            output.ObjectEncoding = objectEncoding;
            output.BeginObjectStream();
            output.WriteObject(array);
            output.EndObjectStream();

            CollectionAssert.AreElementsEqual(expected, stream.ToArray());
        }
Пример #28
0
        public void WriteObject_Strings_Caching_AMF3()
        {
            ASString empty = new ASString("");
            ASString valueA = new ASString("a");
            ASString valueB = new ASString("b");
            ASString valueC = new ASString("c");
            ASXmlDocument xml = new ASXmlDocument(valueB.Value);
            ASArray array = new ASArray(new IASValue[] { valueA, valueB });
            array.DynamicProperties[valueB.Value] = valueA;
            ASClass clazz = new ASClass(valueB.Value, ASClassLayout.Dynamic, new string[] { valueC.Value });
            ASObject obj = new ASObject(clazz);
            obj.MemberValues[0] = valueC;
            obj.DynamicProperties[valueA.Value] = valueB;

            output.ObjectEncoding = AMFObjectEncoding.AMF3;
            output.BeginObjectStream();
            output.WriteObject(empty); // empty strings are not cached
            output.WriteObject(valueA); // will get string ref #0
            output.WriteObject(empty); // empty strings are not cached
            output.WriteObject(valueB); // will get string ref #1
            output.WriteObject(valueA); // will use string ref #0
            output.WriteObject(xml); // XML contents are same as valueB, will use ref #1
            output.WriteObject(array); // Array contains valueA and valueB and mixed values with key valueB and value valueA
            output.WriteObject(obj); // Object has class name valueB contains member with key valueC and value valueA dynamic property with key valueA and value valueB
            output.EndObjectStream();

            CollectionAssert.AreElementsEqual(
                new byte[] { (byte)AMF0ObjectTypeCode.AMF3Data,
                    (byte)AMF3ObjectTypeCode.String, 0x01, // ""
                    (byte)AMF3ObjectTypeCode.String, 0x03, 0x61, // valueA
                    (byte)AMF3ObjectTypeCode.String, 0x01, // ""
                    (byte)AMF3ObjectTypeCode.String, 0x03, 0x62, // valueB
                    (byte)AMF3ObjectTypeCode.String, 0x00, // valueA (by ref)
                    (byte)AMF3ObjectTypeCode.Xml, 0x02, // valueB (by ref)
                    (byte)AMF3ObjectTypeCode.Array, 0x05, 0x02, (byte)AMF3ObjectTypeCode.String, 0x00, 0x01, (byte)AMF3ObjectTypeCode.String, 0x00, (byte)AMF3ObjectTypeCode.String, 0x02, // array
                    (byte)AMF3ObjectTypeCode.Object, 0x1b, 0x02, 0x03, 0x63, (byte)AMF3ObjectTypeCode.String, 0x04, 0x00, (byte)AMF3ObjectTypeCode.String, 0x02, 0x01 // object
                }, stream.ToArray());
        }
Пример #29
0
        public void WriteObject_Arrays(AMFObjectEncoding objectEncoding, byte[] expected, string[] values, string[] mixedKeysAndValues)
        {
            ASArray array = new ASArray(WrapStrings(values));
            for (int i = 0; i < mixedKeysAndValues.Length; i += 2)
                array.DynamicProperties[mixedKeysAndValues[i]] = new ASString(mixedKeysAndValues[i + 1]);

            output.ObjectEncoding = objectEncoding;
            output.BeginObjectStream();
            output.WriteObject(array);
            output.EndObjectStream();

            CollectionAssert.AreElementsEqual(expected, stream.ToArray());
        }
Пример #30
0
        public void IndexedValueIndexer()
        {
            ASArray array = new ASArray(new IASValue[] { null, new ASString("abc"), null });

            Assert.AreEqual(new ASString("abc"), array[1]);
            array[1] = new ASString("def");
            Assert.AreEqual(new ASString("def"), array[1]);
        }
Пример #31
0
        private IASValue ReadArray()
        {
            int bits = input.ReadVWInt29();
            int lengthOrReferenceId = bits >> 1;

            // Handle cached objects.
            if ((bits & 1) == 0)
            {
                return(GetObjectFromCache(AMF3ObjectTypeCode.Array, lengthOrReferenceId));
            }

            // Read out the whole array.
            if (lengthOrReferenceId < 0)
            {
                throw new AMFException(String.Format(CultureInfo.CurrentCulture,
                                                     ExceptionPrefix + "Encountered Array token with invalid length '{0}'.", lengthOrReferenceId));
            }

            // Important: Add the array to the cache before deserializing its properties!
            ASArray result = ASArray.CreateUninitializedInstance();

            AddObjectToCache(AMF3ObjectTypeCode.Array, result);

            // Read mixed values if any.
            IDictionary <string, IASValue> mixedValues;

            string key = ReadStringData();

            if (key.Length != 0)
            {
                mixedValues = new Dictionary <string, IASValue>();

                for (; ;)
                {
                    IASValue value = ReadObject();
                    mixedValues.Add(key, value);

                    key = ReadStringData();
                    if (key.Length == 0)
                    {
                        break;
                    }
                }
            }
            else
            {
                mixedValues = EmptyDictionary <string, IASValue> .Instance;
            }

            // Read indexed values if any.
            IASValue[] indexedValues;

            if (lengthOrReferenceId != 0)
            {
                indexedValues = new IASValue[lengthOrReferenceId];

                for (int i = 0; i < lengthOrReferenceId; i++)
                {
                    indexedValues[i] = ReadObject();
                }
            }
            else
            {
                indexedValues = EmptyArray <IASValue> .Instance;
            }

            result.SetProperties(indexedValues, mixedValues);
            return(result);
        }