If-8 operation: Serializer and Reader parts (#7545)
* added ir reader * add serializer * fix code style * fix code style * fix code style * fix codestyle * update IR reader for IF op * move Function comparator to ngraph tests utils, update unit tests * update tests * cleanup * update unit tests * fix build issue * ngraph codestyle * Apply suggestions from code review Co-authored-by: Gleb Kazantaev <gleb.nnstu@gmail.com> Co-authored-by: Eugeny Volosenkov <eugeny.volosenkov@intel.com> Co-authored-by: Gleb Kazantaev <gleb.nnstu@gmail.com>
This commit is contained in:
parent
275d4838c5
commit
dffe4a4251
@ -270,9 +270,9 @@ class XmlSerializer : public ngraph::AttributeVisitor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
std::vector<std::string> map_type_from_body(const pugi::xml_node& xml_node,
|
std::vector<std::string> map_type_from_body(const pugi::xml_node& xml_node,
|
||||||
const std::string& map_type) {
|
const std::string& map_type, const std::string& body_name = "body") {
|
||||||
std::vector<std::string> output;
|
std::vector<std::string> output;
|
||||||
for (pugi::xml_node node : xml_node.child("body").child("layers")) {
|
for (pugi::xml_node node : xml_node.child(body_name.c_str()).child("layers")) {
|
||||||
if (!map_type.compare(node.attribute("type").value())) {
|
if (!map_type.compare(node.attribute("type").value())) {
|
||||||
output.emplace_back(node.attribute("id").value());
|
output.emplace_back(node.attribute("id").value());
|
||||||
}
|
}
|
||||||
@ -285,14 +285,14 @@ class XmlSerializer : public ngraph::AttributeVisitor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void input_descriptions_on_adapter(const std::vector<std::shared_ptr<
|
void input_descriptions_on_adapter(const std::vector<std::shared_ptr<
|
||||||
ngraph::op::util::SubGraphOp::InputDescription>>& input_descriptions,
|
ngraph::op::util::MultiSubGraphOp::InputDescription>>& input_descriptions,
|
||||||
const std::vector<std::string>& parameter_mapping,
|
const std::vector<std::string>& parameter_mapping,
|
||||||
const std::vector<std::string>& result_mapping,
|
const std::vector<std::string>& result_mapping,
|
||||||
pugi::xml_node& port_map) {
|
pugi::xml_node& port_map, const std::string& portmap_name) {
|
||||||
NGRAPH_CHECK(!parameter_mapping.empty(), "No parameters found in body Function.");
|
NGRAPH_CHECK(!parameter_mapping.empty(), "No parameters found in body Function.");
|
||||||
|
|
||||||
if (!m_xml_node.parent().child("port_map")) {
|
if (!m_xml_node.parent().child(portmap_name.c_str())) {
|
||||||
port_map = m_xml_node.parent().insert_child_before("port_map", m_xml_node.parent().first_child());
|
port_map = m_xml_node.parent().insert_child_before(portmap_name.c_str(), m_xml_node.parent().first_child());
|
||||||
}
|
}
|
||||||
|
|
||||||
for (const auto& input_description : input_descriptions) {
|
for (const auto& input_description : input_descriptions) {
|
||||||
@ -319,14 +319,14 @@ class XmlSerializer : public ngraph::AttributeVisitor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void output_descriptions_on_adapter(const std::vector<std::shared_ptr<
|
void output_descriptions_on_adapter(const std::vector<std::shared_ptr<
|
||||||
ngraph::op::util::SubGraphOp::OutputDescription>>& output_descriptions,
|
ngraph::op::util::MultiSubGraphOp::OutputDescription>>& output_descriptions,
|
||||||
const uint32_t& input_count,
|
const uint32_t& input_count,
|
||||||
const std::vector<std::string>& result_mapping,
|
const std::vector<std::string>& result_mapping,
|
||||||
pugi::xml_node& port_map) {
|
pugi::xml_node& port_map, const std::string& portmap_name) {
|
||||||
NGRAPH_CHECK(!result_mapping.empty(), "No results found in body Function.");
|
NGRAPH_CHECK(!result_mapping.empty(), "No results found in body Function.");
|
||||||
|
|
||||||
if (!port_map) {
|
if (!port_map) {
|
||||||
port_map = m_xml_node.parent().insert_child_before("port_map", m_xml_node.parent().first_child());
|
port_map = m_xml_node.parent().insert_child_before(portmap_name.c_str(), m_xml_node.parent().first_child());
|
||||||
}
|
}
|
||||||
|
|
||||||
for (const auto& output_description : output_descriptions) {
|
for (const auto& output_description : output_descriptions) {
|
||||||
@ -379,25 +379,47 @@ public:
|
|||||||
}
|
}
|
||||||
|
|
||||||
void on_adapter(const std::string& name, ngraph::ValueAccessor<void>& adapter) override {
|
void on_adapter(const std::string& name, ngraph::ValueAccessor<void>& adapter) override {
|
||||||
if (m_xml_node.parent().child("body")) {
|
using BodyTargetNames = std::tuple<std::string, std::string, std::vector<std::string>>;
|
||||||
std::vector<std::string> result_mapping = map_type_from_body(m_xml_node.parent(), "Result");
|
|
||||||
std::vector<std::string> parameter_mapping = map_type_from_body(m_xml_node.parent(), "Parameter");
|
const std::vector<BodyTargetNames> body_names = {
|
||||||
pugi::xml_node port_map = m_xml_node.parent().child("port_map");
|
BodyTargetNames{"body", "port_map", {"input_descriptions", "output_descriptions", "special_body_ports"}},
|
||||||
|
BodyTargetNames{"then_body", "then_port_map", {"then_inputs", "then_outputs"}},
|
||||||
|
BodyTargetNames{"else_body", "else_port_map", {"else_inputs", "else_outputs"}} };
|
||||||
|
BodyTargetNames bnames;
|
||||||
|
bool is_body_target = false;
|
||||||
|
for (const auto& _body_target : body_names) {
|
||||||
|
if (m_xml_node.parent().child(std::get<0>(_body_target).c_str())) {
|
||||||
|
auto vec_names = std::get<2>(_body_target);
|
||||||
|
|
||||||
|
if (std::find(vec_names.begin(), vec_names.end(), name) != vec_names.end()) {
|
||||||
|
is_body_target = true;
|
||||||
|
bnames = _body_target;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (is_body_target) {
|
||||||
|
auto body_name = std::get<0>(bnames);
|
||||||
|
auto portmap_name = std::get<1>(bnames);
|
||||||
|
std::vector<std::string> result_mapping = map_type_from_body(m_xml_node.parent(), "Result", body_name);
|
||||||
|
std::vector<std::string> parameter_mapping = map_type_from_body(m_xml_node.parent(), "Parameter", body_name);
|
||||||
|
|
||||||
|
pugi::xml_node port_map = m_xml_node.parent().child(portmap_name.c_str());
|
||||||
|
|
||||||
NGRAPH_CHECK(!parameter_mapping.empty() || !result_mapping.empty(), "No parameters or results found in body Function.");
|
NGRAPH_CHECK(!parameter_mapping.empty() || !result_mapping.empty(), "No parameters or results found in body Function.");
|
||||||
// TI, Loop do not have attributtes as regular ops, it is necessary to append "port_map" and
|
// TI, Loop do not have attributtes as regular ops, it is necessary to append "port_map" and
|
||||||
// "back_edges" to layer above (m_xml_node.parent()) as in ngfunction_2_ir() layer (here "m_xml_node")
|
// "back_edges" to layer above (m_xml_node.parent()) as in ngfunction_2_ir() layer (here "m_xml_node")
|
||||||
// with empty attributes is removed.
|
// with empty attributes is removed.
|
||||||
if (const auto& a = ngraph::as_type<ngraph::AttributeAdapter<std::vector<std::shared_ptr
|
if (const auto& a = ngraph::as_type<ngraph::AttributeAdapter<std::vector<std::shared_ptr
|
||||||
<ngraph::op::util::SubGraphOp::InputDescription>>>>(&adapter)) {
|
<ngraph::op::util::MultiSubGraphOp::InputDescription>>>>(&adapter)) {
|
||||||
input_descriptions_on_adapter(a->get(), parameter_mapping, result_mapping, port_map);
|
input_descriptions_on_adapter(a->get(), parameter_mapping, result_mapping, port_map, portmap_name);
|
||||||
} else if (const auto& a = ngraph::as_type<ngraph::AttributeAdapter<std::vector<std::shared_ptr
|
} else if (const auto& a = ngraph::as_type<ngraph::AttributeAdapter<std::vector<std::shared_ptr
|
||||||
<ngraph::op::util::SubGraphOp::OutputDescription>>>>(&adapter)) {
|
<ngraph::op::util::MultiSubGraphOp::OutputDescription>>>>(&adapter)) {
|
||||||
uint32_t op_input_count = 0;
|
uint32_t op_input_count = 0;
|
||||||
for (auto c = m_xml_node.parent().child("input").first_child(); !c.empty(); c = c.next_sibling()) {
|
for (auto c = m_xml_node.parent().child("input").first_child(); !c.empty(); c = c.next_sibling()) {
|
||||||
op_input_count++;
|
op_input_count++;
|
||||||
}
|
}
|
||||||
output_descriptions_on_adapter(a->get(), op_input_count, result_mapping, port_map);
|
output_descriptions_on_adapter(a->get(), op_input_count, result_mapping, port_map, portmap_name);
|
||||||
} else if (const auto& a = ngraph::as_type<ngraph::AttributeAdapter<ngraph::op::v5::Loop::SpecialBodyPorts>>(&adapter)) {
|
} else if (const auto& a = ngraph::as_type<ngraph::AttributeAdapter<ngraph::op::v5::Loop::SpecialBodyPorts>>(&adapter)) {
|
||||||
special_body_ports_on_adapter(a->get(), parameter_mapping, result_mapping, port_map);
|
special_body_ports_on_adapter(a->get(), parameter_mapping, result_mapping, port_map);
|
||||||
}
|
}
|
||||||
@ -491,7 +513,7 @@ public:
|
|||||||
void on_adapter(
|
void on_adapter(
|
||||||
const std::string& name,
|
const std::string& name,
|
||||||
ngraph::ValueAccessor<std::shared_ptr<Function>>& adapter) override {
|
ngraph::ValueAccessor<std::shared_ptr<Function>>& adapter) override {
|
||||||
if (name == "body") {
|
if (name == "body" || name == "then_body" || name == "else_body") {
|
||||||
// TI, Loop do not have attributtes as regular ops, it is necessary to append "body"
|
// TI, Loop do not have attributtes as regular ops, it is necessary to append "body"
|
||||||
// to layer above (m_xml_node.parent()) as in ngfunction_2_ir() layer (m_xml_node) with empty attributes
|
// to layer above (m_xml_node.parent()) as in ngfunction_2_ir() layer (m_xml_node) with empty attributes
|
||||||
// is removed.
|
// is removed.
|
||||||
|
Binary file not shown.
@ -0,0 +1,438 @@
|
|||||||
|
<?xml version="1.0" ?>
|
||||||
|
<net name="if_diff_case" version="10">
|
||||||
|
<layers>
|
||||||
|
<layer id="0" name="x" type="Parameter" version="opset1">
|
||||||
|
<data element_type="f32" shape="2,4"/>
|
||||||
|
<output>
|
||||||
|
<port id="0" names="Func/PartitionedCall/input/_0:0,x:0" precision="FP32">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</output>
|
||||||
|
</layer>
|
||||||
|
<layer id="1" name="w" type="Parameter" version="opset1">
|
||||||
|
<data element_type="f32" shape="2,4"/>
|
||||||
|
<output>
|
||||||
|
<port id="0" names="Func/PartitionedCall/input/_3:0,w:0" precision="FP32">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</output>
|
||||||
|
</layer>
|
||||||
|
<layer id="2" name="PartitionedCall/model/if/Less" type="Less" version="opset1">
|
||||||
|
<data auto_broadcast="numpy"/>
|
||||||
|
<input>
|
||||||
|
<port id="0">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
<port id="1">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</input>
|
||||||
|
<output>
|
||||||
|
<port id="2" names="PartitionedCall/model/if/Less:0" precision="BOOL">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</output>
|
||||||
|
</layer>
|
||||||
|
<layer id="3" name="PartitionedCall/model/if/Const" type="Const" version="opset1">
|
||||||
|
<data element_type="i64" offset="0" shape="2" size="16"/>
|
||||||
|
<output>
|
||||||
|
<port id="0" names="PartitionedCall/model/if/Const:0" precision="I64">
|
||||||
|
<dim>2</dim>
|
||||||
|
</port>
|
||||||
|
</output>
|
||||||
|
</layer>
|
||||||
|
<layer id="4" name="PartitionedCall/model/if/All" type="ReduceLogicalAnd" version="opset1">
|
||||||
|
<data keep_dims="false"/>
|
||||||
|
<input>
|
||||||
|
<port id="0">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
<port id="1">
|
||||||
|
<dim>2</dim>
|
||||||
|
</port>
|
||||||
|
</input>
|
||||||
|
<output>
|
||||||
|
<port id="2" names="PartitionedCall/model/if/All:0" precision="BOOL"/>
|
||||||
|
</output>
|
||||||
|
</layer>
|
||||||
|
<layer id="5" name="y" type="Parameter" version="opset1">
|
||||||
|
<data element_type="f32" shape="2,4"/>
|
||||||
|
<output>
|
||||||
|
<port id="0" names="Func/PartitionedCall/input/_1:0,y:0" precision="FP32">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</output>
|
||||||
|
</layer>
|
||||||
|
<layer id="6" name="z" type="Parameter" version="opset1">
|
||||||
|
<data element_type="f32" shape="2,4"/>
|
||||||
|
<output>
|
||||||
|
<port id="0" names="Func/PartitionedCall/input/_2:0,z:0" precision="FP32">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</output>
|
||||||
|
</layer>
|
||||||
|
<layer id="7" name="PartitionedCall/model/if/cond" type="If" version="opset8">
|
||||||
|
<input>
|
||||||
|
<port id="0"/>
|
||||||
|
<port id="1">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
<port id="2">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
<port id="3">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
<port id="4">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</input>
|
||||||
|
<output>
|
||||||
|
<port id="5" names="PartitionedCall/model/if/cond/Identity:0,PartitionedCall/model/if/cond:0" precision="FP32">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
<port id="6" names="PartitionedCall/model/if/cond/Identity_1:0,PartitionedCall/model/if/cond:1" precision="FP32">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</output>
|
||||||
|
<then_port_map>
|
||||||
|
<input external_port_id="1" internal_layer_id="0"/>
|
||||||
|
<input external_port_id="2" internal_layer_id="1"/>
|
||||||
|
<input external_port_id="3" internal_layer_id="4"/>
|
||||||
|
<output external_port_id="1" internal_layer_id="6"/>
|
||||||
|
<output external_port_id="0" internal_layer_id="3"/>
|
||||||
|
</then_port_map>
|
||||||
|
<else_port_map>
|
||||||
|
<input external_port_id="2" internal_layer_id="1"/>
|
||||||
|
<input external_port_id="3" internal_layer_id="0"/>
|
||||||
|
<input external_port_id="4" internal_layer_id="2"/>
|
||||||
|
<output external_port_id="0" internal_layer_id="5"/>
|
||||||
|
<output external_port_id="1" internal_layer_id="7"/>
|
||||||
|
</else_port_map>
|
||||||
|
<then_body>
|
||||||
|
<layers>
|
||||||
|
<layer id="0" name="add_x" type="Parameter" version="opset1">
|
||||||
|
<data element_type="f32" shape="2,4"/>
|
||||||
|
<output>
|
||||||
|
<port id="0" names="add_x:0" precision="FP32">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</output>
|
||||||
|
</layer>
|
||||||
|
<layer id="1" name="add_w" type="Parameter" version="opset1">
|
||||||
|
<data element_type="f32" shape="2,4"/>
|
||||||
|
<output>
|
||||||
|
<port id="0" names="add_w:0" precision="FP32">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</output>
|
||||||
|
</layer>
|
||||||
|
<layer id="2" name="Add" type="Add" version="opset1">
|
||||||
|
<data auto_broadcast="numpy"/>
|
||||||
|
<input>
|
||||||
|
<port id="0">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
<port id="1">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</input>
|
||||||
|
<output>
|
||||||
|
<port id="2" names="Add:0" precision="FP32">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</output>
|
||||||
|
</layer>
|
||||||
|
<layer id="3" name="Identity/sink_port_0" type="Result" version="opset1">
|
||||||
|
<input>
|
||||||
|
<port id="0">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</input>
|
||||||
|
</layer>
|
||||||
|
<layer id="4" name="add_1_y" type="Parameter" version="opset1">
|
||||||
|
<data element_type="f32" shape="2,4"/>
|
||||||
|
<output>
|
||||||
|
<port id="0" names="add_1_y:0" precision="FP32">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</output>
|
||||||
|
</layer>
|
||||||
|
<layer id="5" name="Add_1" type="Add" version="opset1">
|
||||||
|
<data auto_broadcast="numpy"/>
|
||||||
|
<input>
|
||||||
|
<port id="0">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
<port id="1">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</input>
|
||||||
|
<output>
|
||||||
|
<port id="2" names="Add_1:0" precision="FP32">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</output>
|
||||||
|
</layer>
|
||||||
|
<layer id="6" name="Identity_1/sink_port_0" type="Result" version="opset1">
|
||||||
|
<input>
|
||||||
|
<port id="0">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</input>
|
||||||
|
</layer>
|
||||||
|
</layers>
|
||||||
|
<edges>
|
||||||
|
<edge from-layer="0" from-port="0" to-layer="2" to-port="0"/>
|
||||||
|
<edge from-layer="1" from-port="0" to-layer="2" to-port="1"/>
|
||||||
|
<edge from-layer="2" from-port="2" to-layer="3" to-port="0"/>
|
||||||
|
<edge from-layer="0" from-port="0" to-layer="5" to-port="0"/>
|
||||||
|
<edge from-layer="4" from-port="0" to-layer="5" to-port="1"/>
|
||||||
|
<edge from-layer="5" from-port="2" to-layer="6" to-port="0"/>
|
||||||
|
</edges>
|
||||||
|
</then_body>
|
||||||
|
<else_body>
|
||||||
|
<layers>
|
||||||
|
<layer id="0" name="add_y" type="Parameter" version="opset1">
|
||||||
|
<data element_type="f32" shape="2,4"/>
|
||||||
|
<output>
|
||||||
|
<port id="0" names="add_y:0" precision="FP32">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</output>
|
||||||
|
</layer>
|
||||||
|
<layer id="1" name="mul_w" type="Parameter" version="opset1">
|
||||||
|
<data element_type="f32" shape="2,4"/>
|
||||||
|
<output>
|
||||||
|
<port id="0" names="mul_w:0" precision="FP32">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</output>
|
||||||
|
</layer>
|
||||||
|
<layer id="2" name="mul_z" type="Parameter" version="opset1">
|
||||||
|
<data element_type="f32" shape="2,4"/>
|
||||||
|
<output>
|
||||||
|
<port id="0" names="mul_z:0" precision="FP32">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</output>
|
||||||
|
</layer>
|
||||||
|
<layer id="3" name="Mul" type="Multiply" version="opset1">
|
||||||
|
<data auto_broadcast="numpy"/>
|
||||||
|
<input>
|
||||||
|
<port id="0">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
<port id="1">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</input>
|
||||||
|
<output>
|
||||||
|
<port id="2" names="Mul:0" precision="FP32">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</output>
|
||||||
|
</layer>
|
||||||
|
<layer id="4" name="Add" type="Add" version="opset1">
|
||||||
|
<data auto_broadcast="numpy"/>
|
||||||
|
<input>
|
||||||
|
<port id="0">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
<port id="1">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</input>
|
||||||
|
<output>
|
||||||
|
<port id="2" names="Add:0" precision="FP32">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</output>
|
||||||
|
</layer>
|
||||||
|
<layer id="5" name="Identity/sink_port_0" type="Result" version="opset1">
|
||||||
|
<input>
|
||||||
|
<port id="0">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</input>
|
||||||
|
</layer>
|
||||||
|
<layer id="6" name="Add_1" type="Add" version="opset1">
|
||||||
|
<data auto_broadcast="numpy"/>
|
||||||
|
<input>
|
||||||
|
<port id="0">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
<port id="1">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</input>
|
||||||
|
<output>
|
||||||
|
<port id="2" names="Add_1:0" precision="FP32">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</output>
|
||||||
|
</layer>
|
||||||
|
<layer id="7" name="Identity_1/sink_port_0" type="Result" version="opset1">
|
||||||
|
<input>
|
||||||
|
<port id="0">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</input>
|
||||||
|
</layer>
|
||||||
|
</layers>
|
||||||
|
<edges>
|
||||||
|
<edge from-layer="1" from-port="0" to-layer="3" to-port="0"/>
|
||||||
|
<edge from-layer="2" from-port="0" to-layer="3" to-port="1"/>
|
||||||
|
<edge from-layer="0" from-port="0" to-layer="4" to-port="0"/>
|
||||||
|
<edge from-layer="3" from-port="2" to-layer="4" to-port="1"/>
|
||||||
|
<edge from-layer="4" from-port="2" to-layer="5" to-port="0"/>
|
||||||
|
<edge from-layer="2" from-port="0" to-layer="6" to-port="0"/>
|
||||||
|
<edge from-layer="1" from-port="0" to-layer="6" to-port="1"/>
|
||||||
|
<edge from-layer="6" from-port="2" to-layer="7" to-port="0"/>
|
||||||
|
</edges>
|
||||||
|
</else_body>
|
||||||
|
</layer>
|
||||||
|
<layer id="8" name="PartitionedCall/model/if/Relu_1" type="ReLU" version="opset1">
|
||||||
|
<input>
|
||||||
|
<port id="0">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</input>
|
||||||
|
<output>
|
||||||
|
<port id="1" names="Func/PartitionedCall/output/_5:0,Identity_1:0,PartitionedCall/Identity_1:0,PartitionedCall/model/if/Relu_1:0" precision="FP32">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</output>
|
||||||
|
</layer>
|
||||||
|
<layer id="9" name="Func/PartitionedCall/output/_5:0" type="Result" version="opset1">
|
||||||
|
<input>
|
||||||
|
<port id="0">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</input>
|
||||||
|
</layer>
|
||||||
|
<layer id="10" name="PartitionedCall/model/if/Relu" type="ReLU" version="opset1">
|
||||||
|
<input>
|
||||||
|
<port id="0">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</input>
|
||||||
|
<output>
|
||||||
|
<port id="1" names="Func/PartitionedCall/output/_4:0,Identity:0,PartitionedCall/Identity:0,PartitionedCall/model/if/Relu:0" precision="FP32">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</output>
|
||||||
|
</layer>
|
||||||
|
<layer id="11" name="Func/PartitionedCall/output/_4:0" type="Result" version="opset1">
|
||||||
|
<input>
|
||||||
|
<port id="0">
|
||||||
|
<dim>2</dim>
|
||||||
|
<dim>4</dim>
|
||||||
|
</port>
|
||||||
|
</input>
|
||||||
|
</layer>
|
||||||
|
</layers>
|
||||||
|
<edges>
|
||||||
|
<edge from-layer="0" from-port="0" to-layer="2" to-port="0"/>
|
||||||
|
<edge from-layer="1" from-port="0" to-layer="2" to-port="1"/>
|
||||||
|
<edge from-layer="2" from-port="2" to-layer="4" to-port="0"/>
|
||||||
|
<edge from-layer="3" from-port="0" to-layer="4" to-port="1"/>
|
||||||
|
<edge from-layer="4" from-port="2" to-layer="7" to-port="0"/>
|
||||||
|
<edge from-layer="0" from-port="0" to-layer="7" to-port="1"/>
|
||||||
|
<edge from-layer="1" from-port="0" to-layer="7" to-port="2"/>
|
||||||
|
<edge from-layer="5" from-port="0" to-layer="7" to-port="3"/>
|
||||||
|
<edge from-layer="6" from-port="0" to-layer="7" to-port="4"/>
|
||||||
|
<edge from-layer="7" from-port="6" to-layer="8" to-port="0"/>
|
||||||
|
<edge from-layer="8" from-port="1" to-layer="9" to-port="0"/>
|
||||||
|
<edge from-layer="7" from-port="5" to-layer="10" to-port="0"/>
|
||||||
|
<edge from-layer="10" from-port="1" to-layer="11" to-port="0"/>
|
||||||
|
</edges>
|
||||||
|
<meta_data>
|
||||||
|
<MO_version value="custom_mo/if_e1c378603739261e2f0e7334708eb6cf0b3c8ed1"/>
|
||||||
|
<cli_parameters>
|
||||||
|
<caffe_parser_path value="DIR"/>
|
||||||
|
<data_type value="FP32"/>
|
||||||
|
<disable_nhwc_to_nchw value="False"/>
|
||||||
|
<disable_omitting_optional value="False"/>
|
||||||
|
<disable_resnet_optimization value="False"/>
|
||||||
|
<disable_weights_compression value="False"/>
|
||||||
|
<enable_concat_optimization value="False"/>
|
||||||
|
<enable_flattening_nested_params value="False"/>
|
||||||
|
<enable_ssd_gluoncv value="False"/>
|
||||||
|
<extensions value="DIR"/>
|
||||||
|
<framework value="tf"/>
|
||||||
|
<freeze_placeholder_with_value value="{}"/>
|
||||||
|
<generate_deprecated_IR_V7 value="False"/>
|
||||||
|
<input value="x,y,z,w"/>
|
||||||
|
<input_model_is_text value="False"/>
|
||||||
|
<input_shape value="(2,4),(2,4),(2,4),(2,4)"/>
|
||||||
|
<k value="DIR\CustomLayersMapping.xml"/>
|
||||||
|
<keep_shape_ops value="True"/>
|
||||||
|
<legacy_ir_generation value="False"/>
|
||||||
|
<legacy_mxnet_model value="False"/>
|
||||||
|
<log_level value="ERROR"/>
|
||||||
|
<mean_scale_values value="{}"/>
|
||||||
|
<mean_values value="()"/>
|
||||||
|
<model_name value="if_diff_case"/>
|
||||||
|
<output_dir value="DIR"/>
|
||||||
|
<placeholder_data_types value="{}"/>
|
||||||
|
<placeholder_shapes value="{'x': array([2, 4], dtype=int64), 'y': array([2, 4], dtype=int64), 'z': array([2, 4], dtype=int64), 'w': array([2, 4], dtype=int64)}"/>
|
||||||
|
<progress value="False"/>
|
||||||
|
<remove_memory value="False"/>
|
||||||
|
<remove_output_softmax value="False"/>
|
||||||
|
<reverse_input_channels value="False"/>
|
||||||
|
<save_params_from_nd value="False"/>
|
||||||
|
<saved_model_dir value="DIR"/>
|
||||||
|
<scale_values value="()"/>
|
||||||
|
<silent value="False"/>
|
||||||
|
<static_shape value="False"/>
|
||||||
|
<stream_output value="False"/>
|
||||||
|
<transform value=""/>
|
||||||
|
<unset unset_cli_parameters="batch, counts, disable_fusing, disable_gfusing, finegrain_fusing, input_checkpoint, input_meta_graph, input_model, input_proto, input_symbol, mean_file, mean_file_offsets, move_to_preprocess, nd_prefix_name, output, pretrained_model_name, saved_model_tags, scale, tensorboard_logdir, tensorflow_custom_layer_libraries, tensorflow_custom_operations_config_update, tensorflow_object_detection_api_pipeline_config, tensorflow_use_custom_operations_config, transformations_config"/>
|
||||||
|
</cli_parameters>
|
||||||
|
</meta_data>
|
||||||
|
</net>
|
@ -77,7 +77,8 @@ INSTANTIATE_TEST_SUITE_P(IRSerialization, SerializationTest,
|
|||||||
std::make_tuple("pad_with_shape_of.xml", ""),
|
std::make_tuple("pad_with_shape_of.xml", ""),
|
||||||
std::make_tuple("conv_with_rt_info.xml", ""),
|
std::make_tuple("conv_with_rt_info.xml", ""),
|
||||||
std::make_tuple("loop_2d_add.xml", "loop_2d_add.bin"),
|
std::make_tuple("loop_2d_add.xml", "loop_2d_add.bin"),
|
||||||
std::make_tuple("nms5_dynamism.xml", "nms5_dynamism.bin")));
|
std::make_tuple("nms5_dynamism.xml", "nms5_dynamism.bin"),
|
||||||
|
std::make_tuple("if_diff_case.xml", "if_diff_case.bin")));
|
||||||
|
|
||||||
#ifdef NGRAPH_ONNX_FRONTEND_ENABLE
|
#ifdef NGRAPH_ONNX_FRONTEND_ENABLE
|
||||||
|
|
||||||
|
@ -60,8 +60,6 @@ static ov::PartialShape resolve_shape(const ov::PartialShape& then_pshape, const
|
|||||||
|
|
||||||
bool op::v8::If::visit_attributes(AttributeVisitor& visitor) {
|
bool op::v8::If::visit_attributes(AttributeVisitor& visitor) {
|
||||||
NGRAPH_OP_SCOPE(v8_If_visit_attributes);
|
NGRAPH_OP_SCOPE(v8_If_visit_attributes);
|
||||||
m_bodies[THEN_BODY_INDEX] = std::make_shared<ngraph::Function>(OutputVector{}, ParameterVector{}, "then_branch");
|
|
||||||
m_bodies[ELSE_BODY_INDEX] = std::make_shared<ngraph::Function>(OutputVector{}, ParameterVector{}, "else_branch");
|
|
||||||
visitor.on_attribute("then_body", m_bodies[THEN_BODY_INDEX]);
|
visitor.on_attribute("then_body", m_bodies[THEN_BODY_INDEX]);
|
||||||
visitor.on_attribute("else_body", m_bodies[ELSE_BODY_INDEX]);
|
visitor.on_attribute("else_body", m_bodies[ELSE_BODY_INDEX]);
|
||||||
visitor.on_attribute("then_inputs", m_input_descriptions[THEN_BODY_INDEX]);
|
visitor.on_attribute("then_inputs", m_input_descriptions[THEN_BODY_INDEX]);
|
||||||
|
@ -17,9 +17,7 @@
|
|||||||
|
|
||||||
using namespace ov;
|
using namespace ov;
|
||||||
|
|
||||||
XmlDeserializer::IoMap XmlDeserializer::updated_io_map(const pugi::xml_node& node) {
|
XmlDeserializer::IoMap XmlDeserializer::updated_io_map(const pugi::xml_node& node, const pugi::xml_node& body_node) {
|
||||||
auto body_node = node.child("body");
|
|
||||||
|
|
||||||
if (body_node.empty()) {
|
if (body_node.empty()) {
|
||||||
IE_THROW() << "Missing body part.";
|
IE_THROW() << "Missing body part.";
|
||||||
}
|
}
|
||||||
@ -42,13 +40,17 @@ XmlDeserializer::IoMap XmlDeserializer::updated_io_map(const pugi::xml_node& nod
|
|||||||
}
|
}
|
||||||
|
|
||||||
std::vector<std::shared_ptr<ngraph::op::util::SubGraphOp::InputDescription>> XmlDeserializer::parseInputDescription(
|
std::vector<std::shared_ptr<ngraph::op::util::SubGraphOp::InputDescription>> XmlDeserializer::parseInputDescription(
|
||||||
const pugi::xml_node& node) {
|
const pugi::xml_node& node,
|
||||||
|
const std::string& body_name,
|
||||||
|
const std::string& port_map_name) {
|
||||||
std::vector<std::shared_ptr<ngraph::op::util::SubGraphOp::InputDescription>> inputs;
|
std::vector<std::shared_ptr<ngraph::op::util::SubGraphOp::InputDescription>> inputs;
|
||||||
const auto up_io_map = updated_io_map(node);
|
auto body_node = node.child(body_name.c_str());
|
||||||
|
|
||||||
|
const auto up_io_map = updated_io_map(node, body_node);
|
||||||
|
|
||||||
// Parse PortMap: external_port_id for inputs does not always appear in consecutive order
|
// Parse PortMap: external_port_id for inputs does not always appear in consecutive order
|
||||||
std::map<uint64_t, pugi::xml_node> input_map;
|
std::map<uint64_t, pugi::xml_node> input_map;
|
||||||
FOREACH_CHILD (input, node.child("port_map"), "input") {
|
FOREACH_CHILD (input, node.child(port_map_name.c_str()), "input") {
|
||||||
int64_t ext_port_id = XMLParseUtils::GetInt64Attr(input, "external_port_id");
|
int64_t ext_port_id = XMLParseUtils::GetInt64Attr(input, "external_port_id");
|
||||||
input_map.emplace(ext_port_id, input);
|
input_map.emplace(ext_port_id, input);
|
||||||
}
|
}
|
||||||
@ -112,14 +114,17 @@ std::vector<std::shared_ptr<ngraph::op::util::SubGraphOp::InputDescription>> Xml
|
|||||||
return inputs;
|
return inputs;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<std::shared_ptr<ngraph::op::util::SubGraphOp::OutputDescription>> XmlDeserializer::parseOutputDescription(
|
std::vector<std::shared_ptr<ngraph::op::util::MultiSubGraphOp::OutputDescription>>
|
||||||
const pugi::xml_node& node) {
|
XmlDeserializer::parseOutputDescription(const pugi::xml_node& node,
|
||||||
std::vector<std::shared_ptr<ngraph::op::util::SubGraphOp::OutputDescription>> outputs;
|
const std::string& body_name,
|
||||||
const auto up_io_map = updated_io_map(node);
|
const std::string& port_map_name) {
|
||||||
|
std::vector<std::shared_ptr<ngraph::op::util::MultiSubGraphOp::OutputDescription>> outputs;
|
||||||
|
auto body_node = node.child(body_name.c_str());
|
||||||
|
const auto up_io_map = updated_io_map(node, body_node);
|
||||||
|
|
||||||
// Parse PortMap: outputs
|
// Parse PortMap: outputs
|
||||||
std::map<int64_t, pugi::xml_node> output_map;
|
std::map<int64_t, pugi::xml_node> output_map;
|
||||||
FOREACH_CHILD (output, node.child("port_map"), "output") {
|
FOREACH_CHILD (output, node.child(port_map_name.c_str()), "output") {
|
||||||
int64_t ext_port_id = XMLParseUtils::GetInt64Attr(output, "external_port_id");
|
int64_t ext_port_id = XMLParseUtils::GetInt64Attr(output, "external_port_id");
|
||||||
output_map.emplace(ext_port_id, output);
|
output_map.emplace(ext_port_id, output);
|
||||||
}
|
}
|
||||||
@ -144,20 +149,22 @@ std::vector<std::shared_ptr<ngraph::op::util::SubGraphOp::OutputDescription>> Xm
|
|||||||
|
|
||||||
const auto output_index = up_io_map.outputs.at(body_result_index);
|
const auto output_index = up_io_map.outputs.at(body_result_index);
|
||||||
|
|
||||||
outputs.push_back(std::make_shared<ngraph::op::util::SubGraphOp::ConcatOutputDescription>(output_index,
|
outputs.push_back(
|
||||||
output_number,
|
std::make_shared<ngraph::op::util::MultiSubGraphOp::ConcatOutputDescription>(output_index,
|
||||||
start,
|
output_number,
|
||||||
stride,
|
start,
|
||||||
part_size,
|
stride,
|
||||||
end,
|
part_size,
|
||||||
axis));
|
end,
|
||||||
|
axis));
|
||||||
} else {
|
} else {
|
||||||
// otherwise create ngraph::TensorIterator::BodyOutput. -1 means last iteration.
|
// otherwise create ngraph::TensorIterator::BodyOutput. -1 means last iteration.
|
||||||
const auto output_index = up_io_map.outputs.at(body_result_index);
|
const auto output_index = up_io_map.outputs.at(body_result_index);
|
||||||
|
|
||||||
outputs.push_back(std::make_shared<ngraph::op::util::SubGraphOp::BodyOutputDescription>(output_index,
|
outputs.push_back(
|
||||||
output_number,
|
std::make_shared<ngraph::op::util::MultiSubGraphOp::BodyOutputDescription>(output_index,
|
||||||
-1));
|
output_number,
|
||||||
|
-1));
|
||||||
}
|
}
|
||||||
output_number++;
|
output_number++;
|
||||||
}
|
}
|
||||||
@ -167,7 +174,8 @@ std::vector<std::shared_ptr<ngraph::op::util::SubGraphOp::OutputDescription>> Xm
|
|||||||
|
|
||||||
ngraph::op::v5::Loop::SpecialBodyPorts XmlDeserializer::parsePurposeAttribute(const pugi::xml_node& node) {
|
ngraph::op::v5::Loop::SpecialBodyPorts XmlDeserializer::parsePurposeAttribute(const pugi::xml_node& node) {
|
||||||
ngraph::op::v5::Loop::SpecialBodyPorts result = {-1, -1};
|
ngraph::op::v5::Loop::SpecialBodyPorts result = {-1, -1};
|
||||||
const auto up_io_map = updated_io_map(node);
|
auto body_node = node.child("body");
|
||||||
|
const auto up_io_map = updated_io_map(node, body_node);
|
||||||
|
|
||||||
NGRAPH_CHECK(!up_io_map.inputs.empty() || !up_io_map.outputs.empty(),
|
NGRAPH_CHECK(!up_io_map.inputs.empty() || !up_io_map.outputs.empty(),
|
||||||
"No parameters or results found in body Function.");
|
"No parameters or results found in body Function.");
|
||||||
@ -209,18 +217,30 @@ ngraph::op::v5::Loop::SpecialBodyPorts XmlDeserializer::parsePurposeAttribute(co
|
|||||||
void XmlDeserializer::on_adapter(const std::string& name, ngraph::ValueAccessor<void>& adapter) {
|
void XmlDeserializer::on_adapter(const std::string& name, ngraph::ValueAccessor<void>& adapter) {
|
||||||
static const std::unordered_set<std::string> skip_names = {"input_descriptions",
|
static const std::unordered_set<std::string> skip_names = {"input_descriptions",
|
||||||
"output_descriptions",
|
"output_descriptions",
|
||||||
"special_body_ports"};
|
"special_body_ports",
|
||||||
|
"then_inputs",
|
||||||
|
"else_inputs",
|
||||||
|
"then_outputs",
|
||||||
|
"else_outputs"};
|
||||||
std::string val;
|
std::string val;
|
||||||
|
|
||||||
// for TensorIterator look for 'port_map' as 'data' does not exist
|
// for TensorIterator look for 'port_map' as 'data' does not exist
|
||||||
if (m_node.child("port_map")) {
|
if (m_node.child("port_map") || m_node.child("then_port_map") || m_node.child("else_port_map")) {
|
||||||
if (auto a = ngraph::as_type<
|
std::string body_name = "body";
|
||||||
ngraph::AttributeAdapter<std::vector<std::shared_ptr<ngraph::op::util::SubGraphOp::InputDescription>>>>(
|
std::string port_map_name = "port_map";
|
||||||
&adapter)) {
|
if (name == "then_inputs" || name == "then_outputs") {
|
||||||
a->set(parseInputDescription(m_node));
|
body_name = "then_body";
|
||||||
|
port_map_name = "then_port_map";
|
||||||
|
} else if (name == "else_inputs" || name == "else_outputs") {
|
||||||
|
body_name = "else_body";
|
||||||
|
port_map_name = "else_port_map";
|
||||||
|
}
|
||||||
|
if (auto a = ngraph::as_type<ngraph::AttributeAdapter<
|
||||||
|
std::vector<std::shared_ptr<ngraph::op::util::MultiSubGraphOp::InputDescription>>>>(&adapter)) {
|
||||||
|
a->set(parseInputDescription(m_node, body_name, port_map_name));
|
||||||
} else if (auto a = ngraph::as_type<ngraph::AttributeAdapter<
|
} else if (auto a = ngraph::as_type<ngraph::AttributeAdapter<
|
||||||
std::vector<std::shared_ptr<ngraph::op::util::SubGraphOp::OutputDescription>>>>(&adapter)) {
|
std::vector<std::shared_ptr<ngraph::op::util::MultiSubGraphOp::OutputDescription>>>>(&adapter)) {
|
||||||
a->set(parseOutputDescription(m_node));
|
a->set(parseOutputDescription(m_node, body_name, port_map_name));
|
||||||
} else if (auto a =
|
} else if (auto a =
|
||||||
ngraph::as_type<ngraph::AttributeAdapter<ngraph::op::v5::Loop::SpecialBodyPorts>>(&adapter)) {
|
ngraph::as_type<ngraph::AttributeAdapter<ngraph::op::v5::Loop::SpecialBodyPorts>>(&adapter)) {
|
||||||
a->set(parsePurposeAttribute(m_node));
|
a->set(parsePurposeAttribute(m_node));
|
||||||
@ -362,7 +382,8 @@ void XmlDeserializer::on_adapter(const std::string& name, ngraph::ValueAccessor<
|
|||||||
void XmlDeserializer::on_adapter(const std::string& name,
|
void XmlDeserializer::on_adapter(const std::string& name,
|
||||||
ngraph::ValueAccessor<std::shared_ptr<ngraph::Function>>& adapter) {
|
ngraph::ValueAccessor<std::shared_ptr<ngraph::Function>>& adapter) {
|
||||||
std::shared_ptr<ngraph::Function> ngraph_function;
|
std::shared_ptr<ngraph::Function> ngraph_function;
|
||||||
if (!name.compare("body")) {
|
|
||||||
|
if (!name.compare("body") || !name.compare("then_body") || !name.compare("else_body")) {
|
||||||
auto body_node = m_node.child(name.c_str());
|
auto body_node = m_node.child(name.c_str());
|
||||||
if (body_node.empty()) {
|
if (body_node.empty()) {
|
||||||
IE_THROW() << "TensorIterator has no body.";
|
IE_THROW() << "TensorIterator has no body.";
|
||||||
|
@ -148,16 +148,16 @@ private:
|
|||||||
/// \brief Traverses port_map in order to create vector of InputDescription shared_ptrs.
|
/// \brief Traverses port_map in order to create vector of InputDescription shared_ptrs.
|
||||||
/// Shall be used only for ops which have port_map attribute.
|
/// Shall be used only for ops which have port_map attribute.
|
||||||
/// \param node xml op representation
|
/// \param node xml op representation
|
||||||
std::vector<std::shared_ptr<ngraph::op::util::SubGraphOp::InputDescription>> parseInputDescription(
|
std::vector<std::shared_ptr<ngraph::op::util::SubGraphOp::InputDescription>>
|
||||||
const pugi::xml_node& node);
|
parseInputDescription(const pugi::xml_node& node, const std::string& body_name, const std::string& port_map_name);
|
||||||
/// \brief Traverses port_map in order to create vector of OutputDescription shared_ptrs.
|
/// \brief Traverses port_map in order to create vector of OutputDescription shared_ptrs.
|
||||||
/// Shall be used only for ops which have port_map attribute.
|
/// Shall be used only for ops which have port_map attribute.
|
||||||
/// \param node xml op representation
|
/// \param node xml op representation
|
||||||
std::vector<std::shared_ptr<ngraph::op::util::SubGraphOp::OutputDescription>> parseOutputDescription(
|
std::vector<std::shared_ptr<ngraph::op::util::SubGraphOp::OutputDescription>>
|
||||||
const pugi::xml_node& node);
|
parseOutputDescription(const pugi::xml_node& node, const std::string& body_name, const std::string& port_map_name);
|
||||||
|
|
||||||
// TODO consider to call only once per layer/TI-Loop node
|
// TODO consider to call only once per layer/TI-Loop node
|
||||||
IoMap updated_io_map(const pugi::xml_node& node);
|
IoMap updated_io_map(const pugi::xml_node& node, const pugi::xml_node& body_node);
|
||||||
|
|
||||||
/// \brief Traverses xml node representation in order to create nGraph function for it.
|
/// \brief Traverses xml node representation in order to create nGraph function for it.
|
||||||
/// \param node xml node representation
|
/// \param node xml node representation
|
||||||
|
@ -292,6 +292,7 @@ set(SRC
|
|||||||
visitors/op/grn.cpp
|
visitors/op/grn.cpp
|
||||||
visitors/op/group_conv.cpp
|
visitors/op/group_conv.cpp
|
||||||
visitors/op/interpolate.cpp
|
visitors/op/interpolate.cpp
|
||||||
|
visitors/op/if.cpp
|
||||||
visitors/op/less_equal.cpp
|
visitors/op/less_equal.cpp
|
||||||
visitors/op/less.cpp
|
visitors/op/less.cpp
|
||||||
visitors/op/log.cpp
|
visitors/op/log.cpp
|
||||||
@ -622,7 +623,8 @@ target_link_libraries(unit-test PRIVATE ngraph_test_util
|
|||||||
interpreter_backend
|
interpreter_backend
|
||||||
Threads::Threads
|
Threads::Threads
|
||||||
openvino::conditional_compilation
|
openvino::conditional_compilation
|
||||||
frontend_manager)
|
frontend_manager
|
||||||
|
PUBLIC commonTestUtils)
|
||||||
|
|
||||||
# Protobuf-lite does not support parsing files from prototxt format
|
# Protobuf-lite does not support parsing files from prototxt format
|
||||||
# Since most of the onnx models are stored in this format it have to be disabled
|
# Since most of the onnx models are stored in this format it have to be disabled
|
||||||
|
@ -96,6 +96,21 @@ public:
|
|||||||
virtual operator HostTensorPtr&() {
|
virtual operator HostTensorPtr&() {
|
||||||
NGRAPH_CHECK(false, "Invalid type access");
|
NGRAPH_CHECK(false, "Invalid type access");
|
||||||
}
|
}
|
||||||
|
virtual operator std::shared_ptr<ov::Function>&() {
|
||||||
|
NGRAPH_CHECK(false, "Invalid type access");
|
||||||
|
}
|
||||||
|
virtual operator std::shared_ptr<ngraph::op::util::MultiSubGraphOp::OutputDescription>&() {
|
||||||
|
NGRAPH_CHECK(false, "Invalid type access");
|
||||||
|
}
|
||||||
|
virtual operator std::shared_ptr<ngraph::op::util::MultiSubGraphOp::InputDescription>&() {
|
||||||
|
NGRAPH_CHECK(false, "Invalid type access");
|
||||||
|
}
|
||||||
|
virtual operator std::vector<std::shared_ptr<ngraph::op::util::MultiSubGraphOp::OutputDescription>>&() {
|
||||||
|
NGRAPH_CHECK(false, "Invalid type access");
|
||||||
|
}
|
||||||
|
virtual operator std::vector<std::shared_ptr<ngraph::op::util::MultiSubGraphOp::InputDescription>>&() {
|
||||||
|
NGRAPH_CHECK(false, "Invalid type access");
|
||||||
|
}
|
||||||
uint64_t get_index() {
|
uint64_t get_index() {
|
||||||
return m_index;
|
return m_index;
|
||||||
}
|
}
|
||||||
@ -178,11 +193,22 @@ protected:
|
|||||||
class DeserializeAttributeVisitor : public AttributeVisitor {
|
class DeserializeAttributeVisitor : public AttributeVisitor {
|
||||||
public:
|
public:
|
||||||
DeserializeAttributeVisitor(ValueMap& value_map) : m_values(value_map) {}
|
DeserializeAttributeVisitor(ValueMap& value_map) : m_values(value_map) {}
|
||||||
|
|
||||||
|
void on_adapter(const std::string& name, ValueAccessor<std::shared_ptr<ov::Function>>& adapter) override {
|
||||||
|
adapter.set(m_values.get<std::shared_ptr<ov::Function>>(name));
|
||||||
|
}
|
||||||
|
|
||||||
void on_adapter(const std::string& name, ValueAccessor<void>& adapter) override {
|
void on_adapter(const std::string& name, ValueAccessor<void>& adapter) override {
|
||||||
if (auto a = ::ngraph::as_type<::ngraph::AttributeAdapter<std::shared_ptr<ngraph::runtime::AlignedBuffer>>>(
|
if (auto a = ::ngraph::as_type<::ngraph::AttributeAdapter<std::shared_ptr<ngraph::runtime::AlignedBuffer>>>(
|
||||||
&adapter)) {
|
&adapter)) {
|
||||||
auto& data = m_values.get<HostTensorPtr>(name);
|
auto& data = m_values.get<HostTensorPtr>(name);
|
||||||
data->read(a->get()->get_ptr(), a->get()->size());
|
data->read(a->get()->get_ptr(), a->get()->size());
|
||||||
|
} else if (auto a = ngraph::as_type<ngraph::AttributeAdapter<
|
||||||
|
std::vector<std::shared_ptr<ngraph::op::util::SubGraphOp::OutputDescription>>>>(&adapter)) {
|
||||||
|
a->set(m_values.get<std::vector<std::shared_ptr<ngraph::op::util::SubGraphOp::OutputDescription>>>(name));
|
||||||
|
} else if (auto a = ngraph::as_type<ngraph::AttributeAdapter<
|
||||||
|
std::vector<std::shared_ptr<ngraph::op::util::SubGraphOp::InputDescription>>>>(&adapter)) {
|
||||||
|
a->set(m_values.get<std::vector<std::shared_ptr<ngraph::op::util::SubGraphOp::InputDescription>>>(name));
|
||||||
} else {
|
} else {
|
||||||
NGRAPH_CHECK(false, "Attribute \"", name, "\" cannot be unmarshalled");
|
NGRAPH_CHECK(false, "Attribute \"", name, "\" cannot be unmarshalled");
|
||||||
}
|
}
|
||||||
@ -247,12 +273,22 @@ class SerializeAttributeVisitor : public AttributeVisitor {
|
|||||||
public:
|
public:
|
||||||
SerializeAttributeVisitor(ValueMap& value_map) : m_values(value_map) {}
|
SerializeAttributeVisitor(ValueMap& value_map) : m_values(value_map) {}
|
||||||
|
|
||||||
|
void on_adapter(const std::string& name, ValueAccessor<std::shared_ptr<ov::Function>>& adapter) override {
|
||||||
|
m_values.insert(name, adapter.get());
|
||||||
|
}
|
||||||
|
|
||||||
void on_adapter(const std::string& name, ValueAccessor<void>& adapter) override {
|
void on_adapter(const std::string& name, ValueAccessor<void>& adapter) override {
|
||||||
if (auto a = ::ngraph::as_type<::ngraph::AttributeAdapter<std::shared_ptr<ngraph::runtime::AlignedBuffer>>>(
|
if (auto a = ::ngraph::as_type<::ngraph::AttributeAdapter<std::shared_ptr<ngraph::runtime::AlignedBuffer>>>(
|
||||||
&adapter)) {
|
&adapter)) {
|
||||||
HostTensorPtr data = std::make_shared<HostTensor>(element::u8, Shape{a->get()->size()});
|
HostTensorPtr data = std::make_shared<HostTensor>(element::u8, Shape{a->get()->size()});
|
||||||
data->write(a->get()->get_ptr(), a->get()->size());
|
data->write(a->get()->get_ptr(), a->get()->size());
|
||||||
m_values.insert(name, data);
|
m_values.insert(name, data);
|
||||||
|
} else if (auto a = ngraph::as_type<ngraph::AttributeAdapter<
|
||||||
|
std::vector<std::shared_ptr<ngraph::op::util::SubGraphOp::OutputDescription>>>>(&adapter)) {
|
||||||
|
m_values.insert_vector(name, a->get());
|
||||||
|
} else if (auto a = ngraph::as_type<ngraph::AttributeAdapter<
|
||||||
|
std::vector<std::shared_ptr<ngraph::op::util::SubGraphOp::InputDescription>>>>(&adapter)) {
|
||||||
|
m_values.insert_vector(name, a->get());
|
||||||
} else {
|
} else {
|
||||||
NGRAPH_CHECK(false, "Attribute \"", name, "\" cannot be marshalled");
|
NGRAPH_CHECK(false, "Attribute \"", name, "\" cannot be marshalled");
|
||||||
}
|
}
|
||||||
|
48
ngraph/test/visitors/op/if.cpp
Normal file
48
ngraph/test/visitors/op/if.cpp
Normal file
@ -0,0 +1,48 @@
|
|||||||
|
// Copyright (C) 2018-2021 Intel Corporation
|
||||||
|
// SPDX-License-Identifier: Apache-2.0
|
||||||
|
//
|
||||||
|
|
||||||
|
#include "common_test_utils/ngraph_test_utils.hpp"
|
||||||
|
#include "gtest/gtest.h"
|
||||||
|
#include "ngraph/ngraph.hpp"
|
||||||
|
#include "ngraph/op/util/attr_types.hpp"
|
||||||
|
#include "ngraph/opsets/opset8.hpp"
|
||||||
|
#include "util/visitor.hpp"
|
||||||
|
|
||||||
|
using namespace std;
|
||||||
|
using namespace ngraph;
|
||||||
|
using namespace ngraph::opset8;
|
||||||
|
using ngraph::test::NodeBuilder;
|
||||||
|
using ngraph::test::ValueMap;
|
||||||
|
|
||||||
|
TEST(attributes, if_op) {
|
||||||
|
NodeBuilder::get_ops().register_factory<If>();
|
||||||
|
auto X = make_shared<Parameter>(element::f32, Shape{1, 2, 2});
|
||||||
|
auto Y = make_shared<Parameter>(element::f32, Shape{1, 2, 2});
|
||||||
|
auto cond = std::make_shared<Constant>(element::boolean, Shape{1}, true);
|
||||||
|
auto cond2 = std::make_shared<Constant>(element::boolean, Shape{1}, false);
|
||||||
|
auto Xt = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
|
||||||
|
auto Yt = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
|
||||||
|
auto Xe = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
|
||||||
|
auto Ye = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
|
||||||
|
auto then_op = std::make_shared<op::v1::Multiply>(Xt, Yt);
|
||||||
|
auto res0 = make_shared<op::Result>(then_op);
|
||||||
|
auto res1 = make_shared<op::Result>(Xe);
|
||||||
|
auto then_body = make_shared<ngraph::Function>(OutputVector{res0}, ParameterVector{Xt, Yt});
|
||||||
|
auto else_body = make_shared<ngraph::Function>(OutputVector{res1}, ParameterVector{Xe});
|
||||||
|
auto if_op = make_shared<If>(cond);
|
||||||
|
if_op->set_then_body(then_body);
|
||||||
|
if_op->set_else_body(else_body);
|
||||||
|
if_op->set_input(X, Xt, Xe);
|
||||||
|
if_op->set_input(Y, Yt, nullptr);
|
||||||
|
if_op->set_output(res0, res1);
|
||||||
|
if_op->validate_and_infer_types();
|
||||||
|
NodeBuilder builder(if_op);
|
||||||
|
auto g_if = ov::as_type_ptr<If>(builder.create());
|
||||||
|
EXPECT_EQ(g_if->get_input_descriptions(0), if_op->get_input_descriptions(0));
|
||||||
|
EXPECT_EQ(g_if->get_input_descriptions(1), if_op->get_input_descriptions(1));
|
||||||
|
EXPECT_EQ(g_if->get_output_descriptions(0), if_op->get_output_descriptions(0));
|
||||||
|
EXPECT_EQ(g_if->get_output_descriptions(1), if_op->get_output_descriptions(1));
|
||||||
|
EXPECT_TRUE(compare_functions(g_if->get_then_body(), if_op->get_then_body()).first);
|
||||||
|
EXPECT_TRUE(compare_functions(g_if->get_else_body(), if_op->get_else_body()).first);
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user