diff --git a/src/common/transformations/include/transformations/common_optimizations/nop_elimination.hpp b/src/common/transformations/include/transformations/common_optimizations/nop_elimination.hpp index 2065dd97825..813b40dc171 100644 --- a/src/common/transformations/include/transformations/common_optimizations/nop_elimination.hpp +++ b/src/common/transformations/include/transformations/common_optimizations/nop_elimination.hpp @@ -14,6 +14,7 @@ class TRANSFORMATIONS_API EliminateConcat; class TRANSFORMATIONS_API EliminateConvert; class TRANSFORMATIONS_API EliminateConvertNonZero; class TRANSFORMATIONS_API EliminateEltwise; +class TRANSFORMATIONS_API EliminateScatterUpdate; class TRANSFORMATIONS_API EliminatePad; class TRANSFORMATIONS_API EliminateSplit; class TRANSFORMATIONS_API EliminateSplitConcat; @@ -104,6 +105,16 @@ public: EliminateEltwise(); }; +/** + * @ingroup ie_transformation_common_api + * @brief EliminateScatterUpdate eliminates scatter ops that do nothing (updates/indices are empty) + */ +class ov::pass::EliminateScatterUpdate : public ov::pass::MatcherPass { +public: + OPENVINO_RTTI("EliminateScatterUpdate", "0"); + EliminateScatterUpdate(); +}; + class ov::pass::NopElimination : public GraphRewrite { public: OPENVINO_RTTI("NopElimination", "0"); @@ -127,6 +138,7 @@ using ov::pass::EliminateConvert; using ov::pass::EliminateConvertNonZero; using ov::pass::EliminateEltwise; using ov::pass::EliminatePad; +using ov::pass::EliminateScatterUpdate; using ov::pass::EliminateSplit; using ov::pass::EliminateSplitConcat; using ov::pass::EliminateSqueeze; diff --git a/src/common/transformations/src/transformations/common_optimizations/moc_transformations.cpp b/src/common/transformations/src/transformations/common_optimizations/moc_transformations.cpp index 5f58f86c5b2..c88e828ba55 100644 --- a/src/common/transformations/src/transformations/common_optimizations/moc_transformations.cpp +++ b/src/common/transformations/src/transformations/common_optimizations/moc_transformations.cpp @@ -109,6 +109,7 @@ bool ov::pass::MOCTransformations::run_on_model(const std::shared_ptr #include +#include "compare.hpp" #include "itt.hpp" using namespace std; @@ -718,6 +719,30 @@ pass::EliminateEltwise::EliminateEltwise() { this->register_matcher(m, callback); } +pass::EliminateScatterUpdate::EliminateScatterUpdate() { + MATCHER_SCOPE(EliminateScatterUpdate); + auto scatter_pattern = + pattern::wrap_type(); + + matcher_pass_callback callback = [=](pattern::Matcher& m) { + auto scatter = m.get_match_root(); + const auto& indices_pshape = scatter->get_input_partial_shape(1); + const auto& updates_pshape = scatter->get_input_partial_shape(2); + + auto has_zero = [](const ov::PartialShape& shape) -> bool { + return std::any_of(shape.cbegin(), shape.cend(), ov::cmp::Equal(0)); + }; + if (has_zero(indices_pshape) || has_zero(updates_pshape)) { + return replace_output_update_name(scatter->output(0), scatter->input_value(0)); + } else { + return false; + } + }; + + auto m = make_shared(scatter_pattern, matcher_name); + this->register_matcher(m, callback); +} + ngraph::pass::NopElimination::NopElimination(bool use_shape_for_elimination) { // shape-agnostic transformations ADD_MATCHER_FOR_THIS(EliminatePad) @@ -732,6 +757,7 @@ ngraph::pass::NopElimination::NopElimination(bool use_shape_for_elimination) { // shape-dependent transformations if (use_shape_for_elimination) { + ADD_MATCHER_FOR_THIS(EliminateScatterUpdate) ADD_MATCHER_FOR_THIS(EliminateReshape) ADD_MATCHER_FOR_THIS(EliminateSqueeze) ADD_MATCHER_FOR_THIS(EliminateUnsqueeze) diff --git a/src/common/transformations/src/transformations/common_optimizations/remove_concat_zero_dim_input.cpp b/src/common/transformations/src/transformations/common_optimizations/remove_concat_zero_dim_input.cpp index fd54d65c966..edd5b66671b 100644 --- a/src/common/transformations/src/transformations/common_optimizations/remove_concat_zero_dim_input.cpp +++ b/src/common/transformations/src/transformations/common_optimizations/remove_concat_zero_dim_input.cpp @@ -45,7 +45,19 @@ ov::pass::RemoveConcatZeroDimInput::RemoveConcatZeroDimInput() { bool inputs_removed = concat->get_input_size() > concat_inputs.size(); if (inputs_removed) { - concat->set_arguments(concat_inputs); + if (concat_inputs.empty()) { + if (concat->get_output_element_type(0).is_dynamic()) + return false; + if (concat->get_output_partial_shape(0).is_dynamic()) + return false; + const auto& empty_constant = opset8::Constant::create(concat->get_output_element_type(0), + concat->get_output_partial_shape(0).to_shape(), + {}); + concat->output(0).replace(empty_constant); + empty_constant->set_friendly_name(concat->get_friendly_name()); + } else { + concat->set_arguments(concat_inputs); + } } return inputs_removed; }; diff --git a/src/common/transformations/tests/common_optimizations/remove_concat_zero_dim_input_test.cpp b/src/common/transformations/tests/common_optimizations/remove_concat_zero_dim_input_test.cpp index 9823d37cbb5..7db279e01a3 100644 --- a/src/common/transformations/tests/common_optimizations/remove_concat_zero_dim_input_test.cpp +++ b/src/common/transformations/tests/common_optimizations/remove_concat_zero_dim_input_test.cpp @@ -178,3 +178,24 @@ TEST_F(TransformationTestsF, RemoveConcatZeroDimTwoInputs) { function_ref = std::make_shared(ov::NodeVector{concat}, ov::ParameterVector{input1}); } } + +TEST_F(TransformationTestsF, RemoveConcatZeroDimAllInputsEmpty) { + { + auto input1 = std::make_shared(ov::element::f32, + ov::PartialShape{1, 0, 1}); + auto input2 = std::make_shared(ov::element::f32, + ov::PartialShape{1, 0, 1}); + + int64_t axis = -1; + auto concat = std::make_shared(ov::OutputVector{input1, input2}, axis); + + function = std::make_shared(ov::NodeVector{concat}, ov::ParameterVector{input1, input2}); + + manager.register_pass(); + } + + { + auto concat = std::make_shared(ov::element::f32, ov::Shape{1, 0, 2}, std::vector{}); + function_ref = std::make_shared(ov::NodeVector{concat}, ov::ParameterVector{}); + } +} diff --git a/src/inference/src/cnn_network_ngraph_impl.cpp b/src/inference/src/cnn_network_ngraph_impl.cpp index e493417ac70..28bc2d48d56 100644 --- a/src/inference/src/cnn_network_ngraph_impl.cpp +++ b/src/inference/src/cnn_network_ngraph_impl.cpp @@ -35,6 +35,7 @@ #include #include #include +#include #include #include #include @@ -150,6 +151,7 @@ CNNNetworkNGraphImpl::CNNNetworkNGraphImpl(const std::shared_ptr& nGra using namespace ngraph::pass; REGISTER_PASS(m, FixRtInfo) using namespace ov::pass; + REGISTER_PASS(m, EliminateScatterUpdate) REGISTER_PASS(m, RemoveConcatZeroDimInput) REGISTER_PASS(m, RemoveMultiSubGraphOpDanglingParams) REGISTER_PASS(m, FoldSubgraphEmptyInputs)