Return-Path: X-Original-To: apmail-ignite-commits-archive@minotaur.apache.org Delivered-To: apmail-ignite-commits-archive@minotaur.apache.org Received: from mail.apache.org (hermes.apache.org [140.211.11.3]) by minotaur.apache.org (Postfix) with SMTP id 6EE9617F8B for ; Fri, 30 Oct 2015 06:21:59 +0000 (UTC) Received: (qmail 98829 invoked by uid 500); 30 Oct 2015 06:21:59 -0000 Delivered-To: apmail-ignite-commits-archive@ignite.apache.org Received: (qmail 98775 invoked by uid 500); 30 Oct 2015 06:21:59 -0000 Mailing-List: contact commits-help@ignite.apache.org; run by ezmlm Precedence: bulk List-Help: List-Unsubscribe: List-Post: List-Id: Reply-To: dev@ignite.apache.org Delivered-To: mailing list commits@ignite.apache.org Received: (qmail 98766 invoked by uid 99); 30 Oct 2015 06:21:59 -0000 Received: from git1-us-west.apache.org (HELO git1-us-west.apache.org) (140.211.11.23) by apache.org (qpsmtpd/0.29) with ESMTP; Fri, 30 Oct 2015 06:21:59 +0000 Received: by git1-us-west.apache.org (ASF Mail Server at git1-us-west.apache.org, from userid 33) id 33646DFAF3; Fri, 30 Oct 2015 06:21:59 +0000 (UTC) Content-Type: text/plain; charset="us-ascii" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit From: vozerov@apache.org To: commits@ignite.apache.org Date: Fri, 30 Oct 2015 06:21:59 -0000 Message-Id: X-Mailer: ASF-Git Admin Mailer Subject: [1/6] ignite git commit: IGNITE-1770: DotNet part. Repository: ignite Updated Branches: refs/heads/ignite-1803 aff064216 -> db069546f http://git-wip-us.apache.org/repos/asf/ignite/blob/ebb59902/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Portable/PortableUtils.cs ---------------------------------------------------------------------- diff --git a/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Portable/PortableUtils.cs b/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Portable/PortableUtils.cs index c9d6172..7f9569a 100644 --- a/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Portable/PortableUtils.cs +++ b/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Portable/PortableUtils.cs @@ -37,9 +37,6 @@ namespace Apache.Ignite.Core.Impl.Portable */ static class PortableUtils { - /** Cache empty dictionary. */ - public static readonly IDictionary EmptyFields = new Dictionary(); - /** Header of NULL object. */ public const byte HdrNull = 101; @@ -52,21 +49,6 @@ namespace Apache.Ignite.Core.Impl.Portable /** Protocol versnion. */ public const byte ProtoVer = 1; - /** Full header length. */ - public const int FullHdrLen = 19; - - /** Offset: hash code. */ - public const int OffsetTypeId = 3; - - /** Offset: hash code. */ - public const int OffsetHashCode = 7; - - /** Offset: length. */ - public const int OffsetLen = 11; - - /** Offset: raw data offset. */ - public const int OffsetRaw = 15; - /** Type: object. */ public const byte TypeObject = HdrFull; @@ -253,9 +235,6 @@ namespace Apache.Ignite.Core.Impl.Portable /** Indicates object array. */ public const int ObjTypeId = -1; - /** Length of tpye ID. */ - public const int LengthTypeId = 1; - /** Length of array size. */ public const int LengthArraySize = 4; @@ -1589,56 +1568,6 @@ namespace Apache.Ignite.Core.Impl.Portable return id; } - /** - * Get fields map for the given object. - * Stream. - * Type ID. - * Raw data offset. - * Dictionary with field ID as key and field position as value. - */ - public static IDictionary ObjectFields(IPortableStream stream, int typeId, int rawDataOffset) - { - int endPos = stream.Position + rawDataOffset - FullHdrLen; - - // First loop detects amount of fields in the object. - int retPos = stream.Position; - int cnt = 0; - - while (stream.Position < endPos) - { - cnt++; - - stream.Seek(4, SeekOrigin.Current); - int len = stream.ReadInt(); - - stream.Seek(stream.Position + len, SeekOrigin.Begin); - } - - if (cnt == 0) - return EmptyFields; - - stream.Seek(retPos, SeekOrigin.Begin); - - IDictionary fields = new Dictionary(cnt); - - // Second loop populates fields. - while (stream.Position < endPos) - { - int id = stream.ReadInt(); - int len = stream.ReadInt(); - - if (fields.ContainsKey(id)) - throw new PortableException("Object contains duplicate field IDs [typeId=" + - typeId + ", fieldId=" + id + ']'); - - fields[id] = stream.Position; // Add field ID and length. - - stream.Seek(stream.Position + len, SeekOrigin.Begin); - } - - return fields; - } - /// /// Compare contents of two byte array chunks. /// @@ -1731,13 +1660,11 @@ namespace Apache.Ignite.Core.Impl.Portable /// /// Validate protocol version. /// - /// Stream. - public static void ValidateProtocolVersion(IPortableStream stream) + /// The version. + public static void ValidateProtocolVersion(byte version) { - byte ver = stream.ReadByte(); - - if (ver != ProtoVer) - throw new PortableException("Unsupported protocol version: " + ver); + if (version != ProtoVer) + throw new PortableException("Unsupported protocol version: " + version); } /** @@ -1851,6 +1778,28 @@ namespace Apache.Ignite.Core.Impl.Portable } /// + /// Gets the schema id as a Fnv1 hash. + /// + /// The schema. + /// + /// Schema id. + /// + public static int GetSchemaId(ResizeableArray schema) + { + var hash = Fnv1Hash.Basis; + + if (schema == null || schema.Count == 0) + return hash; + + var arr = schema.Array; + + for (int i = 0; i < schema.Count; i++) + hash = Fnv1Hash.Update(hash, arr[i].Id); + + return hash; + } + + /// /// Reverses the byte order of an unsigned long. /// private static ulong ReverseByteOrder(ulong l) http://git-wip-us.apache.org/repos/asf/ignite/blob/ebb59902/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Portable/PortableWriterImpl.cs ---------------------------------------------------------------------- diff --git a/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Portable/PortableWriterImpl.cs b/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Portable/PortableWriterImpl.cs index ab7adaa..e17449d 100644 --- a/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Portable/PortableWriterImpl.cs +++ b/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Portable/PortableWriterImpl.cs @@ -21,7 +21,7 @@ namespace Apache.Ignite.Core.Impl.Portable using System.Collections; using System.Collections.Generic; using System.IO; - + using Apache.Ignite.Core.Impl.Common; using Apache.Ignite.Core.Impl.Portable.IO; using Apache.Ignite.Core.Impl.Portable.Metadata; using Apache.Ignite.Core.Impl.Portable.Structure; @@ -58,15 +58,22 @@ namespace Apache.Ignite.Core.Impl.Portable /** Current mapper. */ private IPortableIdMapper _curMapper; + /** Current object start position. */ + private int _curPos; + /** Current raw position. */ - private long _curRawPos; + private int _curRawPos; - /** Current type structure tracker, */ - private PortableStructureTracker _curStruct; - /** Whether we are currently detaching an object. */ private bool _detaching; + /** Current type structure tracker, */ + private PortableStructureTracker _curStruct; + + /** Current schema. */ + private ResizeableArray _curSchema; + + /// /// Gets the marshaller. /// @@ -84,7 +91,6 @@ namespace Apache.Ignite.Core.Impl.Portable { WriteFieldId(fieldName, PU.TypeBool); - _stream.WriteInt(PU.LengthTypeId + 1); _stream.WriteByte(PU.TypeBool); _stream.WriteBool(val); } @@ -111,7 +117,6 @@ namespace Apache.Ignite.Core.Impl.Portable WriteNullField(); else { - _stream.WriteInt(PU.LengthTypeId + PU.LengthArraySize + val.Length); _stream.WriteByte(PU.TypeArrayBool); PU.WriteBooleanArray(val, _stream); } @@ -141,7 +146,6 @@ namespace Apache.Ignite.Core.Impl.Portable { WriteFieldId(fieldName, PU.TypeBool); - _stream.WriteInt(PU.LengthTypeId + 1); _stream.WriteByte(PU.TypeByte); _stream.WriteByte(val); } @@ -168,7 +172,6 @@ namespace Apache.Ignite.Core.Impl.Portable WriteNullField(); else { - _stream.WriteInt(PU.LengthTypeId + PU.LengthArraySize + val.Length); _stream.WriteByte(PU.TypeArrayByte); PU.WriteByteArray(val, _stream); } @@ -198,7 +201,6 @@ namespace Apache.Ignite.Core.Impl.Portable { WriteFieldId(fieldName, PU.TypeShort); - _stream.WriteInt(PU.LengthTypeId + 2); _stream.WriteByte(PU.TypeShort); _stream.WriteShort(val); } @@ -225,7 +227,6 @@ namespace Apache.Ignite.Core.Impl.Portable WriteNullField(); else { - _stream.WriteInt(PU.LengthTypeId + PU.LengthArraySize + (val.Length << 1)); _stream.WriteByte(PU.TypeArrayShort); PU.WriteShortArray(val, _stream); } @@ -255,7 +256,6 @@ namespace Apache.Ignite.Core.Impl.Portable { WriteFieldId(fieldName, PU.TypeChar); - _stream.WriteInt(PU.LengthTypeId + 2); _stream.WriteByte(PU.TypeChar); _stream.WriteChar(val); } @@ -282,7 +282,6 @@ namespace Apache.Ignite.Core.Impl.Portable WriteNullField(); else { - _stream.WriteInt(PU.LengthTypeId + PU.LengthArraySize + (val.Length << 1)); _stream.WriteByte(PU.TypeArrayChar); PU.WriteCharArray(val, _stream); } @@ -312,7 +311,6 @@ namespace Apache.Ignite.Core.Impl.Portable { WriteFieldId(fieldName, PU.TypeInt); - _stream.WriteInt(PU.LengthTypeId + 4); _stream.WriteByte(PU.TypeInt); _stream.WriteInt(val); } @@ -339,7 +337,6 @@ namespace Apache.Ignite.Core.Impl.Portable WriteNullField(); else { - _stream.WriteInt(PU.LengthTypeId + PU.LengthArraySize + (val.Length << 2)); _stream.WriteByte(PU.TypeArrayInt); PU.WriteIntArray(val, _stream); } @@ -369,7 +366,6 @@ namespace Apache.Ignite.Core.Impl.Portable { WriteFieldId(fieldName, PU.TypeLong); - _stream.WriteInt(PU.LengthTypeId + 8); _stream.WriteByte(PU.TypeLong); _stream.WriteLong(val); } @@ -396,7 +392,6 @@ namespace Apache.Ignite.Core.Impl.Portable WriteNullField(); else { - _stream.WriteInt(PU.LengthTypeId + PU.LengthArraySize + (val.Length << 3)); _stream.WriteByte(PU.TypeArrayLong); PU.WriteLongArray(val, _stream); } @@ -426,7 +421,6 @@ namespace Apache.Ignite.Core.Impl.Portable { WriteFieldId(fieldName, PU.TypeFloat); - _stream.WriteInt(PU.LengthTypeId + 4); _stream.WriteByte(PU.TypeFloat); _stream.WriteFloat(val); } @@ -453,7 +447,6 @@ namespace Apache.Ignite.Core.Impl.Portable WriteNullField(); else { - _stream.WriteInt(PU.LengthTypeId + PU.LengthArraySize + (val.Length << 2)); _stream.WriteByte(PU.TypeArrayFloat); PU.WriteFloatArray(val, _stream); } @@ -483,7 +476,6 @@ namespace Apache.Ignite.Core.Impl.Portable { WriteFieldId(fieldName, PU.TypeDouble); - _stream.WriteInt(PU.LengthTypeId + 8); _stream.WriteByte(PU.TypeDouble); _stream.WriteDouble(val); } @@ -510,7 +502,6 @@ namespace Apache.Ignite.Core.Impl.Portable WriteNullField(); else { - _stream.WriteInt(PU.LengthTypeId + PU.LengthArraySize + (val.Length << 3)); _stream.WriteByte(PU.TypeArrayDouble); PU.WriteDoubleArray(val, _stream); } @@ -544,12 +535,8 @@ namespace Apache.Ignite.Core.Impl.Portable WriteNullField(); else { - int pos = SkipFieldLength(); - _stream.WriteByte(PU.TypeDecimal); PortableUtils.WriteDecimal(val.Value, _stream); - - WriteFieldLength(_stream, pos); } } @@ -581,12 +568,8 @@ namespace Apache.Ignite.Core.Impl.Portable WriteNullField(); else { - int pos = SkipFieldLength(); - _stream.WriteByte(PU.TypeArrayDecimal); PU.WriteDecimalArray(val, _stream); - - WriteFieldLength(_stream, pos); } } @@ -618,8 +601,6 @@ namespace Apache.Ignite.Core.Impl.Portable WriteNullField(); else { - _stream.WriteInt(PU.LengthTypeId + 12); - _stream.WriteByte(PortableUtils.TypeTimestamp); PortableUtils.WriteTimestamp(val.Value, _stream); } @@ -653,12 +634,8 @@ namespace Apache.Ignite.Core.Impl.Portable WriteNullField(); else { - int pos = SkipFieldLength(); - _stream.WriteByte(PortableUtils.TypeArrayTimestamp); PortableUtils.WriteTimestampArray(val, _stream); - - WriteFieldLength(_stream, pos); } } @@ -690,12 +667,8 @@ namespace Apache.Ignite.Core.Impl.Portable WriteNullField(); else { - int pos = SkipFieldLength(); - _stream.WriteByte(PU.TypeString); PU.WriteString(val, _stream); - - WriteFieldLength(_stream, pos); } } @@ -727,12 +700,8 @@ namespace Apache.Ignite.Core.Impl.Portable WriteNullField(); else { - int pos = SkipFieldLength(); - _stream.WriteByte(PU.TypeArrayString); PU.WriteStringArray(val, _stream); - - WriteFieldLength(_stream, pos); } } @@ -764,8 +733,6 @@ namespace Apache.Ignite.Core.Impl.Portable WriteNullField(); else { - _stream.WriteInt(PU.LengthTypeId + 16); - _stream.WriteByte(PU.TypeGuid); PU.WriteGuid(val.Value, _stream); } @@ -799,12 +766,8 @@ namespace Apache.Ignite.Core.Impl.Portable WriteNullField(); else { - int pos = SkipFieldLength(); - _stream.WriteByte(PU.TypeArrayGuid); PU.WriteGuidArray(val, _stream); - - WriteFieldLength(_stream, pos); } } @@ -833,8 +796,6 @@ namespace Apache.Ignite.Core.Impl.Portable { WriteFieldId(fieldName, PU.TypeEnum); - _stream.WriteInt(PU.LengthTypeId + 16); - _stream.WriteByte(PU.TypeEnum); PortableUtils.WriteEnum(_stream, (Enum)(object)val); } @@ -864,12 +825,8 @@ namespace Apache.Ignite.Core.Impl.Portable WriteNullField(); else { - int pos = SkipFieldLength(); - _stream.WriteByte(PU.TypeArrayEnum); PortableUtils.WriteArray(val, this); - - WriteFieldLength(_stream, pos); } } @@ -902,13 +859,7 @@ namespace Apache.Ignite.Core.Impl.Portable if (val == null) WriteNullField(); else - { - int pos = SkipFieldLength(); - Write(val); - - WriteFieldLength(_stream, pos); - } } /// @@ -935,12 +886,8 @@ namespace Apache.Ignite.Core.Impl.Portable WriteNullField(); else { - int pos = SkipFieldLength(); - _stream.WriteByte(PU.TypeArray); PortableUtils.WriteArray(val, this); - - WriteFieldLength(_stream, pos); } } @@ -981,13 +928,7 @@ namespace Apache.Ignite.Core.Impl.Portable if (val == null) WriteNullField(); else - { - int pos = SkipFieldLength(); - WriteCollection(val); - - WriteFieldLength(_stream, pos); - } } /// @@ -1012,13 +953,7 @@ namespace Apache.Ignite.Core.Impl.Portable if (val == null) WriteNullField(); else - { - int pos = SkipFieldLength(); - WriteDictionary(val); - - WriteFieldLength(_stream, pos); - } } /// @@ -1036,7 +971,6 @@ namespace Apache.Ignite.Core.Impl.Portable /// private void WriteNullField() { - _stream.WriteInt(1); _stream.WriteByte(PU.HdrNull); } @@ -1129,44 +1063,51 @@ namespace Apache.Ignite.Core.Impl.Portable if (!(desc.Serializer is IPortableSystemTypeSerializer) && WriteHandle(pos, obj)) return; - // Write header. - _stream.WriteByte(PU.HdrFull); - _stream.WriteByte(PU.ProtoVer); - _stream.WriteBool(desc.UserType); - _stream.WriteInt(desc.TypeId); - _stream.WriteInt(obj.GetHashCode()); - - // Skip length as it is not known in the first place. - _stream.Seek(8, SeekOrigin.Current); + // Skip header length as not everything is known now + _stream.Seek(PortableObjectHeader.Size, SeekOrigin.Current); // Preserve old frame. int oldTypeId = _curTypeId; IPortableNameMapper oldConverter = _curConverter; IPortableIdMapper oldMapper = _curMapper; - long oldRawPos = _curRawPos; + int oldRawPos = _curRawPos; + var oldPos = _curPos; var oldStruct = _curStruct; + var oldSchema = _curSchema; // Push new frame. _curTypeId = desc.TypeId; _curConverter = desc.NameConverter; _curMapper = desc.Mapper; _curRawPos = 0; + _curPos = pos; _curStruct = new PortableStructureTracker(desc, desc.WriterTypeStructure); + _curSchema = null; // Write object fields. desc.Serializer.WritePortable(obj, this); - // Calculate and write length. - int len = _stream.Position - pos; + // Write schema + var hasSchema = _curSchema != null; + var schemaOffset = hasSchema ? _stream.Position - pos : PortableObjectHeader.Size; - _stream.WriteInt(pos + PU.OffsetLen, len); - - if (_curRawPos != 0) - _stream.WriteInt(pos + PU.OffsetRaw, (int)(_curRawPos - pos)); - else - _stream.WriteInt(pos + PU.OffsetRaw, len); + if (hasSchema) + PortableObjectSchemaField.WriteArray(_curSchema.Array, _stream, _curSchema.Count); + + // Calculate and write header. + if (hasSchema && _curRawPos > 0) + _stream.WriteInt(_curRawPos - pos); // raw offset is in the last 4 bytes + + var len = _stream.Position - pos; + + var header = new PortableObjectHeader(desc.UserType, desc.TypeId, obj.GetHashCode(), len, + PU.GetSchemaId(_curSchema), schemaOffset, !hasSchema); + + PortableObjectHeader.Write(header, _stream, pos); + + Stream.Seek(pos + len, SeekOrigin.Begin); // Seek to the end // Apply structure updates if any. _curStruct.UpdateWriterStructure(this); @@ -1176,8 +1117,10 @@ namespace Apache.Ignite.Core.Impl.Portable _curConverter = oldConverter; _curMapper = oldMapper; _curRawPos = oldRawPos; + _curPos = oldPos; _curStruct = oldStruct; + _curSchema = oldSchema; } else { @@ -1416,7 +1359,7 @@ namespace Apache.Ignite.Core.Impl.Portable return true; } - + /// /// Write field ID. /// @@ -1427,35 +1370,14 @@ namespace Apache.Ignite.Core.Impl.Portable if (_curRawPos != 0) throw new PortableException("Cannot write named fields after raw data is written."); - _stream.WriteInt(_curStruct.GetFieldId(fieldName, fieldTypeId)); - } + var fieldId = _curStruct.GetFieldId(fieldName, fieldTypeId); - /// - /// Skip field lenght and return position where it is to be written. - /// - /// - private int SkipFieldLength() - { - int pos = _stream.Position; + _curSchema = _curSchema ?? new ResizeableArray(4); - _stream.Seek(4, SeekOrigin.Current); - - return pos; + _curSchema.Add(new PortableObjectSchemaField(fieldId, _stream.Position - _curPos)); } /// - /// Write field length. - /// - /// Stream. - /// Position where length should reside - private static void WriteFieldLength(IPortableStream stream, int pos) - { - // Length is is a difference between current position and previously recorder - // length placeholder position minus 4 bytes for the length itself. - stream.WriteInt(pos, stream.Position - pos - 4); - } - - /// /// Saves metadata for this session. /// /// Type ID. http://git-wip-us.apache.org/repos/asf/ignite/blob/ebb59902/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Portable/PortablesImpl.cs ---------------------------------------------------------------------- diff --git a/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Portable/PortablesImpl.cs b/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Portable/PortablesImpl.cs index 451386b..f48f120 100644 --- a/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Portable/PortablesImpl.cs +++ b/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Portable/PortablesImpl.cs @@ -164,17 +164,15 @@ namespace Apache.Ignite.Core.Impl.Portable /// Empty portable object. private PortableUserObject PortableFromDescriptor(IPortableTypeDescriptor desc) { - PortableHeapStream stream = new PortableHeapStream(18); + var len = PortableObjectHeader.Size; - stream.WriteByte(PortableUtils.HdrFull); - stream.WriteByte(PortableUtils.ProtoVer); - stream.WriteBool(true); - stream.WriteInt(desc.TypeId); - stream.WriteInt(0); // Hash. - stream.WriteInt(PortableUtils.FullHdrLen); // Length. - stream.WriteInt(PortableUtils.FullHdrLen); // Raw data offset. + var hdr = new PortableObjectHeader(desc.UserType, desc.TypeId, 0, len, 0, len, true); - return new PortableUserObject(_marsh, stream.InternalArray, 0, desc.TypeId, 0); + var stream = new PortableHeapStream(len); + + PortableObjectHeader.Write(hdr, stream, 0); + + return new PortableUserObject(_marsh, stream.InternalArray, 0, hdr); } ///