-
Notifications
You must be signed in to change notification settings - Fork 608
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add an integer divisibility analysis. (#18727)
* Also extends the numeric optimization test to elide arith.remui that exactly divides (a reasonable optimization but primarily used for testing in this patch). * Only implements the analysis for `arith.constant` and `util.int.assume` in this patch. * Renames assumption `divisor` to `udiv` to match terminology elsewhere wrt signed/unsigned analysis. * The lattice tracks unsigned and signed interpretations separately as this is needed for propagation through signed ops (but this is not implemented here). --------- Signed-off-by: Stella Laurenzo <stellaraccident@gmail.com>
- Loading branch information
1 parent
1b719b3
commit 5270093
Showing
19 changed files
with
391 additions
and
21 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
69 changes: 69 additions & 0 deletions
69
compiler/src/iree/compiler/Dialect/Util/Analysis/IntegerDivisibilityAnalysis.cpp
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,69 @@ | ||
// Copyright 2024 The IREE Authors | ||
// | ||
// Licensed under the Apache License v2.0 with LLVM Exceptions. | ||
// See https://llvm.org/LICENSE.txt for license information. | ||
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception | ||
|
||
#include "iree/compiler/Dialect/Util/Analysis/IntegerDivisibilityAnalysis.h" | ||
|
||
#include "iree/compiler/Dialect/Util/IR/UtilTypes.h" | ||
#include "llvm/Support/Debug.h" | ||
|
||
#define DEBUG_TYPE "iree-util-int-divisibility-analysis" | ||
|
||
using llvm::dbgs; | ||
|
||
namespace mlir::iree_compiler::IREE::Util { | ||
|
||
void IntegerDivisibilityAnalysis::setToEntryState( | ||
IntegerDivisibilityLattice *lattice) { | ||
propagateIfChanged(lattice, | ||
lattice->join(IntegerDivisibility::getMinDivisibility())); | ||
} | ||
|
||
LogicalResult IntegerDivisibilityAnalysis::visitOperation( | ||
Operation *op, ArrayRef<const IntegerDivisibilityLattice *> operands, | ||
ArrayRef<IntegerDivisibilityLattice *> results) { | ||
auto inferrable = dyn_cast<InferIntDivisibilityOpInterface>(op); | ||
if (!inferrable) { | ||
setAllToEntryStates(results); | ||
return success(); | ||
} | ||
|
||
LLVM_DEBUG(dbgs() << "Inferring divisibility for " << *op << "\n"); | ||
auto argDivs = llvm::map_to_vector( | ||
operands, [](const IntegerDivisibilityLattice *lattice) { | ||
return lattice->getValue(); | ||
}); | ||
auto joinCallback = [&](Value v, const IntegerDivisibility &newDiv) { | ||
auto result = dyn_cast<OpResult>(v); | ||
if (!result) | ||
return; | ||
assert(llvm::is_contained(op->getResults(), result)); | ||
|
||
LLVM_DEBUG(dbgs() << "Inferred divisibility " << newDiv << "\n"); | ||
IntegerDivisibilityLattice *lattice = results[result.getResultNumber()]; | ||
IntegerDivisibility oldDiv = lattice->getValue(); | ||
|
||
ChangeResult changed = lattice->join(newDiv); | ||
|
||
// Catch loop results with loop variant bounds and conservatively make | ||
// them [-inf, inf] so we don't circle around infinitely often (because | ||
// the dataflow analysis in MLIR doesn't attempt to work out trip counts | ||
// and often can't). | ||
bool isYieldedResult = llvm::any_of(v.getUsers(), [](Operation *op) { | ||
return op->hasTrait<OpTrait::IsTerminator>(); | ||
}); | ||
if (isYieldedResult && !oldDiv.isUninitialized() && | ||
!(lattice->getValue() == oldDiv)) { | ||
LLVM_DEBUG(llvm::dbgs() << "Loop variant loop result detected\n"); | ||
changed |= lattice->join(IntegerDivisibility::getMinDivisibility()); | ||
} | ||
propagateIfChanged(lattice, changed); | ||
}; | ||
|
||
inferrable.inferResultDivisibility(argDivs, joinCallback); | ||
return success(); | ||
} | ||
|
||
} // namespace mlir::iree_compiler::IREE::Util |
42 changes: 42 additions & 0 deletions
42
compiler/src/iree/compiler/Dialect/Util/Analysis/IntegerDivisibilityAnalysis.h
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,42 @@ | ||
// Copyright 2024 The IREE Authors | ||
// | ||
// Licensed under the Apache License v2.0 with LLVM Exceptions. | ||
// See https://llvm.org/LICENSE.txt for license information. | ||
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception | ||
|
||
#ifndef IREE_COMPILER_DIALECT_UTIL_INTEGER_DIVISIBILITY_ANALYSIS_H_ | ||
#define IREE_COMPILER_DIALECT_UTIL_INTEGER_DIVISIBILITY_ANALYSIS_H_ | ||
|
||
#include "iree/compiler/Dialect/Util/IR/UtilTypes.h" | ||
#include "mlir/Analysis/DataFlow/SparseAnalysis.h" | ||
|
||
#include <optional> | ||
|
||
namespace mlir::iree_compiler::IREE::Util { | ||
|
||
class IntegerDivisibilityLattice | ||
: public dataflow::Lattice<IntegerDivisibility> { | ||
public: | ||
using Lattice::Lattice; | ||
}; | ||
|
||
class IntegerDivisibilityAnalysis | ||
: public dataflow::SparseForwardDataFlowAnalysis< | ||
IntegerDivisibilityLattice> { | ||
public: | ||
using SparseForwardDataFlowAnalysis::SparseForwardDataFlowAnalysis; | ||
|
||
// At an entry point, set the lattice to the most pessimistic state, | ||
// indicating that no further reasoning can be done. | ||
void setToEntryState(IntegerDivisibilityLattice *lattice) override; | ||
|
||
// Visit an operation, invoking the transfer function. | ||
LogicalResult | ||
visitOperation(Operation *op, | ||
ArrayRef<const IntegerDivisibilityLattice *> operands, | ||
ArrayRef<IntegerDivisibilityLattice *> results) override; | ||
}; | ||
|
||
} // namespace mlir::iree_compiler::IREE::Util | ||
|
||
#endif // IREE_COMPILER_DIALECT_UTIL_INTEGER_DIVISIBILITY_ANALYSIS_H_ |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.