コード例 #1
0
        /// <summary>
        /// Writes an *implementation specific* bundled .NET object, including (as options) type-metadata, identity/re-use, etc.
        /// </summary>
        public static SubItemToken WriteNetObject_Start(object value, ProtoWriter dest, BclHelpers.NetObjectOptions options, out int dynamicTypeKey, out bool writeObject)
        {
#if FEAT_IKVM
            throw new NotSupportedException();
#else
            if (dest == null)
            {
                throw new ArgumentNullException(nameof(dest));
            }

            dynamicTypeKey = -1;

            // length not prefixed to not move data in buffer twice just because of NetObject (will be another nested inside)
            SubItemToken token = ProtoWriter.StartSubItem(null, false, dest);

            if (value == null)
            {
                // null handling
                writeObject = false;
                return(token);
            }

            // even root object can be wrapped with collection
            // so it's not true root
            writeObject = true;
            if ((options & BclHelpers.NetObjectOptions.AsReference) != 0)
            {
                bool existing;
                int  objectKey = dest.NetCache.AddObjectKey(value, out existing);
                ProtoWriter.WriteFieldHeader(existing ? FieldExistingObjectKey : FieldNewObjectKey, WireType.Variant, dest);
                ProtoWriter.WriteInt32(objectKey, dest);
                if (existing)
                {
                    writeObject = false;
                }
            }

            if (writeObject)
            {
                if ((options & BclHelpers.NetObjectOptions.DynamicType) != 0)
                {
                    bool existing;
                    Type type = value.GetType();

                    dynamicTypeKey = dest.GetTypeKey(ref type);
                    int typeRefKey = dest.NetCache.AddObjectKey(type, out existing);
                    ProtoWriter.WriteFieldHeader(existing ? FieldExistingTypeKey : FieldNewTypeKey, WireType.Variant, dest);
                    ProtoWriter.WriteInt32(typeRefKey, dest);
                    if (!existing)
                    {
                        ProtoWriter.WriteFieldHeader(FieldTypeName, WireType.String, dest);
                        ProtoWriter.WriteString(dest.SerializeType(type), dest);
                    }
                }

                // do nothing, write will be outside
                ProtoWriter.WriteFieldHeaderBegin((options & BclHelpers.NetObjectOptions.WriteAsLateReference) != 0 ? FieldLateReferenceObject : FieldObject, dest);
            }
            return(token);
#endif
        }