Exemple #1
0
        object PopulateList(
            IList list,
            BitStreamReader reader,
            ArrayContract contract,
            DsdlProperty containerProperty,
            ArrayDsdlType scheme,
            bool tailArrayOptimization)
        {
            object underlyingList = list is IWrappedCollection wrappedCollection ? wrappedCollection.UnderlyingCollection : list;

            if (contract.ItemContract == null)
            {
                contract.ItemContract = GetContractSafe(contract.CollectionItemType);
            }

            object ReadArrayItem(bool tao = false)
            {
                return(CreateValueInternal(reader, contract.ItemContract, null, contract, containerProperty, null, scheme.ElementType, contract.CollectionItemType, tao));
            }

            switch (scheme.Mode)
            {
            case ArrayDsdlTypeMode.Static:
            {
                for (int i = 0; i < scheme.MaxSize; i++)
                {
                    list.Add(ReadArrayItem());
                }
                break;
            }

            case ArrayDsdlTypeMode.Dynamic:
            {
                if (tailArrayOptimization && scheme.ElementType.MinBitlen >= 8)
                {
                    while (reader.LengthInBytes - reader.CurrentIndex > 1)
                    {
                        list.Add(ReadArrayItem());
                    }
                }
                else
                {
                    var arraySize = ReadDynamicArraySize(reader, scheme);
                    for (int i = 0; i < arraySize; i++)
                    {
                        var tao = i == arraySize - 1 ? tailArrayOptimization : false;
                        list.Add(ReadArrayItem(tao));
                    }
                }
                break;
            }

            default:
                throw new ArgumentOutOfRangeException(nameof(ArrayDsdlTypeMode));
            }

            return(underlyingList);
        }
Exemple #2
0
        IList CreateNewList(BitStreamReader reader, ArrayContract contract, out bool createdFromNonDefaultCreator)
        {
            // some types like non-generic IEnumerable can be serialized but not deserialized
            if (!contract.CanDeserialize)
            {
                throw new SerializationException("Cannot create and populate list type {0}.".FormatWith(CultureInfo.InvariantCulture, contract.CreatedType));
            }

            if (contract.OverrideCreator != null)
            {
                if (contract.HasParameterizedCreator)
                {
                    createdFromNonDefaultCreator = true;
                    return(contract.CreateTemporaryCollection());
                }
                else
                {
                    object list = contract.OverrideCreator();

                    if (contract.ShouldCreateWrapper)
                    {
                        list = contract.CreateWrapper(list);
                    }

                    createdFromNonDefaultCreator = false;
                    return((IList)list);
                }
            }
            else if (contract.IsReadOnlyOrFixedSize)
            {
                createdFromNonDefaultCreator = true;
                IList list = contract.CreateTemporaryCollection();

                if (contract.ShouldCreateWrapper)
                {
                    list = contract.CreateWrapper(list);
                }

                return(list);
            }
            else if (contract.DefaultCreator != null && !contract.DefaultCreatorNonPublic)
            {
                object list = contract.DefaultCreator();

                if (contract.ShouldCreateWrapper)
                {
                    list = contract.CreateWrapper(list);
                }

                createdFromNonDefaultCreator = false;
                return((IList)list);
            }
            else if (contract.HasParameterizedCreatorInternal)
            {
                createdFromNonDefaultCreator = true;
                return(contract.CreateTemporaryCollection());
            }
            else
            {
                if (!contract.IsInstantiable)
                {
                    throw new SerializationException("Could not create an instance of type {0}. Type is an interface or abstract class and cannot be instantiated.".FormatWith(CultureInfo.InvariantCulture, contract.UnderlyingType));
                }

                throw new SerializationException("Unable to find a constructor to use for type {0}.".FormatWith(CultureInfo.InvariantCulture, contract.UnderlyingType));
            }
        }