/** * Copyright - See the COPYRIGHT that is included with this distribution. * pvxs is distributed subject to a Software License Agreement found * in file LICENSE that is included with this distribution. */ #include #include #include #include #include "utilpvt.h" #include "dataimpl.h" using namespace pvxs; namespace { void showSize() { testDiag("%s()", __func__); #define CASE(TYPE) testDiag("sizeof(" #TYPE ") = %u", unsigned(sizeof(TYPE))) CASE(Value); CASE(impl::FieldDesc); CASE(impl::FieldStorage); CASE(impl::StructTop); CASE(BitMask); #undef CASE } void testBasic() { testDiag("%s()", __func__); auto top = TypeDef(TypeCode::Struct, "simple_t", { Member(TypeCode::Float64, "value"), }).create(); testOk1(top.valid()); testEq(top.type(), TypeCode::Struct); { auto val = top["missing"]; testOk1(!val.valid()); testOk1(!val.isMarked()); testThrows([&val]() { val.from(4.2); }); } { auto val = top["value"]; testOk1(!!val.valid()); testOk1(!val.isMarked()); val.from(4.2); testEq(val.as(), 4.2); testOk1(!!val.isMarked()); } testEq(std::string(SB()<\n"); testEq(std::string(SB()< [0:18)\n" " achoice -> 14 [14]\n" " any -> 9 [9]\n" " anya -> 10 [10]\n" " arbitrary -> 5 [5]\n" " arbitrary.sarr -> 6 [6]\n" " choice -> 11 [11]\n" " timeStamp -> 2 [2]\n" " timeStamp.nanoseconds -> 4 [4]\n" " timeStamp.secondsPastEpoch -> 3 [3]\n" " value -> 1 [1]\n" " value : 1 [1]\n" " timeStamp : 2 [2]\n" " arbitrary : 5 [5]\n" " any : 9 [9]\n" " anya : 10 [10]\n" " choice : 11 [11]\n" " achoice : 14 [14]\n" "[1] double[] <1:2> [1:2)\n" "[2] struct time_t <2:3> [2:5)\n" " nanoseconds -> 2 [4]\n" " secondsPastEpoch -> 1 [3]\n" " secondsPastEpoch : 1 [3]\n" " nanoseconds : 2 [4]\n" "[3] uint64_t <3:4> [3:4)\n" "[4] uint32_t <4:5> [4:5)\n" "[5] struct <5:6> [5:9)\n" " sarr -> 1 [6]\n" " sarr : 1 [6]\n" "[6] struct[] <6:7> [6:9)\n" "[7] struct <0:2> [7:9)\n" " value -> 1 [8]\n" " value : 1 [8]\n" "[8] double <1:2> [8:9)\n" "[9] any <7:8> [9:10)\n" "[10] any[] <8:9> [10:11)\n" "[11] union <9:10> [11:14)\n" " a -> 1 [12]\n" " b -> 2 [13]\n" " a : 1 [12]\n" " b : 2 [13]\n" "[12] float <0:1> [12:13)\n" "[13] string <0:1> [13:14)\n" "[14] union[] <10:11> [14:18)\n" "[15] union <0:3> [15:18)\n" " x -> 1 [16]\n" " y -> 2 [17]\n" " x : 1 [16]\n" " y : 2 [17]\n" "[16] float <1:2> [16:17)\n" "[17] float <2:3> [17:18)\n" ""); // try to access all field Kinds // sub-struct and scalar val["timeStamp.secondsPastEpoch"] = 0x123456789abcdef0ull; // array of scalar { shared_array arr({1.0, 2.0}); val["value"] = arr.freeze().castTo(); } // Struct[] { auto fld = val["arbitrary.sarr"]; shared_array arr(3); arr[0] = fld.allocMember(); arr[1] = fld.allocMember(); // leave [2] as null arr[0]["value"] = 1.0; arr[1]["value"] = 2.0; fld = arr.freeze().castTo(); testEq(val["arbitrary.sarr[1]value"].as(), 2.0); } // Union val["choice->b"] = "test"; // Union[] { auto fld = val["achoice"]; shared_array arr(3); arr[0] = fld.allocMember(); arr[1] = fld.allocMember(); // leave [2] as null arr[0]["->x"] = 4.0; arr[1]["->y"] = 5.0; fld = arr.freeze().castTo(); testEq(fld["[1]"].as(), 5.0); testEq(val["achoice[1]"].as(), 5.0); testEq(val["achoice[1]->y"].as(), 5.0); } // Any { auto v = TypeDef(TypeCode::UInt32).create(); v = 42u; val["any"].from(v); testEq(v.as(), 42u); } // Any[] { auto fld = val["anya"]; shared_array arr(3); arr[0] = TypeDef(TypeCode::UInt32).create(); arr[1] = TypeDef(TypeCode::Struct, {Member(TypeCode::String, "q")}).create(); // leave [2] as null arr[0] = 123; arr[1]["q"] = "theq"; fld = arr.freeze().castTo(); testEq(fld["[0]"].as(), 123u); testEq(fld["[1]q"].as(), "theq"); } testShow()<