From 9034747c223cd5ab53148ec40aaf64765fcd6531 Mon Sep 17 00:00:00 2001 From: Jeremy Johnson Date: Mon, 6 Sep 2021 12:04:07 +0100 Subject: Add saturation REQUIREs for ADD,SUB,MUL,INTDIV Change-Id: I358fbd4c958e057687f25d585eb8fdd80fd9ae42 Signed-off-by: Jeremy Johnson --- reference_model/src/ops/ewise_binary.cc | 29 +++++++++++++++++++++++++---- 1 file changed, 25 insertions(+), 4 deletions(-) diff --git a/reference_model/src/ops/ewise_binary.cc b/reference_model/src/ops/ewise_binary.cc index d6a95e1..c33f646 100644 --- a/reference_model/src/ops/ewise_binary.cc +++ b/reference_model/src/ops/ewise_binary.cc @@ -201,8 +201,16 @@ int OpAdd::register_fcn() { switch (InDtype) { - case DType_FLOAT: case DType_INT32: + this->fcn = [this](InEigenType a, InEigenType b) -> OutEigenType { + int64_t res_in_64 = static_cast(a) + b; + int64_t i32_max_in_64 = static_cast(std::numeric_limits::max()); + int64_t i32_min_in_64 = static_cast(std::numeric_limits::min()); + REQUIRE(res_in_64 <= i32_max_in_64 && res_in_64 >= i32_min_in_64, "OpAdd: result not in i32 range"); + return static_cast(res_in_64); + }; + break; + case DType_FLOAT: this->fcn = [](InEigenType a, InEigenType b) -> OutEigenType { return a + b; }; break; default: @@ -310,7 +318,8 @@ int OpIntdiv::register_fcn() REQUIRE(b != 0, "OpIntDiv: divisor must be non-zero value"); int64_t res_in_64 = static_cast(a) / b; int64_t i32_max_in_64 = static_cast(std::numeric_limits::max()); - REQUIRE(a <= i32_max_in_64, "OpIntDiv: result not in i32 range"); + int64_t i32_min_in_64 = static_cast(std::numeric_limits::min()); + REQUIRE(res_in_64 <= i32_max_in_64 && res_in_64 >= i32_min_in_64, "OpIntDiv: result not in i32 range"); return static_cast(res_in_64); }; break; @@ -466,7 +475,11 @@ int OpMul::register_fcn() } else { - result = a * b; + result = static_cast(a) * b; + int64_t i32_max_in_64 = static_cast(std::numeric_limits::max()); + int64_t i32_min_in_64 = static_cast(std::numeric_limits::min()); + REQUIRE(result <= i32_max_in_64 && result >= i32_min_in_64, "OpMul: result not in i32 range"); + return static_cast(result); } return static_cast(result); @@ -509,8 +522,16 @@ int OpSub::register_fcn() { switch (InDtype) { - case DType_FLOAT: case DType_INT32: + this->fcn = [this](InEigenType a, InEigenType b) -> OutEigenType { + int64_t res_in_64 = static_cast(a) - b; + int64_t i32_max_in_64 = static_cast(std::numeric_limits::max()); + int64_t i32_min_in_64 = static_cast(std::numeric_limits::min()); + REQUIRE(res_in_64 <= i32_max_in_64 && res_in_64 >= i32_min_in_64, "OpSub: result not in i32 range"); + return static_cast(res_in_64); + }; + break; + case DType_FLOAT: this->fcn = [](InEigenType a, InEigenType b) -> OutEigenType { return a - b; }; break; default: -- cgit v1.2.1