diff --git a/neuralnetworks/1.0/vts/functional/GeneratedTestHarness.cpp b/neuralnetworks/1.0/vts/functional/GeneratedTestHarness.cpp index 595ad85633..e28605dca2 100644 --- a/neuralnetworks/1.0/vts/functional/GeneratedTestHarness.cpp +++ b/neuralnetworks/1.0/vts/functional/GeneratedTestHarness.cpp @@ -42,10 +42,11 @@ using implementation::PreparedModelCallback; Model createModel(const TestModel& testModel) { // Model operands. - hidl_vec operands(testModel.operands.size()); + CHECK_EQ(testModel.referenced.size(), 0u); // Not supported in 1.0. + hidl_vec operands(testModel.main.operands.size()); size_t constCopySize = 0, constRefSize = 0; - for (uint32_t i = 0; i < testModel.operands.size(); i++) { - const auto& op = testModel.operands[i]; + for (uint32_t i = 0; i < testModel.main.operands.size(); i++) { + const auto& op = testModel.main.operands[i]; DataLocation loc = {}; if (op.lifetime == TestOperandLifeTime::CONSTANT_COPY) { @@ -70,9 +71,9 @@ Model createModel(const TestModel& testModel) { } // Model operations. - hidl_vec operations(testModel.operations.size()); - std::transform(testModel.operations.begin(), testModel.operations.end(), operations.begin(), - [](const TestOperation& op) -> Operation { + hidl_vec operations(testModel.main.operations.size()); + std::transform(testModel.main.operations.begin(), testModel.main.operations.end(), + operations.begin(), [](const TestOperation& op) -> Operation { return {.type = static_cast(op.type), .inputs = op.inputs, .outputs = op.outputs}; @@ -80,8 +81,8 @@ Model createModel(const TestModel& testModel) { // Constant copies. hidl_vec operandValues(constCopySize); - for (uint32_t i = 0; i < testModel.operands.size(); i++) { - const auto& op = testModel.operands[i]; + for (uint32_t i = 0; i < testModel.main.operands.size(); i++) { + const auto& op = testModel.main.operands[i]; if (op.lifetime == TestOperandLifeTime::CONSTANT_COPY) { const uint8_t* begin = op.data.get(); const uint8_t* end = begin + op.data.size(); @@ -102,8 +103,8 @@ Model createModel(const TestModel& testModel) { reinterpret_cast(static_cast(mappedMemory->getPointer())); CHECK(mappedPtr != nullptr); - for (uint32_t i = 0; i < testModel.operands.size(); i++) { - const auto& op = testModel.operands[i]; + for (uint32_t i = 0; i < testModel.main.operands.size(); i++) { + const auto& op = testModel.main.operands[i]; if (op.lifetime == TestOperandLifeTime::CONSTANT_REFERENCE) { const uint8_t* begin = op.data.get(); const uint8_t* end = begin + op.data.size(); @@ -114,8 +115,8 @@ Model createModel(const TestModel& testModel) { return {.operands = std::move(operands), .operations = std::move(operations), - .inputIndexes = testModel.inputIndexes, - .outputIndexes = testModel.outputIndexes, + .inputIndexes = testModel.main.inputIndexes, + .outputIndexes = testModel.main.outputIndexes, .operandValues = std::move(operandValues), .pools = std::move(pools)}; } diff --git a/neuralnetworks/1.0/vts/functional/Utils.cpp b/neuralnetworks/1.0/vts/functional/Utils.cpp index 5b630fd7a6..0dba85acd9 100644 --- a/neuralnetworks/1.0/vts/functional/Utils.cpp +++ b/neuralnetworks/1.0/vts/functional/Utils.cpp @@ -42,10 +42,10 @@ constexpr uint32_t kOutputPoolIndex = 1; Request createRequest(const TestModel& testModel) { // Model inputs. - hidl_vec inputs(testModel.inputIndexes.size()); + hidl_vec inputs(testModel.main.inputIndexes.size()); size_t inputSize = 0; - for (uint32_t i = 0; i < testModel.inputIndexes.size(); i++) { - const auto& op = testModel.operands[testModel.inputIndexes[i]]; + for (uint32_t i = 0; i < testModel.main.inputIndexes.size(); i++) { + const auto& op = testModel.main.operands[testModel.main.inputIndexes[i]]; if (op.data.size() == 0) { // Omitted input. inputs[i] = {.hasNoValue = true}; @@ -59,10 +59,10 @@ Request createRequest(const TestModel& testModel) { } // Model outputs. - hidl_vec outputs(testModel.outputIndexes.size()); + hidl_vec outputs(testModel.main.outputIndexes.size()); size_t outputSize = 0; - for (uint32_t i = 0; i < testModel.outputIndexes.size(); i++) { - const auto& op = testModel.operands[testModel.outputIndexes[i]]; + for (uint32_t i = 0; i < testModel.main.outputIndexes.size(); i++) { + const auto& op = testModel.main.operands[testModel.main.outputIndexes[i]]; // In the case of zero-sized output, we should at least provide a one-byte buffer. // This is because zero-sized tensors are only supported internally to the driver, or @@ -90,8 +90,8 @@ Request createRequest(const TestModel& testModel) { CHECK(inputPtr != nullptr); // Copy input data to the memory pool. - for (uint32_t i = 0; i < testModel.inputIndexes.size(); i++) { - const auto& op = testModel.operands[testModel.inputIndexes[i]]; + for (uint32_t i = 0; i < testModel.main.inputIndexes.size(); i++) { + const auto& op = testModel.main.operands[testModel.main.inputIndexes[i]]; if (op.data.size() > 0) { const uint8_t* begin = op.data.get(); const uint8_t* end = begin + op.data.size(); diff --git a/neuralnetworks/1.1/vts/functional/GeneratedTestHarness.cpp b/neuralnetworks/1.1/vts/functional/GeneratedTestHarness.cpp index 7a929d6063..cee15a35a1 100644 --- a/neuralnetworks/1.1/vts/functional/GeneratedTestHarness.cpp +++ b/neuralnetworks/1.1/vts/functional/GeneratedTestHarness.cpp @@ -49,10 +49,11 @@ using V1_0::implementation::PreparedModelCallback; Model createModel(const TestModel& testModel) { // Model operands. - hidl_vec operands(testModel.operands.size()); + CHECK_EQ(testModel.referenced.size(), 0u); // Not supported in 1.1. + hidl_vec operands(testModel.main.operands.size()); size_t constCopySize = 0, constRefSize = 0; - for (uint32_t i = 0; i < testModel.operands.size(); i++) { - const auto& op = testModel.operands[i]; + for (uint32_t i = 0; i < testModel.main.operands.size(); i++) { + const auto& op = testModel.main.operands[i]; DataLocation loc = {}; if (op.lifetime == TestOperandLifeTime::CONSTANT_COPY) { @@ -77,9 +78,9 @@ Model createModel(const TestModel& testModel) { } // Model operations. - hidl_vec operations(testModel.operations.size()); - std::transform(testModel.operations.begin(), testModel.operations.end(), operations.begin(), - [](const TestOperation& op) -> Operation { + hidl_vec operations(testModel.main.operations.size()); + std::transform(testModel.main.operations.begin(), testModel.main.operations.end(), + operations.begin(), [](const TestOperation& op) -> Operation { return {.type = static_cast(op.type), .inputs = op.inputs, .outputs = op.outputs}; @@ -87,8 +88,8 @@ Model createModel(const TestModel& testModel) { // Constant copies. hidl_vec operandValues(constCopySize); - for (uint32_t i = 0; i < testModel.operands.size(); i++) { - const auto& op = testModel.operands[i]; + for (uint32_t i = 0; i < testModel.main.operands.size(); i++) { + const auto& op = testModel.main.operands[i]; if (op.lifetime == TestOperandLifeTime::CONSTANT_COPY) { const uint8_t* begin = op.data.get(); const uint8_t* end = begin + op.data.size(); @@ -109,8 +110,8 @@ Model createModel(const TestModel& testModel) { reinterpret_cast(static_cast(mappedMemory->getPointer())); CHECK(mappedPtr != nullptr); - for (uint32_t i = 0; i < testModel.operands.size(); i++) { - const auto& op = testModel.operands[i]; + for (uint32_t i = 0; i < testModel.main.operands.size(); i++) { + const auto& op = testModel.main.operands[i]; if (op.lifetime == TestOperandLifeTime::CONSTANT_REFERENCE) { const uint8_t* begin = op.data.get(); const uint8_t* end = begin + op.data.size(); @@ -121,8 +122,8 @@ Model createModel(const TestModel& testModel) { return {.operands = std::move(operands), .operations = std::move(operations), - .inputIndexes = testModel.inputIndexes, - .outputIndexes = testModel.outputIndexes, + .inputIndexes = testModel.main.inputIndexes, + .outputIndexes = testModel.main.outputIndexes, .operandValues = std::move(operandValues), .pools = std::move(pools), .relaxComputationFloat32toFloat16 = testModel.isRelaxed}; diff --git a/neuralnetworks/1.2/vts/functional/CompilationCachingTests.cpp b/neuralnetworks/1.2/vts/functional/CompilationCachingTests.cpp index 2130a76b75..10dec791cf 100644 --- a/neuralnetworks/1.2/vts/functional/CompilationCachingTests.cpp +++ b/neuralnetworks/1.2/vts/functional/CompilationCachingTests.cpp @@ -207,10 +207,10 @@ TestModel createLargeTestModelImpl(TestOperationType op, uint32_t len) { }; return { - .operands = std::move(operands), - .operations = std::move(operations), - .inputIndexes = {1}, - .outputIndexes = {len * 2 + 1}, + .main = {.operands = std::move(operands), + .operations = std::move(operations), + .inputIndexes = {1}, + .outputIndexes = {len * 2 + 1}}, .isRelaxed = false, }; } diff --git a/neuralnetworks/1.2/vts/functional/GeneratedTestHarness.cpp b/neuralnetworks/1.2/vts/functional/GeneratedTestHarness.cpp index 599fd1d9be..4c8fede8b2 100644 --- a/neuralnetworks/1.2/vts/functional/GeneratedTestHarness.cpp +++ b/neuralnetworks/1.2/vts/functional/GeneratedTestHarness.cpp @@ -75,10 +75,11 @@ struct TestConfig { Model createModel(const TestModel& testModel) { // Model operands. - hidl_vec operands(testModel.operands.size()); + CHECK_EQ(testModel.referenced.size(), 0u); // Not supported in 1.1. + hidl_vec operands(testModel.main.operands.size()); size_t constCopySize = 0, constRefSize = 0; - for (uint32_t i = 0; i < testModel.operands.size(); i++) { - const auto& op = testModel.operands[i]; + for (uint32_t i = 0; i < testModel.main.operands.size(); i++) { + const auto& op = testModel.main.operands[i]; DataLocation loc = {}; if (op.lifetime == TestOperandLifeTime::CONSTANT_COPY) { @@ -110,9 +111,9 @@ Model createModel(const TestModel& testModel) { } // Model operations. - hidl_vec operations(testModel.operations.size()); - std::transform(testModel.operations.begin(), testModel.operations.end(), operations.begin(), - [](const TestOperation& op) -> Operation { + hidl_vec operations(testModel.main.operations.size()); + std::transform(testModel.main.operations.begin(), testModel.main.operations.end(), + operations.begin(), [](const TestOperation& op) -> Operation { return {.type = static_cast(op.type), .inputs = op.inputs, .outputs = op.outputs}; @@ -120,8 +121,8 @@ Model createModel(const TestModel& testModel) { // Constant copies. hidl_vec operandValues(constCopySize); - for (uint32_t i = 0; i < testModel.operands.size(); i++) { - const auto& op = testModel.operands[i]; + for (uint32_t i = 0; i < testModel.main.operands.size(); i++) { + const auto& op = testModel.main.operands[i]; if (op.lifetime == TestOperandLifeTime::CONSTANT_COPY) { const uint8_t* begin = op.data.get(); const uint8_t* end = begin + op.data.size(); @@ -142,8 +143,8 @@ Model createModel(const TestModel& testModel) { reinterpret_cast(static_cast(mappedMemory->getPointer())); CHECK(mappedPtr != nullptr); - for (uint32_t i = 0; i < testModel.operands.size(); i++) { - const auto& op = testModel.operands[i]; + for (uint32_t i = 0; i < testModel.main.operands.size(); i++) { + const auto& op = testModel.main.operands[i]; if (op.lifetime == TestOperandLifeTime::CONSTANT_REFERENCE) { const uint8_t* begin = op.data.get(); const uint8_t* end = begin + op.data.size(); @@ -154,15 +155,15 @@ Model createModel(const TestModel& testModel) { return {.operands = std::move(operands), .operations = std::move(operations), - .inputIndexes = testModel.inputIndexes, - .outputIndexes = testModel.outputIndexes, + .inputIndexes = testModel.main.inputIndexes, + .outputIndexes = testModel.main.outputIndexes, .operandValues = std::move(operandValues), .pools = std::move(pools), .relaxComputationFloat32toFloat16 = testModel.isRelaxed}; } static bool isOutputSizeGreaterThanOne(const TestModel& testModel, uint32_t index) { - const auto byteSize = testModel.operands[testModel.outputIndexes[index]].data.size(); + const auto byteSize = testModel.main.operands[testModel.main.outputIndexes[index]].data.size(); return byteSize > 1u; } @@ -302,17 +303,17 @@ void EvaluatePreparedModel(const sp& preparedModel, const TestMo // either empty, or have the same number of elements as the number of outputs. ASSERT_EQ(ErrorStatus::NONE, executionStatus); ASSERT_TRUE(outputShapes.size() == 0 || - outputShapes.size() == testModel.outputIndexes.size()); + outputShapes.size() == testModel.main.outputIndexes.size()); break; case OutputType::UNSPECIFIED: // If the model output operands are not fully specified, outputShapes must have // the same number of elements as the number of outputs. ASSERT_EQ(ErrorStatus::NONE, executionStatus); - ASSERT_EQ(outputShapes.size(), testModel.outputIndexes.size()); + ASSERT_EQ(outputShapes.size(), testModel.main.outputIndexes.size()); break; case OutputType::INSUFFICIENT: ASSERT_EQ(ErrorStatus::OUTPUT_INSUFFICIENT_SIZE, executionStatus); - ASSERT_EQ(outputShapes.size(), testModel.outputIndexes.size()); + ASSERT_EQ(outputShapes.size(), testModel.main.outputIndexes.size()); ASSERT_FALSE(outputShapes[0].isSufficient); return; } @@ -320,7 +321,7 @@ void EvaluatePreparedModel(const sp& preparedModel, const TestMo // Go through all outputs, check returned output shapes. for (uint32_t i = 0; i < outputShapes.size(); i++) { EXPECT_TRUE(outputShapes[i].isSufficient); - const auto& expect = testModel.operands[testModel.outputIndexes[i]].dimensions; + const auto& expect = testModel.main.operands[testModel.main.outputIndexes[i]].dimensions; const std::vector actual = outputShapes[i].dimensions; EXPECT_EQ(expect, actual); } diff --git a/neuralnetworks/1.3/vts/functional/CompilationCachingTests.cpp b/neuralnetworks/1.3/vts/functional/CompilationCachingTests.cpp index 0bd24daec0..ac18c8ffcc 100644 --- a/neuralnetworks/1.3/vts/functional/CompilationCachingTests.cpp +++ b/neuralnetworks/1.3/vts/functional/CompilationCachingTests.cpp @@ -209,10 +209,10 @@ TestModel createLargeTestModelImpl(TestOperationType op, uint32_t len) { }; return { - .operands = std::move(operands), - .operations = std::move(operations), - .inputIndexes = {1}, - .outputIndexes = {len * 2 + 1}, + .main = {.operands = std::move(operands), + .operations = std::move(operations), + .inputIndexes = {1}, + .outputIndexes = {len * 2 + 1}}, .isRelaxed = false, }; } diff --git a/neuralnetworks/1.3/vts/functional/GeneratedTestHarness.cpp b/neuralnetworks/1.3/vts/functional/GeneratedTestHarness.cpp index 82f34ff779..404c2a1e03 100644 --- a/neuralnetworks/1.3/vts/functional/GeneratedTestHarness.cpp +++ b/neuralnetworks/1.3/vts/functional/GeneratedTestHarness.cpp @@ -169,7 +169,8 @@ class DeviceMemoryAllocator { if constexpr (ioType == IOType::INPUT) { if (buffer != nullptr) { // TestBuffer -> Shared memory. - const auto& testBuffer = kTestModel.operands[kTestModel.inputIndexes[index]].data; + const auto& testBuffer = + kTestModel.main.operands[kTestModel.main.inputIndexes[index]].data; ASSERT_GT(testBuffer.size(), 0); hidl_memory tmp = nn::allocateSharedMemory(testBuffer.size()); sp inputMemory = mapMemory(tmp); @@ -195,26 +196,42 @@ class DeviceMemoryAllocator { const TestModel& kTestModel; }; -} // namespace +Subgraph createSubgraph(const TestSubgraph& testSubgraph, uint32_t* constCopySize, + std::vector* constCopies, uint32_t* constRefSize, + std::vector* constReferences) { + CHECK(constCopySize != nullptr); + CHECK(constCopies != nullptr); + CHECK(constRefSize != nullptr); + CHECK(constReferences != nullptr); -Model createModel(const TestModel& testModel) { - // Model operands. - hidl_vec operands(testModel.operands.size()); - size_t constCopySize = 0, constRefSize = 0; - for (uint32_t i = 0; i < testModel.operands.size(); i++) { - const auto& op = testModel.operands[i]; + // Operands. + hidl_vec operands(testSubgraph.operands.size()); + for (uint32_t i = 0; i < testSubgraph.operands.size(); i++) { + const auto& op = testSubgraph.operands[i]; DataLocation loc = {}; if (op.lifetime == TestOperandLifeTime::CONSTANT_COPY) { - loc = {.poolIndex = 0, - .offset = static_cast(constCopySize), - .length = static_cast(op.data.size())}; - constCopySize += op.data.alignedSize(); + loc = { + .poolIndex = 0, + .offset = *constCopySize, + .length = static_cast(op.data.size()), + }; + constCopies->push_back(&op.data); + *constCopySize += op.data.alignedSize(); } else if (op.lifetime == TestOperandLifeTime::CONSTANT_REFERENCE) { - loc = {.poolIndex = 0, - .offset = static_cast(constRefSize), - .length = static_cast(op.data.size())}; - constRefSize += op.data.alignedSize(); + loc = { + .poolIndex = 0, + .offset = *constRefSize, + .length = static_cast(op.data.size()), + }; + constReferences->push_back(&op.data); + *constRefSize += op.data.alignedSize(); + } else if (op.lifetime == TestOperandLifeTime::SUBGRAPH) { + loc = { + .poolIndex = 0, + .offset = *op.data.get(), + .length = 0, + }; } V1_2::Operand::ExtraParams extraParams; @@ -233,25 +250,52 @@ Model createModel(const TestModel& testModel) { .extraParams = std::move(extraParams)}; } - // Model operations. - hidl_vec operations(testModel.operations.size()); - std::transform(testModel.operations.begin(), testModel.operations.end(), operations.begin(), - [](const TestOperation& op) -> Operation { + // Operations. + hidl_vec operations(testSubgraph.operations.size()); + std::transform(testSubgraph.operations.begin(), testSubgraph.operations.end(), + operations.begin(), [](const TestOperation& op) -> Operation { return {.type = static_cast(op.type), .inputs = op.inputs, .outputs = op.outputs}; }); + return {.operands = std::move(operands), + .operations = std::move(operations), + .inputIndexes = testSubgraph.inputIndexes, + .outputIndexes = testSubgraph.outputIndexes}; +} + +void copyTestBuffers(const std::vector& buffers, uint8_t* output) { + uint32_t offset = 0; + for (const TestBuffer* buffer : buffers) { + const uint8_t* begin = buffer->get(); + const uint8_t* end = begin + buffer->size(); + std::copy(begin, end, output + offset); + offset += buffer->alignedSize(); + } +} + +} // namespace + +Model createModel(const TestModel& testModel) { + uint32_t constCopySize = 0; + uint32_t constRefSize = 0; + std::vector constCopies; + std::vector constReferences; + + Subgraph mainSubgraph = createSubgraph(testModel.main, &constCopySize, &constCopies, + &constRefSize, &constReferences); + hidl_vec refSubgraphs(testModel.referenced.size()); + std::transform(testModel.referenced.begin(), testModel.referenced.end(), refSubgraphs.begin(), + [&constCopySize, &constCopies, &constRefSize, + &constReferences](const TestSubgraph& testSubgraph) { + return createSubgraph(testSubgraph, &constCopySize, &constCopies, + &constRefSize, &constReferences); + }); + // Constant copies. hidl_vec operandValues(constCopySize); - for (uint32_t i = 0; i < testModel.operands.size(); i++) { - const auto& op = testModel.operands[i]; - if (op.lifetime == TestOperandLifeTime::CONSTANT_COPY) { - const uint8_t* begin = op.data.get(); - const uint8_t* end = begin + op.data.size(); - std::copy(begin, end, operandValues.data() + operands[i].location.offset); - } - } + copyTestBuffers(constCopies, operandValues.data()); // Shared memory. hidl_vec pools = {}; @@ -266,27 +310,18 @@ Model createModel(const TestModel& testModel) { reinterpret_cast(static_cast(mappedMemory->getPointer())); CHECK(mappedPtr != nullptr); - for (uint32_t i = 0; i < testModel.operands.size(); i++) { - const auto& op = testModel.operands[i]; - if (op.lifetime == TestOperandLifeTime::CONSTANT_REFERENCE) { - const uint8_t* begin = op.data.get(); - const uint8_t* end = begin + op.data.size(); - std::copy(begin, end, mappedPtr + operands[i].location.offset); - } - } + copyTestBuffers(constReferences, mappedPtr); } - return {.main = {.operands = std::move(operands), - .operations = std::move(operations), - .inputIndexes = testModel.inputIndexes, - .outputIndexes = testModel.outputIndexes}, + return {.main = std::move(mainSubgraph), + .referenced = std::move(refSubgraphs), .operandValues = std::move(operandValues), .pools = std::move(pools), .relaxComputationFloat32toFloat16 = testModel.isRelaxed}; } static bool isOutputSizeGreaterThanOne(const TestModel& testModel, uint32_t index) { - const auto byteSize = testModel.operands[testModel.outputIndexes[index]].data.size(); + const auto byteSize = testModel.main.operands[testModel.main.outputIndexes[index]].data.size(); return byteSize > 1u; } @@ -320,10 +355,10 @@ static std::pair>> createRequest( std::vector tokens; // Model inputs. - hidl_vec inputs(testModel.inputIndexes.size()); + hidl_vec inputs(testModel.main.inputIndexes.size()); size_t inputSize = 0; - for (uint32_t i = 0; i < testModel.inputIndexes.size(); i++) { - const auto& op = testModel.operands[testModel.inputIndexes[i]]; + for (uint32_t i = 0; i < testModel.main.inputIndexes.size(); i++) { + const auto& op = testModel.main.operands[testModel.main.inputIndexes[i]]; if (op.data.size() == 0) { // Omitted input. inputs[i] = {.hasNoValue = true}; @@ -350,10 +385,10 @@ static std::pair>> createRequest( } // Model outputs. - hidl_vec outputs(testModel.outputIndexes.size()); + hidl_vec outputs(testModel.main.outputIndexes.size()); size_t outputSize = 0; - for (uint32_t i = 0; i < testModel.outputIndexes.size(); i++) { - const auto& op = testModel.operands[testModel.outputIndexes[i]]; + for (uint32_t i = 0; i < testModel.main.outputIndexes.size(); i++) { + const auto& op = testModel.main.operands[testModel.main.outputIndexes[i]]; if (preferDeviceMemory) { SCOPED_TRACE("Output index = " + std::to_string(i)); auto [buffer, token] = allocator.allocate(i); @@ -398,9 +433,9 @@ static std::pair>> createRequest( CHECK(inputMemory.get() != nullptr); uint8_t* inputPtr = static_cast(static_cast(inputMemory->getPointer())); CHECK(inputPtr != nullptr); - for (uint32_t i = 0; i < testModel.inputIndexes.size(); i++) { + for (uint32_t i = 0; i < testModel.main.inputIndexes.size(); i++) { if (!inputs[i].hasNoValue && inputs[i].location.poolIndex == kInputPoolIndex) { - const auto& op = testModel.operands[testModel.inputIndexes[i]]; + const auto& op = testModel.main.operands[testModel.main.inputIndexes[i]]; const uint8_t* begin = op.data.get(); const uint8_t* end = begin + op.data.size(); std::copy(begin, end, inputPtr + inputs[i].location.offset); @@ -443,7 +478,7 @@ static std::vector getOutputBuffers(const TestModel& testModel, cons if (outputLoc.poolIndex == kOutputPoolIndex) { outputBuffers.emplace_back(outputLoc.length, outputPtr + outputLoc.offset); } else { - const auto& op = testModel.operands[testModel.outputIndexes[i]]; + const auto& op = testModel.main.operands[testModel.main.outputIndexes[i]]; if (op.data.size() == 0) { outputBuffers.emplace_back(); } else { @@ -638,17 +673,17 @@ void EvaluatePreparedModel(const sp& device, const sp& // either empty, or have the same number of elements as the number of outputs. ASSERT_EQ(ErrorStatus::NONE, executionStatus); ASSERT_TRUE(outputShapes.size() == 0 || - outputShapes.size() == testModel.outputIndexes.size()); + outputShapes.size() == testModel.main.outputIndexes.size()); break; case OutputType::UNSPECIFIED: // If the model output operands are not fully specified, outputShapes must have // the same number of elements as the number of outputs. ASSERT_EQ(ErrorStatus::NONE, executionStatus); - ASSERT_EQ(outputShapes.size(), testModel.outputIndexes.size()); + ASSERT_EQ(outputShapes.size(), testModel.main.outputIndexes.size()); break; case OutputType::INSUFFICIENT: ASSERT_EQ(ErrorStatus::OUTPUT_INSUFFICIENT_SIZE, executionStatus); - ASSERT_EQ(outputShapes.size(), testModel.outputIndexes.size()); + ASSERT_EQ(outputShapes.size(), testModel.main.outputIndexes.size()); ASSERT_FALSE(outputShapes[0].isSufficient); return; } @@ -656,7 +691,7 @@ void EvaluatePreparedModel(const sp& device, const sp& // Go through all outputs, check returned output shapes. for (uint32_t i = 0; i < outputShapes.size(); i++) { EXPECT_TRUE(outputShapes[i].isSufficient); - const auto& expect = testModel.operands[testModel.outputIndexes[i]].dimensions; + const auto& expect = testModel.main.operands[testModel.main.outputIndexes[i]].dimensions; const std::vector actual = outputShapes[i].dimensions; EXPECT_EQ(expect, actual); } @@ -862,7 +897,7 @@ INSTANTIATE_GENERATED_TEST(FencedComputeTest, [](const TestModel& testModel) { return !testModel.expectFailure; }); INSTANTIATE_GENERATED_TEST(QuantizationCouplingTest, [](const TestModel& testModel) { - return testModel.hasQuant8CoupledOperands() && testModel.operations.size() == 1; + return testModel.hasQuant8CoupledOperands() && testModel.main.operations.size() == 1; }); } // namespace android::hardware::neuralnetworks::V1_3::vts::functional diff --git a/neuralnetworks/1.3/vts/functional/QualityOfServiceTests.cpp b/neuralnetworks/1.3/vts/functional/QualityOfServiceTests.cpp index 2f1e05c5c6..e07eb4750e 100644 --- a/neuralnetworks/1.3/vts/functional/QualityOfServiceTests.cpp +++ b/neuralnetworks/1.3/vts/functional/QualityOfServiceTests.cpp @@ -237,12 +237,13 @@ void runExecutionTest(const sp& preparedModel, const TestModel& // If the model output operands are fully specified, outputShapes must be either // either empty, or have the same number of elements as the number of outputs. - ASSERT_TRUE(outputShapes.size() == 0 || outputShapes.size() == testModel.outputIndexes.size()); + ASSERT_TRUE(outputShapes.size() == 0 || + outputShapes.size() == testModel.main.outputIndexes.size()); // Go through all outputs, check returned output shapes. for (uint32_t i = 0; i < outputShapes.size(); i++) { EXPECT_TRUE(outputShapes[i].isSufficient); - const auto& expect = testModel.operands[testModel.outputIndexes[i]].dimensions; + const auto& expect = testModel.main.operands[testModel.main.outputIndexes[i]].dimensions; const std::vector actual = outputShapes[i].dimensions; EXPECT_EQ(expect, actual); } diff --git a/neuralnetworks/1.3/vts/functional/ValidateModel.cpp b/neuralnetworks/1.3/vts/functional/ValidateModel.cpp index b9ea430694..09e9922a23 100644 --- a/neuralnetworks/1.3/vts/functional/ValidateModel.cpp +++ b/neuralnetworks/1.3/vts/functional/ValidateModel.cpp @@ -182,6 +182,7 @@ static float getInvalidScale(OperandType type) { case OperandType::TENSOR_FLOAT16: case OperandType::TENSOR_FLOAT32: case OperandType::TENSOR_QUANT8_SYMM_PER_CHANNEL: + case OperandType::SUBGRAPH: return 1.0f; case OperandType::TENSOR_INT32: return -1.0f; @@ -220,6 +221,7 @@ static std::vector getInvalidZeroPoints(OperandType type) { case OperandType::TENSOR_FLOAT32: case OperandType::TENSOR_INT32: case OperandType::TENSOR_QUANT8_SYMM_PER_CHANNEL: + case OperandType::SUBGRAPH: return {1}; case OperandType::TENSOR_QUANT8_ASYMM: return {-1, 256};