http://git-wip-us.apache.org/repos/asf/ignite/blob/58a665aa/modules/platform/src/main/cpp/core-test/src/portable_reader_writer_raw_test.cpp ---------------------------------------------------------------------- diff --git a/modules/platform/src/main/cpp/core-test/src/portable_reader_writer_raw_test.cpp b/modules/platform/src/main/cpp/core-test/src/portable_reader_writer_raw_test.cpp new file mode 100644 index 0000000..c3a98aa --- /dev/null +++ b/modules/platform/src/main/cpp/core-test/src/portable_reader_writer_raw_test.cpp @@ -0,0 +1,1532 @@ +/* + * 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. + */ + +#ifndef _MSC_VER + #define BOOST_TEST_DYN_LINK +#endif + +#include <boost/test/unit_test.hpp> + +#include "ignite/impl/interop/interop.h" +#include "ignite/portable/portable.h" + +#include "ignite/portable_test_defs.h" +#include "ignite/portable_test_utils.h" + +using namespace ignite; +using namespace ignite::impl::interop; +using namespace ignite::impl::portable; +using namespace ignite::portable; +using namespace ignite_test::core::portable; + +template<typename T> +void CheckRawPrimitive(T val) +{ + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writer(&out, NULL); + PortableRawWriter rawWriter(&writer); + + Write<T>(rawWriter, val); + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl reader(&in); + PortableRawReader rawReader(&reader); + + T readVal = Read<T>(rawReader); + + BOOST_REQUIRE(readVal == val); +} + +template<typename T> +void CheckRawPrimitiveArray(T dflt, T val1, T val2) +{ + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writer(&out, NULL); + PortableRawWriter rawWriter(&writer); + + InteropInputStream in(&mem); + PortableReaderImpl reader(&in); + PortableRawReader rawReader(&reader); + + // 1. Write NULL and see what happens. + WriteArray<T>(rawWriter, NULL, 0); + + out.Synchronize(); + in.Synchronize(); + + BOOST_REQUIRE(ReadArray<T>(rawReader, NULL, 0) == -1); + + in.Position(0); + BOOST_REQUIRE(ReadArray<T>(rawReader, NULL, 2) == -1); + + T arr1[2]; + arr1[0] = dflt; + arr1[1] = dflt; + + in.Position(0); + BOOST_REQUIRE(ReadArray<T>(rawReader, arr1, 1) == -1); + + BOOST_REQUIRE(arr1[0] == dflt); + BOOST_REQUIRE(arr1[1] == dflt); + + // 2. Write empty array. + T arr2[2]; + arr2[0] = val1; + arr2[1] = val2; + + out.Position(0); + in.Position(0); + + WriteArray<T>(rawWriter, arr2, 0); + + out.Synchronize(); + in.Synchronize(); + + BOOST_REQUIRE(ReadArray<T>(rawReader, NULL, 0) == 0); + + in.Position(0); + BOOST_REQUIRE(ReadArray<T>(rawReader, NULL, 2) == 0); + + in.Position(0); + BOOST_REQUIRE(ReadArray<T>(rawReader, arr1, 0) == 0); + BOOST_REQUIRE(arr1[0] == dflt); + BOOST_REQUIRE(arr1[1] == dflt); + + in.Position(0); + BOOST_REQUIRE(ReadArray<T>(rawReader, arr1, 2) == 0); + BOOST_REQUIRE(arr1[0] == dflt); + BOOST_REQUIRE(arr1[1] == dflt); + + // 3. Partial array write. + out.Position(0); + in.Position(0); + + WriteArray<T>(rawWriter, arr2, 1); + + out.Synchronize(); + in.Synchronize(); + + BOOST_REQUIRE(ReadArray<T>(rawReader, NULL, 0) == 1); + BOOST_REQUIRE(ReadArray<T>(rawReader, NULL, 2) == 1); + + BOOST_REQUIRE(ReadArray<T>(rawReader, arr1, 0) == 1); + BOOST_REQUIRE(arr1[0] == dflt); + BOOST_REQUIRE(arr1[1] == dflt); + + BOOST_REQUIRE(ReadArray<T>(rawReader, arr1, 1) == 1); + BOOST_REQUIRE(arr1[0] == val1); + BOOST_REQUIRE(arr1[1] == dflt); + arr1[0] = dflt; + + in.Position(0); + BOOST_REQUIRE(ReadArray<T>(rawReader, arr1, 2) == 1); + BOOST_REQUIRE(arr1[0] == val1); + BOOST_REQUIRE(arr1[1] == dflt); + arr1[0] = dflt; + + // 4. Full array write. + out.Position(0); + in.Position(0); + + WriteArray<T>(rawWriter, arr2, 2); + + out.Synchronize(); + in.Synchronize(); + + BOOST_REQUIRE(ReadArray<T>(rawReader, NULL, 0) == 2); + BOOST_REQUIRE(ReadArray<T>(rawReader, NULL, 2) == 2); + + BOOST_REQUIRE(ReadArray<T>(rawReader, arr1, 0) == 2); + BOOST_REQUIRE(arr1[0] == dflt); + BOOST_REQUIRE(arr1[1] == dflt); + + BOOST_REQUIRE(ReadArray<T>(rawReader, arr1, 1) == 2); + BOOST_REQUIRE(arr1[0] == dflt); + BOOST_REQUIRE(arr1[1] == dflt); + + BOOST_REQUIRE(ReadArray<T>(rawReader, arr1, 2) == 2); + BOOST_REQUIRE(arr1[0] == val1); + BOOST_REQUIRE(arr1[1] == val2); +} + +void CheckRawWritesRestricted(PortableRawWriter& writer) +{ + try + { + writer.WriteInt8(1); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + int8_t arr[1]; + + writer.WriteInt8Array(arr, 1); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + Guid val(1, 1); + + writer.WriteGuid(val); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + writer.WriteString("test"); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + writer.WriteArray<int8_t>(); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + writer.WriteCollection<int8_t>(); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + writer.WriteMap<int8_t, int8_t>(); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } +} + +void CheckRawReadsRestricted(PortableRawReader& reader) +{ + try + { + reader.ReadInt8(); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + int8_t arr[1]; + + reader.ReadInt8Array(arr, 1); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + reader.ReadGuid(); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + reader.ReadString(); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + reader.ReadArray<int8_t>(); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + reader.ReadCollection<int8_t>(); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + reader.ReadMap<int8_t, int8_t>(); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } +} + +void CheckRawCollectionEmpty(CollectionType* colType) +{ + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writer(&out, NULL); + PortableRawWriter rawWriter(&writer); + + PortableCollectionWriter<PortableInner> colWriter = colType ? + rawWriter.WriteCollection<PortableInner>(*colType) : rawWriter.WriteCollection<PortableInner>(); + + CheckRawWritesRestricted(rawWriter); + + colWriter.Close(); + + rawWriter.WriteInt8(1); + + try + { + colWriter.Write(1); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + colWriter.Close(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl reader(&in); + PortableRawReader rawReader(&reader); + + PortableCollectionReader<PortableInner> colReader = rawReader.ReadCollection<PortableInner>(); + + if (colType) + BOOST_REQUIRE(colReader.GetType() == *colType); + else + BOOST_REQUIRE(colReader.GetType() == IGNITE_COLLECTION_UNDEFINED); + + BOOST_REQUIRE(colReader.GetSize() == 0); + BOOST_REQUIRE(!colReader.HasNext()); + BOOST_REQUIRE(!colReader.IsNull()); + + try + { + colReader.GetNext(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(rawReader.ReadInt8() == 1); +} + +void CheckRawCollection(CollectionType* colType) +{ + PortableInner writeVal1 = PortableInner(1); + PortableInner writeVal2 = PortableInner(0); + PortableInner writeVal3 = PortableInner(2); + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writer(&out, NULL); + PortableRawWriter rawWriter(&writer); + + PortableCollectionWriter<PortableInner> colWriter = colType ? + rawWriter.WriteCollection<PortableInner>(*colType) : rawWriter.WriteCollection<PortableInner>(); + + colWriter.Write(writeVal1); + colWriter.Write(writeVal2); + colWriter.Write(writeVal3); + + CheckRawWritesRestricted(rawWriter); + + colWriter.Close(); + + rawWriter.WriteInt8(1); + + try + { + colWriter.Write(1); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + colWriter.Close(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl reader(&in); + PortableRawReader rawReader(&reader); + + PortableCollectionReader<PortableInner> colReader = rawReader.ReadCollection<PortableInner>(); + + CheckRawReadsRestricted(rawReader); + + if (colType) + BOOST_REQUIRE(colReader.GetType() == *colType); + else + BOOST_REQUIRE(colReader.GetType() == IGNITE_COLLECTION_UNDEFINED); + + BOOST_REQUIRE(colReader.GetSize() == 3); + BOOST_REQUIRE(!colReader.IsNull()); + + BOOST_REQUIRE(colReader.HasNext()); + BOOST_REQUIRE(colReader.GetNext().GetValue() == writeVal1.GetValue()); + + BOOST_REQUIRE(colReader.HasNext()); + BOOST_REQUIRE(colReader.GetNext().GetValue() == writeVal2.GetValue()); + + BOOST_REQUIRE(colReader.HasNext()); + BOOST_REQUIRE(colReader.GetNext().GetValue() == writeVal3.GetValue()); + + BOOST_REQUIRE(!colReader.HasNext()); + + try + { + colReader.GetNext(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(rawReader.ReadInt8() == 1); +} + +void CheckRawMapEmpty(MapType* mapType) +{ + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writer(&out, NULL); + PortableRawWriter rawWriter(&writer); + + PortableMapWriter<int8_t, PortableInner> mapWriter = mapType ? + rawWriter.WriteMap<int8_t, PortableInner>(*mapType) : rawWriter.WriteMap<int8_t, PortableInner>(); + + CheckRawWritesRestricted(rawWriter); + + mapWriter.Close(); + + rawWriter.WriteInt8(1); + + try + { + mapWriter.Write(1, PortableInner(1)); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + mapWriter.Close(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl reader(&in); + PortableRawReader rawReader(&reader); + + PortableMapReader<int8_t, PortableInner> mapReader = rawReader.ReadMap<int8_t, PortableInner>(); + + if (mapType) + BOOST_REQUIRE(mapReader.GetType() == *mapType); + else + BOOST_REQUIRE(mapReader.GetType() == IGNITE_MAP_UNDEFINED); + + BOOST_REQUIRE(mapReader.GetSize() == 0); + BOOST_REQUIRE(!mapReader.HasNext()); + BOOST_REQUIRE(!mapReader.IsNull()); + + try + { + int8_t key; + PortableInner val; + + mapReader.GetNext(&key, &val); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(rawReader.ReadInt8() == 1); +} + +void CheckRawMap(MapType* mapType) +{ + PortableInner writeVal1 = PortableInner(1); + PortableInner writeVal2 = PortableInner(0); + PortableInner writeVal3 = PortableInner(2); + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writer(&out, NULL); + PortableRawWriter rawWriter(&writer); + + PortableMapWriter<int8_t, PortableInner> mapWriter = mapType ? + rawWriter.WriteMap<int8_t, PortableInner>(*mapType) : rawWriter.WriteMap<int8_t, PortableInner>(); + + mapWriter.Write(1, writeVal1); + mapWriter.Write(2, writeVal2); + mapWriter.Write(3, writeVal3); + + CheckRawWritesRestricted(rawWriter); + + mapWriter.Close(); + + rawWriter.WriteInt8(1); + + try + { + mapWriter.Write(4, PortableInner(4)); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + mapWriter.Close(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl reader(&in); + PortableRawReader rawReader(&reader); + + PortableMapReader<int8_t, PortableInner> mapReader = rawReader.ReadMap<int8_t, PortableInner>(); + + CheckRawReadsRestricted(rawReader); + + if (mapType) + BOOST_REQUIRE(mapReader.GetType() == *mapType); + else + BOOST_REQUIRE(mapReader.GetType() == IGNITE_MAP_UNDEFINED); + + BOOST_REQUIRE(mapReader.GetSize() == 3); + BOOST_REQUIRE(!mapReader.IsNull()); + + int8_t key; + PortableInner val; + + BOOST_REQUIRE(mapReader.HasNext()); + + mapReader.GetNext(&key, &val); + BOOST_REQUIRE(key == 1); + BOOST_REQUIRE(val.GetValue() == writeVal1.GetValue()); + + mapReader.GetNext(&key, &val); + BOOST_REQUIRE(key == 2); + BOOST_REQUIRE(val.GetValue() == writeVal2.GetValue()); + + mapReader.GetNext(&key, &val); + BOOST_REQUIRE(key == 3); + BOOST_REQUIRE(val.GetValue() == writeVal3.GetValue()); + + BOOST_REQUIRE(!mapReader.HasNext()); + + try + { + mapReader.GetNext(&key, &val); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(rawReader.ReadInt8() == 1); +} + +BOOST_AUTO_TEST_SUITE(PortableReaderWriterRawTestSuite) + +BOOST_AUTO_TEST_CASE(TestPrimitiveInt8) +{ + CheckRawPrimitive<int8_t>(1); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveBool) +{ + CheckRawPrimitive<bool>(true); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveInt16) +{ + CheckRawPrimitive<int16_t>(1); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveUInt16) +{ + CheckRawPrimitive<uint16_t>(1); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveInt32) +{ + CheckRawPrimitive<int32_t>(1); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveInt64) +{ + CheckRawPrimitive<int64_t>(1); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveFloat) +{ + CheckRawPrimitive<float>(1.1f); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveDouble) +{ + CheckRawPrimitive<double>(1.1); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveGuid) +{ + Guid val(1, 2); + + CheckRawPrimitive<Guid>(val); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveArrayInt8) +{ + CheckRawPrimitiveArray<int8_t>(1, 2, 3); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveArrayBool) +{ + CheckRawPrimitiveArray<bool>(false, true, false); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveArrayInt16) +{ + CheckRawPrimitiveArray<int16_t>(1, 2, 3); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveArrayUInt16) +{ + CheckRawPrimitiveArray<uint16_t>(1, 2, 3); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveArrayInt32) +{ + CheckRawPrimitiveArray<int32_t>(1, 2, 3); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveArrayInt64) +{ + CheckRawPrimitiveArray<int64_t>(1, 2, 3); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveArrayFloat) +{ + CheckRawPrimitiveArray<float>(1.1f, 2.2f, 3.3f); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveArrayDouble) +{ + CheckRawPrimitiveArray<double>(1.1, 2.2, 3.3); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveArrayGuid) +{ + Guid dflt(1, 2); + Guid val1(3, 4); + Guid val2(5, 6); + + CheckRawPrimitiveArray<Guid>(dflt, val1, val2); +} + +BOOST_AUTO_TEST_CASE(TestGuidNull) +{ + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writer(&out, NULL); + PortableRawWriter rawWriter(&writer); + + rawWriter.WriteNull(); + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl reader(&in); + PortableRawReader rawReader(&reader); + + Guid expVal; + Guid actualVal = rawReader.ReadGuid(); + + BOOST_REQUIRE(actualVal == expVal); +} + +BOOST_AUTO_TEST_CASE(TestString) { + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writer(&out, NULL); + PortableRawWriter rawWriter(&writer); + + const char* writeVal1 = "testtest"; + const char* writeVal2 = "test"; + std::string writeVal3 = writeVal1; + + rawWriter.WriteString(writeVal1); + rawWriter.WriteString(writeVal1, 4); + rawWriter.WriteString(writeVal3); + rawWriter.WriteString(NULL); + rawWriter.WriteString(NULL, 4); + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl reader(&in); + PortableRawReader rawReader(&reader); + + char readVal1[9]; + char readVal2[5]; + + BOOST_REQUIRE(rawReader.ReadString(NULL, 0) == 8); + BOOST_REQUIRE(rawReader.ReadString(NULL, 8) == 8); + BOOST_REQUIRE(rawReader.ReadString(readVal1, 0) == 8); + BOOST_REQUIRE(rawReader.ReadString(readVal1, 4) == 8); + + BOOST_REQUIRE(rawReader.ReadString(readVal1, 9) == 8); + std::string writeVal1Str = writeVal1; + std::string readVal1Str = readVal1; + BOOST_REQUIRE(readVal1Str.compare(writeVal1Str) == 0); + + BOOST_REQUIRE(rawReader.ReadString(readVal2, 5) == 4); + std::string writeVal2Str = writeVal2; + std::string readVal2Str = readVal2; + BOOST_REQUIRE(readVal2Str.compare(writeVal2Str) == 0); + + std::string readVal3 = rawReader.ReadString(); + BOOST_REQUIRE(readVal3.compare(writeVal3) == 0); + + BOOST_REQUIRE(rawReader.ReadString(readVal1, 9) == -1); + BOOST_REQUIRE(rawReader.ReadString(readVal1, 9) == -1); +} + +BOOST_AUTO_TEST_CASE(TestStringArrayNull) +{ + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writer(&out, NULL); + PortableRawWriter rawWriter(&writer); + + rawWriter.WriteNull(); + rawWriter.WriteInt8(1); + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl reader(&in); + PortableRawReader rawReader(&reader); + + PortableStringArrayReader arrReader = rawReader.ReadStringArray(); + + BOOST_REQUIRE(arrReader.GetSize() == -1); + BOOST_REQUIRE(!arrReader.HasNext()); + BOOST_REQUIRE(arrReader.IsNull()); + + try + { + char res[100]; + + arrReader.GetNext(res, 100); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + arrReader.GetNext(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(rawReader.ReadInt8() == 1); +} + +BOOST_AUTO_TEST_CASE(TestStringArrayEmpty) +{ + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writer(&out, NULL); + PortableRawWriter rawWriter(&writer); + + PortableStringArrayWriter arrWriter = rawWriter.WriteStringArray(); + + CheckRawWritesRestricted(rawWriter); + + arrWriter.Close(); + + rawWriter.WriteInt8(1); + + try + { + const char* val = "test"; + + arrWriter.Write(val, 4); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + const char* val = "test"; + + arrWriter.Write(val); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + std::string val = "test"; + + arrWriter.Write(val); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + arrWriter.Close(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl reader(&in); + PortableRawReader rawReader(&reader); + + PortableStringArrayReader arrReader = rawReader.ReadStringArray(); + + BOOST_REQUIRE(arrReader.GetSize() == 0); + BOOST_REQUIRE(!arrReader.HasNext()); + BOOST_REQUIRE(!arrReader.IsNull()); + + try + { + char res[100]; + + arrReader.GetNext(res, 100); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + arrReader.GetNext(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(rawReader.ReadInt8() == 1); +} + +BOOST_AUTO_TEST_CASE(TestStringArray) +{ + const char* writeVal1 = "testtest"; + const char* writeVal2 = "test"; + std::string writeVal3 = "test2"; + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writer(&out, NULL); + PortableRawWriter rawWriter(&writer); + + PortableStringArrayWriter arrWriter = rawWriter.WriteStringArray(); + + arrWriter.Write(writeVal1); + arrWriter.Write(writeVal1, 4); + arrWriter.Write(NULL); // NULL value. + arrWriter.Write(NULL, 100); // NULL value again. + arrWriter.Write(writeVal3); + + CheckRawWritesRestricted(rawWriter); + + arrWriter.Close(); + + rawWriter.WriteInt8(1); + + try + { + const char* val = "test"; + + arrWriter.Write(val, 4); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + const char* val = "test"; + + arrWriter.Write(val); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + std::string val = "test"; + + arrWriter.Write(val); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + arrWriter.Close(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl reader(&in); + PortableRawReader rawReader(&reader); + + PortableStringArrayReader arrReader = rawReader.ReadStringArray(); + + CheckRawReadsRestricted(rawReader); + + BOOST_REQUIRE(arrReader.GetSize() == 5); + BOOST_REQUIRE(!arrReader.IsNull()); + + // 1. Read first value. + BOOST_REQUIRE(arrReader.HasNext()); + + char readVal1[9]; + + BOOST_REQUIRE(arrReader.GetNext(NULL, 0) == 8); + BOOST_REQUIRE(arrReader.GetNext(NULL, 8) == 8); + BOOST_REQUIRE(arrReader.GetNext(readVal1, 0) == 8); + BOOST_REQUIRE(arrReader.GetNext(readVal1, 4) == 8); + + BOOST_REQUIRE(arrReader.GetNext(readVal1, 9) == 8); + std::string writeVal1Str = writeVal1; + std::string readVal1Str = readVal1; + BOOST_REQUIRE(readVal1Str.compare(writeVal1Str) == 0); + + // 2. Read second value. + BOOST_REQUIRE(arrReader.HasNext()); + + char readVal2[5]; + + BOOST_REQUIRE(arrReader.GetNext(readVal2, 5) == 4); + std::string writeVal2Str = writeVal2; + std::string readVal2Str = readVal2; + BOOST_REQUIRE(readVal2Str.compare(writeVal2Str) == 0); + + // 3. Read NULL. + BOOST_REQUIRE(arrReader.HasNext()); + + BOOST_REQUIRE(arrReader.GetNext(readVal1, 4) == -1); + readVal1Str = readVal1; + BOOST_REQUIRE(readVal1Str.compare(writeVal1Str) == 0); + + // 4. Read NULL again, this time through another method. + BOOST_REQUIRE(arrReader.HasNext()); + + std::string readNullVal = arrReader.GetNext(); + + BOOST_REQUIRE(readNullVal.length() == 0); + + // 5. Read third value. + BOOST_REQUIRE(arrReader.HasNext()); + + std::string readVal3 = arrReader.GetNext(); + BOOST_REQUIRE(readVal3.compare(writeVal3) == 0); + + BOOST_REQUIRE(!arrReader.HasNext()); + + try + { + char res[100]; + + arrReader.GetNext(res, 100); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + arrReader.GetNext(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(rawReader.ReadInt8() == 1); +} + +BOOST_AUTO_TEST_CASE(TestObject) +{ + PortableInner writeVal1(1); + PortableInner writeVal2(0); + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writer(&out, NULL); + PortableRawWriter rawWriter(&writer); + + rawWriter.WriteObject(writeVal1); + rawWriter.WriteObject(writeVal2); + rawWriter.WriteNull(); + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl reader(&in); + PortableRawReader rawReader(&reader); + + PortableInner readVal1 = rawReader.ReadObject<PortableInner>(); + BOOST_REQUIRE(writeVal1.GetValue() == readVal1.GetValue()); + + PortableInner readVal2 = rawReader.ReadObject<PortableInner>(); + BOOST_REQUIRE(writeVal2.GetValue() == readVal2.GetValue()); + + PortableInner readVal3 = rawReader.ReadObject<PortableInner>(); + BOOST_REQUIRE(0 == readVal3.GetValue()); +} + +BOOST_AUTO_TEST_CASE(TestNestedObject) +{ + PortableOuter writeVal1(1, 2); + PortableOuter writeVal2(0, 0); + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writer(&out, NULL); + PortableRawWriter rawWriter(&writer); + + rawWriter.WriteObject(writeVal1); + rawWriter.WriteObject(writeVal2); + rawWriter.WriteNull(); + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl reader(&in); + PortableRawReader rawReader(&reader); + + PortableOuter readVal1 = rawReader.ReadObject<PortableOuter>(); + BOOST_REQUIRE(writeVal1.GetValue() == readVal1.GetValue()); + BOOST_REQUIRE(writeVal1.GetInner().GetValue() == readVal1.GetInner().GetValue()); + + PortableOuter readVal2 = rawReader.ReadObject<PortableOuter>(); + BOOST_REQUIRE(writeVal2.GetValue() == readVal2.GetValue()); + BOOST_REQUIRE(writeVal2.GetInner().GetValue() == readVal2.GetInner().GetValue()); + + PortableOuter readVal3 = rawReader.ReadObject<PortableOuter>(); + BOOST_REQUIRE(0 == readVal3.GetValue()); + BOOST_REQUIRE(0 == readVal3.GetInner().GetValue()); +} + +BOOST_AUTO_TEST_CASE(TestArrayNull) +{ + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writer(&out, NULL); + PortableRawWriter rawWriter(&writer); + + rawWriter.WriteNull(); + rawWriter.WriteInt8(1); + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl reader(&in); + PortableRawReader rawReader(&reader); + + PortableArrayReader<PortableInner> arrReader = rawReader.ReadArray<PortableInner>(); + + BOOST_REQUIRE(arrReader.GetSize() == -1); + BOOST_REQUIRE(!arrReader.HasNext()); + BOOST_REQUIRE(arrReader.IsNull()); + + try + { + arrReader.GetNext(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(rawReader.ReadInt8() == 1); +} + +BOOST_AUTO_TEST_CASE(TestArrayEmpty) +{ + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writer(&out, NULL); + PortableRawWriter rawWriter(&writer); + + PortableArrayWriter<PortableInner> arrWriter = rawWriter.WriteArray<PortableInner>(); + + CheckRawWritesRestricted(rawWriter); + + arrWriter.Close(); + + rawWriter.WriteInt8(1); + + try + { + arrWriter.Write(1); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + arrWriter.Close(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl reader(&in); + PortableRawReader rawReader(&reader); + + PortableArrayReader<PortableInner> arrReader = rawReader.ReadArray<PortableInner>(); + + BOOST_REQUIRE(arrReader.GetSize() == 0); + BOOST_REQUIRE(!arrReader.HasNext()); + BOOST_REQUIRE(!arrReader.IsNull()); + + try + { + arrReader.GetNext(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(rawReader.ReadInt8() == 1); +} + +BOOST_AUTO_TEST_CASE(TestArray) +{ + PortableInner writeVal1 = PortableInner(1); + PortableInner writeVal2 = PortableInner(0); + PortableInner writeVal3 = PortableInner(2); + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writer(&out, NULL); + PortableRawWriter rawWriter(&writer); + + PortableArrayWriter<PortableInner> arrWriter = rawWriter.WriteArray<PortableInner>(); + + arrWriter.Write(writeVal1); + arrWriter.Write(writeVal2); + arrWriter.Write(writeVal3); + + CheckRawWritesRestricted(rawWriter); + + arrWriter.Close(); + + rawWriter.WriteInt8(1); + + try + { + arrWriter.Write(1); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + arrWriter.Close(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl reader(&in); + PortableRawReader rawReader(&reader); + + PortableArrayReader<PortableInner> arrReader = rawReader.ReadArray<PortableInner>(); + + CheckRawReadsRestricted(rawReader); + + BOOST_REQUIRE(arrReader.GetSize() == 3); + BOOST_REQUIRE(!arrReader.IsNull()); + + BOOST_REQUIRE(arrReader.HasNext()); + BOOST_REQUIRE(arrReader.GetNext().GetValue() == writeVal1.GetValue()); + + BOOST_REQUIRE(arrReader.HasNext()); + BOOST_REQUIRE(arrReader.GetNext().GetValue() == writeVal2.GetValue()); + + BOOST_REQUIRE(arrReader.HasNext()); + BOOST_REQUIRE(arrReader.GetNext().GetValue() == writeVal3.GetValue()); + + BOOST_REQUIRE(!arrReader.HasNext()); + + try + { + arrReader.GetNext(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(rawReader.ReadInt8() == 1); +} + +BOOST_AUTO_TEST_CASE(TestCollectionNull) +{ + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writer(&out, NULL); + PortableRawWriter rawWriter(&writer); + + rawWriter.WriteNull(); + rawWriter.WriteInt8(1); + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl reader(&in); + PortableRawReader rawReader(&reader); + + PortableCollectionReader<PortableInner> colReader = rawReader.ReadCollection<PortableInner>(); + + BOOST_REQUIRE(colReader.GetType() == IGNITE_COLLECTION_UNDEFINED); + BOOST_REQUIRE(colReader.GetSize() == -1); + BOOST_REQUIRE(!colReader.HasNext()); + BOOST_REQUIRE(colReader.IsNull()); + + try + { + colReader.GetNext(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(rawReader.ReadInt8() == 1); +} + +BOOST_AUTO_TEST_CASE(TestCollectionEmpty) +{ + CheckRawCollectionEmpty(NULL); +} + +BOOST_AUTO_TEST_CASE(TestCollectionEmptyTyped) +{ + CollectionType typ = IGNITE_COLLECTION_CONCURRENT_SKIP_LIST_SET; + + CheckRawCollectionEmpty(&typ); +} + +BOOST_AUTO_TEST_CASE(TestCollection) +{ + CheckRawCollection(NULL); +} + +BOOST_AUTO_TEST_CASE(testCollectionTyped) +{ + CollectionType typ = IGNITE_COLLECTION_CONCURRENT_SKIP_LIST_SET; + + CheckRawCollection(&typ); +} + +BOOST_AUTO_TEST_CASE(TestMapNull) +{ + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writer(&out, NULL); + PortableRawWriter rawWriter(&writer); + + rawWriter.WriteNull(); + rawWriter.WriteInt8(1); + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl reader(&in); + PortableRawReader rawReader(&reader); + + PortableMapReader<int8_t, PortableInner> mapReader = rawReader.ReadMap<int8_t, PortableInner>(); + + BOOST_REQUIRE(mapReader.GetType() == IGNITE_MAP_UNDEFINED); + BOOST_REQUIRE(mapReader.GetSize() == -1); + BOOST_REQUIRE(!mapReader.HasNext()); + BOOST_REQUIRE(mapReader.IsNull()); + + try + { + int8_t key; + PortableInner val; + + mapReader.GetNext(&key, &val); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(rawReader.ReadInt8() == 1); +} + +BOOST_AUTO_TEST_CASE(TestMapEmpty) +{ + CheckRawMapEmpty(NULL); +} + +BOOST_AUTO_TEST_CASE(TestMapEmptyTyped) +{ + MapType typ = IGNITE_MAP_CONCURRENT_HASH_MAP; + + CheckRawMapEmpty(&typ); +} + +BOOST_AUTO_TEST_CASE(TestMap) +{ + CheckRawMap(NULL); +} + +BOOST_AUTO_TEST_CASE(TestMapTyped) +{ + MapType typ = IGNITE_MAP_CONCURRENT_HASH_MAP; + + CheckRawMap(&typ); +} + +BOOST_AUTO_TEST_SUITE_END() \ No newline at end of file
http://git-wip-us.apache.org/repos/asf/ignite/blob/58a665aa/modules/platform/src/main/cpp/core-test/src/portable_reader_writer_test.cpp ---------------------------------------------------------------------- diff --git a/modules/platform/src/main/cpp/core-test/src/portable_reader_writer_test.cpp b/modules/platform/src/main/cpp/core-test/src/portable_reader_writer_test.cpp new file mode 100644 index 0000000..aff929b --- /dev/null +++ b/modules/platform/src/main/cpp/core-test/src/portable_reader_writer_test.cpp @@ -0,0 +1,1951 @@ +/* + * 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. + */ + +#ifndef _MSC_VER + #define BOOST_TEST_DYN_LINK +#endif + +#include <boost/test/unit_test.hpp> + +#include "ignite/impl/interop/interop.h" +#include "ignite/portable/portable.h" + +#include "ignite/portable_test_defs.h" +#include "ignite/portable_test_utils.h" + +using namespace ignite; +using namespace ignite::impl::interop; +using namespace ignite::impl::portable; +using namespace ignite::portable; +using namespace ignite_test::core::portable; + +template<typename T> +void CheckPrimitive(T val) +{ + TemplatedPortableIdResolver<PortableDummy> idRslvr; + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + out.Position(18); + + PortableWriterImpl writerImpl(&out, &idRslvr, NULL, NULL); + PortableWriter writer(&writerImpl); + + try + { + Write<T>(writer, NULL, val); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + Write<T>(writer, "test", val); + + out.Synchronize(); + + InteropInputStream in(&mem); + + in.Position(18); + + PortableReaderImpl readerImpl(&in, &idRslvr, 0, true, idRslvr.GetTypeId(), 0, 100, 100); + PortableReader reader(&readerImpl); + + try + { + Read<T>(reader, NULL); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + T readVal = Read<T>(reader, "test"); + + BOOST_REQUIRE(readVal == val); +} + +template<typename T> +void CheckPrimitiveArray(T dflt, T val1, T val2) +{ + const char* fieldName = "test"; + + TemplatedPortableIdResolver<PortableDummy> idRslvr; + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writerImpl(&out, &idRslvr, NULL, NULL); + PortableWriter writer(&writerImpl); + + InteropInputStream in(&mem); + PortableReaderImpl readerImpl(&in, &idRslvr, 0, true, idRslvr.GetTypeId(), 0, 100, 100); + PortableReader reader(&readerImpl); + + out.Position(18); + + try + { + T nullFieldArr[2]; + + nullFieldArr[0] = val1; + nullFieldArr[1] = val2; + + WriteArray<T>(writer, NULL, nullFieldArr, 2); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + // 1. Write NULL and see what happens. + WriteArray<T>(writer, fieldName, NULL, 0); + + out.Synchronize(); + in.Synchronize(); + + in.Position(18); + BOOST_REQUIRE(ReadArray<T>(reader, fieldName, NULL, 0) == -1); + + in.Position(18); + BOOST_REQUIRE(ReadArray<T>(reader, fieldName, NULL, 2) == -1); + + T arr1[2]; + arr1[0] = dflt; + arr1[1] = dflt; + + in.Position(18); + BOOST_REQUIRE(ReadArray<T>(reader, fieldName, arr1, 1) == -1); + + BOOST_REQUIRE(arr1[0] == dflt); + BOOST_REQUIRE(arr1[1] == dflt); + + // 2. Write empty array. + T arr2[2]; + arr2[0] = val1; + arr2[1] = val2; + + out.Position(18); + + WriteArray<T>(writer, fieldName, arr2, 0); + + out.Synchronize(); + in.Synchronize(); + + in.Position(18); + BOOST_REQUIRE(ReadArray<T>(reader, fieldName, NULL, 0) == 0); + + in.Position(18); + BOOST_REQUIRE(ReadArray<T>(reader, fieldName, NULL, 2) == 0); + + in.Position(18); + BOOST_REQUIRE(ReadArray<T>(reader, fieldName, arr1, 0) == 0); + BOOST_REQUIRE(arr1[0] == dflt); + BOOST_REQUIRE(arr1[1] == dflt); + + in.Position(18); + BOOST_REQUIRE(ReadArray<T>(reader, fieldName, arr1, 2) == 0); + BOOST_REQUIRE(arr1[0] == dflt); + BOOST_REQUIRE(arr1[1] == dflt); + + // 3. Partial array write. + out.Position(18); + + WriteArray<T>(writer, fieldName, arr2, 1); + + out.Synchronize(); + in.Synchronize(); + + in.Position(18); + BOOST_REQUIRE(ReadArray<T>(reader, fieldName, NULL, 0) == 1); + BOOST_REQUIRE(ReadArray<T>(reader, fieldName, NULL, 2) == 1); + BOOST_REQUIRE(ReadArray<T>(reader, fieldName, arr1, 0) == 1); + BOOST_REQUIRE(arr1[0] == dflt); + BOOST_REQUIRE(arr1[1] == dflt); + + in.Position(18); + BOOST_REQUIRE(ReadArray<T>(reader, fieldName, arr1, 1) == 1); + BOOST_REQUIRE(arr1[0] == val1); + BOOST_REQUIRE(arr1[1] == dflt); + arr1[0] = dflt; + + in.Position(18); + BOOST_REQUIRE(ReadArray<T>(reader, fieldName, arr1, 2) == 1); + BOOST_REQUIRE(arr1[0] == val1); + BOOST_REQUIRE(arr1[1] == dflt); + arr1[0] = dflt; + + // 4. Full array write. + out.Position(18); + + WriteArray<T>(writer, fieldName, arr2, 2); + + out.Synchronize(); + in.Synchronize(); + + in.Position(18); + BOOST_REQUIRE(ReadArray<T>(reader, fieldName, NULL, 0) == 2); + + in.Position(18); + BOOST_REQUIRE(ReadArray<T>(reader, fieldName, NULL, 2) == 2); + + try + { + ReadArray<T>(reader, NULL, arr1, 2); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(ReadArray<T>(reader, fieldName, arr1, 0) == 2); + BOOST_REQUIRE(arr1[0] == dflt); + BOOST_REQUIRE(arr1[1] == dflt); + + BOOST_REQUIRE(ReadArray<T>(reader, fieldName, arr1, 1) == 2); + BOOST_REQUIRE(arr1[0] == dflt); + BOOST_REQUIRE(arr1[1] == dflt); + + BOOST_REQUIRE(ReadArray<T>(reader, fieldName, arr1, 2) == 2); + BOOST_REQUIRE(arr1[0] == val1); + BOOST_REQUIRE(arr1[1] == val2); +} + +void CheckWritesRestricted(PortableWriter& writer) +{ + try + { + writer.WriteInt8("field", 1); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + int8_t arr[1]; + + writer.WriteInt8Array("field", arr, 1); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + Guid val(1, 1); + + writer.WriteGuid("field", val); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + writer.WriteString("field", "test"); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + writer.WriteArray<int8_t>("field"); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + writer.WriteCollection<int8_t>("field"); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + writer.WriteMap<int8_t, int8_t>("field"); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } +} + +void CheckReadsRestricted(PortableReader& reader) +{ + try + { + reader.ReadInt8("field"); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + int8_t arr[1]; + + reader.ReadInt8Array("field", arr, 1); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + reader.ReadGuid("field"); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + reader.ReadString("field"); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + reader.ReadArray<int8_t>("field"); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + reader.ReadCollection<int8_t>("field"); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + reader.ReadMap<int8_t, int8_t>("field"); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } +} + +void CheckCollectionEmpty(CollectionType* colType) +{ + TemplatedPortableIdResolver<PortableDummy> idRslvr; + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writerImpl(&out, &idRslvr, NULL, NULL); + PortableWriter writer(&writerImpl); + + out.Position(18); + + PortableCollectionWriter<PortableInner> colWriter = colType ? + writer.WriteCollection<PortableInner>("field1", *colType) : writer.WriteCollection<PortableInner>("field1"); + + CheckWritesRestricted(writer); + + colWriter.Close(); + + writer.WriteInt8("field2", 1); + + try + { + colWriter.Write(1); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + colWriter.Close(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl readerImpl(&in, &idRslvr, 0, true, idRslvr.GetTypeId(), 0, 1000, 1000); + PortableReader reader(&readerImpl); + + in.Position(18); + + PortableCollectionReader<PortableInner> colReader = reader.ReadCollection<PortableInner>("field1"); + + if (colType) + BOOST_REQUIRE(colReader.GetType() == *colType); + else + BOOST_REQUIRE(colReader.GetType() == IGNITE_COLLECTION_UNDEFINED); + + BOOST_REQUIRE(colReader.GetSize() == 0); + BOOST_REQUIRE(!colReader.HasNext()); + BOOST_REQUIRE(!colReader.IsNull()); + + try + { + colReader.GetNext(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(reader.ReadInt8("field2") == 1); +} + +void CheckCollection(CollectionType* colType) +{ + PortableInner writeVal1 = PortableInner(1); + PortableInner writeVal2 = PortableInner(0); + PortableInner writeVal3 = PortableInner(2); + + TemplatedPortableIdResolver<PortableDummy> idRslvr; + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writerImpl(&out, &idRslvr, NULL, NULL); + PortableWriter writer(&writerImpl); + + out.Position(18); + + PortableCollectionWriter<PortableInner> colWriter = colType ? + writer.WriteCollection<PortableInner>("field1", *colType) : writer.WriteCollection<PortableInner>("field1"); + + colWriter.Write(writeVal1); + colWriter.Write(writeVal2); + colWriter.Write(writeVal3); + + CheckWritesRestricted(writer); + + colWriter.Close(); + + writer.WriteInt8("field2", 1); + + try + { + colWriter.Write(1); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + colWriter.Close(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl readerImpl(&in, &idRslvr, 0, true, idRslvr.GetTypeId(), 0, 1000, 1000); + PortableReader reader(&readerImpl); + + in.Position(18); + + PortableCollectionReader<PortableInner> colReader = reader.ReadCollection<PortableInner>("field1"); + + CheckReadsRestricted(reader); + + if (colType) + BOOST_REQUIRE(colReader.GetType() == *colType); + else + BOOST_REQUIRE(colReader.GetType() == IGNITE_COLLECTION_UNDEFINED); + + BOOST_REQUIRE(colReader.GetSize() == 3); + BOOST_REQUIRE(!colReader.IsNull()); + + BOOST_REQUIRE(colReader.HasNext()); + BOOST_REQUIRE(colReader.GetNext().GetValue() == writeVal1.GetValue()); + + BOOST_REQUIRE(colReader.HasNext()); + BOOST_REQUIRE(colReader.GetNext().GetValue() == writeVal2.GetValue()); + + BOOST_REQUIRE(colReader.HasNext()); + BOOST_REQUIRE(colReader.GetNext().GetValue() == writeVal3.GetValue()); + + BOOST_REQUIRE(!colReader.HasNext()); + + try + { + colReader.GetNext(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(reader.ReadInt8("field2") == 1); +} + +void CheckMapEmpty(MapType* mapType) +{ + TemplatedPortableIdResolver<PortableDummy> idRslvr; + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writerImpl(&out, &idRslvr, NULL, NULL); + PortableWriter writer(&writerImpl); + + out.Position(18); + + PortableMapWriter<int8_t, PortableInner> mapWriter = mapType ? + writer.WriteMap<int8_t, PortableInner>("field1", *mapType) : writer.WriteMap<int8_t, PortableInner>("field1"); + + CheckWritesRestricted(writer); + + mapWriter.Close(); + + writer.WriteInt8("field2", 1); + + try + { + mapWriter.Write(1, PortableInner(1)); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + mapWriter.Close(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl readerImpl(&in, &idRslvr, 0, true, idRslvr.GetTypeId(), 0, 1000, 1000); + PortableReader reader(&readerImpl); + + in.Position(18); + + PortableMapReader<int8_t, PortableInner> mapReader = reader.ReadMap<int8_t, PortableInner>("field1"); + + if (mapType) + BOOST_REQUIRE(mapReader.GetType() == *mapType); + else + BOOST_REQUIRE(mapReader.GetType() == IGNITE_MAP_UNDEFINED); + + BOOST_REQUIRE(mapReader.GetSize() == 0); + BOOST_REQUIRE(!mapReader.HasNext()); + BOOST_REQUIRE(!mapReader.IsNull()); + + try + { + int8_t key; + PortableInner val; + + mapReader.GetNext(&key, &val); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(reader.ReadInt8("field2") == 1); +} + +void CheckMap(MapType* mapType) +{ + PortableInner writeVal1 = PortableInner(1); + PortableInner writeVal2 = PortableInner(0); + PortableInner writeVal3 = PortableInner(2); + + TemplatedPortableIdResolver<PortableDummy> idRslvr; + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writerImpl(&out, &idRslvr, NULL, NULL); + PortableWriter writer(&writerImpl); + + out.Position(18); + + PortableMapWriter<int8_t, PortableInner> mapWriter = mapType ? + writer.WriteMap<int8_t, PortableInner>("field1", *mapType) : writer.WriteMap<int8_t, PortableInner>("field1"); + + mapWriter.Write(1, writeVal1); + mapWriter.Write(2, writeVal2); + mapWriter.Write(3, writeVal3); + + CheckWritesRestricted(writer); + + mapWriter.Close(); + + writer.WriteInt8("field2", 1); + + try + { + mapWriter.Write(4, PortableInner(4)); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + mapWriter.Close(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl readerImpl(&in, &idRslvr, 0, true, idRslvr.GetTypeId(), 0, 1000, 1000); + PortableReader reader(&readerImpl); + + in.Position(18); + + PortableMapReader<int8_t, PortableInner> mapReader = reader.ReadMap<int8_t, PortableInner>("field1"); + + CheckReadsRestricted(reader); + + if (mapType) + BOOST_REQUIRE(mapReader.GetType() == *mapType); + else + BOOST_REQUIRE(mapReader.GetType() == IGNITE_MAP_UNDEFINED); + + BOOST_REQUIRE(mapReader.GetSize() == 3); + BOOST_REQUIRE(!mapReader.IsNull()); + + int8_t key; + PortableInner val; + + BOOST_REQUIRE(mapReader.HasNext()); + + mapReader.GetNext(&key, &val); + BOOST_REQUIRE(key == 1); + BOOST_REQUIRE(val.GetValue() == writeVal1.GetValue()); + + mapReader.GetNext(&key, &val); + BOOST_REQUIRE(key == 2); + BOOST_REQUIRE(val.GetValue() == writeVal2.GetValue()); + + mapReader.GetNext(&key, &val); + BOOST_REQUIRE(key == 3); + BOOST_REQUIRE(val.GetValue() == writeVal3.GetValue()); + + BOOST_REQUIRE(!mapReader.HasNext()); + + try + { + mapReader.GetNext(&key, &val); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(reader.ReadInt8("field2") == 1); +} + +BOOST_AUTO_TEST_SUITE(PortableReaderWriterTestSuite) + +BOOST_AUTO_TEST_CASE(TestPrimitiveInt8) +{ + CheckPrimitive<int8_t>(1); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveBool) +{ + CheckPrimitive<bool>(true); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveInt16) +{ + CheckPrimitive<int16_t>(1); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveUInt16) +{ + CheckPrimitive<uint16_t>(1); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveInt32) +{ + CheckPrimitive<int32_t>(1); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveInt64) +{ + CheckPrimitive<int64_t>(1); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveFloat) +{ + CheckPrimitive<float>(1.1f); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveDouble) +{ + CheckPrimitive<double>(1.1); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveGuid) +{ + Guid val(1, 2); + + CheckPrimitive<Guid>(val); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveArrayInt8) +{ + CheckPrimitiveArray<int8_t>(1, 2, 3); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveArrayBool) +{ + CheckPrimitiveArray<bool>(false, true, false); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveArrayInt16) +{ + CheckPrimitiveArray<int16_t>(1, 2, 3); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveArrayUInt16) +{ + CheckPrimitiveArray<uint16_t>(1, 2, 3); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveArrayInt32) +{ + CheckPrimitiveArray<int32_t>(1, 2, 3); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveArrayInt64) +{ + CheckPrimitiveArray<int64_t>(1, 2, 3); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveArrayFloat) +{ + CheckPrimitiveArray<float>(1.1f, 2.2f, 3.3f); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveArrayDouble) +{ + CheckPrimitiveArray<double>(1.1, 2.2, 3.3); +} + +BOOST_AUTO_TEST_CASE(TestPrimitiveArrayGuid) +{ + Guid dflt(1, 2); + Guid val1(3, 4); + Guid val2(5, 6); + + CheckPrimitiveArray<Guid>(dflt, val1, val2); +} + +BOOST_AUTO_TEST_CASE(TestGuidNull) +{ + TemplatedPortableIdResolver<PortableDummy> idRslvr; + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writerImpl(&out, &idRslvr, NULL, NULL); + PortableWriter writer(&writerImpl); + + out.Position(18); + + try + { + writer.WriteNull(NULL); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + writer.WriteNull("test"); + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl readerImpl(&in, &idRslvr, 0, true, idRslvr.GetTypeId(), 0, 100, 100); + PortableReader reader(&readerImpl); + + in.Position(18); + + try + { + reader.ReadGuid(NULL); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + Guid expVal; + Guid actualVal = reader.ReadGuid("test"); + + BOOST_REQUIRE(actualVal == expVal); +} + +BOOST_AUTO_TEST_CASE(TestString) { + TemplatedPortableIdResolver<PortableDummy> idRslvr; + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writerImpl(&out, &idRslvr, NULL, NULL); + PortableWriter writer(&writerImpl); + + out.Position(18); + + const char* writeVal1 = "testtest"; + const char* writeVal2 = "test"; + std::string writeVal3 = writeVal1; + + try + { + writer.WriteString(NULL, writeVal1); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + writer.WriteString(NULL, writeVal1, 4); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + writer.WriteString(NULL, writeVal3); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + writer.WriteString("field1", writeVal1); + writer.WriteString("field2", writeVal1, 4); + writer.WriteString("field3", writeVal3); + writer.WriteString("field4", NULL); + writer.WriteString("field5", NULL, 4); + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl readerImpl(&in, &idRslvr, 0, true, idRslvr.GetTypeId(), 0, 1000, 1000); + PortableReader reader(&readerImpl); + + in.Position(18); + + try + { + char nullCheckRes[9]; + + reader.ReadString(NULL, nullCheckRes, 9); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + reader.ReadString(NULL); + + BOOST_FAIL("Not restricted."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + char readVal1[9]; + char readVal2[5]; + + BOOST_REQUIRE(reader.ReadString("field1", NULL, 0) == 8); + BOOST_REQUIRE(reader.ReadString("field1", NULL, 8) == 8); + BOOST_REQUIRE(reader.ReadString("field1", readVal1, 0) == 8); + BOOST_REQUIRE(reader.ReadString("field1", readVal1, 4) == 8); + + BOOST_REQUIRE(reader.ReadString("field1", readVal1, 9) == 8); + std::string writeVal1Str = writeVal1; + std::string readVal1Str = readVal1; + BOOST_REQUIRE(readVal1Str.compare(writeVal1Str) == 0); + + BOOST_REQUIRE(reader.ReadString("field2", readVal2, 5) == 4); + std::string writeVal2Str = writeVal2; + std::string readVal2Str = readVal2; + BOOST_REQUIRE(readVal2Str.compare(writeVal2Str) == 0); + + std::string readVal3 = reader.ReadString("field3"); + BOOST_REQUIRE(readVal3.compare(writeVal3) == 0); + + BOOST_REQUIRE(reader.ReadString("field4", readVal1, 9) == -1); + BOOST_REQUIRE(reader.ReadString("field5", readVal1, 9) == -1); +} + +BOOST_AUTO_TEST_CASE(TestStringArrayNull) +{ + TemplatedPortableIdResolver<PortableDummy> idRslvr; + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writerImpl(&out, &idRslvr, NULL, NULL); + PortableWriter writer(&writerImpl); + + out.Position(18); + + writer.WriteNull("field1"); + writer.WriteInt8("field2", 1); + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl readerImpl(&in, &idRslvr, 0, true, idRslvr.GetTypeId(), 0, 1000, 1000); + PortableReader reader(&readerImpl); + + in.Position(18); + + PortableStringArrayReader arrReader = reader.ReadStringArray("field1"); + + BOOST_REQUIRE(arrReader.GetSize() == -1); + BOOST_REQUIRE(!arrReader.HasNext()); + BOOST_REQUIRE(arrReader.IsNull()); + + try + { + char res[100]; + + arrReader.GetNext(res, 100); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + arrReader.GetNext(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(reader.ReadInt8("field2") == 1); +} + +BOOST_AUTO_TEST_CASE(TestStringArrayEmpty) +{ + TemplatedPortableIdResolver<PortableDummy> idRslvr; + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writerImpl(&out, &idRslvr, NULL, NULL); + PortableWriter writer(&writerImpl); + + out.Position(18); + + PortableStringArrayWriter arrWriter = writer.WriteStringArray("field1"); + + CheckWritesRestricted(writer); + + arrWriter.Close(); + + writer.WriteInt8("field2", 1); + + try + { + const char* val = "test"; + + arrWriter.Write(val, 4); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + const char* val = "test"; + + arrWriter.Write(val); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + std::string val = "test"; + + arrWriter.Write(val); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + arrWriter.Close(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl readerImpl(&in, &idRslvr, 0, true, idRslvr.GetTypeId(), 0, 1000, 1000); + PortableReader reader(&readerImpl); + + in.Position(18); + + PortableStringArrayReader arrReader = reader.ReadStringArray("field1"); + + BOOST_REQUIRE(arrReader.GetSize() == 0); + BOOST_REQUIRE(!arrReader.HasNext()); + BOOST_REQUIRE(!arrReader.IsNull()); + + try + { + char res[100]; + + arrReader.GetNext(res, 100); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + arrReader.GetNext(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(reader.ReadInt8("field2") == 1); +} + +BOOST_AUTO_TEST_CASE(TestStringArray) +{ + const char* writeVal1 = "testtest"; + const char* writeVal2 = "test"; + std::string writeVal3 = "test2"; + + TemplatedPortableIdResolver<PortableDummy> idRslvr; + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writerImpl(&out, &idRslvr, NULL, NULL); + PortableWriter writer(&writerImpl); + + out.Position(18); + + PortableStringArrayWriter arrWriter = writer.WriteStringArray("field1"); + + arrWriter.Write(writeVal1); + arrWriter.Write(writeVal1, 4); + arrWriter.Write(NULL); // NULL value. + arrWriter.Write(NULL, 100); // NULL value again. + arrWriter.Write(writeVal3); + + CheckWritesRestricted(writer); + + arrWriter.Close(); + + writer.WriteInt8("field2", 1); + + try + { + const char* val = "test"; + + arrWriter.Write(val, 4); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + const char* val = "test"; + + arrWriter.Write(val); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + std::string val = "test"; + + arrWriter.Write(val); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + arrWriter.Close(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl readerImpl(&in, &idRslvr, 0, true, idRslvr.GetTypeId(), 0, 1000, 1000); + PortableReader reader(&readerImpl); + + in.Position(18); + + PortableStringArrayReader arrReader = reader.ReadStringArray("field1"); + + CheckReadsRestricted(reader); + + BOOST_REQUIRE(arrReader.GetSize() == 5); + BOOST_REQUIRE(!arrReader.IsNull()); + + // 1. Read first value. + BOOST_REQUIRE(arrReader.HasNext()); + + char readVal1[9]; + + BOOST_REQUIRE(arrReader.GetNext(NULL, 0) == 8); + BOOST_REQUIRE(arrReader.GetNext(NULL, 8) == 8); + BOOST_REQUIRE(arrReader.GetNext(readVal1, 0) == 8); + BOOST_REQUIRE(arrReader.GetNext(readVal1, 4) == 8); + + BOOST_REQUIRE(arrReader.GetNext(readVal1, 9) == 8); + std::string writeVal1Str = writeVal1; + std::string readVal1Str = readVal1; + BOOST_REQUIRE(readVal1Str.compare(writeVal1Str) == 0); + + // 2. Read second value. + BOOST_REQUIRE(arrReader.HasNext()); + + char readVal2[5]; + + BOOST_REQUIRE(arrReader.GetNext(readVal2, 5) == 4); + std::string writeVal2Str = writeVal2; + std::string readVal2Str = readVal2; + BOOST_REQUIRE(readVal2Str.compare(writeVal2Str) == 0); + + // 3. Read NULL. + BOOST_REQUIRE(arrReader.HasNext()); + + BOOST_REQUIRE(arrReader.GetNext(readVal1, 4) == -1); + readVal1Str = readVal1; + BOOST_REQUIRE(readVal1Str.compare(writeVal1Str) == 0); + + // 4. Read NULL again, this time through another method. + BOOST_REQUIRE(arrReader.HasNext()); + + std::string readNullVal = arrReader.GetNext(); + + BOOST_REQUIRE(readNullVal.length() == 0); + + // 5. Read third value. + BOOST_REQUIRE(arrReader.HasNext()); + + std::string readVal3 = arrReader.GetNext(); + BOOST_REQUIRE(readVal3.compare(writeVal3) == 0); + + BOOST_REQUIRE(!arrReader.HasNext()); + + try + { + char res[100]; + + arrReader.GetNext(res, 100); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + arrReader.GetNext(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(reader.ReadInt8("field2") == 1); +} + +BOOST_AUTO_TEST_CASE(TestObject) +{ + PortableInner writeVal1(1); + PortableInner writeVal2(0); + + TemplatedPortableIdResolver<PortableDummy> idRslvr; + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writerImpl(&out, &idRslvr, NULL, NULL); + PortableWriter writer(&writerImpl); + + out.Position(18); + + writer.WriteObject("field1", writeVal1); + writer.WriteObject("field2", writeVal2); + writer.WriteNull("field3"); + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl readerImpl(&in, &idRslvr, 0, true, idRslvr.GetTypeId(), 0, 1000, 1000); + PortableReader reader(&readerImpl); + + in.Position(18); + + PortableInner readVal1 = reader.ReadObject<PortableInner>("field1"); + BOOST_REQUIRE(writeVal1.GetValue() == readVal1.GetValue()); + + PortableInner readVal2 = reader.ReadObject<PortableInner>("field2"); + BOOST_REQUIRE(writeVal2.GetValue() == readVal2.GetValue()); + + PortableInner readVal3 = reader.ReadObject<PortableInner>("field3"); + BOOST_REQUIRE(0 == readVal3.GetValue()); +} + +BOOST_AUTO_TEST_CASE(TestNestedObject) +{ + PortableOuter writeVal1(1, 2); + PortableOuter writeVal2(0, 0); + + TemplatedPortableIdResolver<PortableDummy> idRslvr; + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writerImpl(&out, &idRslvr, NULL, NULL); + PortableWriter writer(&writerImpl); + + out.Position(18); + + writer.WriteObject("field1", writeVal1); + writer.WriteObject("field2", writeVal2); + writer.WriteNull("field3"); + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl readerImpl(&in, &idRslvr, 0, true, idRslvr.GetTypeId(), 0, 1000, 1000); + PortableReader reader(&readerImpl); + + in.Position(18); + + PortableOuter readVal1 = reader.ReadObject<PortableOuter>("field1"); + BOOST_REQUIRE(writeVal1.GetValue() == readVal1.GetValue()); + BOOST_REQUIRE(writeVal1.GetInner().GetValue() == readVal1.GetInner().GetValue()); + + PortableOuter readVal2 = reader.ReadObject<PortableOuter>("field2"); + BOOST_REQUIRE(writeVal2.GetValue() == readVal2.GetValue()); + BOOST_REQUIRE(writeVal2.GetInner().GetValue() == readVal2.GetInner().GetValue()); + + PortableOuter readVal3 = reader.ReadObject<PortableOuter>("field3"); + BOOST_REQUIRE(0 == readVal3.GetValue()); + BOOST_REQUIRE(0 == readVal3.GetInner().GetValue()); +} + +BOOST_AUTO_TEST_CASE(TestArrayNull) +{ + TemplatedPortableIdResolver<PortableDummy> idRslvr; + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writerImpl(&out, &idRslvr, NULL, NULL); + PortableWriter writer(&writerImpl); + + out.Position(18); + + writer.WriteNull("field1"); + writer.WriteInt8("field2", 1); + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl readerImpl(&in, &idRslvr, 0, true, idRslvr.GetTypeId(), 0, 1000, 1000); + PortableReader reader(&readerImpl); + + in.Position(18); + + PortableArrayReader<PortableInner> arrReader = reader.ReadArray<PortableInner>("field1"); + + BOOST_REQUIRE(arrReader.GetSize() == -1); + BOOST_REQUIRE(!arrReader.HasNext()); + BOOST_REQUIRE(arrReader.IsNull()); + + try + { + arrReader.GetNext(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(reader.ReadInt8("field2") == 1); +} + +BOOST_AUTO_TEST_CASE(TestArrayEmpty) +{ + TemplatedPortableIdResolver<PortableDummy> idRslvr; + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writerImpl(&out, &idRslvr, NULL, NULL); + PortableWriter writer(&writerImpl); + + out.Position(18); + + PortableArrayWriter<PortableInner> arrWriter = writer.WriteArray<PortableInner>("field1"); + + CheckWritesRestricted(writer); + + arrWriter.Close(); + + writer.WriteInt8("field2", 1); + + try + { + arrWriter.Write(1); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + arrWriter.Close(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl readerImpl(&in, &idRslvr, 0, true, idRslvr.GetTypeId(), 0, 1000, 1000); + PortableReader reader(&readerImpl); + + in.Position(18); + + PortableArrayReader<PortableInner> arrReader = reader.ReadArray<PortableInner>("field1"); + + BOOST_REQUIRE(arrReader.GetSize() == 0); + BOOST_REQUIRE(!arrReader.HasNext()); + BOOST_REQUIRE(!arrReader.IsNull()); + + try + { + arrReader.GetNext(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(reader.ReadInt8("field2") == 1); +} + +BOOST_AUTO_TEST_CASE(TestArray) +{ + PortableInner writeVal1 = PortableInner(1); + PortableInner writeVal2 = PortableInner(0); + PortableInner writeVal3 = PortableInner(2); + + TemplatedPortableIdResolver<PortableDummy> idRslvr; + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writerImpl(&out, &idRslvr, NULL, NULL); + PortableWriter writer(&writerImpl); + + out.Position(18); + + PortableArrayWriter<PortableInner> arrWriter = writer.WriteArray<PortableInner>("field1"); + + arrWriter.Write(writeVal1); + arrWriter.Write(writeVal2); + arrWriter.Write(writeVal3); + + CheckWritesRestricted(writer); + + arrWriter.Close(); + + writer.WriteInt8("field2", 1); + + try + { + arrWriter.Write(1); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + try + { + arrWriter.Close(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl readerImpl(&in, &idRslvr, 0, true, idRslvr.GetTypeId(), 0, 1000, 1000); + PortableReader reader(&readerImpl); + + in.Position(18); + + PortableArrayReader<PortableInner> arrReader = reader.ReadArray<PortableInner>("field1"); + + CheckReadsRestricted(reader); + + BOOST_REQUIRE(arrReader.GetSize() == 3); + BOOST_REQUIRE(!arrReader.IsNull()); + + BOOST_REQUIRE(arrReader.HasNext()); + BOOST_REQUIRE(arrReader.GetNext().GetValue() == writeVal1.GetValue()); + + BOOST_REQUIRE(arrReader.HasNext()); + BOOST_REQUIRE(arrReader.GetNext().GetValue() == writeVal2.GetValue()); + + BOOST_REQUIRE(arrReader.HasNext()); + BOOST_REQUIRE(arrReader.GetNext().GetValue() == writeVal3.GetValue()); + + BOOST_REQUIRE(!arrReader.HasNext()); + + try + { + arrReader.GetNext(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(reader.ReadInt8("field2") == 1); +} + +BOOST_AUTO_TEST_CASE(TestCollectionNull) +{ + TemplatedPortableIdResolver<PortableDummy> idRslvr; + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writerImpl(&out, &idRslvr, NULL, NULL); + PortableWriter writer(&writerImpl); + + out.Position(18); + + writer.WriteNull("field1"); + writer.WriteInt8("field2", 1); + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl readerImpl(&in, &idRslvr, 0, true, idRslvr.GetTypeId(), 0, 1000, 1000); + PortableReader reader(&readerImpl); + + in.Position(18); + + PortableCollectionReader<PortableInner> colReader = reader.ReadCollection<PortableInner>("field1"); + + BOOST_REQUIRE(colReader.GetType() == IGNITE_COLLECTION_UNDEFINED); + BOOST_REQUIRE(colReader.GetSize() == -1); + BOOST_REQUIRE(!colReader.HasNext()); + BOOST_REQUIRE(colReader.IsNull()); + + try + { + colReader.GetNext(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(reader.ReadInt8("field2") == 1); +} + +BOOST_AUTO_TEST_CASE(TestCollectionEmpty) +{ + CheckCollectionEmpty(NULL); +} + +BOOST_AUTO_TEST_CASE(TestCollectionEmptyTyped) +{ + CollectionType typ = IGNITE_COLLECTION_CONCURRENT_SKIP_LIST_SET; + + CheckCollectionEmpty(&typ); +} + +BOOST_AUTO_TEST_CASE(TestCollection) +{ + CheckCollection(NULL); +} + +BOOST_AUTO_TEST_CASE(testCollectionTyped) +{ + CollectionType typ = IGNITE_COLLECTION_CONCURRENT_SKIP_LIST_SET; + + CheckCollection(&typ); +} + +BOOST_AUTO_TEST_CASE(TestMapNull) +{ + TemplatedPortableIdResolver<PortableDummy> idRslvr; + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writerImpl(&out, &idRslvr, NULL, NULL); + PortableWriter writer(&writerImpl); + + out.Position(18); + + writer.WriteNull("field1"); + writer.WriteInt8("field2", 1); + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl readerImpl(&in, &idRslvr, 0, true, idRslvr.GetTypeId(), 0, 1000, 1000); + PortableReader reader(&readerImpl); + + in.Position(18); + + PortableMapReader<int8_t, PortableInner> mapReader = reader.ReadMap<int8_t, PortableInner>("field1"); + + BOOST_REQUIRE(mapReader.GetType() == IGNITE_MAP_UNDEFINED); + BOOST_REQUIRE(mapReader.GetSize() == -1); + BOOST_REQUIRE(!mapReader.HasNext()); + BOOST_REQUIRE(mapReader.IsNull()); + + try + { + int8_t key; + PortableInner val; + + mapReader.GetNext(&key, &val); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(reader.ReadInt8("field2") == 1); +} + +BOOST_AUTO_TEST_CASE(TestMapEmpty) +{ + CheckMapEmpty(NULL); +} + +BOOST_AUTO_TEST_CASE(TestMapEmptyTyped) +{ + MapType typ = IGNITE_MAP_CONCURRENT_HASH_MAP; + + CheckMapEmpty(&typ); +} + +BOOST_AUTO_TEST_CASE(TestMap) +{ + CheckMap(NULL); +} + +BOOST_AUTO_TEST_CASE(TestMapTyped) +{ + MapType typ = IGNITE_MAP_CONCURRENT_HASH_MAP; + + CheckMap(&typ); +} + +BOOST_AUTO_TEST_CASE(TestRawMode) +{ + TemplatedPortableIdResolver<PortableDummy> idRslvr; + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writerImpl(&out, &idRslvr, NULL, NULL); + PortableWriter writer(&writerImpl); + + out.Position(18); + + PortableRawWriter rawWriter = writer.RawWriter(); + + try + { + writer.RawWriter(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + rawWriter.WriteInt8(1); + + CheckWritesRestricted(writer); + + out.Synchronize(); + + InteropInputStream in(&mem); + PortableReaderImpl readerImpl(&in, &idRslvr, 0, true, idRslvr.GetTypeId(), 0, 1000, 18); + PortableReader reader(&readerImpl); + + in.Position(18); + + PortableRawReader rawReader = reader.RawReader(); + + try + { + reader.RawReader(); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(rawReader.ReadInt8() == 1); + + CheckReadsRestricted(reader); +} + +BOOST_AUTO_TEST_CASE(TestFieldSeek) +{ + TemplatedPortableIdResolver<PortableFields> idRslvr; + + InteropUnpooledMemory mem(1024); + + InteropOutputStream out(&mem); + PortableWriterImpl writer(&out, NULL); + + PortableFields writeVal(1, 2, 3, 4); + + writer.WriteTopObject<PortableFields>(writeVal); + + out.Synchronize(); + + InteropInputStream in(&mem); + + int32_t pos = in.Position(); + in.ReadInt8(); // We do not need a header here. + bool usrType = in.ReadBool(); + int32_t typeId = in.ReadInt32(); + int32_t hashCode = in.ReadInt32(); + int32_t len = in.ReadInt32(); + int32_t rawOff = in.ReadInt32(); + + PortableReaderImpl readerImpl(&in, &idRslvr, pos, usrType, typeId, hashCode, len, rawOff); + PortableReader reader(&readerImpl); + + // 1. Clockwise. + BOOST_REQUIRE(reader.ReadInt32("val1") == 1); + BOOST_REQUIRE(reader.ReadInt32("val2") == 2); + BOOST_REQUIRE(reader.ReadInt32("val1") == 1); + BOOST_REQUIRE(reader.ReadInt32("val2") == 2); + + // 2. Counter closkwise. + in.Position(18); + BOOST_REQUIRE(reader.ReadInt32("val2") == 2); + BOOST_REQUIRE(reader.ReadInt32("val1") == 1); + BOOST_REQUIRE(reader.ReadInt32("val2") == 2); + BOOST_REQUIRE(reader.ReadInt32("val1") == 1); + + // 3. Same field twice. + in.Position(18); + BOOST_REQUIRE(reader.ReadInt32("val1") == 1); + BOOST_REQUIRE(reader.ReadInt32("val1") == 1); + + in.Position(18); + BOOST_REQUIRE(reader.ReadInt32("val2") == 2); + BOOST_REQUIRE(reader.ReadInt32("val2") == 2); + + // 4. Read missing field in between. + in.Position(18); + BOOST_REQUIRE(reader.ReadInt32("val1") == 1); + BOOST_REQUIRE(reader.ReadInt32("missing") == 0); + BOOST_REQUIRE(reader.ReadInt32("val2") == 2); + + in.Position(18); + BOOST_REQUIRE(reader.ReadInt32("val2") == 2); + BOOST_REQUIRE(reader.ReadInt32("missing") == 0); + BOOST_REQUIRE(reader.ReadInt32("val1") == 1); + + // 5. Invalid field type. + in.Position(18); + BOOST_REQUIRE(reader.ReadInt32("val1") == 1); + + try + { + reader.ReadInt64("val2"); + + BOOST_FAIL("Error expected."); + } + catch (IgniteError& err) + { + BOOST_REQUIRE(err.GetCode() == IgniteError::IGNITE_ERR_PORTABLE); + } + + BOOST_REQUIRE(reader.ReadInt32("val2") == 2); + + // 6. Read missing primitive fields. + BOOST_REQUIRE(reader.ReadInt8("missing") == 0); + BOOST_REQUIRE(reader.ReadBool("missing") == false); + BOOST_REQUIRE(reader.ReadInt16("missing") == 0); + BOOST_REQUIRE(reader.ReadUInt16("missing") == 0); + BOOST_REQUIRE(reader.ReadInt32("missing") == 0); + BOOST_REQUIRE(reader.ReadInt64("missing") == 0); + BOOST_REQUIRE(reader.ReadFloat("missing") == 0); + BOOST_REQUIRE(reader.ReadDouble("missing") == 0); + + BOOST_REQUIRE(reader.ReadGuid("missing").GetMostSignificantBits() == 0); + BOOST_REQUIRE(reader.ReadGuid("missing").GetLeastSignificantBits() == 0); + + // 7. Read missing primitive array fields. + BOOST_REQUIRE(reader.ReadInt8Array("missing", NULL, 1) == -1); + BOOST_REQUIRE(reader.ReadBoolArray("missing", NULL, 1) == -1); + BOOST_REQUIRE(reader.ReadInt16Array("missing", NULL, 1) == -1); + BOOST_REQUIRE(reader.ReadUInt16Array("missing", NULL, 1) == -1); + BOOST_REQUIRE(reader.ReadInt32Array("missing", NULL, 1) == -1); + BOOST_REQUIRE(reader.ReadInt64Array("missing", NULL, 1) == -1); + BOOST_REQUIRE(reader.ReadFloatArray("missing", NULL, 1) == -1); + BOOST_REQUIRE(reader.ReadDoubleArray("missing", NULL, 1) == -1); + + BOOST_REQUIRE(reader.ReadGuidArray("missing", NULL, 1) == -1); + + // 8. Read missing string fields. + BOOST_REQUIRE(reader.ReadString("missing", NULL, 1) == -1); + BOOST_REQUIRE(reader.ReadString("missing").length() == 0); + + // 9. Read missing object fields. + BOOST_REQUIRE(reader.ReadObject<PortableFields*>("missing") == NULL); + + // 10. Read missing container fields. + PortableStringArrayReader stringArrReader = reader.ReadStringArray("missing"); + BOOST_REQUIRE(stringArrReader.IsNull()); + + PortableArrayReader<PortableFields> arrReader = reader.ReadArray<PortableFields>("missing"); + BOOST_REQUIRE(arrReader.IsNull()); + + PortableCollectionReader<PortableFields> colReader = reader.ReadCollection<PortableFields>("missing"); + BOOST_REQUIRE(colReader.IsNull()); + + PortableMapReader<int32_t, PortableFields> mapReader = reader.ReadMap<int32_t, PortableFields>("missing"); + BOOST_REQUIRE(mapReader.IsNull()); +} + +BOOST_AUTO_TEST_SUITE_END() \ No newline at end of file
