You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@ignite.apache.org by vo...@apache.org on 2015/10/30 13:22:16 UTC
[6/6] ignite git commit: IGNITE-1770: Implemented constant-time field
lookup on protocol level.
IGNITE-1770: Implemented constant-time field lookup on protocol level.
Project: http://git-wip-us.apache.org/repos/asf/ignite/repo
Commit: http://git-wip-us.apache.org/repos/asf/ignite/commit/b85fa171
Tree: http://git-wip-us.apache.org/repos/asf/ignite/tree/b85fa171
Diff: http://git-wip-us.apache.org/repos/asf/ignite/diff/b85fa171
Branch: refs/heads/ignite-1282
Commit: b85fa1714d40daa4a47b7cb0449b5f1712fa0a0b
Parents: 667c2e6
Author: vozerov-gridgain <vo...@gridgain.com>
Authored: Fri Oct 30 15:22:45 2015 +0300
Committer: vozerov-gridgain <vo...@gridgain.com>
Committed: Fri Oct 30 15:22:45 2015 +0300
----------------------------------------------------------------------
.../portable/GridPortableMarshaller.java | 26 +-
.../portable/PortableClassDescriptor.java | 121 +-
.../internal/portable/PortableContext.java | 95 +
.../internal/portable/PortableObjectEx.java | 9 +
.../internal/portable/PortableObjectImpl.java | 12 +-
.../portable/PortableObjectOffheapImpl.java | 15 +-
.../internal/portable/PortableObjectSchema.java | 63 +
.../portable/PortablePositionReadable.java | 39 +
.../portable/PortableReaderContext.java | 37 +-
.../internal/portable/PortableReaderExImpl.java | 1734 ++++++------------
.../ignite/internal/portable/PortableUtils.java | 159 +-
.../internal/portable/PortableWriterExImpl.java | 555 +++---
.../portable/builder/PortableBuilderImpl.java | 196 +-
.../portable/builder/PortableBuilderReader.java | 22 +-
.../builder/PortableBuilderSerializer.java | 6 +-
.../portable/builder/PortableLazyArrayList.java | 6 +-
.../builder/PortableLazyLinkedList.java | 6 +-
.../portable/builder/PortableLazyMap.java | 6 +-
.../portable/builder/PortableLazySet.java | 4 +-
.../streams/PortableAbstractInputStream.java | 24 +-
.../streams/PortableAbstractOutputStream.java | 15 +
.../streams/PortableHeapInputStream.java | 12 +-
.../streams/PortableHeapOutputStream.java | 8 +
.../portable/streams/PortableInputStream.java | 12 +-
.../streams/PortableOffheapInputStream.java | 12 +-
.../streams/PortableOffheapOutputStream.java | 8 +
.../portable/streams/PortableOutputStream.java | 8 +
.../CacheObjectPortableProcessorImpl.java | 6 +-
.../PlatformBigEndianInputStreamImpl.java | 9 +-
.../PlatformBigEndianOutputStreamImpl.java | 5 +
.../memory/PlatformInputStreamImpl.java | 12 +-
.../memory/PlatformOutputStreamImpl.java | 7 +
.../marshaller/portable/PortableMarshaller.java | 2 +-
.../GridPortableMarshallerSelfTest.java | 55 +-
.../src/portable_reader_writer_test.cpp | 555 ++++--
modules/platforms/cpp/core/Makefile.am | 1 +
modules/platforms/cpp/core/include/Makefile.am | 1 +
.../ignite/impl/interop/interop_output_stream.h | 8 +
.../ignite/impl/portable/portable_common.h | 33 +-
.../ignite/impl/portable/portable_reader_impl.h | 241 ++-
.../ignite/impl/portable/portable_schema.h | 114 ++
.../ignite/impl/portable/portable_writer_impl.h | 105 +-
.../platforms/cpp/core/project/vs/core.vcxproj | 2 +
.../cpp/core/project/vs/core.vcxproj.filters | 6 +
.../src/impl/interop/interop_input_stream.cpp | 2 +-
.../src/impl/interop/interop_output_stream.cpp | 11 +
.../src/impl/portable/portable_reader_impl.cpp | 218 ++-
.../core/src/impl/portable/portable_schema.cpp | 88 +
.../src/impl/portable/portable_writer_impl.cpp | 100 +-
.../Portable/PortableWriteBenchmark.cs | 4 +-
.../Apache.Ignite.Core.csproj | 5 +
.../Apache.Ignite.Core/Impl/Common/Fnv1Hash.cs | 54 +
.../Impl/Common/ResizeableArray.cs | 70 +
.../Impl/Memory/PlatformMemoryStream.cs | 35 +-
.../Impl/Portable/IPortableTypeDescriptor.cs | 5 +
.../Impl/Portable/Io/IPortableStream.cs | 8 +-
.../Impl/Portable/Io/PortableAbstractStream.cs | 72 +-
.../Impl/Portable/Io/PortableHeapStream.cs | 99 +-
.../Impl/Portable/PortableBuilderImpl.cs | 145 +-
.../Impl/Portable/PortableFullTypeDescriptor.cs | 9 +
.../Impl/Portable/PortableMarshaller.cs | 2 +-
.../Impl/Portable/PortableObjectHeader.cs | 343 ++++
.../Impl/Portable/PortableObjectSchema.cs | 98 +
.../Impl/Portable/PortableObjectSchemaField.cs | 113 ++
.../Impl/Portable/PortableReaderImpl.cs | 173 +-
.../Portable/PortableSurrogateTypeDescriptor.cs | 9 +
.../Impl/Portable/PortableUserObject.cs | 82 +-
.../Impl/Portable/PortableUtils.cs | 103 +-
.../Impl/Portable/PortableWriterImpl.cs | 164 +-
.../Impl/Portable/PortablesImpl.cs | 16 +-
.../Structure/PortableStructureTracker.cs | 8 +
parent/pom.xml | 8 +-
72 files changed, 3703 insertions(+), 2713 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/ignite/blob/b85fa171/modules/core/src/main/java/org/apache/ignite/internal/portable/GridPortableMarshaller.java
----------------------------------------------------------------------
diff --git a/modules/core/src/main/java/org/apache/ignite/internal/portable/GridPortableMarshaller.java b/modules/core/src/main/java/org/apache/ignite/internal/portable/GridPortableMarshaller.java
index 6f16755..9afe2ee 100644
--- a/modules/core/src/main/java/org/apache/ignite/internal/portable/GridPortableMarshaller.java
+++ b/modules/core/src/main/java/org/apache/ignite/internal/portable/GridPortableMarshaller.java
@@ -198,23 +198,26 @@ public class GridPortableMarshaller {
/** Protocol version position. */
public static final int PROTO_VER_POS = 1;
- /** */
- public static final int TYPE_ID_POS = 3;
+ /** Flags position in header. */
+ public static final int FLAGS_POS = 2;
/** */
- public static final int HASH_CODE_POS = 7;
+ public static final int TYPE_ID_POS = 4;
/** */
- public static final int TOTAL_LEN_POS = 11;
+ public static final int HASH_CODE_POS = 8;
/** */
- public static final byte RAW_DATA_OFF_POS = 15;
+ public static final int TOTAL_LEN_POS = 12;
/** */
- public static final int CLS_NAME_POS = 19;
+ public static final int SCHEMA_ID_POS = 16;
+
+ /** Schema or raw offset position. */
+ public static final int SCHEMA_OR_RAW_OFF_POS = 20;
/** */
- public static final byte DFLT_HDR_LEN = 19;
+ public static final byte DFLT_HDR_LEN = 24;
/** */
private final PortableContext ctx;
@@ -228,16 +231,15 @@ public class GridPortableMarshaller {
/**
* @param obj Object to marshal.
- * @param off Offset.
* @return Byte array.
* @throws PortableException In case of error.
*/
- public byte[] marshal(@Nullable Object obj, int off) throws PortableException {
+ public byte[] marshal(@Nullable Object obj) throws PortableException {
if (obj == null)
return new byte[] { NULL };
- try (PortableWriterExImpl writer = new PortableWriterExImpl(ctx, off)) {
- writer.marshal(obj, false);
+ try (PortableWriterExImpl writer = new PortableWriterExImpl(ctx)) {
+ writer.marshal(obj);
return writer.array();
}
@@ -293,7 +295,7 @@ public class GridPortableMarshaller {
* @return Writer.
*/
public PortableWriterExImpl writer(PortableOutputStream out) {
- return new PortableWriterExImpl(ctx, out, 0);
+ return new PortableWriterExImpl(ctx, out);
}
/**
http://git-wip-us.apache.org/repos/asf/ignite/blob/b85fa171/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableClassDescriptor.java
----------------------------------------------------------------------
diff --git a/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableClassDescriptor.java b/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableClassDescriptor.java
index 0a9974e..9f7f0c6 100644
--- a/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableClassDescriptor.java
+++ b/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableClassDescriptor.java
@@ -17,6 +17,18 @@
package org.apache.ignite.internal.portable;
+import org.apache.ignite.IgniteCheckedException;
+import org.apache.ignite.internal.processors.cache.CacheObjectImpl;
+import org.apache.ignite.internal.util.typedef.internal.U;
+import org.apache.ignite.marshaller.MarshallerExclusions;
+import org.apache.ignite.marshaller.optimized.OptimizedMarshaller;
+import org.apache.ignite.marshaller.portable.PortableMarshaller;
+import org.apache.ignite.portable.PortableException;
+import org.apache.ignite.portable.PortableIdMapper;
+import org.apache.ignite.portable.PortableMarshalAware;
+import org.apache.ignite.portable.PortableSerializer;
+import org.jetbrains.annotations.Nullable;
+
import java.io.Externalizable;
import java.io.IOException;
import java.io.ObjectInputStream;
@@ -35,17 +47,6 @@ import java.util.HashMap;
import java.util.HashSet;
import java.util.Map;
import java.util.UUID;
-import org.apache.ignite.IgniteCheckedException;
-import org.apache.ignite.internal.processors.cache.CacheObjectImpl;
-import org.apache.ignite.internal.util.typedef.internal.U;
-import org.apache.ignite.marshaller.MarshallerExclusions;
-import org.apache.ignite.marshaller.optimized.OptimizedMarshaller;
-import org.apache.ignite.marshaller.portable.PortableMarshaller;
-import org.apache.ignite.portable.PortableException;
-import org.apache.ignite.portable.PortableIdMapper;
-import org.apache.ignite.portable.PortableMarshalAware;
-import org.apache.ignite.portable.PortableSerializer;
-import org.jetbrains.annotations.Nullable;
import static java.lang.reflect.Modifier.isStatic;
import static java.lang.reflect.Modifier.isTransient;
@@ -63,6 +64,9 @@ public class PortableClassDescriptor {
/** */
private final PortableSerializer serializer;
+ /** ID mapper. */
+ private final PortableIdMapper idMapper;
+
/** */
private final Mode mode;
@@ -138,6 +142,7 @@ public class PortableClassDescriptor {
this.typeId = typeId;
this.typeName = typeName;
this.serializer = serializer;
+ this.idMapper = idMapper;
this.keepDeserialized = keepDeserialized;
this.registered = registered;
@@ -307,6 +312,15 @@ public class PortableClassDescriptor {
}
/**
+ * Get ID mapper.
+ *
+ * @return ID mapper.
+ */
+ public PortableIdMapper idMapper() {
+ return idMapper;
+ }
+
+ /**
* @return portableWriteReplace() method
*/
@Nullable Method getWriteReplaceMethod() {
@@ -409,57 +423,57 @@ public class PortableClassDescriptor {
break;
case SHORT_ARR:
- writer.doWriteShortArray((short[])obj);
+ writer.doWriteShortArray((short[]) obj);
break;
case INT_ARR:
- writer.doWriteIntArray((int[])obj);
+ writer.doWriteIntArray((int[]) obj);
break;
case LONG_ARR:
- writer.doWriteLongArray((long[])obj);
+ writer.doWriteLongArray((long[]) obj);
break;
case FLOAT_ARR:
- writer.doWriteFloatArray((float[])obj);
+ writer.doWriteFloatArray((float[]) obj);
break;
case DOUBLE_ARR:
- writer.doWriteDoubleArray((double[])obj);
+ writer.doWriteDoubleArray((double[]) obj);
break;
case CHAR_ARR:
- writer.doWriteCharArray((char[])obj);
+ writer.doWriteCharArray((char[]) obj);
break;
case BOOLEAN_ARR:
- writer.doWriteBooleanArray((boolean[])obj);
+ writer.doWriteBooleanArray((boolean[]) obj);
break;
case DECIMAL_ARR:
- writer.doWriteDecimalArray((BigDecimal[])obj);
+ writer.doWriteDecimalArray((BigDecimal[]) obj);
break;
case STRING_ARR:
- writer.doWriteStringArray((String[])obj);
+ writer.doWriteStringArray((String[]) obj);
break;
case UUID_ARR:
- writer.doWriteUuidArray((UUID[])obj);
+ writer.doWriteUuidArray((UUID[]) obj);
break;
case DATE_ARR:
- writer.doWriteDateArray((Date[])obj);
+ writer.doWriteDateArray((Date[]) obj);
break;
@@ -515,8 +529,7 @@ public class PortableClassDescriptor {
else
((PortableMarshalAware)obj).writePortable(writer);
- writer.writeRawOffsetIfNeeded();
- writer.writeLength();
+ writer.postWrite(userType);
if (obj.getClass() != PortableMetaDataImpl.class
&& ctx.isMetaDataChanged(typeId, writer.metaDataHashSum())) {
@@ -535,6 +548,8 @@ public class PortableClassDescriptor {
case EXTERNALIZABLE:
if (writeHeader(obj, writer)) {
+ writer.rawWriter();
+
try {
((Externalizable)obj).writeExternal(writer);
}
@@ -542,7 +557,7 @@ public class PortableClassDescriptor {
throw new PortableException("Failed to write Externalizable object: " + obj, e);
}
- writer.writeLength();
+ writer.postWrite(userType);
}
break;
@@ -552,8 +567,7 @@ public class PortableClassDescriptor {
for (FieldInfo info : fields)
info.write(obj, writer);
- writer.writeRawOffsetIfNeeded();
- writer.writeLength();
+ writer.postWrite(userType);
}
break;
@@ -646,28 +660,13 @@ public class PortableClassDescriptor {
if (writer.tryWriteAsHandle(obj))
return false;
- int pos = writer.position();
-
- writer.doWriteByte(GridPortableMarshaller.OBJ);
- writer.doWriteByte(GridPortableMarshaller.PROTO_VER);
- writer.doWriteBoolean(userType);
- writer.doWriteInt(registered ? typeId : GridPortableMarshaller.UNREGISTERED_TYPE_ID);
- writer.doWriteInt(obj instanceof CacheObjectImpl ? 0 : obj.hashCode());
-
- // For length and raw offset.
- int reserved = writer.reserve(8);
-
- // Class name in case if typeId registration is failed.
- if (!registered)
- writer.doWriteString(cls.getName());
-
- int current = writer.position();
- int len = current - pos;
-
- // Default raw offset (equal to header length).
- writer.position(reserved + 4);
- writer.doWriteInt(len);
- writer.position(current);
+ PortableUtils.writeHeader(
+ writer,
+ userType,
+ registered ? typeId : GridPortableMarshaller.UNREGISTERED_TYPE_ID,
+ obj instanceof CacheObjectImpl ? 0 : obj.hashCode(),
+ registered ? null : cls.getName()
+ );
return true;
}
@@ -859,7 +858,7 @@ public class PortableClassDescriptor {
assert obj != null;
assert writer != null;
- writer.doWriteInt(id);
+ writer.writeFieldId(id);
Object val;
@@ -942,57 +941,57 @@ public class PortableClassDescriptor {
break;
case SHORT_ARR:
- writer.writeShortArrayField((short[])val);
+ writer.writeShortArrayField((short[]) val);
break;
case INT_ARR:
- writer.writeIntArrayField((int[])val);
+ writer.writeIntArrayField((int[]) val);
break;
case LONG_ARR:
- writer.writeLongArrayField((long[])val);
+ writer.writeLongArrayField((long[]) val);
break;
case FLOAT_ARR:
- writer.writeFloatArrayField((float[])val);
+ writer.writeFloatArrayField((float[]) val);
break;
case DOUBLE_ARR:
- writer.writeDoubleArrayField((double[])val);
+ writer.writeDoubleArrayField((double[]) val);
break;
case CHAR_ARR:
- writer.writeCharArrayField((char[])val);
+ writer.writeCharArrayField((char[]) val);
break;
case BOOLEAN_ARR:
- writer.writeBooleanArrayField((boolean[])val);
+ writer.writeBooleanArrayField((boolean[]) val);
break;
case DECIMAL_ARR:
- writer.writeDecimalArrayField((BigDecimal[])val);
+ writer.writeDecimalArrayField((BigDecimal[]) val);
break;
case STRING_ARR:
- writer.writeStringArrayField((String[])val);
+ writer.writeStringArrayField((String[]) val);
break;
case UUID_ARR:
- writer.writeUuidArrayField((UUID[])val);
+ writer.writeUuidArrayField((UUID[]) val);
break;
case DATE_ARR:
- writer.writeDateArrayField((Date[])val);
+ writer.writeDateArrayField((Date[]) val);
break;
http://git-wip-us.apache.org/repos/asf/ignite/blob/b85fa171/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableContext.java
----------------------------------------------------------------------
diff --git a/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableContext.java b/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableContext.java
index 26e098f..3c08df6 100644
--- a/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableContext.java
+++ b/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableContext.java
@@ -155,6 +155,9 @@ public class PortableContext implements Externalizable {
/** */
private boolean keepDeserialized;
+ /** Object schemas. */
+ private volatile Map<Integer, Object> schemas;
+
/**
* For {@link Externalizable}.
*/
@@ -854,6 +857,98 @@ public class PortableContext implements Externalizable {
}
/**
+ * Get schema for the given schema ID.
+ *
+ * @param schemaId Schema ID.
+ * @return Schema or {@code null} if there are no such schema.
+ */
+ @SuppressWarnings("unchecked")
+ @Nullable public PortableObjectSchema schema(int typeId, int schemaId) {
+ Map<Integer, Object> schemas0 = schemas;
+
+ if (schemas0 != null) {
+ Object typeSchemas = schemas0.get(typeId);
+
+ if (typeSchemas instanceof IgniteBiTuple) {
+ // The most common case goes first.
+ IgniteBiTuple<Integer, PortableObjectSchema> schema =
+ (IgniteBiTuple<Integer, PortableObjectSchema>)typeSchemas;
+
+ if (schema.get1() == schemaId)
+ return schema.get2();
+ }
+ else if (typeSchemas instanceof Map) {
+ Map<Integer, PortableObjectSchema> curSchemas = (Map<Integer, PortableObjectSchema>)typeSchemas;
+
+ return curSchemas.get(schemaId);
+ }
+ }
+
+ return null;
+ }
+
+ /**
+ * Add schema.
+ *
+ * @param schemaId Schema ID.
+ * @param newTypeSchema New schema.
+ */
+ @SuppressWarnings("unchecked")
+ public void addSchema(int typeId, int schemaId, PortableObjectSchema newTypeSchema) {
+ synchronized (this) {
+ if (schemas == null) {
+ // This is the very first schema recorded.
+ Map<Integer, Object> newSchemas = new HashMap<>();
+
+ newSchemas.put(typeId, new IgniteBiTuple<>(schemaId, newTypeSchema));
+
+ schemas = newSchemas;
+ }
+ else {
+ Object typeSchemas = schemas.get(typeId);
+
+ if (typeSchemas == null) {
+ // This is the very first object schema.
+ Map<Integer, Object> newSchemas = new HashMap<>(schemas);
+
+ newSchemas.put(typeId, new IgniteBiTuple<>(schemaId, newTypeSchema));
+
+ schemas = newSchemas;
+ }
+ else if (typeSchemas instanceof IgniteBiTuple) {
+ IgniteBiTuple<Integer, PortableObjectSchema> typeSchema =
+ (IgniteBiTuple<Integer, PortableObjectSchema>)typeSchemas;
+
+ if (typeSchema.get1() != schemaId) {
+ Map<Integer, PortableObjectSchema> newTypeSchemas = new HashMap();
+
+ newTypeSchemas.put(typeSchema.get1(), typeSchema.get2());
+ newTypeSchemas.put(schemaId, newTypeSchema);
+
+ Map<Integer, Object> newSchemas = new HashMap<>(schemas);
+
+ newSchemas.put(typeId, newTypeSchemas);
+
+ schemas = newSchemas;
+ }
+ }
+ else {
+ Map<Integer, PortableObjectSchema> newTypeSchemas =
+ new HashMap((Map<Integer, PortableObjectSchema>)typeSchemas);
+
+ newTypeSchemas.put(schemaId, newTypeSchema);
+
+ Map<Integer, Object> newSchemas = new HashMap<>(schemas);
+
+ newSchemas.put(typeId, newTypeSchemas);
+
+ schemas = newSchemas;
+ }
+ }
+ }
+ }
+
+ /**
* Returns instance of {@link OptimizedMarshaller}.
*
* @return Optimized marshaller.
http://git-wip-us.apache.org/repos/asf/ignite/blob/b85fa171/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableObjectEx.java
----------------------------------------------------------------------
diff --git a/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableObjectEx.java b/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableObjectEx.java
index fe4b628..ef9ee24 100644
--- a/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableObjectEx.java
+++ b/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableObjectEx.java
@@ -58,6 +58,15 @@ public abstract class PortableObjectEx implements PortableObject {
public abstract long offheapAddress();
/**
+ * Gets field value.
+ *
+ * @param fieldId Field ID.
+ * @return Field value.
+ * @throws PortableException In case of any other error.
+ */
+ @Nullable public abstract <F> F field(int fieldId) throws PortableException;
+
+ /**
* @param ctx Reader context.
* @param fieldName Field name.
* @return Field name.
http://git-wip-us.apache.org/repos/asf/ignite/blob/b85fa171/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableObjectImpl.java
----------------------------------------------------------------------
diff --git a/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableObjectImpl.java b/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableObjectImpl.java
index b156eda..f1868b1 100644
--- a/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableObjectImpl.java
+++ b/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableObjectImpl.java
@@ -235,7 +235,15 @@ public final class PortableObjectImpl extends PortableObjectEx implements Extern
@Nullable @Override public <F> F field(String fieldName) throws PortableException {
PortableReaderExImpl reader = new PortableReaderExImpl(ctx, arr, start, null);
- return (F)reader.unmarshal(fieldName);
+ return (F)reader.unmarshalField(fieldName);
+ }
+
+ /** {@inheritDoc} */
+ @SuppressWarnings("unchecked")
+ @Nullable @Override public <F> F field(int fieldId) throws PortableException {
+ PortableReaderExImpl reader = new PortableReaderExImpl(ctx, arr, start, null);
+
+ return (F)reader.unmarshalField(fieldId);
}
/** {@inheritDoc} */
@@ -247,7 +255,7 @@ public final class PortableObjectImpl extends PortableObjectEx implements Extern
null,
rCtx);
- return (F)reader.unmarshal(fieldName);
+ return (F)reader.unmarshalField(fieldName);
}
/** {@inheritDoc} */
http://git-wip-us.apache.org/repos/asf/ignite/blob/b85fa171/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableObjectOffheapImpl.java
----------------------------------------------------------------------
diff --git a/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableObjectOffheapImpl.java b/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableObjectOffheapImpl.java
index 0dc8612..0b3e3ea 100644
--- a/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableObjectOffheapImpl.java
+++ b/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableObjectOffheapImpl.java
@@ -136,7 +136,18 @@ public class PortableObjectOffheapImpl extends PortableObjectEx implements Exter
start,
null);
- return (F)reader.unmarshal(fieldName);
+ return (F)reader.unmarshalField(fieldName);
+ }
+
+ /** {@inheritDoc} */
+ @SuppressWarnings("unchecked")
+ @Nullable @Override public <F> F field(int fieldId) throws PortableException {
+ PortableReaderExImpl reader = new PortableReaderExImpl(ctx,
+ new PortableOffheapInputStream(ptr, size, false),
+ start,
+ null);
+
+ return (F)reader.unmarshalField(fieldId);
}
/** {@inheritDoc} */
@@ -148,7 +159,7 @@ public class PortableObjectOffheapImpl extends PortableObjectEx implements Exter
null,
rCtx);
- return (F)reader.unmarshal(fieldName);
+ return (F)reader.unmarshalField(fieldName);
}
/** {@inheritDoc} */
http://git-wip-us.apache.org/repos/asf/ignite/blob/b85fa171/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableObjectSchema.java
----------------------------------------------------------------------
diff --git a/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableObjectSchema.java b/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableObjectSchema.java
new file mode 100644
index 0000000..917ee73
--- /dev/null
+++ b/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableObjectSchema.java
@@ -0,0 +1,63 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.ignite.internal.portable;
+
+import java.util.Map;
+
+/**
+ * Portable object schema.
+ */
+public class PortableObjectSchema {
+ /** Schema ID. */
+ private final int schemaId;
+
+ /** Fields. */
+ private final Map<Integer, Integer> fields;
+
+ /**
+ * Constructor.
+ *
+ * @param schemaId Schema ID.
+ * @param fields Fields.
+ */
+ public PortableObjectSchema(int schemaId, Map<Integer, Integer> fields) {
+ this.schemaId = schemaId;
+ this.fields = fields;
+ }
+
+ /**
+ * Get schema ID.
+ *
+ * @return Schema ID.
+ */
+ public int schemaId() {
+ return schemaId;
+ }
+
+ /**
+ * Get field offset position.
+ *
+ * @param fieldId Field ID.
+ * @return Field offset position.
+ */
+ public int fieldOffsetPosition(int fieldId) {
+ Integer pos = fields.get(fieldId);
+
+ return pos != null ? pos : 0;
+ }
+}
http://git-wip-us.apache.org/repos/asf/ignite/blob/b85fa171/modules/core/src/main/java/org/apache/ignite/internal/portable/PortablePositionReadable.java
----------------------------------------------------------------------
diff --git a/modules/core/src/main/java/org/apache/ignite/internal/portable/PortablePositionReadable.java b/modules/core/src/main/java/org/apache/ignite/internal/portable/PortablePositionReadable.java
new file mode 100644
index 0000000..7e8d9d3
--- /dev/null
+++ b/modules/core/src/main/java/org/apache/ignite/internal/portable/PortablePositionReadable.java
@@ -0,0 +1,39 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.ignite.internal.portable;
+
+/**
+ * Interface allowing for positioned read.
+ */
+public interface PortablePositionReadable {
+ /**
+ * Read short at the given position.
+ *
+ * @param pos Position.
+ * @return Value.
+ */
+ public short readShortPositioned(int pos);
+
+ /**
+ * Read integer at the given position.
+ *
+ * @param pos Position.
+ * @return Value.
+ */
+ public int readIntPositioned(int pos);
+}
http://git-wip-us.apache.org/repos/asf/ignite/blob/b85fa171/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableReaderContext.java
----------------------------------------------------------------------
diff --git a/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableReaderContext.java b/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableReaderContext.java
index 2d4a1c3..51fc407 100644
--- a/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableReaderContext.java
+++ b/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableReaderContext.java
@@ -20,15 +20,16 @@ package org.apache.ignite.internal.portable;
import java.util.HashMap;
import java.util.Map;
import org.apache.ignite.internal.util.typedef.internal.S;
+import org.apache.ignite.lang.IgniteBiTuple;
import org.apache.ignite.portable.PortableObject;
import org.jetbrains.annotations.Nullable;
/**
- * Reader context.
- */
+* Reader context.
+*/
class PortableReaderContext {
/** */
- private Map<Integer, Object> oHandles;
+ private Object oHandles;
/** */
private Map<Integer, PortableObject> poHandles;
@@ -37,13 +38,24 @@ class PortableReaderContext {
* @param handle Handle.
* @param obj Object.
*/
+ @SuppressWarnings("unchecked")
void setObjectHandler(int handle, Object obj) {
assert obj != null;
if (oHandles == null)
- oHandles = new HashMap<>(3, 1.0f);
+ oHandles = new IgniteBiTuple(handle, obj);
+ else if (oHandles instanceof IgniteBiTuple) {
+ Map map = new HashMap(3, 1.0f);
+
+ IgniteBiTuple t = (IgniteBiTuple)oHandles;
+
+ map.put(t.getKey(), t.getValue());
+ map.put(handle, obj);
- oHandles.put(handle, obj);
+ oHandles = map;
+ }
+ else
+ ((Map)oHandles).put(handle, obj);
}
/**
@@ -64,7 +76,18 @@ class PortableReaderContext {
* @return Object.
*/
@Nullable Object getObjectByHandle(int handle) {
- return oHandles != null ? oHandles.get(handle) : null;
+ if (oHandles != null) {
+ if (oHandles instanceof IgniteBiTuple) {
+ IgniteBiTuple t = (IgniteBiTuple)oHandles;
+
+ if ((int)t.get1() == handle)
+ return t.get2();
+ }
+ else
+ return ((Map)oHandles).get(handle);
+ }
+
+ return null;
}
/**
@@ -79,4 +102,4 @@ class PortableReaderContext {
@Override public String toString() {
return S.toString(PortableReaderContext.class, this);
}
-}
\ No newline at end of file
+}