public string GetFullName(TypeMap typeMap)
        {
            if (!string.IsNullOrEmpty(_fullName))
            {
                return(_fullName);
            }

            if (!IsGeneric)
            {
                _fullName = this.ToString();
            }
            else
            {
                StringBuilder sb = new StringBuilder();
                sb.Append(this.ToString()).Append("<");
                bool isFirst = true;
                foreach (ushort s in GenericArguments)
                {
                    if (!isFirst)
                    {
                        sb.Append(",");
                    }
                    else
                    {
                        isFirst = false;
                    }
                    BinaryTypeInfo ti = typeMap.GetTypeInfo(s);
                    sb.Append(ti.GetFullName(typeMap));
                }
                sb.Append(">");
                _fullName = sb.ToString();
            }

            return(_fullName);
        }
        private Type CreateGenericType(TypeMap typeMap, Type type, BinaryTypeInfo typeInfo)
        {
            if (!typeInfo.IsGeneric || typeInfo.Type == TypeEnum.Array)
            {
                return(type);
            }



            Type[] genericArguments = new Type[typeInfo.GenericArgumentCount];
            for (int i = 0; i < typeInfo.GenericArgumentCount; i++)
            {
                var ti = typeMap.GetTypeInfo(typeInfo.GenericArguments[i]);
                if (ti == null)
                {
                    throw new Exception();
                }
                if (TryResolveType(typeMap, ti, out Type t))
                {
                    genericArguments[i] = t;
                }
                else
                {
                    throw new Exception();
                }
            }

            return(type.MakeGenericType(genericArguments));
        }
        internal BinaryTypeInfo[] ReadTypeList()
        {
            ushort typeLen = ReadUInt16Value();

            BinaryTypeInfo[] typeList = new BinaryTypeInfo[typeLen];
            for (ushort i = 0; i < typeLen; i++)
            {
                typeList[i] = ReadTypeInfo();
            }
            return(typeList);
        }
Ejemplo n.º 4
0
        //public BinaryTypeInfo PrimaryTypeInfo
        //{
        //    get
        //    {
        //        return GetTypeInfo(0);
        //    }
        //}
        internal string GetTypeName(ushort seq)
        {
            BinaryTypeInfo ti = GetTypeInfo(seq);

            if (ti == null)
            {
                return(null);
            }

            return(ti.GetFullName(this));
        }
Ejemplo n.º 5
0
        internal bool TrySetTypeMemberInfos(ushort seq, Func <BinaryMemberInfo[]> getMemberInfos)
        {
            BinaryTypeInfo ti = GetTypeInfo(seq);

            if (ti != null && ti.MemberInfos == null)
            {
                var mis = getMemberInfos();
                ti.MemberInfos = new Dictionary <ushort, BinaryMemberInfo>(mis?.Select(mi => new KeyValuePair <ushort, BinaryMemberInfo>(mi.Seq, mi)));
                return(true);
            }
            return(false);
        }
        public override bool TryResolveType(TypeMap typeMap, BinaryTypeInfo typeInfo, out Type type)
        {
            type = null;
            if (typeInfo.Type == TypeEnum.None)
            {
                return(true);
            }
            if (string.IsNullOrEmpty(typeInfo.FullName) && _internalTypeMaps.ContainsKey(typeInfo.Type))
            {
                type = _internalTypeMaps[typeInfo.Type];
            }

            if (type == null || type.IsGenericType)
            {
                string typeName = typeInfo.GetFullName(typeMap);
                Type   tmp      = type;
                type = _typeNameMaps.GetOrAdd(typeName, (tn) =>
                {
                    if (typeInfo.Type == TypeEnum.Array)
                    {
                        TryResolveType(typeMap, typeMap.GetTypeInfo(typeInfo.GenericArguments[0]), out Type elementType);
                        if (elementType != null)
                        {
                            return(elementType.MakeArrayType());
                        }
                        return(null);
                    }
                    else if (typeInfo.Type == TypeEnum.Tuple ||
                             typeInfo.Type == TypeEnum.ValueTuple)
                    {
                        tmp = GetTupleType(typeInfo);
                    }

                    // 从fullName获取Type
                    Type t = tmp ?? ParseType(typeInfo.FullName);
                    if (t != null)
                    {
                        t = CreateGenericType(typeMap, t, typeInfo);
                    }
                    return(t);
                });
            }


            if (type != null)
            {
                return(true);
            }


            return(false);
        }
        public BinaryConverter InitializeReEntry(Type type, BinarySerializerOptions options)
        {
            BinaryClassInfo classInfo = options.GetOrAddClass(type);


            // Set for exception handling calculation of BinaryPath.
            // BinaryPropertyNameAsString = propertyName;

            PolymorphicBinaryClassInfo = classInfo;
            PolymorphicBinaryTypeInfo  = TypeMap.GetTypeInfo(classInfo.TypeSeq);

            return(classInfo.PropertyInfoForClassInfo.ConverterBase);
        }
