[CPU] Inconsistent behavior/errors of Equal operation in comparison with TF framework (#24640)

Fix for TEST_DEVICE=CPU comparison of float16 infinite values

### Details:
- Introduced specialization for conversion float16->float32 in the CPU
plugin
 - xfail in layer tests is disabled for CPU device

### Tickets:
 - *24245*
This commit is contained in:
Daniel 2024-05-27 08:55:36 +02:00 committed by GitHub
parent dc523beb3e
commit 30d6e85505
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
2 changed files with 31 additions and 7 deletions

View File

@ -382,8 +382,7 @@ struct ConvertPrecision<std::tuple<src_t, ov::float16>> {
src_t lbound, ubound;
std::tie(lbound, ubound) = ctx.range<src_t>();
if (std::is_integral<src_t>::value
|| ctx.interimPrc.is_real()) {
if (std::is_integral<src_t>::value) {
parallel_for(iterations, [&](size_t i) {
batch_type tmp;
const size_t offset = i * batch;
@ -392,6 +391,19 @@ struct ConvertPrecision<std::tuple<src_t, ov::float16>> {
tmp[j] = static_cast<float>(std::max(std::min(src[offset + j], ubound), lbound));
jit_convert(tmp, dst + offset, current_batch_size); // fp32 -> fp16
});
} else if (ctx.interimPrc.is_real()) {
parallel_for(iterations, [&](size_t i) {
const size_t offset = i * batch;
const size_t current_batch_size = std::min(ctx.size - offset, batch);
if (std::is_same<typename std::remove_cv<src_t>::type, float>::value) { // fp32 -> fp16
jit_convert(reinterpret_cast<const float *>(src) + offset, dst + offset, current_batch_size);
} else {
batch_type tmp;
for (size_t j = 0; j < current_batch_size; ++j) // src_t -> fp32
tmp[j] = static_cast<float>(src[offset + j]);
jit_convert(tmp, dst + offset, current_batch_size); // fp32 -> fp16
}
});
} else {
parallel_for(iterations, [&](size_t i) {
batch_type tmp;
@ -420,8 +432,7 @@ struct ConvertPrecision<std::tuple<ov::float16, dst_t>> {
float lbound, ubound;
std::tie(lbound, ubound) = ctx.range<ov::float16>();
if (ctx.interimPrc.is_real()
|| std::is_integral<dst_t>::value) {
if (std::is_integral<dst_t>::value) {
parallel_for(iterations, [&](size_t i) {
batch_type tmp;
const size_t offset = i * batch;
@ -430,6 +441,19 @@ struct ConvertPrecision<std::tuple<ov::float16, dst_t>> {
for (size_t j = 0; j < current_batch_size; ++j) // fp32 -> dst_t
dst[offset + j] = static_cast<dst_t>(std::max(std::min(tmp[j], ubound), lbound));
});
} else if (ctx.interimPrc.is_real()) {
parallel_for(iterations, [&](size_t i) {
const size_t offset = i * batch;
const size_t current_batch_size = std::min(ctx.size - offset, batch);
if (std::is_same<typename std::remove_cv<dst_t>::type, float>::value) { // fp16 -> fp32
jit_convert(src + offset, reinterpret_cast<float *>(dst) + offset, current_batch_size);
} else {
batch_type tmp;
jit_convert(src + offset, tmp, current_batch_size); // fp16 -> fp32
for (size_t j = 0; j < current_batch_size; ++j) // fp32 -> dst_t
dst[offset + j] = static_cast<dst_t>(tmp[j]);
}
});
} else {
parallel_for(iterations, [&](size_t i) {
batch_type tmp;

View File

@ -157,7 +157,7 @@ class TestTFEqual(CommonTFLayerTest):
pytest.param(
dict(x_shape=[9], y_shape=[9], # Comparing shapes which contains corner cases
x_value=x_corner, y_value=y_corner),
marks=pytest.mark.xfail(reason="94234")),
marks=pytest.mark.special_xfail(args={"ie_device": "GPU"}, reason="94234")),
dict(x_shape=[1, 2, 3, 4], y_shape=[1, 2, 3, 4])
# Comparing shapes with different dimensions (more than 3, for case with nchw/nhcw), random values (false and possible true)
]
@ -179,7 +179,7 @@ class TestTFEqual(CommonTFLayerTest):
pytest.param(
dict(x_shape=[9], y_shape=[9], # Comparing shapes which contains corner cases
x_value=x_corner, y_value=y_corner),
marks=pytest.mark.xfail(reason="94234")),
marks=pytest.mark.special_xfail(args={"ie_device": "GPU"}, reason="94234")),
dict(x_shape=[1, 2, 3, 4], y_shape=[1, 2, 3, 4])
# Comparing shapes with different dimensions (more than 3, for case with nchw/nhcw), random values (false and possible true)
]
@ -201,7 +201,7 @@ class TestTFEqual(CommonTFLayerTest):
pytest.param(
dict(x_shape=[9], y_shape=[9], # Comparing shapes which contains corner cases
x_value=x_corner, y_value=y_corner),
marks=pytest.mark.xfail(reason="94234")),
marks=pytest.mark.special_xfail(args={"ie_device": "GPU"}, reason="94234")),
dict(x_shape=[1, 2, 3, 4], y_shape=[1, 2, 3, 4])
# Comparing shapes with different dimensions (more than 3, for case with nchw/nhcw), random values (false and possible true)
]