[Mlir-commits] [mlir] 37881ba - [mlir][tosa][tosa-to-linalg] Fix resize bilinear delta computation for negative offsets (#184799)

llvmlistbot at llvm.org llvmlistbot at llvm.org
Mon Mar 9 10:13:45 PDT 2026


Author: Luke Hutton
Date: 2026-03-09T17:13:39Z
New Revision: 37881bac75248ca48385d634554b4050e27be0d1

URL: https://github.com/llvm/llvm-project/commit/37881bac75248ca48385d634554b4050e27be0d1
DIFF: https://github.com/llvm/llvm-project/commit/37881bac75248ca48385d634554b4050e27be0d1.diff

LOG: [mlir][tosa][tosa-to-linalg] Fix resize bilinear delta computation for negative offsets (#184799)

Use floor-consistent remainder when lowering floating-point tosa.resize
to linalg: compute `r = in - floor(in/scale_n)*scale_n` instead of
RemSIOp. This keeps bilinear deltas in-range for negative offsets and
avoids invalid interpolation weights.

Added: 
    

Modified: 
    mlir/lib/Conversion/TosaToLinalg/TosaToLinalg.cpp
    mlir/test/Conversion/TosaToLinalg/tosa-to-linalg-resize.mlir

Removed: 
    


################################################################################
diff  --git a/mlir/lib/Conversion/TosaToLinalg/TosaToLinalg.cpp b/mlir/lib/Conversion/TosaToLinalg/TosaToLinalg.cpp
index b834106b10528..76346a766f1f7 100644
--- a/mlir/lib/Conversion/TosaToLinalg/TosaToLinalg.cpp
+++ b/mlir/lib/Conversion/TosaToLinalg/TosaToLinalg.cpp
@@ -2036,10 +2036,12 @@ class GenericResizeConverter : public OpRewritePattern<tosa::ResizeOp> {
         val = arith::AddIOp::create(b, val, offset);
         index = arith::FloorDivSIOp::create(b, val, scaleN);
 
-        // rx = x % scale_n
-        // dx = rx / scale_n
-        Value r = arith::RemSIOp::create(b, val, scaleN);
+        // rx = x - ix * scale_n (x % scale_n, if values are positive)
+        Value scaledIndex = arith::MulIOp::create(b, index, scaleN);
+        Value r = arith::SubIOp::create(b, val, scaledIndex);
         Value rFp = arith::SIToFPOp::create(b, floatTy, r);
+
+        // dx = rx / scale_n
         Value scaleNfp = arith::UIToFPOp::create(b, floatTy, scaleN);
         delta = arith::DivFOp::create(b, rFp, scaleNfp);
       };

diff  --git a/mlir/test/Conversion/TosaToLinalg/tosa-to-linalg-resize.mlir b/mlir/test/Conversion/TosaToLinalg/tosa-to-linalg-resize.mlir
index 6998aee45b887..4900476b25dc5 100644
--- a/mlir/test/Conversion/TosaToLinalg/tosa-to-linalg-resize.mlir
+++ b/mlir/test/Conversion/TosaToLinalg/tosa-to-linalg-resize.mlir
@@ -389,7 +389,8 @@ func.func @resize_nearest_fp32(%input: tensor<1x50x48x1xf32>) -> () {
   // CHECK: %[[VAL_29:.*]] = arith.muli %[[Y]], %[[SCALE_Y_D]]
   // CHECK: %[[Y_TEMP:.*]] = arith.addi %[[VAL_29]], %[[OFFSET_Y]]
   // CHECK: %[[IY_TEMP:.*]] = arith.floordivsi %[[Y_TEMP]], %[[SCALE_Y_N]]
-  // CHECK: %[[RY:.*]] = arith.remsi %[[Y_TEMP]], %[[SCALE_Y_N]]
+  // CHECK: %[[SCALED_IY:.*]] = arith.muli %[[IY_TEMP]], %[[SCALE_Y_N]]
+  // CHECK: %[[RY:.*]] = arith.subi %[[Y_TEMP]], %[[SCALED_IY]]
   // CHECK: %[[RY_FP:.*]] = arith.sitofp %[[RY]]
   // CHECK: %[[SCALE_Y_N_FP:.*]] = arith.uitofp %[[SCALE_Y_N]]
   // CHECK: %[[D_Y:.*]] = arith.divf %[[RY_FP]], %[[SCALE_Y_N_FP]]
@@ -397,7 +398,8 @@ func.func @resize_nearest_fp32(%input: tensor<1x50x48x1xf32>) -> () {
   // CHECK: %[[VAL_30:.*]] = arith.muli %[[X]], %[[SCALE_X_D]]
   // CHECK: %[[X_TEMP:.*]] = arith.addi %[[VAL_30]], %[[OFFSET_X]]
   // CHECK: %[[IX_TEMP:.*]] = arith.floordivsi %[[X_TEMP]], %[[SCALE_X_N]]
-  // CHECK: %[[RX:.*]] = arith.remsi %[[X_TEMP]], %[[SCALE_X_N]]
+  // CHECK: %[[SCALED_IX:.*]] = arith.muli %[[IX_TEMP]], %[[SCALE_X_N]]
+  // CHECK: %[[RX:.*]] = arith.subi %[[X_TEMP]], %[[SCALED_IX]]
   // CHECK: %[[RX_FP:.*]] = arith.sitofp %[[RX]]
   // CHECK: %[[SCALE_X_N_FP:.*]] = arith.uitofp %[[SCALE_X_N]]
   // CHECK: %[[D_X:.*]] = arith.divf %[[RX_FP]], %[[SCALE_X_N_FP]]
@@ -456,7 +458,8 @@ func.func @resize_bilinear_fp(%input: tensor<1x23x24x1xf32>) -> () {
   // CHECK: %[[VAL_29:.*]] = arith.muli %[[Y]], %[[SCALE_Y_D]]
   // CHECK: %[[Y_TEMP:.*]] = arith.addi %[[VAL_29]], %[[OFFSET_Y]]
   // CHECK: %[[I_Y:.*]] = arith.floordivsi %[[Y_TEMP]], %[[SCALE_Y_N]]
-  // CHECK: %[[RY:.*]] = arith.remsi %[[Y_TEMP]], %[[SCALE_Y_N]]
+  // CHECK: %[[SCALED_IY:.*]] = arith.muli %[[I_Y]], %[[SCALE_Y_N]]
+  // CHECK: %[[RY:.*]] = arith.subi %[[Y_TEMP]], %[[SCALED_IY]]
   // CHECK: %[[RY_FP:.*]] = arith.sitofp %[[RY]]
   // CHECK: %[[SCALE_Y_N_FP:.*]] = arith.uitofp %[[SCALE_Y_N]]
   // CHECK: %[[D_Y:.*]] = arith.divf %[[RY_FP]], %[[SCALE_Y_N_FP]]
@@ -464,7 +467,8 @@ func.func @resize_bilinear_fp(%input: tensor<1x23x24x1xf32>) -> () {
   // CHECK: %[[VAL_30:.*]] = arith.muli %[[X]], %[[SCALE_X_D]]
   // CHECK: %[[X_TEMP:.*]] = arith.addi %[[VAL_30]], %[[OFFSET_X]]
   // CHECK: %[[I_X:.*]] = arith.floordivsi %[[X_TEMP]], %[[SCALE_X_N]]
-  // CHECK: %[[RX:.*]] = arith.remsi %[[X_TEMP]], %[[SCALE_X_N]]
+  // CHECK: %[[SCALED_IX:.*]] = arith.muli %[[I_X]], %[[SCALE_X_N]]
+  // CHECK: %[[RX:.*]] = arith.subi %[[X_TEMP]], %[[SCALED_IX]]
   // CHECK: %[[RX_FP:.*]] = arith.sitofp %[[RX]]
   // CHECK: %[[SCALE_X_N_FP:.*]] = arith.uitofp %[[SCALE_X_N]]
   // CHECK: %[[D_X:.*]] = arith.divf %[[RX_FP]], %[[SCALE_X_N_FP]]


        


More information about the Mlir-commits mailing list