Ejemplo n.º 8
0
        public IReadOnlyList <ushort> GetGenericTypeSeqs(ushort seq)
        {
            List <ushort>  seqList = new List <ushort>();
            BinaryTypeInfo ti      = GetTypeInfo(seq);

            if (ti == null || !ti.IsGeneric)
            {
                return(seqList);
            }

            GetGenericTypeSeqs(seq, seqList);

            return(seqList);
        }
        //internal BitStack _bitStack;


        public BinaryReaderState(TypeMap typeMap, int version, BinaryReaderOptions options = default)
        {
            _bytePosition      = default;
            _inObject          = default;
            _isNotPrimitive    = default;
            _tokenType         = default;
            _previousTokenType = default;
            _readerOptions     = options;
            _typeMap           = typeMap;
            _typeSeq           = default;
            _version           = version;
            _typeInfo          = default;
            _propertySeq       = default;
            _dicKeySeq         = default;
        }
 private Type GetTupleType(BinaryTypeInfo ti)
 {
     if (!ti.IsGeneric)
     {
         return(null);
     }
     if (ti.Type == TypeEnum.Tuple)
     {
         return(_tupleTypeMaps[ti.GenericArgumentCount]);
     }
     else if (ti.Type == TypeEnum.ValueTuple)
     {
         return(_valueTupleTypeMaps[ti.GenericArgumentCount]);
     }
     return(null);
 }
Ejemplo n.º 11
0
        private void GetGenericTypeSeqs(ushort seq, List <ushort> seqList)
        {
            BinaryTypeInfo ti = GetTypeInfo(seq);

            if (ti == null || !ti.IsGeneric)
            {
                return;
            }

            foreach (ushort s in ti.GenericArguments)
            {
                if (seqList.Contains(s))
                {
                    continue;
                }
                seqList.Add(s);
                GetGenericTypeSeqs(s, seqList);
            }
        }
        internal bool TrySkipObjectProperties(ref int offset)
        {
            int curOffset = offset;

            // 读取属性
            while (true)
            {
                if (!TryReadPropertySeq(ref curOffset, out ushort propertySeq))
                {
                    return(false);
                }

                if (propertySeq == BinarySerializerConstants.EndObjectSeq)
                {
                    break;
                }

                // 记得处理扩展属性

                if (!TryReadTypeSeq(ref curOffset, out ushort typeSeq))
                {
                    return(false);
                }

                if (typeSeq == TypeMap.NullTypeSeq)
                {
                    continue;
                }

                BinaryTypeInfo ti = _typeMap.GetTypeInfo(typeSeq);
                if (ti == null)
                {
                }
                if (!TryForwardRead(ti, ref curOffset))
                {
                    return(false);
                }
            }

            offset = curOffset;
            return(true);
        }
 public void Reset()
 {
     CtorArgumentStateIndex       = 0;
     CtorArgumentState            = null;
     BinaryClassInfo              = null !;
     PolymorphicBinaryClassInfo   = null;
     PolymorphicBinaryTypeInfo    = null;
     BinaryTypeInfo               = null;
     PropertyPolymorphicConverter = null;
     ObjectState          = StackFrameObjectState.None;
     OriginalDepth        = 0;
     PropertyIndex        = 0;
     PropertyRefCache     = null;
     ReturnValue          = null;
     EnumerableIndexBytes = 0;
     EnumerableLength     = 0;
     EnumerableIndex      = 0;
     PropertyValueCache   = null;
     RefState             = RefState.None;
     EndProperty();
 }
        private BinaryTypeInfo ReadTypeInfo()
        {
            // ushort
            ushort    seq                  = ReadUInt16Value();
            ClassType sType                = (ClassType)ReadByteValue();
            bool      isGeneric            = ReadBooleanValue();
            byte      genericArgumentCount = ReadByteValue();

            ushort[] genericArguments = new ushort[genericArgumentCount];
            for (byte i = 0; i < genericArgumentCount; i++)
            {
                genericArguments[i] = ReadUInt16Value();
            }

            TypeEnum type    = (TypeEnum)ReadByteValue();
            ushort   nameLen = ReadUInt16Value();

            string name = null;

            if (nameLen > 0)
            {
                name = ReadStringValue(nameLen);
            }

            BinaryTypeInfo ti = new BinaryTypeInfo()
            {
                Seq                  = seq,
                SerializeType        = sType,
                IsGeneric            = isGeneric,
                GenericArgumentCount = genericArgumentCount,
                GenericArguments     = genericArguments,
                FullName             = name,
                Type                 = type
            };

            ti.MemberInfos = ReadMembers();

            return(ti);
        }
