Skip to content

Commit 2ee3acb

Browse files
committed
Support for more complex cases with data paddings after the crop axis
1 parent 61e5d61 commit 2ee3acb

File tree

2 files changed

+36
-17
lines changed

2 files changed

+36
-17
lines changed

src/plugins/intel_gpu/src/graph/impls/ocl/crop.cpp

+20-9
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,8 @@
88
#include "eltwise/eltwise_kernel_selector.h"
99
#include "eltwise/eltwise_kernel_base.h"
1010

11+
#include "openvino/core/validation_util.hpp"
12+
1113
namespace cldnn {
1214
namespace ocl {
1315

@@ -56,18 +58,27 @@ struct crop_impl : typed_primitive_impl_ocl<crop> {
5658

5759
update_shapes(*_kernel_data.params, impl_param);
5860

59-
// Reset input_layout padding as the offset configured by crop should affect only "data"
60-
// area and shouldn't depend on input_layout paddings.
61-
// For example, for an input shape like: [1, 32, 128 (pad_before=512, pad_after=0), 8]
61+
// The padding sizes are reset to 0 up to crop_axis, as kernel reads data using
62+
// "input[GET_INDEX(INPUT, order) + runtime_offset]", where GET_INDEX handles all paddings before
63+
// specified axis. However, for proper runtime offset calculation, we have to consider paddings
64+
// after the crop_axis, which requires subtracting input_offset from the runtime buffer, since
65+
// padding for the first element is already included in the GET_INDEX() call.
66+
// For example, for input shape like: [1, 32, 128 (pad_before=512, pad_after=0), 8 (pad_before=4, pad_after=4)]
6267
// with crop_axis=2 and split_lengths = {64, 64},
63-
// runtime_offset should be set in terms of [1, 32, 128, 8] shape, as the kernel reads data
64-
// using "input[GET_INDEX(INPUT, order) + runtime_offset]", where GET_INDEX already reflects input
65-
// data paddings.
66-
// So crop.out0's runtime_offset=0 and crop.out1's runtime_offset=512.
68+
// runtime_offset should be set in terms of [1, 32, 128 (pad_before=0, pad_after=0), 8 (pad_before=4, pad_after=4)] shape.
69+
// So crop.out0's runtime_offset=0 and crop.out1's runtime_offset=1024.
70+
6771
auto input_layout = impl_param.get_input_layout();
68-
input_layout.data_padding = padding();
72+
auto crop_axis = ov::util::normalize(impl_param.typed_desc<crop>()->axis, static_cast<int64_t>(input_layout.get_partial_shape().size()));
73+
74+
input_layout.data_padding._dynamic_dims_mask = padding::EMPTY_MASK;
75+
for (size_t i = 0; i <= static_cast<size_t>(crop_axis); i++) {
76+
input_layout.data_padding._lower_size[i] = 0;
77+
input_layout.data_padding._upper_size[i] = 0;
78+
}
6979

70-
auto runtime_offset = convert_data_tensor(input_layout, impl_param.input_offsets[0]).GetFirstElementOffset();
80+
auto input_offset = convert_data_tensor(input_layout).GetFirstElementOffset();
81+
auto runtime_offset = convert_data_tensor(input_layout, impl_param.input_offsets[0]).GetFirstElementOffset() - input_offset;
7182
kernel_selector::ScalarDescriptor s;
7283
s.t = kernel_selector::ScalarDescriptor::Types::UINT32;
7384
s.v.u32 = static_cast<uint32_t>(runtime_offset);

src/plugins/intel_gpu/tests/unit/test_cases/crop_gpu_test.cpp

+16-8
Original file line numberDiff line numberDiff line change
@@ -1485,16 +1485,24 @@ TEST(crop_gpu, dynamic_input_padding_varaidic_split) {
14851485
auto y_size = 128;
14861486
auto x_size = 4;
14871487

1488-
auto axis = 2;
1488+
auto split_axis = 2;
1489+
auto data_y_pad_axis = 2;
1490+
auto data_x_pad_axis = 3;
14891491
auto input_y_pad_before = 64;
14901492
auto input_y_pad_after = 32;
1493+
auto input_x_pad_before = 8;
1494+
auto input_x_pad_after = 2;
14911495

14921496
auto input_dyn_layout = layout{ ov::PartialShape{-1, feature_num, y_size, x_size}, data_types::f32, format::bfyx };
1493-
input_dyn_layout.data_padding._dynamic_dims_mask[axis] = 1;
1497+
input_dyn_layout.data_padding._dynamic_dims_mask[data_y_pad_axis] = 1;
1498+
input_dyn_layout.data_padding._lower_size[data_x_pad_axis] = input_x_pad_before;
1499+
input_dyn_layout.data_padding._upper_size[data_x_pad_axis] = input_x_pad_after;
14941500

14951501
auto input_actual_layout = layout{ ov::PartialShape{batch_num, feature_num, y_size, x_size}, data_types::f32, format::bfyx };
1496-
input_actual_layout.data_padding._lower_size[axis] = input_y_pad_before;
1497-
input_actual_layout.data_padding._upper_size[axis] = input_y_pad_after;
1502+
input_actual_layout.data_padding._lower_size[data_y_pad_axis] = input_y_pad_before;
1503+
input_actual_layout.data_padding._upper_size[data_y_pad_axis] = input_y_pad_after;
1504+
input_actual_layout.data_padding._lower_size[data_x_pad_axis] = input_x_pad_before;
1505+
input_actual_layout.data_padding._upper_size[data_x_pad_axis] = input_x_pad_after;
14981506

14991507
auto input_mem = engine.allocate_memory(input_actual_layout);
15001508
auto axis_mem = engine.allocate_memory({ {}, data_types::i64, format::bfyx });
@@ -1506,16 +1514,16 @@ TEST(crop_gpu, dynamic_input_padding_varaidic_split) {
15061514
cldnn::crop_ngraph_op_mode op_mode = cldnn::crop_ngraph_op_mode::variadic_split;
15071515
topology topology;
15081516
topology.add(input_layout("input", input_dyn_layout));
1509-
topology.add(data("axis", axis_mem));
1517+
topology.add(data("split_axis", axis_mem));
15101518
topology.add(data("splits_length", splits_length_mem));
1511-
topology.add(crop("variadic_split.out0", { input_info("input"), input_info("axis"), input_info("splits_length") }, tensor(1), tensor(0), op_mode, 0, axis));
1512-
topology.add(crop("variadic_split.out1", { input_info("input"), input_info("axis"), input_info("splits_length") }, tensor(1), tensor(0), op_mode, 1, axis));
1519+
topology.add(crop("variadic_split.out0", { input_info("input"), input_info("split_axis"), input_info("splits_length") }, tensor(1), tensor(0), op_mode, 0, split_axis));
1520+
topology.add(crop("variadic_split.out1", { input_info("input"), input_info("split_axis"), input_info("splits_length") }, tensor(1), tensor(0), op_mode, 1, split_axis));
15131521

15141522
std::vector<int64_t> splits_vec = { 64, 64 };
15151523

15161524
set_values(input_mem, input_data);
15171525
set_values(splits_length_mem, splits_vec);
1518-
set_values<int64_t>(axis_mem, {axis});
1526+
set_values<int64_t>(axis_mem, {split_axis});
15191527

15201528
ExecutionConfig config = get_test_default_config(engine);
15211529
config.set_property(ov::intel_gpu::allow_new_shape_infer(true));

0 commit comments

Comments
 (0)