Ejemplo n.º 15
0
        public bool TryAdd(Type type, out BinaryTypeInfo typeInfo)
        {
            if (HasType(type))
            {
                typeInfo = _typeInfoMap[type];
                return(false);
            }

            lock (_typeSeqMap)
            {
                if (HasType(type))
                {
                    typeInfo = _typeInfoMap[type];
                    return(false);
                }

                ushort cur = (ushort)_currentSeq;
                if (cur >= 0xFF)
                {
                    // OXFF 固定为Null值类型
                    // TODO
                    throw new Exception();
                }
                _currentSeq++;
                BinaryTypeInfo ti = new BinaryTypeInfo()
                {
                    Seq = cur
                };
                _typeSeqMap.Add(type, cur);
                _typeInfoMap.Add(type, ti);
                _seqTypeMap.Add(cur, type);
                _typeSeqToTypeInfoMap.Add(cur, ti);

                typeInfo = ti;
                return(true);
            }
        }
Ejemplo n.º 16
0
 public abstract bool TryResolveType(TypeMap typeMap, BinaryTypeInfo typeInfo, out Type type);
Ejemplo n.º 17
0
        public void Push(BinaryTypeInfo typeInfo)
        {
            if (_continuationCount == 0)
            {
                if (_count == 0)
                {
                    // The first stack frame is held in Current.
                    Current.BinaryTypeInfo = typeInfo;
                    Current.TypeMap        = TypeMap;
                    _count = 1;
                }
                else
                {
                    BinaryClassInfo binaryClassInfo;
                    if (Current.BinaryClassInfo.ClassType == ClassType.Object)
                    {
                        if (Current.BinaryPropertyInfo != null)
                        {
                            binaryClassInfo = Current.PolymorphicBinaryClassInfo ?? Current.BinaryPropertyInfo.RuntimeClassInfo;
                        }
                        else
                        {
                            binaryClassInfo = Current.PolymorphicBinaryClassInfo ?? Current.CtorArgumentState !.BinaryParameterInfo !.RuntimeClassInfo;
                        }
                    }
                    else if (((ClassType.Value | ClassType.NewValue) & Current.BinaryClassInfo.ClassType) != 0)
                    {
                        // Although ClassType.Value doesn't push, a custom custom converter may re-enter serialization.
                        binaryClassInfo = Current.BinaryPropertyInfo !.RuntimeClassInfo;
                    }
                    else
                    {
                        Debug.Assert(((ClassType.Enumerable | ClassType.Dictionary) & Current.BinaryClassInfo.ClassType) != 0);
                        binaryClassInfo = Current.PolymorphicBinaryClassInfo ?? Current.BinaryClassInfo.ElementClassInfo !;
                    }

                    AddCurrent();
                    Current.Reset();

                    Current.BinaryClassInfo    = binaryClassInfo;
                    Current.BinaryPropertyInfo = binaryClassInfo.PropertyInfoForClassInfo;
                    Current.BinaryTypeInfo     = typeInfo;

                    Current.TypeMap = TypeMap;
                }
            }
            else if (_continuationCount == 1)
            {
                // No need for a push since there is only one stack frame.
                Debug.Assert(_count == 1);
                _continuationCount = 0;
            }
            else
            {
                // A continuation; adjust the index.
                Current = _previous[_count - 1];

                // Check if we are done.
                if (_count == _continuationCount)
                {
                    _continuationCount = 0;
                }
                else
                {
                    _count++;
                }
            }

            SetConstructorArgumentState();
        }
        internal bool TryForwardRead(BinaryTypeInfo typeInfo, ref int offset)
        {
            if (typeInfo.SerializeType == ClassType.Value)
            {
                if (_binaryTypeToBytesLen.ContainsKey(typeInfo.Type))
                {
                    int len = _binaryTypeToBytesLen[typeInfo.Type];
                    if (!TryRequestData(offset, len))
                    {
                        return(false);
                    }

                    offset += len;
                    return(true);
                }
                else if (typeInfo.Type == TypeEnum.Nullable)
                {
                    int curOffset = offset;
                    if (!TryReadTypeSeq(ref curOffset, out ushort typeSeq))
                    {
                        return(false);
                    }
                    if (typeSeq == TypeMap.NullTypeSeq)
                    {
                        offset = curOffset;
                        return(true);
                    }
                    if (!TryForwardRead(_typeMap.GetTypeInfo(typeSeq), ref curOffset))
                    {
                        return(false);
                    }

                    offset = curOffset;
                    return(true);
                }
                else
                {
                    if (!TrySkipBytes(ref offset))
                    {
                        return(false);
                    }
                }
            }
            else if (typeInfo.SerializeType == ClassType.Object)
            {
                int curOffset = offset;
                // 引用、非引用
                if (!TryRequestData(curOffset, 1))
                {
                    return(false);
                }

                byte _ = _buffer[curOffset++];

                if (!TryRequestData(curOffset, 4))
                {
                    return(false);
                }
                curOffset += 4;

                // 读取属性
                if (!TrySkipObjectProperties(ref curOffset))
                {
                    return(false);
                }

                offset = curOffset;
            }
            else if (typeInfo.SerializeType == ClassType.Enumerable)
            {
                int curOffset = offset;
                // 可枚举类型
                // 引用、非引用
                if (!TryRequestData(curOffset, 1))
                {
                    return(false);
                }

                byte refSign = _buffer[curOffset++];

                // 引用
                if (!TryRequestData(curOffset, 4))
                {
                    return(false);
                }
                curOffset += 4;

                // 非引用
                if (refSign == 0x00)
                {
                    // 索引长度
                    if (!TryRequestData(curOffset, 1))
                    {
                        return(false);
                    }

                    byte lenBytes = _buffer[curOffset++];
                    if (!TryRequestData(curOffset, lenBytes))
                    {
                        return(false);
                    }

                    var   lenSpan = _buffer.Slice(curOffset, lenBytes);
                    ulong len     = GetEnumerableLength(lenSpan);
                    curOffset += lenBytes;

                    // 按顺序读取
                    ulong curIdx = 0;
                    while (curIdx < len)
                    {
                        // 读取索引
                        if (!TrySkipBytes(ref curOffset, lenBytes))
                        {
                            return(false);
                        }

                        if (!TryReadTypeSeq(ref curOffset, out ushort typeSeq))
                        {
                            return(false);
                        }

                        if (typeSeq == TypeMap.NullTypeSeq)
                        {
                            continue;
                        }

                        BinaryTypeInfo ti = _typeMap.GetTypeInfo(typeSeq);
                        if (!TryForwardRead(ti, ref curOffset))
                        {
                            return(false);
                        }
                        curIdx++;
                    }
                }


                // 读取自定义属性
                if (!TrySkipObjectProperties(ref curOffset))
                {
                    return(false);
                }

                offset = curOffset;
            }
            else if (typeInfo.SerializeType == ClassType.Dictionary)
            {
                int curOffset = offset;
                // 引用、非引用
                if (!TryRequestData(curOffset, 1))
                {
                    return(false);
                }

                byte refSign = _buffer[curOffset++];

                if (!TryRequestData(curOffset, 4))
                {
                    return(false);
                }
                curOffset += 4;

                if (refSign == 0x00)
                {
                    // Key Value
                    while (true)
                    {
                        if (!TryRequestData(curOffset, 1))
                        {
                            return(false);
                        }

                        byte keySeq = _buffer[curOffset++];

                        if (keySeq == BinarySerializerConstants.EndDictionaryKey)
                        {
                            break;
                        }
                        else if (keySeq != BinarySerializerConstants.DictionaryKeySeq)
                        {
                            ThrowHelper.ThrowBinaryReaderException(ref this, ExceptionResource.InvalidByte);
                        }

                        // Key
                        if (!TryReadTypeSeq(ref curOffset, out ushort typeSeq))
                        {
                            return(false);
                        }

                        if (typeSeq != TypeMap.NullTypeSeq)
                        {
                            BinaryTypeInfo ti = _typeMap.GetTypeInfo(typeSeq);
                            if (!TryForwardRead(ti, ref curOffset))
                            {
                                return(false);
                            }
                        }

                        // Value
                        if (!TryReadTypeSeq(ref curOffset, out typeSeq))
                        {
                            return(false);
                        }

                        if (typeSeq != TypeMap.NullTypeSeq)
                        {
                            BinaryTypeInfo ti = _typeMap.GetTypeInfo(typeSeq);
                            if (!TryForwardRead(ti, ref curOffset))
                            {
                                return(false);
                            }
                        }
                    }
                }


                // 读取属性
                if (!TrySkipObjectProperties(ref curOffset))
                {
                    return(false);
                }

                offset = curOffset;
            }
            else
            {
                ThrowHelper.ThrowBinaryException();
            }

            return(true);
        }