mirror of https://github.com/llvm/circt.git
LLVM bump (as we know it) (#3074)
* LLVM bump (as we know it) * minor format fix * DCMAKE_BUILD_TYPE=? * Update lib/Dialect/MSFT/MSFTOps.cpp Co-authored-by: Andrew Young <youngar17@gmail.com> * Update lib/Dialect/FIRRTL/FIRRTLOps.cpp Co-authored-by: Andrew Young <youngar17@gmail.com> * Update lib/Dialect/Calyx/CalyxOps.cpp Co-authored-by: Andrew Young <youngar17@gmail.com> * removed anon module test Co-authored-by: Andrew Young <youngar17@gmail.com>
This commit is contained in:
parent
ca28a00b7f
commit
37b7baff75
|
@ -181,6 +181,7 @@ jobs:
|
|||
mkdir configure_unified
|
||||
cd configure_unified
|
||||
cmake ../llvm/llvm \
|
||||
-DCMAKE_BUILD_TYPE=Release \
|
||||
-DBUILD_SHARED_LIBS=ON \
|
||||
-DLLVM_ENABLE_PROJECTS=mlir \
|
||||
-DLLVM_TARGETS_TO_BUILD=host \
|
||||
|
|
|
@ -5,7 +5,7 @@ on:
|
|||
# 10:00 AM UTC is 3AM Pacific Time
|
||||
- cron: '0 10 * * *'
|
||||
# Run this workflow on pull requests which change this workflow
|
||||
pull_request:
|
||||
pull_request:
|
||||
paths:
|
||||
- .github/workflows/trackLLVMChanges.yml
|
||||
workflow_dispatch:
|
||||
|
@ -50,7 +50,7 @@ jobs:
|
|||
cd llvm
|
||||
echo "::set-output name=sha::$(git rev-parse HEAD)"
|
||||
cmake --build ../build --config Debug --target check-circt -- -j$(nproc)
|
||||
|
||||
|
||||
- name: Build latest LLVM commit
|
||||
id: build-latest-llvm-commit
|
||||
continue-on-error: true
|
||||
|
@ -60,7 +60,7 @@ jobs:
|
|||
git checkout --detach origin/main
|
||||
echo "::set-output name=sha::$(git rev-parse HEAD)"
|
||||
cmake --build ../build --config Debug --target check-circt -- -j$(nproc)
|
||||
|
||||
|
||||
- name: Bisect commits
|
||||
if: steps.build-latest-llvm-commit.outcome != 'success'
|
||||
run: |
|
||||
|
|
|
@ -214,16 +214,6 @@ def NodeOp : FIRRTLOp<"node",
|
|||
}];
|
||||
|
||||
let hasCanonicalizer = true;
|
||||
|
||||
let extraClassDeclaration = [{
|
||||
/// Infer the return types of this operation.
|
||||
static LogicalResult inferReturnTypes(MLIRContext *context,
|
||||
Optional<Location> loc,
|
||||
ValueRange operands,
|
||||
DictionaryAttr attrs,
|
||||
mlir::RegionRange regions,
|
||||
SmallVectorImpl<Type> &results);
|
||||
}];
|
||||
}
|
||||
|
||||
def RegOp : FIRRTLOp<"reg", [HasCustomSSAName/*MemAlloc*/]> {
|
||||
|
|
|
@ -30,18 +30,16 @@ StringAttr getPortNameAttr(MLIRContext *context, StringRef name);
|
|||
/// This is a variant of mlor::parseFunctionSignature that allows names on
|
||||
/// result arguments.
|
||||
ParseResult parseModuleFunctionSignature(
|
||||
OpAsmParser &parser,
|
||||
SmallVectorImpl<OpAsmParser::UnresolvedOperand> &argNames,
|
||||
SmallVectorImpl<Type> &argTypes, SmallVectorImpl<NamedAttrList> &argAttrs,
|
||||
OpAsmParser &parser, SmallVectorImpl<OpAsmParser::Argument> &args,
|
||||
bool &isVariadic, SmallVectorImpl<Type> &resultTypes,
|
||||
SmallVectorImpl<NamedAttrList> &resultAttrs,
|
||||
SmallVectorImpl<DictionaryAttr> &resultAttrs,
|
||||
SmallVectorImpl<Attribute> &resultNames);
|
||||
|
||||
/// Parse a function result list with named results.
|
||||
ParseResult parseFunctionResultList(OpAsmParser &parser,
|
||||
SmallVectorImpl<Type> &resultTypes,
|
||||
SmallVectorImpl<NamedAttrList> &resultAttrs,
|
||||
SmallVectorImpl<Attribute> &resultNames);
|
||||
ParseResult
|
||||
parseFunctionResultList(OpAsmParser &parser, SmallVectorImpl<Type> &resultTypes,
|
||||
SmallVectorImpl<DictionaryAttr> &resultAttrs,
|
||||
SmallVectorImpl<Attribute> &resultNames);
|
||||
|
||||
/// Print a module signature with named results.
|
||||
void printModuleSignature(OpAsmPrinter &p, Operation *op,
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
// REQUIRES: ieee-sim
|
||||
// UNSUPPORTED: ieee-sim-iverilog
|
||||
// RUN: circt-opt %s --lower-std-to-handshake \
|
||||
// RUN: circt-opt %s --lower-std-to-handshake \
|
||||
// RUN: --canonicalize='top-down=true region-simplify=true' \
|
||||
// RUN: --handshake-materialize-forks-sinks --canonicalize \
|
||||
// RUN: --handshake-insert-buffers=strategy=all --lower-handshake-to-firrtl | \
|
||||
|
@ -9,7 +9,7 @@
|
|||
// CHECK: Result={{.*}}3589632
|
||||
|
||||
module {
|
||||
func @top() -> i32 {
|
||||
func.func @top() -> i32 {
|
||||
%c123_i32 = arith.constant 123 : i32
|
||||
%c456_i32 = arith.constant 456 : i32
|
||||
%c0_i32 = arith.constant 0 : i32
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
// REQUIRES: ieee-sim
|
||||
// UNSUPPORTED: ieee-sim-iverilog
|
||||
// RUN: circt-opt %s --lower-std-to-handshake \
|
||||
// RUN: circt-opt %s --lower-std-to-handshake \
|
||||
// RUN: --canonicalize='top-down=true region-simplify=true' \
|
||||
// RUN: --handshake-materialize-forks-sinks --canonicalize \
|
||||
// RUN: --handshake-insert-buffers=strategy=all --lower-handshake-to-firrtl | \
|
||||
|
@ -9,7 +9,7 @@
|
|||
// CHECK: Result={{.*}}448704
|
||||
|
||||
module {
|
||||
func @top() -> i32 {
|
||||
func.func @top() -> i32 {
|
||||
%c123_i32 = arith.constant 123 : i32
|
||||
%c456_i32 = arith.constant 456 : i32
|
||||
%c0_i32 = arith.constant 0 : i32
|
||||
|
|
|
@ -445,16 +445,17 @@ void ComponentOp::print(OpAsmPrinter &p) {
|
|||
/// port names to `attrName`.
|
||||
static ParseResult
|
||||
parsePortDefList(OpAsmParser &parser, OperationState &result,
|
||||
SmallVectorImpl<OpAsmParser::UnresolvedOperand> &ports,
|
||||
SmallVectorImpl<OpAsmParser::Argument> &ports,
|
||||
SmallVectorImpl<Type> &portTypes,
|
||||
SmallVectorImpl<NamedAttrList> &portAttrs) {
|
||||
auto parsePort = [&]() -> ParseResult {
|
||||
OpAsmParser::UnresolvedOperand port;
|
||||
OpAsmParser::Argument port;
|
||||
Type portType;
|
||||
// Expect each port to have the form `%<ssa-name> : <type>`.
|
||||
if (parser.parseRegionArgument(port) || parser.parseColon() ||
|
||||
if (parser.parseArgument(port) || parser.parseColon() ||
|
||||
parser.parseType(portType))
|
||||
return failure();
|
||||
port.type = portType;
|
||||
ports.push_back(port);
|
||||
portTypes.push_back(portType);
|
||||
|
||||
|
@ -472,9 +473,9 @@ parsePortDefList(OpAsmParser &parser, OperationState &result,
|
|||
/// Parses the signature of a Calyx component.
|
||||
static ParseResult
|
||||
parseComponentSignature(OpAsmParser &parser, OperationState &result,
|
||||
SmallVectorImpl<OpAsmParser::UnresolvedOperand> &ports,
|
||||
SmallVectorImpl<OpAsmParser::Argument> &ports,
|
||||
SmallVectorImpl<Type> &portTypes) {
|
||||
SmallVector<OpAsmParser::UnresolvedOperand> inPorts, outPorts;
|
||||
SmallVector<OpAsmParser::Argument> inPorts, outPorts;
|
||||
SmallVector<Type> inPortTypes, outPortTypes;
|
||||
SmallVector<NamedAttrList> portAttributes;
|
||||
|
||||
|
@ -490,7 +491,7 @@ parseComponentSignature(OpAsmParser &parser, OperationState &result,
|
|||
// just inferred from the SSA names of the component.
|
||||
SmallVector<Attribute> portNames;
|
||||
auto getPortName = [context](const auto &port) -> StringAttr {
|
||||
StringRef name = port.name;
|
||||
StringRef name = port.ssaName.name;
|
||||
if (name.startswith("%"))
|
||||
name = name.drop_front();
|
||||
return StringAttr::get(context, name);
|
||||
|
@ -525,7 +526,8 @@ ParseResult ComponentOp::parse(OpAsmParser &parser, OperationState &result) {
|
|||
result.attributes))
|
||||
return failure();
|
||||
|
||||
SmallVector<OpAsmParser::UnresolvedOperand> ports;
|
||||
SmallVector<mlir::OpAsmParser::Argument> ports;
|
||||
|
||||
SmallVector<Type> portTypes;
|
||||
if (parseComponentSignature(parser, result, ports, portTypes))
|
||||
return failure();
|
||||
|
@ -537,7 +539,7 @@ ParseResult ComponentOp::parse(OpAsmParser &parser, OperationState &result) {
|
|||
result.addAttribute(ComponentOp::getTypeAttrName(), TypeAttr::get(type));
|
||||
|
||||
auto *body = result.addRegion();
|
||||
if (parser.parseRegion(*body, ports, portTypes))
|
||||
if (parser.parseRegion(*body, ports))
|
||||
return failure();
|
||||
|
||||
if (body->empty())
|
||||
|
|
|
@ -851,7 +851,7 @@ static bool printModulePorts(OpAsmPrinter &p, Block *block,
|
|||
/// will populate `entryArgs`.
|
||||
static ParseResult
|
||||
parseModulePorts(OpAsmParser &parser, bool hasSSAIdentifiers,
|
||||
SmallVectorImpl<OpAsmParser::UnresolvedOperand> &entryArgs,
|
||||
SmallVectorImpl<OpAsmParser::Argument> &entryArgs,
|
||||
SmallVectorImpl<Direction> &portDirections,
|
||||
SmallVectorImpl<Attribute> &portNames,
|
||||
SmallVectorImpl<Attribute> &portTypes,
|
||||
|
@ -870,17 +870,19 @@ parseModulePorts(OpAsmParser &parser, bool hasSSAIdentifiers,
|
|||
|
||||
// Parse the port name.
|
||||
if (hasSSAIdentifiers) {
|
||||
OpAsmParser::UnresolvedOperand arg;
|
||||
if (parser.parseRegionArgument(arg))
|
||||
OpAsmParser::Argument arg;
|
||||
if (parser.parseArgument(arg))
|
||||
return failure();
|
||||
entryArgs.push_back(arg);
|
||||
// The name of an argument is of the form "%42" or "%id", and since
|
||||
// parsing succeeded, we know it always has one character.
|
||||
assert(arg.name.size() > 1 && arg.name[0] == '%' && "Unknown MLIR name");
|
||||
if (isdigit(arg.name[1]))
|
||||
assert(arg.ssaName.name.size() > 1 && arg.ssaName.name[0] == '%' &&
|
||||
"Unknown MLIR name");
|
||||
if (isdigit(arg.ssaName.name[1]))
|
||||
portNames.push_back(StringAttr::get(context, ""));
|
||||
else
|
||||
portNames.push_back(StringAttr::get(context, arg.name.drop_front()));
|
||||
portNames.push_back(
|
||||
StringAttr::get(context, arg.ssaName.name.drop_front()));
|
||||
} else {
|
||||
std::string portName;
|
||||
if (parser.parseKeywordOrString(&portName))
|
||||
|
@ -894,6 +896,9 @@ parseModulePorts(OpAsmParser &parser, bool hasSSAIdentifiers,
|
|||
return failure();
|
||||
portTypes.push_back(TypeAttr::get(portType));
|
||||
|
||||
if (hasSSAIdentifiers)
|
||||
entryArgs.back().type = portType;
|
||||
|
||||
// Parse the optional port symbol.
|
||||
StringAttr portSym;
|
||||
if (succeeded(parser.parseOptionalKeyword("sym"))) {
|
||||
|
@ -1053,7 +1058,7 @@ static ParseResult parseFModuleLikeOp(OpAsmParser &parser,
|
|||
result.addAttribute("parameters", builder.getArrayAttr(parameters));
|
||||
|
||||
// Parse the module ports.
|
||||
SmallVector<OpAsmParser::UnresolvedOperand> entryArgs;
|
||||
SmallVector<OpAsmParser::Argument> entryArgs;
|
||||
SmallVector<Direction, 4> portDirections;
|
||||
SmallVector<Attribute, 4> portNames;
|
||||
SmallVector<Attribute, 4> portTypes;
|
||||
|
@ -1114,15 +1119,7 @@ static ParseResult parseFModuleLikeOp(OpAsmParser &parser,
|
|||
auto *body = result.addRegion();
|
||||
|
||||
if (hasSSAIdentifiers) {
|
||||
// Collect block argument types.
|
||||
SmallVector<Type, 4> argTypes;
|
||||
if (!entryArgs.empty())
|
||||
llvm::transform(portTypes, std::back_inserter(argTypes),
|
||||
[](Attribute typeAttr) -> Type {
|
||||
return typeAttr.cast<TypeAttr>().getValue();
|
||||
});
|
||||
|
||||
if (parser.parseRegion(*body, entryArgs, argTypes))
|
||||
if (parser.parseRegion(*body, entryArgs))
|
||||
return failure();
|
||||
if (body->empty())
|
||||
body->push_back(new Block());
|
||||
|
@ -1505,7 +1502,7 @@ ParseResult InstanceOp::parse(OpAsmParser &parser, OperationState &result) {
|
|||
std::string name;
|
||||
StringAttr innerSymAttr;
|
||||
FlatSymbolRefAttr moduleName;
|
||||
SmallVector<OpAsmParser::UnresolvedOperand> entryArgs;
|
||||
SmallVector<OpAsmParser::Argument> entryArgs;
|
||||
SmallVector<Direction, 4> portDirections;
|
||||
SmallVector<Attribute, 4> portNames;
|
||||
SmallVector<Attribute, 4> portTypes;
|
||||
|
@ -2005,17 +2002,6 @@ void MemOp::getAsmResultNames(OpAsmSetValueNameFn setNameFn) {
|
|||
// Construct name of the module which will be used for the memory definition.
|
||||
StringAttr FirMemory::getFirMemoryName() const { return modName; }
|
||||
|
||||
/// Infer the return types of this operation.
|
||||
LogicalResult NodeOp::inferReturnTypes(MLIRContext *context,
|
||||
Optional<Location> loc,
|
||||
ValueRange operands,
|
||||
DictionaryAttr attrs,
|
||||
mlir::RegionRange regions,
|
||||
SmallVectorImpl<Type> &results) {
|
||||
results.push_back(operands[0].getType());
|
||||
return success();
|
||||
}
|
||||
|
||||
void NodeOp::getAsmResultNames(OpAsmSetValueNameFn setNameFn) {
|
||||
setNameFn(getResult(), name());
|
||||
}
|
||||
|
@ -2502,7 +2488,7 @@ FIRRTLType SubaccessOp::inferReturnType(ValueRange operands,
|
|||
|
||||
ParseResult MultibitMuxOp::parse(OpAsmParser &parser, OperationState &result) {
|
||||
OpAsmParser::UnresolvedOperand index;
|
||||
llvm::SmallVector<OpAsmParser::UnresolvedOperand, 16> inputs;
|
||||
SmallVector<OpAsmParser::UnresolvedOperand, 16> inputs;
|
||||
Type indexType, elemType;
|
||||
|
||||
if (parser.parseOperand(index) || parser.parseComma() ||
|
||||
|
|
|
@ -788,14 +788,13 @@ static ParseResult parseOptionalParameters(OpAsmParser &parser,
|
|||
|
||||
static ParseResult parseHWModuleOp(OpAsmParser &parser, OperationState &result,
|
||||
ExternModKind modKind = PlainMod) {
|
||||
|
||||
using namespace mlir::function_interface_impl;
|
||||
|
||||
auto loc = parser.getCurrentLocation();
|
||||
|
||||
SmallVector<OpAsmParser::UnresolvedOperand, 4> entryArgs;
|
||||
SmallVector<NamedAttrList, 4> argAttrs;
|
||||
SmallVector<NamedAttrList, 4> resultAttrs;
|
||||
SmallVector<Type, 4> argTypes;
|
||||
SmallVector<OpAsmParser::Argument, 4> entryArgs;
|
||||
SmallVector<DictionaryAttr> resultAttrs;
|
||||
SmallVector<Type, 4> resultTypes;
|
||||
SmallVector<Attribute> parameters;
|
||||
auto &builder = parser.getBuilder();
|
||||
|
@ -822,14 +821,18 @@ static ParseResult parseHWModuleOp(OpAsmParser &parser, OperationState &result,
|
|||
SmallVector<Attribute> resultNames;
|
||||
if (parseOptionalParameters(parser, parameters) ||
|
||||
module_like_impl::parseModuleFunctionSignature(
|
||||
parser, entryArgs, argTypes, argAttrs, isVariadic, resultTypes,
|
||||
resultAttrs, resultNames) ||
|
||||
parser, entryArgs, isVariadic, resultTypes, resultAttrs,
|
||||
resultNames) ||
|
||||
// If function attributes are present, parse them.
|
||||
parser.parseOptionalAttrDictWithKeyword(result.attributes))
|
||||
return failure();
|
||||
|
||||
// Record the argument and result types as an attribute. This is necessary
|
||||
// for external modules.
|
||||
SmallVector<Type> argTypes;
|
||||
for (auto &arg : entryArgs)
|
||||
argTypes.push_back(arg.type);
|
||||
|
||||
auto type = builder.getFunctionType(argTypes, resultTypes);
|
||||
result.addAttribute(getTypeAttrName(), TypeAttr::get(type));
|
||||
|
||||
|
@ -846,7 +849,8 @@ static ParseResult parseHWModuleOp(OpAsmParser &parser, OperationState &result,
|
|||
SmallVector<Attribute> argNames;
|
||||
if (!entryArgs.empty()) {
|
||||
for (auto &arg : entryArgs)
|
||||
argNames.push_back(module_like_impl::getPortNameAttr(context, arg.name));
|
||||
argNames.push_back(
|
||||
module_like_impl::getPortNameAttr(context, arg.ssaName.name));
|
||||
} else if (!argTypes.empty()) {
|
||||
// The parser returns empty names in a special way.
|
||||
argNames.assign(argTypes.size(), StringAttr::get(context, ""));
|
||||
|
@ -863,17 +867,15 @@ static ParseResult parseHWModuleOp(OpAsmParser &parser, OperationState &result,
|
|||
if (!hasAttribute("comment", result.attributes))
|
||||
result.addAttribute("comment", StringAttr::get(context, ""));
|
||||
|
||||
assert(argAttrs.size() == argTypes.size());
|
||||
assert(resultAttrs.size() == resultTypes.size());
|
||||
|
||||
// Add the attributes to the function arguments.
|
||||
addArgAndResultAttrs(builder, result, argAttrs, resultAttrs);
|
||||
addArgAndResultAttrs(builder, result, entryArgs, resultAttrs);
|
||||
|
||||
// Parse the optional function body.
|
||||
auto *body = result.addRegion();
|
||||
if (modKind == PlainMod) {
|
||||
if (parser.parseRegion(*body, entryArgs,
|
||||
entryArgs.empty() ? ArrayRef<Type>() : argTypes))
|
||||
if (parser.parseRegion(*body, entryArgs))
|
||||
return failure();
|
||||
|
||||
HWModuleOp::ensureTerminator(*body, parser.getBuilder(), result.location);
|
||||
|
|
|
@ -42,7 +42,7 @@ StringAttr module_like_impl::getPortNameAttr(MLIRContext *context,
|
|||
///
|
||||
ParseResult module_like_impl::parseFunctionResultList(
|
||||
OpAsmParser &parser, SmallVectorImpl<Type> &resultTypes,
|
||||
SmallVectorImpl<NamedAttrList> &resultAttrs,
|
||||
SmallVectorImpl<DictionaryAttr> &resultAttrs,
|
||||
SmallVectorImpl<Attribute> &resultNames) {
|
||||
|
||||
auto parseElt = [&]() -> ParseResult {
|
||||
|
@ -53,9 +53,14 @@ ParseResult module_like_impl::parseFunctionResultList(
|
|||
|
||||
resultTypes.emplace_back();
|
||||
resultAttrs.emplace_back();
|
||||
|
||||
NamedAttrList attrs;
|
||||
if (parser.parseColonType(resultTypes.back()) ||
|
||||
parser.parseOptionalAttrDict(resultAttrs.back()))
|
||||
parser.parseOptionalAttrDict(attrs))
|
||||
return failure();
|
||||
|
||||
resultAttrs.back() = attrs.getDictionary(parser.getContext());
|
||||
|
||||
return success();
|
||||
};
|
||||
|
||||
|
@ -66,18 +71,14 @@ ParseResult module_like_impl::parseFunctionResultList(
|
|||
/// This is a variant of mlor::parseFunctionSignature that allows names on
|
||||
/// result arguments.
|
||||
ParseResult module_like_impl::parseModuleFunctionSignature(
|
||||
OpAsmParser &parser,
|
||||
SmallVectorImpl<OpAsmParser::UnresolvedOperand> &argNames,
|
||||
SmallVectorImpl<Type> &argTypes, SmallVectorImpl<NamedAttrList> &argAttrs,
|
||||
OpAsmParser &parser, SmallVectorImpl<OpAsmParser::Argument> &args,
|
||||
bool &isVariadic, SmallVectorImpl<Type> &resultTypes,
|
||||
SmallVectorImpl<NamedAttrList> &resultAttrs,
|
||||
SmallVectorImpl<DictionaryAttr> &resultAttrs,
|
||||
SmallVectorImpl<Attribute> &resultNames) {
|
||||
|
||||
using namespace mlir::function_interface_impl;
|
||||
bool allowArgAttrs = true;
|
||||
bool allowVariadic = false;
|
||||
if (parseFunctionArgumentList(parser, allowArgAttrs, allowVariadic, argNames,
|
||||
argTypes, argAttrs, isVariadic))
|
||||
if (parser.parseArgumentList(args, OpAsmParser::Delimiter::Paren,
|
||||
/*allowTypes=*/true, /*allowAttrs=*/true))
|
||||
return failure();
|
||||
|
||||
if (succeeded(parser.parseOptionalArrow()))
|
||||
|
|
|
@ -532,22 +532,20 @@ LogicalResult FuncOp::verify() {
|
|||
/// mlir::function_interface_impl::parseFunctionSignature while getting access
|
||||
/// to the parsed SSA names to store as attributes.
|
||||
static ParseResult parseFuncOpArgs(
|
||||
OpAsmParser &parser,
|
||||
SmallVectorImpl<OpAsmParser::UnresolvedOperand> &entryArgs,
|
||||
SmallVectorImpl<Type> &argTypes, SmallVectorImpl<Attribute> &argNames,
|
||||
SmallVectorImpl<NamedAttrList> &argAttrs, SmallVectorImpl<Type> &resTypes,
|
||||
SmallVectorImpl<NamedAttrList> &resAttrs) {
|
||||
OpAsmParser &parser, SmallVectorImpl<OpAsmParser::Argument> &entryArgs,
|
||||
SmallVectorImpl<Attribute> &argNames, SmallVectorImpl<Type> &resTypes,
|
||||
SmallVectorImpl<DictionaryAttr> &resAttrs) {
|
||||
auto *context = parser.getContext();
|
||||
|
||||
bool isVariadic;
|
||||
if (mlir::function_interface_impl::parseFunctionSignature(
|
||||
parser, /*allowVariadic=*/true, entryArgs, argTypes, argAttrs,
|
||||
isVariadic, resTypes, resAttrs)
|
||||
parser, /*allowVariadic=*/true, entryArgs, isVariadic, resTypes,
|
||||
resAttrs)
|
||||
.failed())
|
||||
return failure();
|
||||
|
||||
llvm::transform(entryArgs, std::back_inserter(argNames), [&](auto arg) {
|
||||
return StringAttr::get(context, arg.name.drop_front());
|
||||
return StringAttr::get(context, arg.ssaName.name.drop_front());
|
||||
});
|
||||
|
||||
return success();
|
||||
|
@ -628,9 +626,9 @@ void handshake::FuncOp::resolveArgAndResNames() {
|
|||
ParseResult FuncOp::parse(OpAsmParser &parser, OperationState &result) {
|
||||
auto &builder = parser.getBuilder();
|
||||
StringAttr nameAttr;
|
||||
SmallVector<OpAsmParser::UnresolvedOperand, 4> args;
|
||||
SmallVector<Type, 4> argTypes, resTypes;
|
||||
SmallVector<NamedAttrList, 4> argAttributes, resAttributes;
|
||||
SmallVector<OpAsmParser::Argument> args;
|
||||
SmallVector<Type> resTypes;
|
||||
SmallVector<DictionaryAttr> resAttributes;
|
||||
SmallVector<Attribute> argNames;
|
||||
|
||||
// Parse visibility.
|
||||
|
@ -639,13 +637,16 @@ ParseResult FuncOp::parse(OpAsmParser &parser, OperationState &result) {
|
|||
// Parse signature
|
||||
if (parser.parseSymbolName(nameAttr, SymbolTable::getSymbolAttrName(),
|
||||
result.attributes) ||
|
||||
parseFuncOpArgs(parser, args, argTypes, argNames, argAttributes, resTypes,
|
||||
resAttributes))
|
||||
parseFuncOpArgs(parser, args, argNames, resTypes, resAttributes))
|
||||
return failure();
|
||||
mlir::function_interface_impl::addArgAndResultAttrs(
|
||||
builder, result, argAttributes, resAttributes);
|
||||
mlir::function_interface_impl::addArgAndResultAttrs(builder, result, args,
|
||||
resAttributes);
|
||||
|
||||
// Set function type
|
||||
SmallVector<Type> argTypes;
|
||||
for (auto arg : args)
|
||||
argTypes.push_back(arg.type);
|
||||
|
||||
result.addAttribute(
|
||||
handshake::FuncOp::getTypeAttrName(),
|
||||
TypeAttr::get(builder.getFunctionType(argTypes, resTypes)));
|
||||
|
@ -665,7 +666,7 @@ ParseResult FuncOp::parse(OpAsmParser &parser, OperationState &result) {
|
|||
|
||||
// Parse region
|
||||
auto *body = result.addRegion();
|
||||
return parser.parseRegion(*body, args, argTypes);
|
||||
return parser.parseRegion(*body, args);
|
||||
}
|
||||
|
||||
void FuncOp::print(OpAsmPrinter &p) {
|
||||
|
|
|
@ -496,15 +496,20 @@ SuccessorOperands llhd::WaitOp::getSuccessorOperands(unsigned index) {
|
|||
/// respectively.
|
||||
static ParseResult
|
||||
parseArgumentList(OpAsmParser &parser,
|
||||
SmallVectorImpl<OpAsmParser::UnresolvedOperand> &args,
|
||||
SmallVectorImpl<OpAsmParser::Argument> &args,
|
||||
SmallVectorImpl<Type> &argTypes) {
|
||||
auto parseElt = [&]() -> ParseResult {
|
||||
OpAsmParser::UnresolvedOperand argument;
|
||||
OpAsmParser::Argument argument;
|
||||
Type argType;
|
||||
if (succeeded(parser.parseOptionalRegionArgument(argument))) {
|
||||
if (!argument.name.empty() && succeeded(parser.parseColonType(argType))) {
|
||||
args.push_back(argument);
|
||||
argTypes.push_back(argType);
|
||||
auto optArg = parser.parseOptionalArgument(argument);
|
||||
if (optArg.hasValue()) {
|
||||
if (succeeded(optArg.getValue())) {
|
||||
if (!argument.ssaName.name.empty() &&
|
||||
succeeded(parser.parseColonType(argType))) {
|
||||
args.push_back(argument);
|
||||
argTypes.push_back(argType);
|
||||
args.back().type = argType;
|
||||
}
|
||||
}
|
||||
}
|
||||
return success();
|
||||
|
@ -518,7 +523,7 @@ parseArgumentList(OpAsmParser &parser,
|
|||
/// (%arg0 : T0, %arg1 : T1, <...>) -> (%out0 : T0, %out1 : T1, <...>)
|
||||
static ParseResult
|
||||
parseEntitySignature(OpAsmParser &parser, OperationState &result,
|
||||
SmallVectorImpl<OpAsmParser::UnresolvedOperand> &args,
|
||||
SmallVectorImpl<OpAsmParser::Argument> &args,
|
||||
SmallVectorImpl<Type> &argTypes) {
|
||||
if (parseArgumentList(parser, args, argTypes))
|
||||
return failure();
|
||||
|
@ -533,7 +538,7 @@ parseEntitySignature(OpAsmParser &parser, OperationState &result,
|
|||
|
||||
ParseResult llhd::EntityOp::parse(OpAsmParser &parser, OperationState &result) {
|
||||
StringAttr entityName;
|
||||
SmallVector<OpAsmParser::UnresolvedOperand, 4> args;
|
||||
SmallVector<OpAsmParser::Argument, 4> args;
|
||||
SmallVector<Type, 4> argTypes;
|
||||
|
||||
if (parser.parseSymbolName(entityName, SymbolTable::getSymbolAttrName(),
|
||||
|
@ -550,7 +555,7 @@ ParseResult llhd::EntityOp::parse(OpAsmParser &parser, OperationState &result) {
|
|||
TypeAttr::get(type));
|
||||
|
||||
auto &body = *result.addRegion();
|
||||
if (parser.parseRegion(body, args, argTypes))
|
||||
if (parser.parseRegion(body, args))
|
||||
return failure();
|
||||
if (body.empty())
|
||||
body.push_back(std::make_unique<Block>().release());
|
||||
|
@ -711,9 +716,9 @@ LogicalResult llhd::ProcOp::verify() {
|
|||
return success();
|
||||
}
|
||||
|
||||
static ParseResult parseProcArgumentList(
|
||||
OpAsmParser &parser, SmallVectorImpl<Type> &argTypes,
|
||||
SmallVectorImpl<OpAsmParser::UnresolvedOperand> &argNames) {
|
||||
static ParseResult
|
||||
parseProcArgumentList(OpAsmParser &parser, SmallVectorImpl<Type> &argTypes,
|
||||
SmallVectorImpl<OpAsmParser::Argument> &argNames) {
|
||||
if (parser.parseLParen())
|
||||
return failure();
|
||||
|
||||
|
@ -724,26 +729,30 @@ static ParseResult parseProcArgumentList(
|
|||
llvm::SMLoc loc = parser.getCurrentLocation();
|
||||
|
||||
// Parse argument name if present.
|
||||
OpAsmParser::UnresolvedOperand argument;
|
||||
OpAsmParser::Argument argument;
|
||||
Type argumentType;
|
||||
if (succeeded(parser.parseOptionalRegionArgument(argument)) &&
|
||||
!argument.name.empty()) {
|
||||
// Reject this if the preceding argument was missing a name.
|
||||
if (argNames.empty() && !argTypes.empty())
|
||||
return parser.emitError(loc, "expected type instead of SSA identifier");
|
||||
argNames.push_back(argument);
|
||||
auto optArg = parser.parseOptionalArgument(argument);
|
||||
if (optArg.hasValue()) {
|
||||
if (succeeded(optArg.getValue())) {
|
||||
// Reject this if the preceding argument was missing a name.
|
||||
if (argNames.empty() && !argTypes.empty())
|
||||
return parser.emitError(loc,
|
||||
"expected type instead of SSA identifier");
|
||||
argNames.push_back(argument);
|
||||
|
||||
if (parser.parseColonType(argumentType))
|
||||
if (parser.parseColonType(argumentType))
|
||||
return failure();
|
||||
} else if (!argNames.empty()) {
|
||||
// Reject this if the preceding argument had a name.
|
||||
return parser.emitError(loc, "expected SSA identifier");
|
||||
} else if (parser.parseType(argumentType)) {
|
||||
return failure();
|
||||
} else if (!argNames.empty()) {
|
||||
// Reject this if the preceding argument had a name.
|
||||
return parser.emitError(loc, "expected SSA identifier");
|
||||
} else if (parser.parseType(argumentType)) {
|
||||
return failure();
|
||||
}
|
||||
}
|
||||
|
||||
// Add the argument type.
|
||||
argTypes.push_back(argumentType);
|
||||
argNames.back().type = argumentType;
|
||||
|
||||
return success();
|
||||
};
|
||||
|
@ -768,7 +777,7 @@ static ParseResult parseProcArgumentList(
|
|||
|
||||
ParseResult llhd::ProcOp::parse(OpAsmParser &parser, OperationState &result) {
|
||||
StringAttr procName;
|
||||
SmallVector<OpAsmParser::UnresolvedOperand, 8> argNames;
|
||||
SmallVector<OpAsmParser::Argument, 8> argNames;
|
||||
SmallVector<Type, 8> argTypes;
|
||||
Builder &builder = parser.getBuilder();
|
||||
|
||||
|
@ -791,8 +800,7 @@ ParseResult llhd::ProcOp::parse(OpAsmParser &parser, OperationState &result) {
|
|||
TypeAttr::get(type));
|
||||
|
||||
auto *body = result.addRegion();
|
||||
parser.parseRegion(*body, argNames,
|
||||
argNames.empty() ? ArrayRef<Type>() : argTypes);
|
||||
parser.parseRegion(*body, argNames);
|
||||
|
||||
return success();
|
||||
}
|
||||
|
|
|
@ -402,10 +402,8 @@ ParseResult MSFTModuleOp::parse(OpAsmParser &parser, OperationState &result) {
|
|||
|
||||
auto loc = parser.getCurrentLocation();
|
||||
|
||||
SmallVector<OpAsmParser::UnresolvedOperand, 4> entryArgs;
|
||||
SmallVector<NamedAttrList, 4> argAttrs;
|
||||
SmallVector<NamedAttrList, 4> resultAttrs;
|
||||
SmallVector<Type, 4> argTypes;
|
||||
SmallVector<OpAsmParser::Argument, 4> entryArgs;
|
||||
SmallVector<DictionaryAttr, 4> resultAttrs;
|
||||
SmallVector<Type, 4> resultTypes;
|
||||
auto &builder = parser.getBuilder();
|
||||
|
||||
|
@ -425,12 +423,14 @@ ParseResult MSFTModuleOp::parse(OpAsmParser &parser, OperationState &result) {
|
|||
bool isVariadic = false;
|
||||
SmallVector<Attribute> resultNames;
|
||||
if (hw::module_like_impl::parseModuleFunctionSignature(
|
||||
parser, entryArgs, argTypes, argAttrs, isVariadic, resultTypes,
|
||||
resultAttrs, resultNames))
|
||||
parser, entryArgs, isVariadic, resultTypes, resultAttrs, resultNames))
|
||||
return failure();
|
||||
|
||||
// Record the argument and result types as an attribute. This is necessary
|
||||
// for external modules.
|
||||
SmallVector<Type> argTypes;
|
||||
for (auto arg : entryArgs)
|
||||
argTypes.push_back(arg.type);
|
||||
auto type = builder.getFunctionType(argTypes, resultTypes);
|
||||
result.addAttribute(getTypeAttrName(), TypeAttr::get(type));
|
||||
|
||||
|
@ -452,25 +452,20 @@ ParseResult MSFTModuleOp::parse(OpAsmParser &parser, OperationState &result) {
|
|||
if (!entryArgs.empty()) {
|
||||
for (auto &arg : entryArgs)
|
||||
argNames.push_back(
|
||||
hw::module_like_impl::getPortNameAttr(context, arg.name));
|
||||
} else if (!argTypes.empty()) {
|
||||
// The parser returns empty names in a special way.
|
||||
argNames.assign(argTypes.size(), StringAttr::get(context, ""));
|
||||
hw::module_like_impl::getPortNameAttr(context, arg.ssaName.name));
|
||||
}
|
||||
|
||||
result.addAttribute("argNames", ArrayAttr::get(context, argNames));
|
||||
result.addAttribute("resultNames", ArrayAttr::get(context, resultNames));
|
||||
|
||||
assert(argAttrs.size() == argTypes.size());
|
||||
assert(resultAttrs.size() == resultTypes.size());
|
||||
|
||||
// Add the attributes to the module arguments.
|
||||
addArgAndResultAttrs(builder, result, argAttrs, resultAttrs);
|
||||
addArgAndResultAttrs(builder, result, entryArgs, resultAttrs);
|
||||
|
||||
// Parse the optional module body.
|
||||
auto regionSuccess = parser.parseOptionalRegion(
|
||||
*result.addRegion(), entryArgs,
|
||||
entryArgs.empty() ? ArrayRef<Type>() : argTypes);
|
||||
auto regionSuccess =
|
||||
parser.parseOptionalRegion(*result.addRegion(), entryArgs);
|
||||
if (regionSuccess.hasValue() && failed(*regionSuccess))
|
||||
return failure();
|
||||
|
||||
|
@ -650,10 +645,8 @@ ParseResult MSFTModuleExternOp::parse(OpAsmParser &parser,
|
|||
|
||||
auto loc = parser.getCurrentLocation();
|
||||
|
||||
SmallVector<OpAsmParser::UnresolvedOperand, 4> entryArgs;
|
||||
SmallVector<NamedAttrList, 4> argAttrs;
|
||||
SmallVector<NamedAttrList, 4> resultAttrs;
|
||||
SmallVector<Type, 4> argTypes;
|
||||
SmallVector<OpAsmParser::Argument, 4> entryArgs;
|
||||
SmallVector<DictionaryAttr, 4> resultAttrs;
|
||||
SmallVector<Type, 4> resultTypes;
|
||||
SmallVector<Attribute> parameters;
|
||||
auto &builder = parser.getBuilder();
|
||||
|
@ -669,14 +662,18 @@ ParseResult MSFTModuleExternOp::parse(OpAsmParser &parser,
|
|||
SmallVector<Attribute> resultNames;
|
||||
if (parseParameterList(parser, parameters) ||
|
||||
hw::module_like_impl::parseModuleFunctionSignature(
|
||||
parser, entryArgs, argTypes, argAttrs, isVariadic, resultTypes,
|
||||
resultAttrs, resultNames) ||
|
||||
parser, entryArgs, isVariadic, resultTypes, resultAttrs,
|
||||
resultNames) ||
|
||||
// If function attributes are present, parse them.
|
||||
parser.parseOptionalAttrDictWithKeyword(result.attributes))
|
||||
return failure();
|
||||
|
||||
// Record the argument and result types as an attribute. This is necessary
|
||||
// for external modules.
|
||||
SmallVector<Type> argTypes;
|
||||
for (auto arg : entryArgs)
|
||||
argTypes.push_back(arg.type);
|
||||
|
||||
auto type = builder.getFunctionType(argTypes, resultTypes);
|
||||
result.addAttribute(getTypeAttrName(), TypeAttr::get(type));
|
||||
|
||||
|
@ -694,10 +691,7 @@ ParseResult MSFTModuleExternOp::parse(OpAsmParser &parser,
|
|||
if (!entryArgs.empty()) {
|
||||
for (auto &arg : entryArgs)
|
||||
argNames.push_back(
|
||||
hw::module_like_impl::getPortNameAttr(context, arg.name));
|
||||
} else if (!argTypes.empty()) {
|
||||
// The parser returns empty names in a special way.
|
||||
argNames.assign(argTypes.size(), StringAttr::get(context, ""));
|
||||
hw::module_like_impl::getPortNameAttr(context, arg.ssaName.name));
|
||||
}
|
||||
|
||||
// An explicit `argNames` attribute overrides the MLIR names. This is how
|
||||
|
@ -709,11 +703,10 @@ ParseResult MSFTModuleExternOp::parse(OpAsmParser &parser,
|
|||
result.addAttribute("resultNames", ArrayAttr::get(context, resultNames));
|
||||
result.addAttribute("parameters", ArrayAttr::get(context, parameters));
|
||||
|
||||
assert(argAttrs.size() == argTypes.size());
|
||||
assert(resultAttrs.size() == resultTypes.size());
|
||||
|
||||
// Add the attributes to the function arguments.
|
||||
addArgAndResultAttrs(builder, result, argAttrs, resultAttrs);
|
||||
addArgAndResultAttrs(builder, result, entryArgs, resultAttrs);
|
||||
|
||||
// Extern modules carry an empty region to work with HWModuleImplementation.h.
|
||||
result.addRegion();
|
||||
|
@ -857,10 +850,22 @@ ParseResult SystolicArrayOp::parse(OpAsmParser &parser,
|
|||
result.addOperands(operands);
|
||||
|
||||
Type peOutputType;
|
||||
SmallVector<OpAsmParser::UnresolvedOperand> peArgs;
|
||||
if (parser.parseKeyword("pe") ||
|
||||
parser.parseOperandList(peArgs, 2, AsmParser::Delimiter::Paren) ||
|
||||
parser.parseArrow() || parser.parseLParen() ||
|
||||
SmallVector<OpAsmParser::Argument> peArgs;
|
||||
if (parser.parseKeyword("pe")) {
|
||||
return failure();
|
||||
}
|
||||
llvm::SMLoc peLoc = parser.getCurrentLocation();
|
||||
if (parser.parseArgumentList(peArgs, AsmParser::Delimiter::Paren)) {
|
||||
return failure();
|
||||
}
|
||||
if (peArgs.size() != 2) {
|
||||
return parser.emitError(peLoc, "expected two operands");
|
||||
}
|
||||
|
||||
peArgs[0].type = rowType;
|
||||
peArgs[1].type = columnType;
|
||||
|
||||
if (parser.parseArrow() || parser.parseLParen() ||
|
||||
parser.parseType(peOutputType) || parser.parseRParen())
|
||||
return failure();
|
||||
|
||||
|
@ -868,9 +873,12 @@ ParseResult SystolicArrayOp::parse(OpAsmParser &parser,
|
|||
hw::ArrayType::get(peOutputType, numColumns), numRows)});
|
||||
|
||||
Region *pe = result.addRegion();
|
||||
llvm::SMLoc peLoc = parser.getCurrentLocation();
|
||||
if (parser.parseRegion(*pe, peArgs, {rowType, columnType}))
|
||||
|
||||
peLoc = parser.getCurrentLocation();
|
||||
|
||||
if (parser.parseRegion(*pe, peArgs))
|
||||
return failure();
|
||||
|
||||
if (pe->getBlocks().size() != 1)
|
||||
return parser.emitError(peLoc, "expected one block for the PE");
|
||||
Operation *peTerm = pe->getBlocks().front().getTerminator();
|
||||
|
|
|
@ -44,7 +44,8 @@ ParseResult PipelineWhileOp::parse(OpAsmParser &parser,
|
|||
}
|
||||
|
||||
// Parse iter_args assignment list.
|
||||
SmallVector<OpAsmParser::UnresolvedOperand> regionArgs, operands;
|
||||
SmallVector<OpAsmParser::Argument> regionArgs;
|
||||
SmallVector<OpAsmParser::UnresolvedOperand> operands;
|
||||
if (succeeded(parser.parseOptionalKeyword("iter_args"))) {
|
||||
if (parser.parseAssignmentList(regionArgs, operands))
|
||||
return failure();
|
||||
|
@ -59,19 +60,22 @@ ParseResult PipelineWhileOp::parse(OpAsmParser &parser,
|
|||
result.addTypes(type.getResults());
|
||||
|
||||
// Resolve iter_args operands.
|
||||
for (auto [operand, type] : llvm::zip(operands, type.getInputs()))
|
||||
for (auto [regionArg, operand, type] :
|
||||
llvm::zip(regionArgs, operands, type.getInputs())) {
|
||||
regionArg.type = type;
|
||||
if (parser.resolveOperand(operand, type, result.operands))
|
||||
return failure();
|
||||
}
|
||||
|
||||
// Parse condition region.
|
||||
Region *condition = result.addRegion();
|
||||
parser.parseRegion(*condition, regionArgs, type.getInputs());
|
||||
parser.parseRegion(*condition, regionArgs);
|
||||
|
||||
// Parse stages region.
|
||||
if (parser.parseKeyword("do"))
|
||||
return failure();
|
||||
Region *stages = result.addRegion();
|
||||
parser.parseRegion(*stages, regionArgs, type.getInputs());
|
||||
parser.parseRegion(*stages, regionArgs);
|
||||
|
||||
return success();
|
||||
}
|
||||
|
|
2
llvm
2
llvm
|
@ -1 +1 @@
|
|||
Subproject commit 2d014b72ccb51de9a9627c31667a3edf8cca7616
|
||||
Subproject commit 9a12138b5fd8c807c3b95144236c07dfc323974f
|
|
@ -1,7 +1,7 @@
|
|||
// RUN: circt-opt %s -test-dependence-analysis | FileCheck %s
|
||||
|
||||
// CHECK-LABEL: func @test1
|
||||
func @test1(%arg0: memref<?xi32>) -> i32 {
|
||||
func.func @test1(%arg0: memref<?xi32>) -> i32 {
|
||||
%c0_i32 = arith.constant 0 : i32
|
||||
%0:2 = affine.for %arg1 = 0 to 10 iter_args(%arg2 = %c0_i32, %arg3 = %c0_i32) -> (i32, i32) {
|
||||
// CHECK: affine.load %arg0[%arg1] {dependences = []}
|
||||
|
@ -14,7 +14,7 @@ func @test1(%arg0: memref<?xi32>) -> i32 {
|
|||
|
||||
// CHECK-LABEL: func @test2
|
||||
#set = affine_set<(d0) : (d0 - 3 >= 0)>
|
||||
func @test2(%arg0: memref<?xi32>, %arg1: memref<?xi32>) {
|
||||
func.func @test2(%arg0: memref<?xi32>, %arg1: memref<?xi32>) {
|
||||
affine.for %arg2 = 0 to 10 {
|
||||
// CHECK: affine.load %arg0[%arg2] {dependences = []}
|
||||
%0 = affine.load %arg0[%arg2] : memref<?xi32>
|
||||
|
@ -30,7 +30,7 @@ func @test2(%arg0: memref<?xi32>, %arg1: memref<?xi32>) {
|
|||
}
|
||||
|
||||
// CHECK-LABEL: func @test3
|
||||
func @test3(%arg0: memref<?xi32>) {
|
||||
func.func @test3(%arg0: memref<?xi32>) {
|
||||
%0 = memref.alloca() : memref<1xi32>
|
||||
%1 = memref.alloca() : memref<1xi32>
|
||||
%2 = memref.alloca() : memref<1xi32>
|
||||
|
@ -55,7 +55,7 @@ func @test3(%arg0: memref<?xi32>) {
|
|||
}
|
||||
|
||||
// CHECK-LABEL: func @test4
|
||||
func @test4(%arg0: memref<?xi32>, %arg1: memref<?xi32>) {
|
||||
func.func @test4(%arg0: memref<?xi32>, %arg1: memref<?xi32>) {
|
||||
%c1_i32 = arith.constant 1 : i32
|
||||
affine.for %arg2 = 0 to 10 {
|
||||
// CHECK: affine.load %arg1[%arg2] {dependences = []}
|
||||
|
@ -69,7 +69,7 @@ func @test4(%arg0: memref<?xi32>, %arg1: memref<?xi32>) {
|
|||
}
|
||||
|
||||
// CHECK-LABEL: func @test5
|
||||
func @test5(%arg0: memref<?xi32>) {
|
||||
func.func @test5(%arg0: memref<?xi32>) {
|
||||
affine.for %arg1 = 2 to 10 {
|
||||
// CHECK{LITERAL}: affine.load %arg0[%arg1 - 2] {dependences = [[[1, 1]], [[2, 2]]]}
|
||||
%0 = affine.load %arg0[%arg1 - 2] : memref<?xi32>
|
||||
|
@ -84,7 +84,7 @@ func @test5(%arg0: memref<?xi32>) {
|
|||
|
||||
// CHECK-LABEL: func @test6
|
||||
#set1 = affine_set<(d0) : (d0 - 5 >= 0)>
|
||||
func @test6(%arg0: memref<?xi32>) {
|
||||
func.func @test6(%arg0: memref<?xi32>) {
|
||||
affine.for %arg1 = 0 to 10 {
|
||||
%0 = affine.if #set1(%arg1) -> i32 {
|
||||
// CHECK: affine.load %arg0[%arg1] {dependences = []}
|
||||
|
@ -103,7 +103,7 @@ func @test6(%arg0: memref<?xi32>) {
|
|||
// CHECK-LABEL: func @test7
|
||||
#set2 = affine_set<(d0) : (d0 - 2 >= 0)>
|
||||
#set3 = affine_set<(d0) : (d0 - 6 >= 0)>
|
||||
func @test7(%arg0: memref<?xi32>) {
|
||||
func.func @test7(%arg0: memref<?xi32>) {
|
||||
affine.for %arg1 = 0 to 10 {
|
||||
affine.if #set2(%arg1) {
|
||||
%0 = affine.if #set3(%arg1) -> i32 {
|
||||
|
@ -119,7 +119,7 @@ func @test7(%arg0: memref<?xi32>) {
|
|||
}
|
||||
|
||||
// CHECK-LABEL: func @test8
|
||||
func @test8(%arg0: memref<?xi32>) {
|
||||
func.func @test8(%arg0: memref<?xi32>) {
|
||||
affine.for %arg1 = 0 to 10 {
|
||||
affine.if #set2(%arg1) {
|
||||
%0 = affine.if #set3(%arg1) -> i32 {
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
// RUN: circt-opt %s -test-scheduling-analysis | FileCheck %s
|
||||
|
||||
// CHECK-LABEL: func @test1
|
||||
func @test1(%arg0: memref<?xi32>) -> i32 {
|
||||
func.func @test1(%arg0: memref<?xi32>) -> i32 {
|
||||
%c0_i32 = arith.constant 0 : i32
|
||||
%0:2 = affine.for %arg1 = 0 to 10 iter_args(%arg2 = %c0_i32, %arg3 = %c0_i32) -> (i32, i32) {
|
||||
%1 = affine.load %arg0[%arg1] : memref<?xi32>
|
||||
|
@ -13,7 +13,7 @@ func @test1(%arg0: memref<?xi32>) -> i32 {
|
|||
}
|
||||
// CHECK-LABEL: func @test2
|
||||
#set = affine_set<(d0) : (d0 - 3 >= 0)>
|
||||
func @test2(%arg0: memref<?xi32>, %arg1: memref<?xi32>) {
|
||||
func.func @test2(%arg0: memref<?xi32>, %arg1: memref<?xi32>) {
|
||||
affine.for %arg2 = 0 to 10 {
|
||||
%0 = affine.load %arg0[%arg2] : memref<?xi32>
|
||||
affine.if #set(%arg2) {
|
||||
|
@ -27,7 +27,7 @@ func @test2(%arg0: memref<?xi32>, %arg1: memref<?xi32>) {
|
|||
}
|
||||
|
||||
// CHECK-LABEL: func @test3
|
||||
func @test3(%arg0: memref<?xi32>) {
|
||||
func.func @test3(%arg0: memref<?xi32>) {
|
||||
%0 = memref.alloca() : memref<1xi32>
|
||||
%1 = memref.alloca() : memref<1xi32>
|
||||
%2 = memref.alloca() : memref<1xi32>
|
||||
|
@ -52,7 +52,7 @@ func @test3(%arg0: memref<?xi32>) {
|
|||
|
||||
// CHECK-LABEL: func @test4
|
||||
// CHECK-NOT: dependence
|
||||
func @test4(%arg0: memref<?xi32>, %arg1: memref<?xi32>) {
|
||||
func.func @test4(%arg0: memref<?xi32>, %arg1: memref<?xi32>) {
|
||||
%c1_i32 = arith.constant 1 : i32
|
||||
affine.for %arg2 = 0 to 10 {
|
||||
%0 = affine.load %arg1[%arg2] : memref<?xi32>
|
||||
|
@ -65,7 +65,7 @@ func @test4(%arg0: memref<?xi32>, %arg1: memref<?xi32>) {
|
|||
}
|
||||
|
||||
// CHECK-LABEL: func @test5
|
||||
func @test5(%arg0: memref<?xi32>) {
|
||||
func.func @test5(%arg0: memref<?xi32>) {
|
||||
affine.for %arg1 = 2 to 10 {
|
||||
// CHECK: affine.load %arg0[%arg1 - 2] {dependence}
|
||||
%0 = affine.load %arg0[%arg1 - 2] : memref<?xi32>
|
||||
|
@ -79,7 +79,7 @@ func @test5(%arg0: memref<?xi32>) {
|
|||
|
||||
// CHECK-LABEL: func @test6
|
||||
#set1 = affine_set<(d0) : (d0 - 5 >= 0)>
|
||||
func @test6(%arg0: memref<?xi32>) {
|
||||
func.func @test6(%arg0: memref<?xi32>) {
|
||||
affine.for %arg1 = 0 to 10 {
|
||||
%0 = affine.if #set1(%arg1) -> i32 {
|
||||
%1 = affine.load %arg0[%arg1] : memref<?xi32>
|
||||
|
@ -98,7 +98,7 @@ func @test6(%arg0: memref<?xi32>) {
|
|||
// CHECK-LABEL: func @test7
|
||||
#set2 = affine_set<(d0) : (d0 - 2 >= 0)>
|
||||
#set3 = affine_set<(d0) : (d0 - 6 >= 0)>
|
||||
func @test7(%arg0: memref<?xi32>) {
|
||||
func.func @test7(%arg0: memref<?xi32>) {
|
||||
affine.for %arg1 = 0 to 10 {
|
||||
affine.if #set2(%arg1) {
|
||||
%0 = affine.if #set3(%arg1) -> i32 {
|
||||
|
@ -114,7 +114,7 @@ func @test7(%arg0: memref<?xi32>) {
|
|||
}
|
||||
|
||||
// CHECK-LABEL: func @test8
|
||||
func @test8(%arg0: memref<?xi32>) {
|
||||
func.func @test8(%arg0: memref<?xi32>) {
|
||||
affine.for %arg1 = 0 to 10 {
|
||||
affine.if #set2(%arg1) {
|
||||
%0 = affine.if #set3(%arg1) -> i32 {
|
||||
|
@ -133,7 +133,7 @@ func @test8(%arg0: memref<?xi32>) {
|
|||
}
|
||||
|
||||
// CHECK-LABEL: func @test9
|
||||
func @test9(%arg0: memref<4x4xi32>, %arg1: memref<4x4xi32>, %arg2: memref<4x4xi32>) {
|
||||
func.func @test9(%arg0: memref<4x4xi32>, %arg1: memref<4x4xi32>, %arg2: memref<4x4xi32>) {
|
||||
affine.for %arg3 = 0 to 4 {
|
||||
affine.for %arg4 = 0 to 4 {
|
||||
affine.for %arg5 = 0 to 4 {
|
||||
|
@ -152,7 +152,7 @@ func @test9(%arg0: memref<4x4xi32>, %arg1: memref<4x4xi32>, %arg2: memref<4x4xi3
|
|||
}
|
||||
|
||||
// CHECK-LABEL: func @test10
|
||||
func @test10(%arg0: memref<5xi32>) {
|
||||
func.func @test10(%arg0: memref<5xi32>) {
|
||||
%true = arith.constant 1 : i1
|
||||
%c0_i32 = arith.constant 0 : i32
|
||||
affine.for %arg1 = 0 to 5 {
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
// RUN: circt-opt -convert-affine-to-staticlogic %s | FileCheck %s
|
||||
|
||||
// CHECK-LABEL: func @minimal
|
||||
func @minimal(%arg0 : memref<10xindex>) {
|
||||
func.func @minimal(%arg0 : memref<10xindex>) {
|
||||
// Setup constants.
|
||||
// CHECK: %[[LB:.+]] = arith.constant 0 : [[ITER_TYPE:.+]]
|
||||
// CHECK: %[[UB:.+]] = arith.constant [[TRIP_COUNT:.+]] : [[ITER_TYPE]]
|
||||
|
@ -30,7 +30,7 @@ func @minimal(%arg0 : memref<10xindex>) {
|
|||
}
|
||||
|
||||
// CHECK-LABEL: func @dot
|
||||
func @dot(%arg0: memref<64xi32>, %arg1: memref<64xi32>) -> i32 {
|
||||
func.func @dot(%arg0: memref<64xi32>, %arg1: memref<64xi32>) -> i32 {
|
||||
// Pipeline boilerplate checked above, just check the stages computations.
|
||||
|
||||
// First stage.
|
||||
|
|
|
@ -10,7 +10,7 @@
|
|||
|
||||
firrtl.circuit "OperandTypeIsFIRRTL" {
|
||||
firrtl.module @OperandTypeIsFIRRTL() { }
|
||||
func.func @Test() {
|
||||
func.func @Test() {
|
||||
// expected-error @+1 {{Found unhandled FIRRTL operation 'firrtl.constant'}}
|
||||
%a = firrtl.constant 0 : !firrtl.uint<1>
|
||||
return
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
// RUN: circt-opt %s --convert-llhd-to-llvm | FileCheck %s
|
||||
|
||||
// CHECK-LABEL: llvm.func @convertBitcast
|
||||
func @convertBitcast(%arg0 : i32, %arg1: !hw.array<2xi32>, %arg2: !hw.struct<foo: i32, bar: i32>) {
|
||||
func.func @convertBitcast(%arg0 : i32, %arg1: !hw.array<2xi32>, %arg2: !hw.struct<foo: i32, bar: i32>) {
|
||||
|
||||
// CHECK-NEXT: %[[ONE1:.*]] = llvm.mlir.constant(1 : i32) : i32
|
||||
// CHECK-NEXT: %[[A1:.*]] = llvm.alloca %[[ONE1]] x i32 {alignment = 4 : i64} : (i32) -> !llvm.ptr<i32>
|
||||
|
@ -28,7 +28,7 @@ func @convertBitcast(%arg0 : i32, %arg1: !hw.array<2xi32>, %arg2: !hw.struct<foo
|
|||
}
|
||||
|
||||
// CHECK-LABEL: llvm.func @convertArray
|
||||
func @convertArray(%arg0 : i1, %arg1: !hw.array<2xi32>) {
|
||||
func.func @convertArray(%arg0 : i1, %arg1: !hw.array<2xi32>) {
|
||||
|
||||
// CHECK-NEXT: %[[ZERO:.*]] = llvm.mlir.constant(0 : i32) : i32
|
||||
// CHECK-NEXT: %[[ONE:.*]] = llvm.mlir.constant(1 : i32) : i32
|
||||
|
@ -59,12 +59,12 @@ func @convertArray(%arg0 : i1, %arg1: !hw.array<2xi32>) {
|
|||
// CHECK-NEXT: %[[E4:.*]] = llvm.extractvalue %arg1[1 : i32] : !llvm.array<2 x i32>
|
||||
// CHECK-NEXT: llvm.insertvalue %[[E4]], %[[I3]][3 : i32] : !llvm.array<4 x i32>
|
||||
%2 = hw.array_concat %arg1, %arg1 : !hw.array<2xi32>, !hw.array<2xi32>
|
||||
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
// CHECK-LABEL: llvm.func @convertStruct
|
||||
func @convertStruct(%arg0 : i32, %arg1: !hw.struct<foo: i32, bar: i8>) {
|
||||
func.func @convertStruct(%arg0 : i32, %arg1: !hw.struct<foo: i32, bar: i8>) {
|
||||
// CHECK-NEXT: llvm.extractvalue %arg1[1 : i32] : !llvm.struct<(i8, i32)>
|
||||
%0 = hw.struct_extract %arg1["foo"] : !hw.struct<foo: i32, bar: i8>
|
||||
|
||||
|
|
|
@ -2,7 +2,7 @@
|
|||
// RUN: circt-opt %s --convert-llhd-to-llvm | FileCheck %s
|
||||
|
||||
// CHECK-LABEL: llvm.func @convertArithmetic
|
||||
func @convertArithmetic(%arg0: i32, %arg1: i32, %arg2: i32) -> i32 {
|
||||
func.func @convertArithmetic(%arg0: i32, %arg1: i32, %arg2: i32) -> i32 {
|
||||
// CHECK: %[[R0:.*]] = llvm.add %arg0, %arg1 : i32
|
||||
// CHECK: %[[R1:.*]] = llvm.add %[[R0]], %arg2 : i32
|
||||
%0 = comb.add %arg0, %arg1, %arg2 : i32
|
||||
|
@ -28,7 +28,7 @@ func @convertArithmetic(%arg0: i32, %arg1: i32, %arg2: i32) -> i32 {
|
|||
}
|
||||
|
||||
// CHECK-LABEL: llvm.func @convertRelational
|
||||
func @convertRelational(%arg0: i32, %arg1: i32) {
|
||||
func.func @convertRelational(%arg0: i32, %arg1: i32) {
|
||||
// CHECK: llvm.icmp "eq" %arg0, %arg1 : i32
|
||||
%0 = comb.icmp eq %arg0, %arg1 : i32
|
||||
// CHECK: llvm.icmp "ne" %arg0, %arg1 : i32
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
// CHECK-LABEL: convert_bitwise_i1
|
||||
// CHECK-SAME: %[[LHS:.*]]: i1,
|
||||
// CHECK-SAME: %[[RHS:.*]]: i1
|
||||
func @convert_bitwise_i1(%lhs : i1, %rhs : i1) {
|
||||
func.func @convert_bitwise_i1(%lhs : i1, %rhs : i1) {
|
||||
// CHECK-NEXT: %{{.*}} = llvm.and %[[LHS]], %[[RHS]] : i1
|
||||
%1 = comb.and %lhs, %rhs : i1
|
||||
// CHECK-NEXT: %{{.*}} = llvm.or %[[LHS]], %[[RHS]] : i1
|
||||
|
@ -17,7 +17,7 @@ func @convert_bitwise_i1(%lhs : i1, %rhs : i1) {
|
|||
// CHECK-LABEL: convert_bitwise_i32
|
||||
// CHECK-SAME: %[[LHS:.*]]: i32,
|
||||
// CHECK-SAME: %[[RHS:.*]]: i32
|
||||
func @convert_bitwise_i32(%lhs : i32, %rhs : i32) {
|
||||
func.func @convert_bitwise_i32(%lhs : i32, %rhs : i32) {
|
||||
// CHECK-NEXT: %{{.*}} = llvm.and %[[LHS]], %[[RHS]] : i32
|
||||
comb.and %lhs, %rhs : i32
|
||||
// CHECK-NEXT: %{{.*}} = llvm.or %[[LHS]], %[[RHS]] : i32
|
||||
|
@ -29,7 +29,7 @@ func @convert_bitwise_i32(%lhs : i32, %rhs : i32) {
|
|||
}
|
||||
|
||||
// CHECK-LABEL: convert_bitwise_i32_variadic
|
||||
func @convert_bitwise_i32_variadic(%arg0 : i32, %arg1 : i32, %arg2 : i32) {
|
||||
func.func @convert_bitwise_i32_variadic(%arg0 : i32, %arg1 : i32, %arg2 : i32) {
|
||||
%a = comb.and %arg0 : i32
|
||||
%b = comb.or %arg1 : i32
|
||||
%c = comb.xor %arg2 : i32
|
||||
|
@ -51,7 +51,7 @@ func @convert_bitwise_i32_variadic(%arg0 : i32, %arg1 : i32, %arg2 : i32) {
|
|||
// CHECK-SAME: %[[BASE:.*]]: i5,
|
||||
// CHECK-SAME: %[[HIDDEN:.*]]: i2,
|
||||
// CHECK-SAME: %[[AMOUNT:.*]]: i2
|
||||
func @convert_shl_i5_i2_i2(%base : i5, %hidden : i2, %amount : i2) {
|
||||
func.func @convert_shl_i5_i2_i2(%base : i5, %hidden : i2, %amount : i2) {
|
||||
// CHECK-NEXT: %[[ZEXTB:.*]] = llvm.zext %[[BASE]] : i5 to i7
|
||||
// CHECK-NEXT: %[[ZEXTH:.*]] = llvm.zext %[[HIDDEN]] : i2 to i7
|
||||
// CHECK-NEXT: %[[ZEXTA:.*]] = llvm.zext %[[AMOUNT]] : i2 to i7
|
||||
|
@ -70,7 +70,7 @@ func @convert_shl_i5_i2_i2(%base : i5, %hidden : i2, %amount : i2) {
|
|||
// CHECK-SAME: %[[BASE:.*]]: i5,
|
||||
// CHECK-SAME: %[[HIDDEN:.*]]: i2,
|
||||
// CHECK-SAME: %[[AMOUNT:.*]]: i2
|
||||
func @convert_shr_i5_i2_i2(%base : i5, %hidden : i2, %amount : i2) {
|
||||
func.func @convert_shr_i5_i2_i2(%base : i5, %hidden : i2, %amount : i2) {
|
||||
// CHECK-NEXT: %[[ZEXTB:.*]] = llvm.zext %[[BASE]] : i5 to i7
|
||||
// CHECK-NEXT: %[[ZEXTH:.*]] = llvm.zext %[[HIDDEN]] : i2 to i7
|
||||
// CHECK-NEXT: %[[ZEXTA:.*]] = llvm.zext %[[AMOUNT]] : i2 to i7
|
||||
|
@ -85,7 +85,7 @@ func @convert_shr_i5_i2_i2(%base : i5, %hidden : i2, %amount : i2) {
|
|||
}
|
||||
|
||||
// CHECK-LABEL: llvm.func @convert_comb_shift
|
||||
func @convert_comb_shift(%arg0: i32, %arg1: i32, %arg2: i1) -> i32 {
|
||||
func.func @convert_comb_shift(%arg0: i32, %arg1: i32, %arg2: i1) -> i32 {
|
||||
|
||||
// CHECK: %[[R0:.*]] = llvm.shl %arg0, %arg1 : i32
|
||||
%0 = comb.shl %arg0, %arg1 : i32
|
||||
|
|
|
@ -34,7 +34,7 @@
|
|||
// CHECK: llvm.store %[[VAL_26]], %[[VAL_28]] : !llvm.ptr<struct<(ptr<i8>, i64, i64, i64)>>
|
||||
// CHECK: llvm.return
|
||||
// CHECK: }
|
||||
func @convertSigExtract (%c : i5, %sI32 : !llhd.sig<i32>) {
|
||||
func.func @convertSigExtract (%c : i5, %sI32 : !llhd.sig<i32>) {
|
||||
%0 = llhd.sig.extract %sI32 from %c : (!llhd.sig<i32>) -> !llhd.sig<i10>
|
||||
|
||||
return
|
||||
|
@ -70,7 +70,7 @@ func @convertSigExtract (%c : i5, %sI32 : !llhd.sig<i32>) {
|
|||
// CHECK: llvm.store %[[VAL_23]], %[[VAL_25]] : !llvm.ptr<struct<(ptr<i8>, i64, i64, i64)>>
|
||||
// CHECK: llvm.return
|
||||
// CHECK: }
|
||||
func @convertSigArraySlice (%c : i2, %sArr : !llhd.sig<!hw.array<4xi4>>) {
|
||||
func.func @convertSigArraySlice (%c : i2, %sArr : !llhd.sig<!hw.array<4xi4>>) {
|
||||
%1 = llhd.sig.array_slice %sArr at %c : (!llhd.sig<!hw.array<4xi4>>) -> !llhd.sig<!hw.array<2xi4>>
|
||||
|
||||
return
|
||||
|
@ -105,7 +105,7 @@ func @convertSigArraySlice (%c : i2, %sArr : !llhd.sig<!hw.array<4xi4>>) {
|
|||
// CHECK: llvm.store %[[VAL_22]], %[[VAL_24]] : !llvm.ptr<struct<(ptr<i8>, i64, i64, i64)>>
|
||||
// CHECK: llvm.return
|
||||
// CHECK: }
|
||||
func @convertSigStructExtract (%sTup : !llhd.sig<!hw.struct<foo: i1, bar: i2, baz: i3>>) {
|
||||
func.func @convertSigStructExtract (%sTup : !llhd.sig<!hw.struct<foo: i1, bar: i2, baz: i3>>) {
|
||||
%1 = llhd.sig.struct_extract %sTup["bar"] : !llhd.sig<!hw.struct<foo: i1, bar: i2, baz: i3>>
|
||||
|
||||
return
|
||||
|
@ -141,7 +141,7 @@ func @convertSigStructExtract (%sTup : !llhd.sig<!hw.struct<foo: i1, bar: i2, ba
|
|||
// CHECK: llvm.store %[[VAL_23]], %[[VAL_25]] : !llvm.ptr<struct<(ptr<i8>, i64, i64, i64)>>
|
||||
// CHECK: llvm.return
|
||||
// CHECK: }
|
||||
func @convertSigArrayGet(%sArr : !llhd.sig<!hw.array<4xi4>>, %c : i2) {
|
||||
func.func @convertSigArrayGet(%sArr : !llhd.sig<!hw.array<4xi4>>, %c : i2) {
|
||||
%1 = llhd.sig.array_get %sArr[%c] : !llhd.sig<!hw.array<4xi4>>
|
||||
|
||||
return
|
||||
|
|
|
@ -12,7 +12,7 @@
|
|||
// CHECK: llvm.store %[[VAL_1]], %[[VAL_5]] : !llvm.ptr<i32>
|
||||
// CHECK: llvm.return
|
||||
// CHECK: }
|
||||
func @lower_var(%i1 : i1, %i32 : i32) {
|
||||
func.func @lower_var(%i1 : i1, %i32 : i32) {
|
||||
%0 = llhd.var %i1 : i1
|
||||
%1 = llhd.var %i32 : i32
|
||||
return
|
||||
|
@ -25,7 +25,7 @@ func @lower_var(%i1 : i1, %i32 : i32) {
|
|||
// CHECK: %[[VAL_3:.*]] = llvm.load %[[VAL_1]] : !llvm.ptr<i32>
|
||||
// CHECK: llvm.return
|
||||
// CHECK: }
|
||||
func @lower_load(%i1 : !llhd.ptr<i1>, %i32 : !llhd.ptr<i32>) {
|
||||
func.func @lower_load(%i1 : !llhd.ptr<i1>, %i32 : !llhd.ptr<i32>) {
|
||||
%0 = llhd.load %i1 : !llhd.ptr<i1>
|
||||
%1 = llhd.load %i32 : !llhd.ptr<i32>
|
||||
return
|
||||
|
@ -40,7 +40,7 @@ func @lower_load(%i1 : !llhd.ptr<i1>, %i32 : !llhd.ptr<i32>) {
|
|||
// CHECK: llvm.store %[[VAL_2]], %[[VAL_3]] : !llvm.ptr<i32>
|
||||
// CHECK: llvm.return
|
||||
// CHECK: }
|
||||
func @lower_store(%i1 : i1, %i1Ptr : !llhd.ptr<i1>, %i32 : i32, %i32Ptr : !llhd.ptr<i32>) {
|
||||
func.func @lower_store(%i1 : i1, %i1Ptr : !llhd.ptr<i1>, %i32 : i32, %i32Ptr : !llhd.ptr<i32>) {
|
||||
llhd.store %i1Ptr, %i1 : !llhd.ptr<i1>
|
||||
llhd.store %i32Ptr, %i32 : !llhd.ptr<i32>
|
||||
return
|
||||
|
|
|
@ -2,27 +2,27 @@
|
|||
// RUN: circt-opt %s --convert-llhd-to-llvm | FileCheck %s
|
||||
|
||||
// CHECK-LABEL: @dummy_i1
|
||||
func @dummy_i1 (%0 : i1) {
|
||||
func.func @dummy_i1 (%0 : i1) {
|
||||
return
|
||||
}
|
||||
|
||||
// CHECK-LABEL: @dummy_i32
|
||||
func @dummy_i32 (%0 : i32) {
|
||||
func.func @dummy_i32 (%0 : i32) {
|
||||
return
|
||||
}
|
||||
|
||||
// CHECK-LABEL: @dummy_time
|
||||
func @dummy_time (%0 : !llhd.time) {
|
||||
func.func @dummy_time (%0 : !llhd.time) {
|
||||
return
|
||||
}
|
||||
|
||||
// CHECK-LABEL: @dummy_ptr
|
||||
func @dummy_ptr(%0 : !llhd.ptr<i32>) {
|
||||
func.func @dummy_ptr(%0 : !llhd.ptr<i32>) {
|
||||
return
|
||||
}
|
||||
|
||||
// CHECK-LABEL: @dummy_subsig
|
||||
func @dummy_subsig(%0 : !llhd.sig<i10>) {
|
||||
func.func @dummy_subsig(%0 : !llhd.sig<i10>) {
|
||||
return
|
||||
}
|
||||
|
||||
|
@ -62,7 +62,7 @@ llhd.proc @convert_persistent_i1 () -> () {
|
|||
%0 = hw.constant 0 : i1
|
||||
cf.br ^resume
|
||||
^resume:
|
||||
call @dummy_i1(%0) : (i1) -> ()
|
||||
func.call @dummy_i1(%0) : (i1) -> ()
|
||||
cf.br ^resume
|
||||
}
|
||||
|
||||
|
@ -103,7 +103,7 @@ llhd.proc @convert_persistent_i32 () -> () {
|
|||
%0 = hw.constant 0 : i32
|
||||
cf.br ^resume
|
||||
^resume:
|
||||
call @dummy_i32(%0) : (i32) -> ()
|
||||
func.call @dummy_i32(%0) : (i32) -> ()
|
||||
cf.br ^resume
|
||||
}
|
||||
|
||||
|
@ -143,7 +143,7 @@ llhd.proc @convert_persistent_time () -> () {
|
|||
%0 = llhd.constant_time #llhd.time<0ns, 0d, 1e>
|
||||
cf.br ^resume
|
||||
^resume:
|
||||
call @dummy_time(%0) : (!llhd.time) -> ()
|
||||
func.call @dummy_time(%0) : (!llhd.time) -> ()
|
||||
cf.br ^resume
|
||||
}
|
||||
|
||||
|
@ -187,7 +187,7 @@ llhd.proc @convert_persistent_ptr () -> () {
|
|||
%1 = llhd.var %0 : i32
|
||||
cf.br ^resume
|
||||
^resume:
|
||||
call @dummy_ptr(%1) : (!llhd.ptr<i32>) -> ()
|
||||
func.call @dummy_ptr(%1) : (!llhd.ptr<i32>) -> ()
|
||||
cf.br ^resume
|
||||
}
|
||||
|
||||
|
@ -258,7 +258,7 @@ llhd.proc @convert_persistent_subsig () -> (%out : !llhd.sig<i32>) {
|
|||
%0 = llhd.sig.extract %out from %zero : (!llhd.sig<i32>) -> !llhd.sig<i10>
|
||||
cf.br ^resume
|
||||
^resume:
|
||||
call @dummy_subsig(%0) : (!llhd.sig<i10>) -> ()
|
||||
func.call @dummy_subsig(%0) : (!llhd.sig<i10>) -> ()
|
||||
cf.br ^resume
|
||||
}
|
||||
|
||||
|
@ -306,7 +306,7 @@ llhd.proc @convert_persistent_block_argument () -> () {
|
|||
^argBB(%i : i32):
|
||||
cf.br ^end
|
||||
^end:
|
||||
call @dummy_i32(%i) : (i32) -> ()
|
||||
func.call @dummy_i32(%i) : (i32) -> ()
|
||||
llhd.halt
|
||||
}
|
||||
|
||||
|
|
|
@ -32,7 +32,7 @@ llvm.func @convert_const() {
|
|||
// CHECK: %[[VAL_10:.*]] = llvm.insertvalue %[[VAL_1]], %[[VAL_9]][3 : i32] : !llvm.array<4 x i32>
|
||||
// CHECK: llvm.return
|
||||
// CHECK: }
|
||||
func @convert_array(%ci1 : i1, %ci32 : i32) {
|
||||
func.func @convert_array(%ci1 : i1, %ci32 : i32) {
|
||||
%0 = hw.array_create %ci1, %ci1, %ci1 : i1
|
||||
%1 = hw.array_create %ci32, %ci32, %ci32, %ci32 : i32
|
||||
|
||||
|
@ -49,7 +49,7 @@ func @convert_array(%ci1 : i1, %ci32 : i32) {
|
|||
// CHECK: %[[VAL_6:.*]] = llvm.insertvalue %[[VAL_0]], %[[VAL_5]][2 : i32] : !llvm.struct<(i3, i2, i1)>
|
||||
// CHECK: llvm.return
|
||||
// CHECK: }
|
||||
func @convert_tuple(%ci1 : i1, %ci2 : i2, %ci3 : i3) {
|
||||
func.func @convert_tuple(%ci1 : i1, %ci2 : i2, %ci3 : i3) {
|
||||
%0 = hw.struct_create (%ci1, %ci2, %ci3) : !hw.struct<foo: i1, bar: i2, baz: i3>
|
||||
|
||||
return
|
||||
|
|
|
@ -14,14 +14,14 @@ llhd.entity @test1() -> () {
|
|||
|
||||
// CHECK-LABEL: func @FuncArgsAndReturns
|
||||
// CHECK-SAME: (%arg0: i8, %arg1: i32, %arg2: i1) -> i8
|
||||
func @FuncArgsAndReturns(%arg0: !moore.byte, %arg1: !moore.int, %arg2: !moore.bit) -> !moore.byte {
|
||||
func.func @FuncArgsAndReturns(%arg0: !moore.byte, %arg1: !moore.int, %arg2: !moore.bit) -> !moore.byte {
|
||||
// CHECK-NEXT: return %arg0 : i8
|
||||
return %arg0 : !moore.byte
|
||||
}
|
||||
|
||||
// CHECK-LABEL: func @ControlFlow
|
||||
// CHECK-SAME: (%arg0: i32, %arg1: i1)
|
||||
func @ControlFlow(%arg0: !moore.int, %arg1: i1) {
|
||||
func.func @ControlFlow(%arg0: !moore.int, %arg1: i1) {
|
||||
// CHECK-NEXT: cf.br ^bb1(%arg0 : i32)
|
||||
// CHECK-NEXT: ^bb1(%0: i32):
|
||||
// CHECK-NEXT: cf.cond_br %arg1, ^bb1(%0 : i32), ^bb2(%arg0 : i32)
|
||||
|
@ -36,7 +36,7 @@ func @ControlFlow(%arg0: !moore.int, %arg1: i1) {
|
|||
|
||||
// CHECK-LABEL: func @Calls
|
||||
// CHECK-SAME: (%arg0: i8, %arg1: i32, %arg2: i1) -> i8
|
||||
func @Calls(%arg0: !moore.byte, %arg1: !moore.int, %arg2: !moore.bit) -> !moore.byte {
|
||||
func.func @Calls(%arg0: !moore.byte, %arg1: !moore.int, %arg2: !moore.bit) -> !moore.byte {
|
||||
// CHECK-NEXT: %true =
|
||||
// CHECK-NEXT: call @ControlFlow(%arg1, %true) : (i32, i1) -> ()
|
||||
// CHECK-NEXT: [[TMP:%.+]] = call @FuncArgsAndReturns(%arg0, %arg1, %arg2) : (i8, i32, i1) -> i8
|
||||
|
@ -48,7 +48,7 @@ func @Calls(%arg0: !moore.byte, %arg1: !moore.int, %arg2: !moore.bit) -> !moore.
|
|||
}
|
||||
|
||||
// CHECK-LABEL: func @UnrealizedConversionCast
|
||||
func @UnrealizedConversionCast(%arg0: !moore.byte) -> !moore.shortint {
|
||||
func.func @UnrealizedConversionCast(%arg0: !moore.byte) -> !moore.shortint {
|
||||
// CHECK-NEXT: [[TMP:%.+]] = comb.concat %arg0, %arg0 : i8, i8
|
||||
// CHECK-NEXT: return [[TMP]] : i16
|
||||
%0 = builtin.unrealized_conversion_cast %arg0 : !moore.byte to i8
|
||||
|
@ -58,7 +58,7 @@ func @UnrealizedConversionCast(%arg0: !moore.byte) -> !moore.shortint {
|
|||
}
|
||||
|
||||
// CHECK-LABEL: func @Expressions
|
||||
func @Expressions(%arg0: !moore.bit, %arg1: !moore.logic, %arg2: !moore.packed<range<bit, 5:0>>, %arg3: !moore.packed<range<bit<signed>, 4:0>>) {
|
||||
func.func @Expressions(%arg0: !moore.bit, %arg1: !moore.logic, %arg2: !moore.packed<range<bit, 5:0>>, %arg3: !moore.packed<range<bit<signed>, 4:0>>) {
|
||||
// CHECK-NEXT: %0 = comb.concat %arg0, %arg0 : i1, i1
|
||||
// CHECK-NEXT: %1 = comb.concat %arg1, %arg1 : i1, i1
|
||||
%0 = moore.mir.concat %arg0, %arg0 : (!moore.bit, !moore.bit) -> !moore.packed<range<bit, 1:0>>
|
||||
|
|
|
@ -2,7 +2,7 @@
|
|||
|
||||
module {
|
||||
// CHECK: module attributes {calyx.metadata = ["loc({{.*}}11:5)", "loc({{.*}}13:5)"]}
|
||||
func @main(%a0 : i32, %a1 : i32, %a2 : i32) -> i32 {
|
||||
func.func @main(%a0 : i32, %a1 : i32, %a2 : i32) -> i32 {
|
||||
%0 = arith.addi %a0, %a1 : i32
|
||||
%1 = arith.addi %0, %a1 : i32
|
||||
%b = arith.cmpi uge, %1, %a2 : i32
|
||||
|
|
|
@ -47,7 +47,7 @@
|
|||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: }
|
||||
module {
|
||||
func @main(%arg0 : i32, %arg1 : i32) -> i32 {
|
||||
func.func @main(%arg0 : i32, %arg1 : i32) -> i32 {
|
||||
%0 = arith.cmpi slt, %arg0, %arg1 : i32
|
||||
cf.cond_br %0, ^bb1, ^bb2
|
||||
^bb1:
|
||||
|
@ -170,7 +170,7 @@ module {
|
|||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: }
|
||||
module {
|
||||
func @main(%arg0: i32, %arg1: i32, %arg2: i32) -> i32 {
|
||||
func.func @main(%arg0: i32, %arg1: i32, %arg2: i32) -> i32 {
|
||||
%cst = arith.constant 0 : i32
|
||||
%0:3 = scf.while (%arg3 = %arg0, %arg4 = %cst, %arg5 = %cst) : (i32, i32, i32) -> (i32, i32, i32) {
|
||||
%1 = arith.cmpi slt, %arg3, %arg1 : i32
|
||||
|
@ -305,7 +305,7 @@ module {
|
|||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: }
|
||||
module {
|
||||
func @main(%arg0: i32, %arg1: i32, %arg2: i32) -> i32 {
|
||||
func.func @main(%arg0: i32, %arg1: i32, %arg2: i32) -> i32 {
|
||||
%cst = arith.constant 0 : i32
|
||||
%0:3 = scf.while (%arg3 = %arg0, %arg4 = %cst, %arg5 = %cst) : (i32, i32, i32) -> (i32, i32, i32) {
|
||||
%1 = arith.cmpi slt, %arg3, %arg1 : i32
|
||||
|
@ -381,7 +381,7 @@ module {
|
|||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: }
|
||||
module {
|
||||
func @main(%a0 : i32, %a1 : i32, %a2 : i32) -> i32 {
|
||||
func.func @main(%a0 : i32, %a1 : i32, %a2 : i32) -> i32 {
|
||||
%0 = arith.addi %a0, %a1 : i32
|
||||
%1 = arith.addi %0, %a1 : i32
|
||||
%b = arith.cmpi uge, %1, %a2 : i32
|
||||
|
|
|
@ -56,7 +56,7 @@
|
|||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: }
|
||||
module {
|
||||
func @main() {
|
||||
func.func @main() {
|
||||
%c0 = arith.constant 0 : index
|
||||
%c1 = arith.constant 1 : index
|
||||
%c64 = arith.constant 64 : index
|
||||
|
@ -124,7 +124,7 @@ module {
|
|||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: }
|
||||
module {
|
||||
func @main(%arg0 : i32) -> i32 {
|
||||
func.func @main(%arg0 : i32) -> i32 {
|
||||
%0 = memref.alloc() : memref<64xi32>
|
||||
%c0 = arith.constant 0 : index
|
||||
%c1 = arith.constant 1 : i32
|
||||
|
@ -182,7 +182,7 @@ module {
|
|||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: }
|
||||
module {
|
||||
func @main(%arg0 : i32) -> i32 {
|
||||
func.func @main(%arg0 : i32) -> i32 {
|
||||
%0 = memref.alloc() : memref<64xi32>
|
||||
%c0 = arith.constant 0 : index
|
||||
%c1 = arith.constant 1 : i32
|
||||
|
@ -246,7 +246,7 @@ module {
|
|||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: }
|
||||
module {
|
||||
func @main(%arg0 : i6) -> i32 {
|
||||
func.func @main(%arg0 : i6) -> i32 {
|
||||
%0 = memref.alloc() : memref<64xi32>
|
||||
%c1 = arith.constant 1 : index
|
||||
%arg0_idx = arith.index_cast %arg0 : i6 to index
|
||||
|
@ -287,7 +287,7 @@ module {
|
|||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: }
|
||||
module {
|
||||
func @main(%i : index) -> i32 {
|
||||
func.func @main(%i : index) -> i32 {
|
||||
%0 = memref.alloc() : memref<64xi32>
|
||||
%1 = memref.load %0[%i] : memref<64xi32>
|
||||
return %1 : i32
|
||||
|
@ -322,7 +322,7 @@ module {
|
|||
// CHECH-NEXT: }
|
||||
// CHECH-NEXT: }
|
||||
module {
|
||||
func @main(%i : i8) -> index {
|
||||
func.func @main(%i : i8) -> index {
|
||||
%0 = arith.index_cast %i : i8 to index
|
||||
return %0 : index
|
||||
}
|
||||
|
@ -355,7 +355,7 @@ module {
|
|||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: }
|
||||
module {
|
||||
func @main(%arg0 : i32, %mem0 : memref<8xi32>, %i : index) {
|
||||
func.func @main(%arg0 : i32, %mem0 : memref<8xi32>, %i : index) {
|
||||
memref.store %arg0, %mem0[%i] : memref<8xi32>
|
||||
return
|
||||
}
|
||||
|
@ -390,7 +390,7 @@ module {
|
|||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: }
|
||||
module {
|
||||
func @main(%i : index, %mem0 : memref<8xi32>) -> i32 {
|
||||
func.func @main(%i : index, %mem0 : memref<8xi32>) -> i32 {
|
||||
%0 = memref.load %mem0[%i] : memref<8xi32>
|
||||
return %0 : i32
|
||||
}
|
||||
|
@ -447,7 +447,7 @@ module {
|
|||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: }
|
||||
module {
|
||||
func @main(%i0 : index, %i1 : index, %mem0 : memref<8xi32>) -> (i32, i32) {
|
||||
func.func @main(%i0 : index, %i1 : index, %mem0 : memref<8xi32>) -> (i32, i32) {
|
||||
%0 = memref.load %mem0[%i0] : memref<8xi32>
|
||||
%1 = memref.load %mem0[%i1] : memref<8xi32>
|
||||
return %0, %1 : i32, i32
|
||||
|
@ -473,7 +473,7 @@ module {
|
|||
// CHECK-NEXT: calyx.group_done %mem_0.done : i1
|
||||
// CHECK-NEXT: }
|
||||
module {
|
||||
func @main(%i : index) -> i32 {
|
||||
func.func @main(%i : index) -> i32 {
|
||||
%c1_32 = arith.constant 1 : i32
|
||||
%0 = memref.alloc() : memref<1xi32>
|
||||
%1 = memref.load %0[%i] : memref<1xi32>
|
||||
|
@ -488,7 +488,7 @@ module {
|
|||
|
||||
// CHECK: calyx.std_slice {{.*}} i32, i6
|
||||
module {
|
||||
func @main(%mem : memref<33xi32>) -> i32 {
|
||||
func.func @main(%mem : memref<33xi32>) -> i32 {
|
||||
%c0 = arith.constant 0 : index
|
||||
%0 = memref.load %mem[%c0] : memref<33xi32>
|
||||
return %0 : i32
|
||||
|
@ -505,7 +505,7 @@ module {
|
|||
// CHECK-DAG: calyx.assign %mem_0.addr0 = %std_slice_3.out : i1
|
||||
// CHECK-DAG: calyx.assign %mem_0.addr1 = %std_slice_2.out : i1
|
||||
module {
|
||||
func @main() {
|
||||
func.func @main() {
|
||||
%c1_32 = arith.constant 1 : i32
|
||||
%i = arith.constant 0 : index
|
||||
%0 = memref.alloc() : memref<1x1x1x1xi32>
|
||||
|
|
|
@ -34,7 +34,7 @@
|
|||
// CHECK-NEXT: } {bound = 10 : i64}
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: }
|
||||
func @minimal() {
|
||||
func.func @minimal() {
|
||||
%c0_i64 = arith.constant 0 : i64
|
||||
%c10_i64 = arith.constant 10 : i64
|
||||
%c1_i64 = arith.constant 1 : i64
|
||||
|
@ -158,7 +158,7 @@ func @minimal() {
|
|||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: }
|
||||
func @dot(%arg0: memref<64xi32>, %arg1: memref<64xi32>) -> i32 {
|
||||
func.func @dot(%arg0: memref<64xi32>, %arg1: memref<64xi32>) -> i32 {
|
||||
%c0_i32 = arith.constant 0 : i32
|
||||
%c0 = arith.constant 0 : index
|
||||
%c64 = arith.constant 64 : index
|
||||
|
|
|
@ -31,7 +31,7 @@
|
|||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: }
|
||||
module {
|
||||
func @main(%a0 : i32, %a1 : i32) -> i32 {
|
||||
func.func @main(%a0 : i32, %a1 : i32) -> i32 {
|
||||
%0 = arith.addi %a0, %a1 : i32
|
||||
%1 = arith.shli %0, %a0 : i32
|
||||
%2 = arith.subi %1, %0 : i32
|
||||
|
@ -70,7 +70,7 @@ module {
|
|||
// CHECK-NEXT: }
|
||||
// CHECK-NEXT: }
|
||||
module {
|
||||
func @main(%a0 : i32, %a1 : i32) -> (i32, i32) {
|
||||
func.func @main(%a0 : i32, %a1 : i32) -> (i32, i32) {
|
||||
return %a0, %a1 : i32, i32
|
||||
}
|
||||
}
|
||||
|
@ -78,7 +78,7 @@ module {
|
|||
// -----
|
||||
|
||||
module {
|
||||
func @main(%a0 : i32, %a1 : i32) -> i32 {
|
||||
func.func @main(%a0 : i32, %a1 : i32) -> i32 {
|
||||
// CHECK: calyx.group @bb0_0 {
|
||||
// CHECK-DAG: calyx.assign %std_mult_pipe_0.left = %in0 : i32
|
||||
// CHECK-DAG: calyx.assign %std_mult_pipe_0.right = %in1 : i32
|
||||
|
@ -95,7 +95,7 @@ module {
|
|||
// -----
|
||||
|
||||
module {
|
||||
func @main(%a0 : i32, %a1 : i32) -> i32 {
|
||||
func.func @main(%a0 : i32, %a1 : i32) -> i32 {
|
||||
// CHECK: calyx.group @bb0_0 {
|
||||
// CHECK-DAG: calyx.assign %std_div_pipe_0.left = %in0 : i32
|
||||
// CHECK-DAG: calyx.assign %std_div_pipe_0.right = %in1 : i32
|
||||
|
@ -112,7 +112,7 @@ module {
|
|||
// -----
|
||||
|
||||
module {
|
||||
func @main(%a0 : i32, %a1 : i32) -> i32 {
|
||||
func.func @main(%a0 : i32, %a1 : i32) -> i32 {
|
||||
// CHECK: calyx.group @bb0_0 {
|
||||
// CHECK-DAG: calyx.assign %std_div_pipe_0.left = %in0 : i32
|
||||
// CHECK-DAG: calyx.assign %std_div_pipe_0.right = %in1 : i32
|
||||
|
@ -143,7 +143,7 @@ module {
|
|||
// CHECK-DAG: calyx.group_done %0 ? %true : i1
|
||||
// CHECK-NEXT: }
|
||||
module {
|
||||
func @main(%a0 : i32) -> (i32, i32, i32, i32, i32) {
|
||||
func.func @main(%a0 : i32) -> (i32, i32, i32, i32, i32) {
|
||||
return %a0, %a0, %a0, %a0, %a0 : i32, i32, i32, i32, i32
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
// RUN: circt-opt --lower-scf-to-calyx %s -split-input-file -verify-diagnostics
|
||||
|
||||
module {
|
||||
func @f(%arg0 : f32, %arg1 : f32) -> f32 {
|
||||
func.func @f(%arg0 : f32, %arg1 : f32) -> f32 {
|
||||
// expected-error @+1 {{failed to legalize operation 'arith.addf' that was explicitly marked illegal}}
|
||||
%2 = arith.addf %arg0, %arg1 : f32
|
||||
return %2 : f32
|
||||
|
@ -12,17 +12,17 @@ module {
|
|||
|
||||
// expected-error @+1 {{Module contains multiple functions, but no top level function was set. Please see --top-level-function}}
|
||||
module {
|
||||
func @f1() {
|
||||
func.func @f1() {
|
||||
return
|
||||
}
|
||||
func @f2() {
|
||||
func.func @f2() {
|
||||
return
|
||||
}
|
||||
}
|
||||
|
||||
// -----
|
||||
|
||||
func @main() {
|
||||
func.func @main() {
|
||||
cf.br ^bb1
|
||||
^bb1:
|
||||
cf.br ^bb2
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
// RUN: circt-opt -lower-std-to-handshake %s -split-input-file -verify-diagnostics
|
||||
|
||||
func @multidim() -> i32 {
|
||||
func.func @multidim() -> i32 {
|
||||
// expected-error @+1 {{memref's must be both statically sized and unidimensional.}}
|
||||
%0 = memref.alloc() : memref<2x2xi32>
|
||||
%idx = arith.constant 0 : index
|
||||
|
@ -10,7 +10,7 @@ func @multidim() -> i32 {
|
|||
|
||||
// -----
|
||||
|
||||
func @dynsize(%dyn : index) -> i32{
|
||||
func.func @dynsize(%dyn : index) -> i32{
|
||||
// expected-error @+1 {{memref's must be both statically sized and unidimensional.}}
|
||||
%0 = memref.alloc(%dyn) : memref<?xi32>
|
||||
%idx = arith.constant 0 : index
|
||||
|
@ -23,7 +23,7 @@ func @dynsize(%dyn : index) -> i32{
|
|||
// Test non-canonical loops that have multiple entry points (irreducible cfg).
|
||||
|
||||
// expected-error @+1 {{Non-canonical loop structures detected; a potential loop header has backedges not dominated by the loop header. This indicates that the loop has multiple entry points. Handshake lowering does not yet support this form of control flow, exiting.}}
|
||||
func @non_canon_loop(%arg0 : memref<100xi32>, %arg1 : i32) -> i32 {
|
||||
func.func @non_canon_loop(%arg0 : memref<100xi32>, %arg1 : i32) -> i32 {
|
||||
%c0_i32 = arith.constant 0 : i32
|
||||
%c100 = arith.constant 100 : index
|
||||
%c0 = arith.constant 0 : index
|
||||
|
|
|
@ -5,7 +5,7 @@
|
|||
// an exit block.
|
||||
|
||||
// expected-error @+1 {{Multiple exits detected within a loop. Loop task pipelining is only supported for loops with unified loop exit blocks.}}
|
||||
func @main(%cond : i1) -> index {
|
||||
func.func @main(%cond : i1) -> index {
|
||||
%c1 = arith.constant 1 : index
|
||||
%c42 = arith.constant 42 : index
|
||||
%c1_0 = arith.constant 1 : index
|
||||
|
@ -13,10 +13,10 @@ func @main(%cond : i1) -> index {
|
|||
^bb1(%0: index): // 2 preds: ^bb0, ^bb2
|
||||
%1 = arith.cmpi slt, %0, %c42 : index
|
||||
cf.cond_br %1, ^bb2, ^bb3
|
||||
^bb2:
|
||||
^bb2:
|
||||
%2 = arith.addi %0, %c1_0 : index
|
||||
cf.cond_br %cond, ^bb1(%2 : index), ^bb3
|
||||
^bb3:
|
||||
^bb3:
|
||||
return %0 : index
|
||||
}
|
||||
|
||||
|
@ -27,7 +27,7 @@ func @main(%cond : i1) -> index {
|
|||
// exit blocks). Like the above, but the loop header is not an exit point.
|
||||
|
||||
// expected-error @+1 {{Multiple exits detected within a loop. Loop task pipelining is only supported for loops with unified loop exit blocks.}}
|
||||
func @main(%cond : i1) -> index {
|
||||
func.func @main(%cond : i1) -> index {
|
||||
%c1 = arith.constant 1 : index
|
||||
%c42 = arith.constant 42 : index
|
||||
%c1_0 = arith.constant 1 : index
|
||||
|
@ -35,13 +35,13 @@ func @main(%cond : i1) -> index {
|
|||
^bb1(%0: index):
|
||||
%1 = arith.cmpi slt, %0, %c42 : index
|
||||
cf.br ^bb2
|
||||
^bb2:
|
||||
^bb2:
|
||||
%2 = arith.addi %0, %c1_0 : index
|
||||
cf.cond_br %cond, ^bb3, ^bb4
|
||||
^bb3:
|
||||
%3 = arith.addi %0, %c1_0 : index
|
||||
cf.cond_br %cond, ^bb1(%2 : index), ^bb4
|
||||
^bb4:
|
||||
^bb4:
|
||||
return %0 : index
|
||||
}
|
||||
|
||||
|
@ -51,7 +51,7 @@ func @main(%cond : i1) -> index {
|
|||
// A loop with a single exit point but with multiple loop latches.
|
||||
|
||||
// expected-error @+1 {{Multiple loop latches detected (backedges from within the loop to the loop header). Loop task pipelining is only supported for loops with unified loop latches.}}
|
||||
func @main(%cond : i1) -> index {
|
||||
func.func @main(%cond : i1) -> index {
|
||||
%c1 = arith.constant 1 : index
|
||||
%c42 = arith.constant 42 : index
|
||||
%c1_0 = arith.constant 1 : index
|
||||
|
@ -59,12 +59,12 @@ func @main(%cond : i1) -> index {
|
|||
^bb1(%0: index):
|
||||
%1 = arith.cmpi slt, %0, %c42 : index
|
||||
cf.br ^bb2
|
||||
^bb2:
|
||||
^bb2:
|
||||
%2 = arith.addi %0, %c1_0 : index
|
||||
cf.cond_br %cond, ^bb1(%2 : index), ^bb3
|
||||
^bb3:
|
||||
%3 = arith.addi %0, %c1_0 : index
|
||||
cf.cond_br %cond, ^bb1(%2 : index), ^bb4
|
||||
^bb4:
|
||||
^bb4:
|
||||
return %0 : index
|
||||
}
|
||||
|
|
|
@ -8,7 +8,7 @@
|
|||
// CHECK: %[[VAL_7:.*]] = select %[[VAL_4]], %[[VAL_6]], %[[VAL_5]] : i32
|
||||
// CHECK: return %[[VAL_7]], %[[VAL_3]] : i32, none
|
||||
// CHECK: }
|
||||
func @main(%c : i1, %a : i32, %b : i32) -> i32 {
|
||||
func.func @main(%c : i1, %a : i32, %b : i32) -> i32 {
|
||||
%0 = arith.select %c, %a, %b : i32
|
||||
return %0 : i32
|
||||
}
|
||||
|
@ -19,5 +19,5 @@ func @main(%c : i1, %a : i32, %b : i32) -> i32 {
|
|||
|
||||
// CHECK-LABEL: handshake.func private @foo(i32, i32, none, ...) -> (i32, none)
|
||||
module {
|
||||
func private @foo(%a:i32, %b: i32) -> i32
|
||||
func.func private @foo(%a:i32, %b: i32) -> i32
|
||||
}
|
||||
|
|
|
@ -44,7 +44,7 @@
|
|||
// CHECK: sink %[[VAL_42]] : index
|
||||
// CHECK: return %[[VAL_41]] : none
|
||||
// CHECK: }
|
||||
func @simple_loop() {
|
||||
func.func @simple_loop() {
|
||||
^bb0:
|
||||
cf.br ^bb1
|
||||
^bb1: // pred: ^bb0
|
||||
|
|
|
@ -110,7 +110,7 @@
|
|||
// CHECK: sink %[[VAL_107]] : index
|
||||
// CHECK: return %[[VAL_106]] : none
|
||||
// CHECK: }
|
||||
func @affine_dma_start(%arg0: index) {
|
||||
func.func @affine_dma_start(%arg0: index) {
|
||||
%0 = memref.alloc() : memref<100xf32>
|
||||
%1 = memref.alloc() : memref<100xf32, 2>
|
||||
%2 = memref.alloc() : memref<1xi32>
|
||||
|
|
|
@ -103,7 +103,7 @@
|
|||
// CHECK: sink %[[VAL_106]] : index
|
||||
// CHECK: return %[[VAL_105]] : none
|
||||
// CHECK: }
|
||||
func @imperfectly_nested_loops() {
|
||||
func.func @imperfectly_nested_loops() {
|
||||
%c0 = arith.constant 0 : index
|
||||
%c42 = arith.constant 42 : index
|
||||
%c1 = arith.constant 1 : index
|
||||
|
|
|
@ -158,7 +158,7 @@
|
|||
// CHECK: sink %[[VAL_166]] : index
|
||||
// CHECK: return %[[VAL_165]] : none
|
||||
// CHECK: }
|
||||
func @more_imperfectly_nested_loops() {
|
||||
func.func @more_imperfectly_nested_loops() {
|
||||
%c0 = arith.constant 0 : index
|
||||
%c42 = arith.constant 42 : index
|
||||
%c1 = arith.constant 1 : index
|
||||
|
|
|
@ -104,7 +104,7 @@
|
|||
// CHECK: sink %[[VAL_107]] : index
|
||||
// CHECK: return %[[VAL_106]] : none
|
||||
// CHECK: }
|
||||
func @affine_apply_loops_shorthand(%arg0: index) {
|
||||
func.func @affine_apply_loops_shorthand(%arg0: index) {
|
||||
%c0 = arith.constant 0 : index
|
||||
%c1 = arith.constant 1 : index
|
||||
cf.br ^bb1(%c0 : index)
|
||||
|
|
|
@ -78,7 +78,7 @@
|
|||
// CHECK: sink %[[VAL_77]] : index
|
||||
// CHECK: return %[[VAL_76]] : none
|
||||
// CHECK: }
|
||||
func @affine_store(%arg0: index) {
|
||||
func.func @affine_store(%arg0: index) {
|
||||
%0 = memref.alloc() : memref<10xf32>
|
||||
%cst = arith.constant 1.100000e+01 : f32
|
||||
%c0 = arith.constant 0 : index
|
||||
|
|
|
@ -68,7 +68,7 @@
|
|||
// CHECK: sink %[[VAL_66]] : index
|
||||
// CHECK: return %[[VAL_65]] : none
|
||||
// CHECK: }
|
||||
func @affine_load(%arg0: index) {
|
||||
func.func @affine_load(%arg0: index) {
|
||||
%0 = memref.alloc() : memref<10xf32>
|
||||
%c0 = arith.constant 0 : index
|
||||
%c10 = arith.constant 10 : index
|
||||
|
|
|
@ -23,7 +23,7 @@
|
|||
// CHECK: %[[VAL_19:.*]] = select %[[VAL_11]]#0, %[[VAL_18]], %[[VAL_17]] : index
|
||||
// CHECK: return %[[VAL_19]], %[[VAL_4]]#3 : index, none
|
||||
// CHECK: }
|
||||
func @affine_apply_ceildiv(%arg0: index) -> index {
|
||||
func.func @affine_apply_ceildiv(%arg0: index) -> index {
|
||||
%c42 = arith.constant 42 : index
|
||||
%c0 = arith.constant 0 : index
|
||||
%c1 = arith.constant 1 : index
|
||||
|
|
|
@ -20,7 +20,7 @@
|
|||
// CHECK: %[[VAL_16:.*]] = select %[[VAL_10]]#0, %[[VAL_14]]#0, %[[VAL_15]] : index
|
||||
// CHECK: return %[[VAL_16]], %[[VAL_4]]#3 : index, none
|
||||
// CHECK: }
|
||||
func @affine_apply_floordiv(%arg0: index) -> index {
|
||||
func.func @affine_apply_floordiv(%arg0: index) -> index {
|
||||
%c42 = arith.constant 42 : index
|
||||
%c0 = arith.constant 0 : index
|
||||
%c-1 = arith.constant -1 : index
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
// CHECK: %[[VAL_11:.*]] = select %[[VAL_9]], %[[VAL_7]]#0, %[[VAL_10]] : index
|
||||
// CHECK: return %[[VAL_11]], %[[VAL_3]]#2 : index, none
|
||||
// CHECK: }
|
||||
func @affine_apply_mod(%arg0: index) -> index {
|
||||
func.func @affine_apply_mod(%arg0: index) -> index {
|
||||
%c42 = arith.constant 42 : index
|
||||
%0 = arith.remsi %arg0, %c42 : index
|
||||
%c0 = arith.constant 0 : index
|
||||
|
|
|
@ -41,7 +41,7 @@
|
|||
// CHECK: sink %[[VAL_33]] : index
|
||||
// CHECK: return %[[VAL_1]]#17 : none
|
||||
// CHECK: }
|
||||
func @affine_applies() {
|
||||
func.func @affine_applies() {
|
||||
%c0 = arith.constant 0 : index
|
||||
%c101 = arith.constant 101 : index
|
||||
%c102 = arith.constant 102 : index
|
||||
|
|
|
@ -94,7 +94,7 @@
|
|||
// CHECK: sink %[[VAL_96]] : index
|
||||
// CHECK: return %[[VAL_95]] : none
|
||||
// CHECK: }
|
||||
func @imperfectly_nested_loops() {
|
||||
func.func @imperfectly_nested_loops() {
|
||||
^bb0:
|
||||
cf.br ^bb1
|
||||
^bb1: // pred: ^bb0
|
||||
|
|
|
@ -67,7 +67,7 @@
|
|||
// CHECK: sink %[[VAL_65]] : index
|
||||
// CHECK: return %[[VAL_64]] : none
|
||||
// CHECK: }
|
||||
func @min_reduction_tree(%arg0: index) {
|
||||
func.func @min_reduction_tree(%arg0: index) {
|
||||
%c0 = arith.constant 0 : index
|
||||
%0 = arith.cmpi slt, %arg0, %arg0 : index
|
||||
%1 = arith.select %0, %arg0, %arg0 : index
|
||||
|
|
|
@ -129,7 +129,7 @@
|
|||
// CHECK: sink %[[VAL_133]] : index
|
||||
// CHECK: return %[[VAL_132]] : none
|
||||
// CHECK: }
|
||||
func @loop_min_max(%arg0: index) {
|
||||
func.func @loop_min_max(%arg0: index) {
|
||||
%c0 = arith.constant 0 : index
|
||||
%c42 = arith.constant 42 : index
|
||||
%c1 = arith.constant 1 : index
|
||||
|
|
|
@ -204,7 +204,7 @@
|
|||
// CHECK: sink %[[VAL_220]] : index
|
||||
// CHECK: return %[[VAL_219]] : none
|
||||
// CHECK: }
|
||||
func @if_for() {
|
||||
func.func @if_for() {
|
||||
%c0 = arith.constant 0 : index
|
||||
%c-1 = arith.constant -1 : index
|
||||
%1 = arith.muli %c-1, %c-1 : index
|
||||
|
|
|
@ -43,7 +43,7 @@
|
|||
// CHECK: sink %[[VAL_44]] : index
|
||||
// CHECK: return %[[VAL_43]] : none
|
||||
// CHECK: }
|
||||
func @multi_cond(%arg0: index, %arg1: index, %arg2: index, %arg3: index) {
|
||||
func.func @multi_cond(%arg0: index, %arg1: index, %arg2: index, %arg3: index) {
|
||||
%c0 = arith.constant 0 : index
|
||||
%c-1 = arith.constant -1 : index
|
||||
%1 = arith.muli %c0, %c-1 : index
|
||||
|
|
|
@ -48,7 +48,7 @@
|
|||
// CHECK: sink %[[VAL_48]] : index
|
||||
// CHECK: return %[[VAL_47]] : none
|
||||
// CHECK: }
|
||||
func @nested_ifs() {
|
||||
func.func @nested_ifs() {
|
||||
%c0 = arith.constant 0 : index
|
||||
%c-1 = arith.constant -1 : index
|
||||
%1 = arith.muli %c0, %c-1 : index
|
||||
|
|
|
@ -21,7 +21,7 @@
|
|||
// CHECK: sink %[[VAL_18]] : index
|
||||
// CHECK: return %[[VAL_17]] : none
|
||||
// CHECK: }
|
||||
func @if_else() {
|
||||
func.func @if_else() {
|
||||
%c0 = arith.constant 0 : index
|
||||
%c-1 = arith.constant -1 : index
|
||||
%1 = arith.muli %c0, %c-1 : index
|
||||
|
|
|
@ -18,7 +18,7 @@
|
|||
// CHECK: sink %[[VAL_15]] : index
|
||||
// CHECK: return %[[VAL_14]] : none
|
||||
// CHECK: }
|
||||
func @if_only() {
|
||||
func.func @if_only() {
|
||||
%c0 = arith.constant 0 : index
|
||||
%c-1 = arith.constant -1 : index
|
||||
%1 = arith.muli %c0, %c-1 : index
|
||||
|
|
|
@ -44,7 +44,7 @@
|
|||
// CHECK: sink %[[VAL_42]] : index
|
||||
// CHECK: return %[[VAL_41]] : none
|
||||
// CHECK: }
|
||||
func @simple_loop() {
|
||||
func.func @simple_loop() {
|
||||
^bb0:
|
||||
cf.br ^bb1
|
||||
^bb1: // pred: ^bb0
|
||||
|
|
|
@ -74,7 +74,7 @@
|
|||
// CHECK: sink %[[VAL_75]] : index
|
||||
// CHECK: return %[[VAL_74]] : none
|
||||
// CHECK: }
|
||||
func @affine_load(%arg0: index) {
|
||||
func.func @affine_load(%arg0: index) {
|
||||
%0 = memref.alloc() : memref<10xf32>
|
||||
%10 = memref.alloc() : memref<10xf32>
|
||||
%c0 = arith.constant 0 : index
|
||||
|
|
|
@ -19,7 +19,7 @@
|
|||
// CHECK: sink %[[VAL_15]] : i32
|
||||
// CHECK: return %[[VAL_12]] : none
|
||||
// CHECK: }
|
||||
func @load_store(%0 : memref<4xi32>, %1 : index) {
|
||||
func.func @load_store(%0 : memref<4xi32>, %1 : index) {
|
||||
%c1 = arith.constant 11 : i32
|
||||
memref.store %c1, %0[%1] : memref<4xi32>
|
||||
%3 = memref.load %0[%1] : memref<4xi32>
|
||||
|
|
|
@ -144,7 +144,7 @@
|
|||
// CHECK: sink %[[VAL_150]] : index
|
||||
// CHECK: return %[[VAL_149]] : none
|
||||
// CHECK: }
|
||||
func @more_imperfectly_nested_loops() {
|
||||
func.func @more_imperfectly_nested_loops() {
|
||||
^bb0:
|
||||
cf.br ^bb1
|
||||
^bb1: // pred: ^bb0
|
||||
|
|
|
@ -88,7 +88,7 @@
|
|||
// CHECK: sink %[[VAL_89]] : index
|
||||
// CHECK: return %[[VAL_88]] : none
|
||||
// CHECK: }
|
||||
func @affine_load(%arg0: index) {
|
||||
func.func @affine_load(%arg0: index) {
|
||||
%0 = memref.alloc() : memref<10xf32>
|
||||
%c0 = arith.constant 0 : index
|
||||
%c10 = arith.constant 10 : index
|
||||
|
|
|
@ -88,7 +88,7 @@
|
|||
// CHECK: sink %[[VAL_89]] : index
|
||||
// CHECK: return %[[VAL_88]] : none
|
||||
// CHECK: }
|
||||
func @affine_load(%arg0: index) {
|
||||
func.func @affine_load(%arg0: index) {
|
||||
%0 = memref.alloc() : memref<10xf32>
|
||||
%10 = memref.alloc() : memref<10xf32>
|
||||
%c0 = arith.constant 0 : index
|
||||
|
|
|
@ -62,7 +62,7 @@
|
|||
// CHECK: sink %[[VAL_63]] : index
|
||||
// CHECK: return %[[VAL_62]] : none
|
||||
// CHECK: }
|
||||
func @test() {
|
||||
func.func @test() {
|
||||
%10 = memref.alloc() : memref<10xf32>
|
||||
%c0 = arith.constant 0 : index
|
||||
%c10 = arith.constant 10 : index
|
||||
|
|
|
@ -53,7 +53,7 @@
|
|||
// CHECK: sink %[[VAL_54]] : index
|
||||
// CHECK: return %[[VAL_53]] : none
|
||||
// CHECK: }
|
||||
func @test() {
|
||||
func.func @test() {
|
||||
%10 = memref.alloc() : memref<10xf32>
|
||||
%c0 = arith.constant 0 : index
|
||||
%c10 = arith.constant 10 : index
|
||||
|
|
|
@ -56,7 +56,7 @@
|
|||
// CHECK: sink %[[VAL_56]] : index
|
||||
// CHECK: return %[[VAL_55]] : none
|
||||
// CHECK: }
|
||||
func @test() {
|
||||
func.func @test() {
|
||||
%10 = memref.alloc() : memref<10xf32>
|
||||
%c0 = arith.constant 0 : index
|
||||
%c10 = arith.constant 10 : index
|
||||
|
|
|
@ -63,7 +63,7 @@
|
|||
// CHECK: sink %[[VAL_65]] : index
|
||||
// CHECK: return %[[VAL_64]] : none
|
||||
// CHECK: }
|
||||
func @test() {
|
||||
func.func @test() {
|
||||
%10 = memref.alloc() : memref<10xf32>
|
||||
%11 = memref.alloca() : memref<10xf32>
|
||||
%c0 = arith.constant 0 : index
|
||||
|
|
|
@ -34,7 +34,7 @@
|
|||
// CHECK: sink %[[VAL_25]] : i32
|
||||
// CHECK: return %[[VAL_13]], %[[VAL_16]], %[[VAL_4]] : f32, i32, none
|
||||
// CHECK: }
|
||||
func @ops(f32, f32, i32, i32) -> (f32, i32) {
|
||||
func.func @ops(f32, f32, i32, i32) -> (f32, i32) {
|
||||
^bb0(%arg0: f32, %arg1: f32, %arg2: i32, %arg3: i32):
|
||||
%0 = arith.subf %arg0, %arg1: f32
|
||||
%1 = arith.subi %arg2, %arg3: i32
|
||||
|
|
|
@ -21,7 +21,7 @@
|
|||
// CHECK: %[[VAL_8]] = br %[[VAL_17]] : i32
|
||||
// CHECK: return %[[VAL_12]], %[[VAL_9]] : i32, none
|
||||
// CHECK: }
|
||||
func @dfs_block_order() -> (i32) {
|
||||
func.func @dfs_block_order() -> (i32) {
|
||||
%0 = arith.constant 42 : i32
|
||||
cf.br ^bb2
|
||||
^bb1:
|
||||
|
|
|
@ -36,7 +36,7 @@
|
|||
// CHECK: sink %[[VAL_27]] : i32
|
||||
// CHECK: return %[[VAL_13]]#0, %[[VAL_18]]#0, %[[VAL_4]] : f32, i32, none
|
||||
// CHECK: }
|
||||
func @ops(f32, f32, i32, i32) -> (f32, i32) {
|
||||
func.func @ops(f32, f32, i32, i32) -> (f32, i32) {
|
||||
^bb0(%arg0: f32, %arg1: f32, %arg2: i32, %arg3: i32):
|
||||
%0 = arith.subf %arg0, %arg1: f32
|
||||
%1 = arith.subi %arg2, %arg3: i32
|
||||
|
|
|
@ -36,7 +36,7 @@
|
|||
// CHECK: sink %[[VAL_34]] : index
|
||||
// CHECK: return %[[VAL_33]] : none
|
||||
// CHECK: }
|
||||
func @simple_loop() {
|
||||
func.func @simple_loop() {
|
||||
^bb0:
|
||||
cf.br ^bb1
|
||||
^bb1: // pred: ^bb0
|
||||
|
|
|
@ -36,7 +36,7 @@
|
|||
// CHECK: sink %[[VAL_32]] : index
|
||||
// CHECK: return %[[VAL_31]] : none
|
||||
// CHECK: }
|
||||
func @simple_loop() {
|
||||
func.func @simple_loop() {
|
||||
^bb0:
|
||||
cf.br ^bb1
|
||||
^bb1: // pred: ^bb0
|
||||
|
|
|
@ -82,7 +82,7 @@
|
|||
// CHECK: sink %[[VAL_79]] : index
|
||||
// CHECK: return %[[VAL_78]] : none
|
||||
// CHECK: }
|
||||
func @affine_dma_wait(%arg0: index) {
|
||||
func.func @affine_dma_wait(%arg0: index) {
|
||||
%0 = memref.alloc() : memref<1xi32>
|
||||
%c64 = arith.constant 64 : index
|
||||
%c0 = arith.constant 0 : index
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
// CHECK: %[[VAL_2:.*]] = merge %[[VAL_0]] : i32
|
||||
// CHECK: return %[[VAL_2]], %[[VAL_1]] : i32, none
|
||||
// CHECK: }
|
||||
func @bar(%0 : i32) -> i32 {
|
||||
func.func @bar(%0 : i32) -> i32 {
|
||||
return %0 : i32
|
||||
}
|
||||
|
||||
|
@ -19,7 +19,7 @@ func @bar(%0 : i32) -> i32 {
|
|||
// CHECK: sink %[[VAL_4]]#1 : none
|
||||
// CHECK: return %[[VAL_4]]#0, %[[VAL_3]]#1 : i32, none
|
||||
// CHECK: }
|
||||
func @foo(%0 : i32) -> i32 {
|
||||
func.func @foo(%0 : i32) -> i32 {
|
||||
%a1 = call @bar(%0) : (i32) -> i32
|
||||
return %a1 : i32
|
||||
}
|
||||
|
@ -29,13 +29,13 @@ func @foo(%0 : i32) -> i32 {
|
|||
// Branching control flow with calls in each branch.
|
||||
|
||||
// CHECK-LABEL: handshake.func @add(
|
||||
func @add(%arg0 : i32, %arg1: i32) -> i32 {
|
||||
func.func @add(%arg0 : i32, %arg1: i32) -> i32 {
|
||||
%0 = arith.addi %arg0, %arg1 : i32
|
||||
return %0 : i32
|
||||
}
|
||||
|
||||
// CHECK-LABEL: handshake.func @sub(
|
||||
func @sub(%arg0 : i32, %arg1: i32) -> i32 {
|
||||
func.func @sub(%arg0 : i32, %arg1: i32) -> i32 {
|
||||
%0 = arith.subi %arg0, %arg1 : i32
|
||||
return %0 : i32
|
||||
}
|
||||
|
@ -70,7 +70,7 @@ func @sub(%arg0 : i32, %arg1: i32) -> i32 {
|
|||
// CHECK: %[[VAL_32:.*]] = mux %[[VAL_31]] {{\[}}%[[VAL_29]], %[[VAL_21]]] : index, i32
|
||||
// CHECK: return %[[VAL_32]], %[[VAL_30]] : i32, none
|
||||
// CHECK: }
|
||||
func @main(%arg0 : i32, %arg1 : i32, %cond : i1) -> i32 {
|
||||
func.func @main(%arg0 : i32, %arg1 : i32, %cond : i1) -> i32 {
|
||||
cf.cond_br %cond, ^bb1, ^bb2
|
||||
^bb1:
|
||||
%0 = call @add(%arg0, %arg1) : (i32, i32) -> i32
|
||||
|
|
|
@ -39,7 +39,7 @@
|
|||
// CHECK: sink %[[VAL_36]] : index
|
||||
// CHECK: return %[[VAL_35]] : none
|
||||
// CHECK: }
|
||||
func @simple_loop() {
|
||||
func.func @simple_loop() {
|
||||
^bb0:
|
||||
cf.br ^bb1
|
||||
^bb1: // pred: ^bb0
|
||||
|
|
|
@ -11,7 +11,7 @@
|
|||
// CHECK: %[[VAL_8:.*]], %[[VAL_3]] = load {{\[}}%[[VAL_7]]] %[[VAL_2]]#0, %[[VAL_4]]#0 : index, i32
|
||||
// CHECK: return %[[VAL_8]], %[[VAL_6]] : i32, none
|
||||
// CHECK: }
|
||||
func @main(%mem : memref<4xi32>) -> i32 {
|
||||
func.func @main(%mem : memref<4xi32>) -> i32 {
|
||||
%idx = arith.constant 0 : index
|
||||
%0 = memref.load %mem[%idx] : memref<4xi32>
|
||||
return %0 : i32
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
// RUN: circt-opt -lower-std-to-handshake %s | FileCheck %s
|
||||
|
||||
// CHECK-LABEL: handshake.func @main(%arg0: i32, %arg1: i32, %arg2: i32, %arg3: none, ...) -> (i32, none) attributes {argNames = ["a", "b", "c", "inCtrl"], resNames = ["res", "outCtrl"]} {
|
||||
func @main(%arg0 : i32, %b : i32, %c: i32) -> i32 attributes {argNames = ["a", "b", "c"], resNames = ["res"]} {
|
||||
func.func @main(%arg0 : i32, %b : i32, %c: i32) -> i32 attributes {argNames = ["a", "b", "c"], resNames = ["res"]} {
|
||||
return %arg0 : i32
|
||||
}
|
||||
|
|
|
@ -9,7 +9,7 @@
|
|||
// CHECK: return %[[VAL_4]], %[[VAL_1]] : i32, none
|
||||
// CHECK: }
|
||||
|
||||
func @foo(%arg0 : i32) -> i32 {
|
||||
func.func @foo(%arg0 : i32) -> i32 {
|
||||
%c1_i32 = arith.constant 1 : i32
|
||||
%0 = arith.addi %arg0, %c1_i32 : i32
|
||||
return %0 : i32
|
||||
|
|
|
@ -30,7 +30,7 @@
|
|||
// CHECK: }
|
||||
// CHECK: }
|
||||
|
||||
func @simple_loop() {
|
||||
func.func @simple_loop() {
|
||||
^bb0:
|
||||
cf.br ^bb1
|
||||
^bb1: // pred: ^bb0
|
||||
|
|
|
@ -47,8 +47,8 @@ hw.module @test(%clk: i1, %rstn: i1) {
|
|||
// CHECK-NEXT: hw.instance "nullRcvr" @Reciever(a: [[NULLI1]]: !esi.channel<i1>) -> ()
|
||||
}
|
||||
|
||||
hw.module.extern @IFaceSender(!sv.modport<@IData::@Source>) -> ()
|
||||
hw.module.extern @IFaceRcvr(!sv.modport<@IData::@Sink>) -> ()
|
||||
hw.module.extern @IFaceSender(%x: !sv.modport<@IData::@Source>) -> ()
|
||||
hw.module.extern @IFaceRcvr(%x: !sv.modport<@IData::@Sink>) -> ()
|
||||
sv.interface @IData {
|
||||
sv.interface.signal @data : i32
|
||||
sv.interface.signal @valid : i1
|
||||
|
@ -59,26 +59,26 @@ sv.interface @IData {
|
|||
hw.module @testIfaceWrap() {
|
||||
%ifaceOut = sv.interface.instance : !sv.interface<@IData>
|
||||
%ifaceOutSource = sv.modport.get %ifaceOut @Source : !sv.interface<@IData> -> !sv.modport<@IData::@Source>
|
||||
hw.instance "ifaceSender" @IFaceSender ("": %ifaceOutSource: !sv.modport<@IData::@Source>) -> ()
|
||||
hw.instance "ifaceSender" @IFaceSender (x: %ifaceOutSource: !sv.modport<@IData::@Source>) -> ()
|
||||
%ifaceOutSink = sv.modport.get %ifaceOut @Sink: !sv.interface<@IData> -> !sv.modport<@IData::@Sink>
|
||||
%idataChanOut = esi.wrap.iface %ifaceOutSink: !sv.modport<@IData::@Sink> -> !esi.channel<i32>
|
||||
|
||||
// CHECK-LABEL: hw.module @testIfaceWrap() {
|
||||
// CHECK-NEXT: %0 = sv.interface.instance {name = "ifaceOut"} : !sv.interface<@IData>
|
||||
// CHECK-NEXT: %1 = sv.modport.get %0 @Source : !sv.interface<@IData> -> !sv.modport<@IData::@Source>
|
||||
// CHECK-NEXT: hw.instance "ifaceSender" @IFaceSender("": %1: !sv.modport<@IData::@Source>) -> ()
|
||||
// CHECK-NEXT: hw.instance "ifaceSender" @IFaceSender(x: %1: !sv.modport<@IData::@Source>) -> ()
|
||||
// CHECK-NEXT: %2 = sv.modport.get %0 @Sink : !sv.interface<@IData> -> !sv.modport<@IData::@Sink>
|
||||
// CHECK-NEXT: %3 = esi.wrap.iface %2 : !sv.modport<@IData::@Sink> -> !esi.channel<i32>
|
||||
|
||||
%ifaceIn = sv.interface.instance : !sv.interface<@IData>
|
||||
%ifaceInSink = sv.modport.get %ifaceIn @Sink : !sv.interface<@IData> -> !sv.modport<@IData::@Sink>
|
||||
hw.instance "ifaceRcvr" @IFaceRcvr ("": %ifaceInSink: !sv.modport<@IData::@Sink>) -> ()
|
||||
hw.instance "ifaceRcvr" @IFaceRcvr (x: %ifaceInSink: !sv.modport<@IData::@Sink>) -> ()
|
||||
%ifaceInSource = sv.modport.get %ifaceIn @Sink : !sv.interface<@IData> -> !sv.modport<@IData::@Source>
|
||||
esi.unwrap.iface %idataChanOut into %ifaceInSource : (!esi.channel<i32>, !sv.modport<@IData::@Source>)
|
||||
|
||||
// CHECK-NEXT: %4 = sv.interface.instance {name = "ifaceIn"} : !sv.interface<@IData>
|
||||
// CHECK-NEXT: %5 = sv.modport.get %4 @Sink : !sv.interface<@IData> -> !sv.modport<@IData::@Sink>
|
||||
// CHECK-NEXT: hw.instance "ifaceRcvr" @IFaceRcvr("": %5: !sv.modport<@IData::@Sink>) -> ()
|
||||
// CHECK-NEXT: hw.instance "ifaceRcvr" @IFaceRcvr(x: %5: !sv.modport<@IData::@Sink>) -> ()
|
||||
// CHECK-NEXT: %6 = sv.modport.get %4 @Sink : !sv.interface<@IData> -> !sv.modport<@IData::@Source>
|
||||
// CHECK-NEXT: esi.unwrap.iface %3 into %6 : (!esi.channel<i32>, !sv.modport<@IData::@Source>)
|
||||
}
|
||||
|
|
|
@ -96,7 +96,7 @@ hw.module @bar(%clk: i1, %rst_n: i1) {
|
|||
}
|
||||
|
||||
// Software-style instantiation and triggering.
|
||||
func @qux() {
|
||||
func.func @qux() {
|
||||
%foo_inst = fsm.instance "foo_inst" @foo
|
||||
%in0 = arith.constant true
|
||||
%out0 = fsm.trigger %foo_inst(%in0) : (i1) -> i1
|
||||
|
|
|
@ -535,7 +535,7 @@ hw.module @concat_fold_3(%arg0: i1) -> (result: i8) {
|
|||
|
||||
// CHECK-LABEL: hw.module @concat_fold_4
|
||||
hw.module @concat_fold_4(%arg0: i3) -> (result: i5) {
|
||||
// CHECK-NEXT: %0 = comb.extract %arg0 from 2 : (i3) -> i1
|
||||
// CHECK-NEXT: %0 = comb.extract %arg0 from 2 : (i3) -> i1
|
||||
%0 = comb.extract %arg0 from 2 : (i3) -> (i1)
|
||||
// CHECK-NEXT: %1 = comb.replicate %0 : (i1) -> i2
|
||||
%1 = comb.concat %0, %0, %arg0 : i1, i1, i3
|
||||
|
@ -578,7 +578,7 @@ hw.module @concat_fold7(%arg0: i5) -> (result: i20) {
|
|||
hw.module @concat_fold8(%arg0: i5, %arg1: i3) -> (r0: i28, r1: i28, r2: i13) {
|
||||
%0 = comb.replicate %arg0 : (i5) -> i20
|
||||
|
||||
// CHECK-NEXT: %0 = comb.replicate %arg0 : (i5) -> i25
|
||||
// CHECK-NEXT: %0 = comb.replicate %arg0 : (i5) -> i25
|
||||
// CHECK-NEXT: %1 = comb.concat %arg1, %0 : i3, i25
|
||||
%1 = comb.concat %arg1, %arg0, %0 : i3, i5, i20
|
||||
|
||||
|
@ -840,7 +840,7 @@ hw.module @shru_shift_to_extract_and_concat0(%arg0: i12) -> (result: i12) {
|
|||
|
||||
// CHECK-LABEL: hw.module @shru_shift_to_extract_and_concat1(%arg0: i12) -> (result: i12) {
|
||||
// CHECK-NEXT: %0 = comb.extract %arg0 from 11 : (i12) -> i1
|
||||
// CHECK-NEXT: %1 = comb.replicate %0 : (i1) -> i2
|
||||
// CHECK-NEXT: %1 = comb.replicate %0 : (i1) -> i2
|
||||
// CHECK-NEXT: %2 = comb.extract %arg0 from 2 : (i12) -> i10
|
||||
// CHECK-NEXT: %3 = comb.concat %1, %2 : i2, i10
|
||||
// CHECK-NEXT: hw.output %3
|
||||
|
@ -1036,8 +1036,8 @@ hw.module @wire5() -> () {
|
|||
hw.module @replicate(%arg0: i7) -> (r1: i9, r2: i7) {
|
||||
%c2 = hw.constant 2 : i3
|
||||
%r1 = comb.replicate %c2 : (i3) -> i9
|
||||
|
||||
// CHECK-NEXT: %c146_i9 = hw.constant 146 : i9
|
||||
|
||||
// CHECK-NEXT: %c146_i9 = hw.constant 146 : i9
|
||||
%r2 = comb.replicate %arg0 : (i7) -> i7
|
||||
|
||||
// CHECK-NEXT: hw.output %c146_i9, %arg0
|
||||
|
@ -1287,10 +1287,10 @@ hw.module @foo() {
|
|||
}
|
||||
|
||||
// CHECK-LABEL: hw.module @MemDepth1(%clock: i1, %en: i1, %addr: i1) -> (data: i32) {
|
||||
// CHECK-NEXT: %mem0.0 = hw.instance "mem0" @FIRRTLMem_1_0_0_32_1_0_1_1("": %clock: i1, "": %en: i1, "": %addr: i1) -> ("": i32)
|
||||
// CHECK-NEXT: %mem0.0 = hw.instance "mem0" @FIRRTLMem_1_0_0_32_1_0_1_1(x: %clock: i1, y: %en: i1, z: %addr: i1) -> ("": i32)
|
||||
// CHECK-NEXT: hw.output %mem0.0 : i32
|
||||
// CHECK-NEXT: }
|
||||
hw.module.extern @FIRRTLMem_1_0_0_32_1_0_1_1(i1, i1, i1) -> ("": i32)
|
||||
hw.module.extern @FIRRTLMem_1_0_0_32_1_0_1_1(%x: i1, %y: i1, %z: i1) -> ("": i32)
|
||||
hw.module @MemDepth1(%clock: i1, %en: i1, %addr: i1) -> (data: i32) {
|
||||
%.load0.clk.wire = sv.wire : !hw.inout<i1>
|
||||
%0 = sv.read_inout %.load0.clk.wire : !hw.inout<i1>
|
||||
|
@ -1298,7 +1298,7 @@ hw.module @MemDepth1(%clock: i1, %en: i1, %addr: i1) -> (data: i32) {
|
|||
%1 = sv.read_inout %.load0.en.wire : !hw.inout<i1>
|
||||
%.load0.addr.wire = sv.wire : !hw.inout<i1>
|
||||
%2 = sv.read_inout %.load0.addr.wire : !hw.inout<i1>
|
||||
%mem0.ro_data_0 = hw.instance "mem0" @FIRRTLMem_1_0_0_32_1_0_1_1("": %0: i1, "": %1: i1, "": %2: i1) -> ("": i32)
|
||||
%mem0.ro_data_0 = hw.instance "mem0" @FIRRTLMem_1_0_0_32_1_0_1_1("x": %0: i1, "y": %1: i1, "z": %2: i1) -> ("": i32)
|
||||
%3 = sv.read_inout %.load0.clk.wire : !hw.inout<i1>
|
||||
sv.assign %.load0.clk.wire, %clock : i1
|
||||
%4 = sv.read_inout %.load0.addr.wire : !hw.inout<i1>
|
||||
|
|
|
@ -1,27 +1,27 @@
|
|||
// RUN: circt-opt %s -split-input-file -verify-diagnostics
|
||||
|
||||
func private @test_extract(%arg0: i4) {
|
||||
func.func private @test_extract(%arg0: i4) {
|
||||
// expected-error @+1 {{'comb.extract' op from bit too large for input}}
|
||||
%a = comb.extract %arg0 from 6 : (i4) -> i3
|
||||
}
|
||||
|
||||
// -----
|
||||
|
||||
func private @test_extract(%arg0: i4) {
|
||||
func.func private @test_extract(%arg0: i4) {
|
||||
// expected-error @+1 {{'comb.extract' op from bit too large for input}}
|
||||
%b = comb.extract %arg0 from 2 : (i4) -> i3
|
||||
}
|
||||
|
||||
// -----
|
||||
|
||||
func private @test_and() {
|
||||
func.func private @test_and() {
|
||||
// expected-error @+1 {{'comb.and' op expected 1 or more operands}}
|
||||
%b = comb.and : i111
|
||||
}
|
||||
|
||||
// -----
|
||||
|
||||
func private @notModule () {
|
||||
func.func private @notModule () {
|
||||
return
|
||||
}
|
||||
|
||||
|
@ -58,12 +58,12 @@ hw.module @A() -> ("": i1) { }
|
|||
// -----
|
||||
|
||||
// expected-error @+1 {{expected non-function type}}
|
||||
func private @arrayDims(%a: !hw.array<3 x 4 x i5>) { }
|
||||
func.func private @arrayDims(%a: !hw.array<3 x 4 x i5>) { }
|
||||
|
||||
// -----
|
||||
|
||||
// expected-error @+1 {{invalid element for hw.inout type}}
|
||||
func private @invalidInout(%arg0: !hw.inout<tensor<*xf32>>) { }
|
||||
func.func private @invalidInout(%arg0: !hw.inout<tensor<*xf32>>) { }
|
||||
|
||||
// -----
|
||||
|
||||
|
|
|
@ -53,6 +53,3 @@ hw.generator.schema @MEMORY, "Simple-Memory", ["ports", "write_latency", "read_l
|
|||
hw.module.generated @genmod1, @MEMORY() -> (FOOBAR: i1) attributes {write_latency=1, read_latency=1, ports=["read","write"]}
|
||||
// CHECK-LABEL: hw.generator.schema @MEMORY, "Simple-Memory", ["ports", "write_latency", "read_latency"]
|
||||
// CHECK-NEXT: hw.module.generated @genmod1, @MEMORY() -> (FOOBAR: i1) attributes {ports = ["read", "write"], read_latency = 1 : i64, write_latency = 1 : i64}
|
||||
|
||||
// CHECK-LABEL: hw.module.extern @AnonArg(i42)
|
||||
hw.module.extern @AnonArg(i42)
|
||||
|
|
|
@ -3,32 +3,32 @@
|
|||
// CHECK-LABEL: module
|
||||
module {
|
||||
// CHECK-LABEL: func @i20x5array(%{{.*}}: !hw.array<5xi20>)
|
||||
func @i20x5array(%A: !hw.array<5 x i20>) {
|
||||
func.func @i20x5array(%A: !hw.array<5 x i20>) {
|
||||
return
|
||||
}
|
||||
|
||||
// CHECK-LABEL: func @si20x5array(%{{.*}}: !hw.array<5xsi20>)
|
||||
func @si20x5array(%A: !hw.array<5 x si20>) {
|
||||
func.func @si20x5array(%A: !hw.array<5 x si20>) {
|
||||
return
|
||||
}
|
||||
|
||||
// CHECK-LABEL: func @inoutType(%arg0: !hw.inout<i42>) {
|
||||
func @inoutType(%arg0: !hw.inout<i42>) {
|
||||
func.func @inoutType(%arg0: !hw.inout<i42>) {
|
||||
return
|
||||
}
|
||||
|
||||
// CHECK-LABEL: func @structType(%arg0: !hw.struct<>, %arg1: !hw.struct<foo: i32, bar: i4, baz: !hw.struct<foo: i7>>) {
|
||||
func @structType(%SE: !hw.struct<>, %SF: !hw.struct<foo: i32, bar: i4, baz: !hw.struct<foo: i7>>) {
|
||||
func.func @structType(%SE: !hw.struct<>, %SF: !hw.struct<foo: i32, bar: i4, baz: !hw.struct<foo: i7>>) {
|
||||
return
|
||||
}
|
||||
|
||||
// CHECK-LABEL: func @unionType(%arg0: !hw.union<foo: i32, bar: i4, baz: !hw.struct<foo: i7>>) {
|
||||
func @unionType(%SF: !hw.union<foo: i32, bar: i4, baz: !hw.struct<foo: i7>>) {
|
||||
func.func @unionType(%SF: !hw.union<foo: i32, bar: i4, baz: !hw.struct<foo: i7>>) {
|
||||
return
|
||||
}
|
||||
|
||||
// CHECK-LABEL: nestedType
|
||||
func @nestedType(
|
||||
func.func @nestedType(
|
||||
// CHECK: %arg0: !hw.inout<array<42xi8>>,
|
||||
%arg0: !hw.inout<!hw.array<42xi8>>,
|
||||
// CHECK: %arg1: !hw.inout<array<42xi8>>,
|
||||
|
@ -44,7 +44,7 @@ module {
|
|||
}
|
||||
|
||||
// CHECK-LABEL: aliasedAggregates
|
||||
func @aliasedAggregates(%i: i1) {
|
||||
func.func @aliasedAggregates(%i: i1) {
|
||||
// CHECK: !hw.typealias<@ns::@bar, !hw.struct<a: i1, b: i1>>
|
||||
%0 = hw.struct_create(%i, %i) : !hw.typealias<@ns::@bar, !hw.struct<a: i1, b: i1>>
|
||||
// CHECK: !hw.typealias<@ns::@bar, !hw.union<a: i1, b: i1>>
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
// CHECK-LABEL: @check_shl_folding
|
||||
// CHECK-SAME: %[[BASE:.*]]: i4
|
||||
// CHECK-SAME: %[[HIDDEN:.*]]: i8
|
||||
func @check_shl_folding(%base : i4, %hidden : i8) -> (i4, i4) {
|
||||
func.func @check_shl_folding(%base : i4, %hidden : i8) -> (i4, i4) {
|
||||
// CHECK-NEXT: %[[NEGSEVEN:.*]] = hw.constant -7 : i4
|
||||
%0 = hw.constant 2 : i4
|
||||
%1 = hw.constant 4 : i4
|
||||
|
@ -18,7 +18,7 @@ func @check_shl_folding(%base : i4, %hidden : i8) -> (i4, i4) {
|
|||
// CHECK-LABEL: @check_shr_folding
|
||||
// CHECK-SAME: %[[BASE:.*]]: i4
|
||||
// CHECK-SAME: %[[HIDDEN:.*]]: i8
|
||||
func @check_shr_folding(%base : i4, %hidden : i8) -> (i4, i4) {
|
||||
func.func @check_shr_folding(%base : i4, %hidden : i8) -> (i4, i4) {
|
||||
// CHECK-NEXT: %[[NEGSEVEN:.*]] = hw.constant -7 : i4
|
||||
%0 = hw.constant 2 : i4
|
||||
%1 = hw.constant 4 : i4
|
||||
|
|
|
@ -2,7 +2,7 @@
|
|||
|
||||
// CHECK-LABEL: @const_hoisting
|
||||
// CHECK-SAME: %[[SIG:.*]]: !llhd.sig<i32>
|
||||
func @const_hoisting(%sig : !llhd.sig<i32>) {
|
||||
func.func @const_hoisting(%sig : !llhd.sig<i32>) {
|
||||
// CHECK-DAG: %[[C0:.*]] = hw.constant -1 : i32
|
||||
// CHECK-DAG: %[[TIME:.*]] = llhd.constant_time <1ns, 0d, 0e>
|
||||
// CHECK-NEXT: cf.br ^[[BB:.*]]
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
// RUN: circt-opt %s -canonicalize='top-down=true region-simplify=true' | FileCheck %s
|
||||
|
||||
// CHECK-LABEL: @sigExtractOp
|
||||
func @sigExtractOp(%arg0 : !llhd.sig<i32>, %arg1: i5) -> (!llhd.sig<i32>, !llhd.sig<i32>) {
|
||||
func.func @sigExtractOp(%arg0 : !llhd.sig<i32>, %arg1: i5) -> (!llhd.sig<i32>, !llhd.sig<i32>) {
|
||||
%zero = hw.constant 0 : i5
|
||||
|
||||
// CHECK: %[[EXT:.*]] = llhd.sig.extract %arg0 from %arg1 : (!llhd.sig<i32>) -> !llhd.sig<i32>
|
||||
|
@ -14,7 +14,7 @@ func @sigExtractOp(%arg0 : !llhd.sig<i32>, %arg1: i5) -> (!llhd.sig<i32>, !llhd.
|
|||
}
|
||||
|
||||
// CHECK-LABEL: @sigArraySlice
|
||||
func @sigArraySliceOp(%arg0: !llhd.sig<!hw.array<30xi32>>, %arg1: !llhd.sig<!hw.array<30xi32>>, %arg2: i5)
|
||||
func.func @sigArraySliceOp(%arg0: !llhd.sig<!hw.array<30xi32>>, %arg1: !llhd.sig<!hw.array<30xi32>>, %arg2: i5)
|
||||
-> (!llhd.sig<!hw.array<30xi32>>, !llhd.sig<!hw.array<30xi32>>, !llhd.sig<!hw.array<20xi32>>, !llhd.sig<!hw.array<3xi32>>) {
|
||||
%zero = hw.constant 0 : i5
|
||||
|
||||
|
@ -40,8 +40,8 @@ func @sigArraySliceOp(%arg0: !llhd.sig<!hw.array<30xi32>>, %arg1: !llhd.sig<!hw.
|
|||
}
|
||||
|
||||
// CHECK-LABEL: @sigArrayGetOp
|
||||
func @sigArrayGetOp(%arg0: !llhd.sig<!hw.array<30xi32>>, %arg1: !llhd.sig<!hw.array<30xi32>>) -> (!llhd.sig<i32>, !llhd.sig<i32>) {
|
||||
|
||||
func.func @sigArrayGetOp(%arg0: !llhd.sig<!hw.array<30xi32>>, %arg1: !llhd.sig<!hw.array<30xi32>>) -> (!llhd.sig<i32>, !llhd.sig<i32>) {
|
||||
|
||||
// CHECK-NEXT: %c4_i5 = hw.constant 4 : i5
|
||||
// CHECK-NEXT: %c6_i5 = hw.constant 6 : i5
|
||||
%a = hw.constant 3 : i5
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
// CHECK-LABEL: @check_mem_dce
|
||||
// CHECK-SAME: %[[INT:.*]]: i32,
|
||||
// CHECK-SAME: %[[INT2:.*]]: i32
|
||||
func @check_mem_dce(%int : i32, %int2 : i32) -> i32 {
|
||||
func.func @check_mem_dce(%int : i32, %int2 : i32) -> i32 {
|
||||
// CHECK-NEXT: %[[VAR:.*]] = llhd.var %[[INT]] : i32
|
||||
%0 = llhd.var %int : i32
|
||||
%1 = llhd.var %int2 : i32
|
||||
|
@ -23,7 +23,7 @@ func @check_mem_dce(%int : i32, %int2 : i32) -> i32 {
|
|||
// CHECK-LABEL: @check_mem_cse
|
||||
// CHECK-SAME: %[[INT:.*]]: i32,
|
||||
// CHECK-SAME: %[[INT2:.*]]: i32
|
||||
func @check_mem_cse(%int : i32, %int2 : i32) {
|
||||
func.func @check_mem_cse(%int : i32, %int2 : i32) {
|
||||
// CHECK-NEXT: %[[VAR1:.*]] = llhd.var %[[INT]] : i32
|
||||
%0 = llhd.var %int : i32
|
||||
// CHECK-NEXT: %[[VAR2:.*]] = llhd.var %[[INT2]] : i32
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
|
||||
// CHECK-LABEL: @check_dce_prb_but_not_cse
|
||||
// CHECK-SAME: %[[SIG:.*]]: !llhd.sig<i32>
|
||||
func @check_dce_prb_but_not_cse(%sig : !llhd.sig<i32>) -> (i32, i32) {
|
||||
func.func @check_dce_prb_but_not_cse(%sig : !llhd.sig<i32>) -> (i32, i32) {
|
||||
// CHECK-NEXT: %[[P1:.*]] = llhd.prb %[[SIG]] : !llhd.sig<i32>
|
||||
%1 = llhd.prb %sig : !llhd.sig<i32>
|
||||
// CHECK-NEXT: %[[P2:.*]] = llhd.prb %[[SIG]] : !llhd.sig<i32>
|
||||
|
|
|
@ -5,7 +5,7 @@
|
|||
// CHECK-SAME: %[[VAL:.*]]: i32
|
||||
// CHECK-SAME: %[[TIME:.*]]: !llhd.time
|
||||
// CHECK-SAME: %[[COND:.*]]: i1
|
||||
func @drv_folding(%sig: !llhd.sig<i32>, %val: i32, %time: !llhd.time, %cond: i1) {
|
||||
func.func @drv_folding(%sig: !llhd.sig<i32>, %val: i32, %time: !llhd.time, %cond: i1) {
|
||||
%true = hw.constant 1 : i1
|
||||
%false = hw.constant 0 : i1
|
||||
|
||||
|
|
|
@ -9,7 +9,7 @@
|
|||
// CHECK-SAME: %[[SIGARRAY2:.*]]: !llhd.sig<!hw.array<2xi8>>
|
||||
// CHECK-SAME: %[[ARRAY4:.*]]: !hw.array<4xi8>
|
||||
// CHECK-SAME: %[[ARRAY2:.*]]: !hw.array<2xi8>
|
||||
func @check_bitwise(%a : i64, %c : i8,
|
||||
func.func @check_bitwise(%a : i64, %c : i8,
|
||||
%sig1 : !llhd.sig<i32>, %sig2 : !llhd.sig<i4>,
|
||||
%sigarray4: !llhd.sig<!hw.array<4xi8>>, %sigarray2: !llhd.sig<!hw.array<2xi8>>,
|
||||
%array4: !hw.array<4xi8>, %array2: !hw.array<2xi8>) {
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
// RUN: circt-opt %s -mlir-print-op-generic -split-input-file -verify-diagnostics
|
||||
|
||||
func @illegal_signal_to_array(%sig : !llhd.sig<!hw.array<3xi32>>, %ind: i2) {
|
||||
func.func @illegal_signal_to_array(%sig : !llhd.sig<!hw.array<3xi32>>, %ind: i2) {
|
||||
// expected-error @+1 {{'llhd.sig.array_slice' op result #0 must be LLHD sig type of an ArrayType values, but got '!hw.array<3xi32>'}}
|
||||
%0 = llhd.sig.array_slice %sig at %ind : (!llhd.sig<!hw.array<3xi32>>) -> !hw.array<3xi32>
|
||||
|
||||
|
@ -9,7 +9,7 @@ func @illegal_signal_to_array(%sig : !llhd.sig<!hw.array<3xi32>>, %ind: i2) {
|
|||
|
||||
// -----
|
||||
|
||||
func @illegal_array_element_type_mismatch(%sig : !llhd.sig<!hw.array<3xi32>>, %ind: i2) {
|
||||
func.func @illegal_array_element_type_mismatch(%sig : !llhd.sig<!hw.array<3xi32>>, %ind: i2) {
|
||||
// expected-error @+1 {{arrays element type must match}}
|
||||
%0 = llhd.sig.array_slice %sig at %ind : (!llhd.sig<!hw.array<3xi32>>) -> !llhd.sig<!hw.array<2xi1>>
|
||||
|
||||
|
@ -18,7 +18,7 @@ func @illegal_array_element_type_mismatch(%sig : !llhd.sig<!hw.array<3xi32>>, %i
|
|||
|
||||
// -----
|
||||
|
||||
func @illegal_result_array_too_big(%sig : !llhd.sig<!hw.array<3xi32>>, %ind: i2) {
|
||||
func.func @illegal_result_array_too_big(%sig : !llhd.sig<!hw.array<3xi32>>, %ind: i2) {
|
||||
// expected-error @+1 {{width of result type has to be smaller than or equal to the input type}}
|
||||
%0 = llhd.sig.array_slice %sig at %ind : (!llhd.sig<!hw.array<3xi32>>) -> !llhd.sig<!hw.array<4xi32>>
|
||||
|
||||
|
@ -27,7 +27,7 @@ func @illegal_result_array_too_big(%sig : !llhd.sig<!hw.array<3xi32>>, %ind: i2)
|
|||
|
||||
// -----
|
||||
|
||||
func @illegal_sig_to_int(%s : !llhd.sig<i32>, %ind: i5) {
|
||||
func.func @illegal_sig_to_int(%s : !llhd.sig<i32>, %ind: i5) {
|
||||
// expected-error @+1 {{'llhd.sig.extract' op result #0 must be LLHD sig type of an integer bitvector of one or more bits values, but got 'i10'}}
|
||||
%0 = llhd.sig.extract %s from %ind : (!llhd.sig<i32>) -> i10
|
||||
|
||||
|
@ -36,7 +36,7 @@ func @illegal_sig_to_int(%s : !llhd.sig<i32>, %ind: i5) {
|
|||
|
||||
// -----
|
||||
|
||||
func @illegal_sig_to_int_to_wide(%s : !llhd.sig<i32>, %ind: i5) {
|
||||
func.func @illegal_sig_to_int_to_wide(%s : !llhd.sig<i32>, %ind: i5) {
|
||||
// expected-error @+1 {{width of result type has to be smaller than or equal to the input type}}
|
||||
%0 = llhd.sig.extract %s from %ind : (!llhd.sig<i32>) -> !llhd.sig<i64>
|
||||
|
||||
|
@ -45,7 +45,7 @@ func @illegal_sig_to_int_to_wide(%s : !llhd.sig<i32>, %ind: i5) {
|
|||
|
||||
// -----
|
||||
|
||||
func @extract_element_tuple_index_out_of_bounds(%tup : !llhd.sig<!hw.struct<foo: i1, bar: i2, baz: i3>>) {
|
||||
func.func @extract_element_tuple_index_out_of_bounds(%tup : !llhd.sig<!hw.struct<foo: i1, bar: i2, baz: i3>>) {
|
||||
// expected-error @+1 {{invalid field name specified}}
|
||||
%0 = llhd.sig.struct_extract %tup["foobar"] : !llhd.sig<!hw.struct<foo: i1, bar: i2, baz: i3>>
|
||||
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
// RUN: circt-opt %s -mlir-print-op-generic -split-input-file -verify-diagnostics | circt-opt | circt-opt | FileCheck %s
|
||||
|
||||
// CHECK-LABEL: @sigExtract
|
||||
func @sigExtract (%arg0 : !llhd.sig<i32>, %arg1: i5) -> () {
|
||||
func.func @sigExtract (%arg0 : !llhd.sig<i32>, %arg1: i5) -> () {
|
||||
// CHECK-NEXT: %{{.*}} = llhd.sig.extract %arg0 from %arg1 : (!llhd.sig<i32>) -> !llhd.sig<i5>
|
||||
%1 = llhd.sig.extract %arg0 from %arg1 : (!llhd.sig<i32>) -> !llhd.sig<i5>
|
||||
|
||||
|
@ -9,7 +9,7 @@ func @sigExtract (%arg0 : !llhd.sig<i32>, %arg1: i5) -> () {
|
|||
}
|
||||
|
||||
// CHECK-LABEL: @sigArray
|
||||
func @sigArray (%arg0 : !llhd.sig<!hw.array<5xi1>>, %arg1: i3) -> () {
|
||||
func.func @sigArray (%arg0 : !llhd.sig<!hw.array<5xi1>>, %arg1: i3) -> () {
|
||||
// CHECK-NEXT: %{{.*}} = llhd.sig.array_slice %arg0 at %arg1 : (!llhd.sig<!hw.array<5xi1>>) -> !llhd.sig<!hw.array<3xi1>>
|
||||
%0 = llhd.sig.array_slice %arg0 at %arg1 : (!llhd.sig<!hw.array<5xi1>>) -> !llhd.sig<!hw.array<3xi1>>
|
||||
// CHECK-NEXT: %{{.*}} = llhd.sig.array_get %arg0[%arg1] : !llhd.sig<!hw.array<5xi1>>
|
||||
|
@ -19,7 +19,7 @@ func @sigArray (%arg0 : !llhd.sig<!hw.array<5xi1>>, %arg1: i3) -> () {
|
|||
}
|
||||
|
||||
// CHECK-LABEL: @sigStructExtract
|
||||
func @sigStructExtract(%arg0 : !llhd.sig<!hw.struct<foo: i1, bar: i2, baz: i3>>) {
|
||||
func.func @sigStructExtract(%arg0 : !llhd.sig<!hw.struct<foo: i1, bar: i2, baz: i3>>) {
|
||||
// CHECK-NEXT: %{{.*}} = llhd.sig.struct_extract %arg0["foo"] : !llhd.sig<!hw.struct<foo: i1, bar: i2, baz: i3>>
|
||||
%0 = llhd.sig.struct_extract %arg0["foo"] : !llhd.sig<!hw.struct<foo: i1, bar: i2, baz: i3>>
|
||||
// CHECK-NEXT: %{{.*}} = llhd.sig.struct_extract %arg0["baz"] : !llhd.sig<!hw.struct<foo: i1, bar: i2, baz: i3>>
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
// RUN: circt-opt %s -mlir-print-op-generic -split-input-file -verify-diagnostics
|
||||
|
||||
// expected-note @+1 {{prior use here}}
|
||||
func @check_illegal_store(%i1Ptr : !llhd.ptr<i1>, %i32Const : i32) {
|
||||
func.func @check_illegal_store(%i1Ptr : !llhd.ptr<i1>, %i32Const : i32) {
|
||||
// expected-error @+1 {{use of value '%i32Const' expects different type than prior uses: 'i1' vs 'i32'}}
|
||||
llhd.store %i1Ptr, %i32Const : !llhd.ptr<i1>
|
||||
|
||||
|
|
|
@ -4,7 +4,7 @@
|
|||
// CHECK-SAME: %[[INT:.*]]: i32
|
||||
// CHECK-SAME: %[[ARRAY:.*]]: !hw.array<3xi1>
|
||||
// CHECK-SAME: %[[TUP:.*]]: !hw.struct<foo: i1, bar: i2, baz: i3>
|
||||
func @check_var(%int : i32, %array : !hw.array<3xi1>, %tup : !hw.struct<foo: i1, bar: i2, baz: i3>) {
|
||||
func.func @check_var(%int : i32, %array : !hw.array<3xi1>, %tup : !hw.struct<foo: i1, bar: i2, baz: i3>) {
|
||||
// CHECK-NEXT: %{{.*}} = llhd.var %[[INT]] : i32
|
||||
%0 = llhd.var %int : i32
|
||||
// CHECK-NEXT: %{{.*}} = llhd.var %[[ARRAY]] : !hw.array<3xi1>
|
||||
|
@ -19,7 +19,7 @@ func @check_var(%int : i32, %array : !hw.array<3xi1>, %tup : !hw.struct<foo: i1,
|
|||
// CHECK-SAME: %[[INT:.*]]: !llhd.ptr<i32>
|
||||
// CHECK-SAME: %[[ARRAY:.*]]: !llhd.ptr<!hw.array<3xi1>>
|
||||
// CHECK-SAME: %[[TUP:.*]]: !llhd.ptr<!hw.struct<foo: i1, bar: i2, baz: i3>>
|
||||
func @check_load(%int : !llhd.ptr<i32>, %array : !llhd.ptr<!hw.array<3xi1>>, %tup : !llhd.ptr<!hw.struct<foo: i1, bar: i2, baz: i3>>) {
|
||||
func.func @check_load(%int : !llhd.ptr<i32>, %array : !llhd.ptr<!hw.array<3xi1>>, %tup : !llhd.ptr<!hw.struct<foo: i1, bar: i2, baz: i3>>) {
|
||||
// CHECK-NEXT: %{{.*}} = llhd.load %[[INT]] : !llhd.ptr<i32>
|
||||
%0 = llhd.load %int : !llhd.ptr<i32>
|
||||
// CHECK-NEXT: %{{.*}} = llhd.load %[[ARRAY]] : !llhd.ptr<!hw.array<3xi1>>
|
||||
|
@ -37,7 +37,7 @@ func @check_load(%int : !llhd.ptr<i32>, %array : !llhd.ptr<!hw.array<3xi1>>, %tu
|
|||
// CHECK-SAME: %[[ARRAYC:.*]]: !hw.array<3xi1>
|
||||
// CHECK-SAME: %[[TUP:.*]]: !llhd.ptr<!hw.struct<foo: i1, bar: i2, baz: i3>>
|
||||
// CHECK-SAME: %[[TUPC:.*]]: !hw.struct<foo: i1, bar: i2, baz: i3>
|
||||
func @check_store(%int : !llhd.ptr<i32>, %intC : i32 , %array : !llhd.ptr<!hw.array<3xi1>>, %arrayC : !hw.array<3xi1>, %tup : !llhd.ptr<!hw.struct<foo: i1, bar: i2, baz: i3>>, %tupC : !hw.struct<foo: i1, bar: i2, baz: i3>) {
|
||||
func.func @check_store(%int : !llhd.ptr<i32>, %intC : i32 , %array : !llhd.ptr<!hw.array<3xi1>>, %arrayC : !hw.array<3xi1>, %tup : !llhd.ptr<!hw.struct<foo: i1, bar: i2, baz: i3>>, %tupC : !hw.struct<foo: i1, bar: i2, baz: i3>) {
|
||||
// CHECK-NEXT: llhd.store %[[INT]], %[[INTC]] : !llhd.ptr<i32>
|
||||
llhd.store %int, %intC : !llhd.ptr<i32>
|
||||
// CHECK-NEXT: llhd.store %[[ARRAY]], %[[ARRAYC]] : !llhd.ptr<!hw.array<3xi1>>
|
||||
|
|
|
@ -23,7 +23,7 @@ llhd.entity @checkSigInst () -> () {
|
|||
}
|
||||
|
||||
// CHECK-LABEL: checkPrb
|
||||
func @checkPrb(%arg0 : !llhd.sig<i1>, %arg1 : !llhd.sig<i64>, %arg2 : !llhd.sig<!hw.array<3xi8>>, %arg3 : !llhd.sig<!hw.struct<foo: i1, bar: i2, baz: i4>>) {
|
||||
func.func @checkPrb(%arg0 : !llhd.sig<i1>, %arg1 : !llhd.sig<i64>, %arg2 : !llhd.sig<!hw.array<3xi8>>, %arg3 : !llhd.sig<!hw.struct<foo: i1, bar: i2, baz: i4>>) {
|
||||
// CHECK: %{{.*}} = llhd.prb %arg0 : !llhd.sig<i1>
|
||||
%0 = llhd.prb %arg0 : !llhd.sig<i1>
|
||||
// CHECK-NEXT: %{{.*}} = llhd.prb %arg1 : !llhd.sig<i64>
|
||||
|
@ -37,7 +37,7 @@ func @checkPrb(%arg0 : !llhd.sig<i1>, %arg1 : !llhd.sig<i64>, %arg2 : !llhd.sig<
|
|||
}
|
||||
|
||||
// CHECK-LABEL: checkOutput
|
||||
func @checkOutput(%arg0: i32, %arg1: !llhd.time) {
|
||||
func.func @checkOutput(%arg0: i32, %arg1: !llhd.time) {
|
||||
// CHECK-NEXT: %{{.+}} = llhd.output %arg0 after %arg1 : i32
|
||||
%0 = llhd.output %arg0 after %arg1 : i32
|
||||
// CHECK-NEXT: %{{.+}} = llhd.output "sigName" %arg0 after %arg1 : i32
|
||||
|
@ -47,11 +47,11 @@ func @checkOutput(%arg0: i32, %arg1: !llhd.time) {
|
|||
}
|
||||
|
||||
// CHECK-LABEL: checkDrv
|
||||
func @checkDrv(%arg0 : !llhd.sig<i1>, %arg1 : !llhd.sig<i64>, %arg2 : i1,
|
||||
func.func @checkDrv(%arg0 : !llhd.sig<i1>, %arg1 : !llhd.sig<i64>, %arg2 : i1,
|
||||
%arg3 : i64, %arg4 : !llhd.time, %arg5 : !llhd.sig<!hw.array<3xi8>>,
|
||||
%arg6 : !llhd.sig<!hw.struct<foo: i1, bar: i2, baz: i4>>,
|
||||
%arg7 : !hw.array<3xi8>, %arg8 : !hw.struct<foo: i1, bar: i2, baz: i4>) {
|
||||
|
||||
|
||||
// CHECK-NEXT: llhd.drv %arg0, %arg2 after %arg4 : !llhd.sig<i1>
|
||||
llhd.drv %arg0, %arg2 after %arg4 : !llhd.sig<i1>
|
||||
// CHECK-NEXT: llhd.drv %arg1, %arg3 after %arg4 : !llhd.sig<i64>
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
// RUN: circt-opt %s -allow-unregistered-dialect | FileCheck %s
|
||||
|
||||
func @test_time_type() {
|
||||
func.func @test_time_type() {
|
||||
// CHECK: %[[CONST:.*]] = "time_result"() : () -> !llhd.time
|
||||
%0 = "time_result"() : () -> !llhd.time
|
||||
// CHECK-NEXT: "time_const_arg"(%[[CONST]]) : (!llhd.time) -> ()
|
||||
|
@ -8,7 +8,7 @@ func @test_time_type() {
|
|||
return
|
||||
}
|
||||
|
||||
func @test_time_attr() {
|
||||
func.func @test_time_attr() {
|
||||
"time_attr"() {
|
||||
// CHECK: time0 = #llhd.time<1ns, 0d, 0e>
|
||||
time0 = #llhd.time<1ns, 0d, 0e> : !llhd.time,
|
||||
|
|
|
@ -1,14 +1,14 @@
|
|||
// RUN: circt-opt %s --split-input-file --verify-diagnostics
|
||||
|
||||
// expected-error @+1 {{unknown type `illegaltype` in dialect `llhd`}}
|
||||
func @illegaltype(%arg0: !llhd.illegaltype) {
|
||||
func.func @illegaltype(%arg0: !llhd.illegaltype) {
|
||||
return
|
||||
}
|
||||
|
||||
// -----
|
||||
|
||||
// expected-error @+2 {{unknown attribute `illegalattr` in dialect `llhd`}}
|
||||
func @illegalattr() {
|
||||
func.func @illegalattr() {
|
||||
%0 = llhd.constant_time #llhd.illegalattr : i1
|
||||
return
|
||||
}
|
||||
|
|
|
@ -41,7 +41,7 @@ llhd.proc @check_simple() -> () {
|
|||
// CHECK: %[[VAL_1:.*]] = llhd.var %[[VAL_0]] : i32
|
||||
// CHECK: return %[[VAL_1]] : !llhd.ptr<i32>
|
||||
// CHECK: }
|
||||
func @allocate_mem() -> !llhd.ptr<i32> {
|
||||
func.func @allocate_mem() -> !llhd.ptr<i32> {
|
||||
%c = hw.constant 0 : i32
|
||||
%ptr = llhd.var %c : i32
|
||||
return %ptr : !llhd.ptr<i32>
|
||||
|
@ -50,7 +50,7 @@ func @allocate_mem() -> !llhd.ptr<i32> {
|
|||
// CHECK-LABEL: llhd.proc @pointer_returned_from_call() -> () {
|
||||
// CHECK: %[[ALLSET:.*]] = hw.constant -1 : i32
|
||||
// CHECK: %[[VAL_0:.*]] = hw.constant true
|
||||
// CHECK: %[[VAL_1:.*]] = call @allocate_mem() : () -> !llhd.ptr<i32>
|
||||
// CHECK: %[[VAL_1:.*]] = func.call @allocate_mem() : () -> !llhd.ptr<i32>
|
||||
// CHECK: cf.cond_br %[[VAL_0]], ^bb1, ^bb2
|
||||
// CHECK: ^bb1:
|
||||
// CHECK: %[[VAL_2:.*]] = hw.constant 6 : i32
|
||||
|
@ -68,7 +68,7 @@ func @allocate_mem() -> !llhd.ptr<i32> {
|
|||
llhd.proc @pointer_returned_from_call() -> () {
|
||||
%allset = hw.constant -1 : i32
|
||||
%cond = hw.constant 1 : i1
|
||||
%ptr = call @allocate_mem() : () -> !llhd.ptr<i32>
|
||||
%ptr = func.call @allocate_mem() : () -> !llhd.ptr<i32>
|
||||
cf.cond_br %cond, ^bb1, ^bb2
|
||||
^bb1:
|
||||
%c6 = hw.constant 6 : i32
|
||||
|
@ -90,7 +90,7 @@ llhd.proc @pointer_returned_from_call() -> () {
|
|||
// CHECK: llhd.store %[[VAL_0]], %[[VAL_1]] : !llhd.ptr<i32>
|
||||
// CHECK: return
|
||||
// CHECK: }
|
||||
func @store_something(%ptr : !llhd.ptr<i32>) {
|
||||
func.func @store_something(%ptr : !llhd.ptr<i32>) {
|
||||
%c = hw.constant 0 : i32
|
||||
llhd.store %ptr, %c : !llhd.ptr<i32>
|
||||
return
|
||||
|
@ -121,7 +121,7 @@ llhd.proc @pointer_passed_to_function() -> () {
|
|||
%ptr = llhd.var %c5 : i32
|
||||
cf.cond_br %cond, ^bb1, ^bb2
|
||||
^bb1:
|
||||
call @store_something(%ptr) : (!llhd.ptr<i32>) -> ()
|
||||
func.call @store_something(%ptr) : (!llhd.ptr<i32>) -> ()
|
||||
cf.br ^bb3
|
||||
^bb2:
|
||||
%c7 = hw.constant 7 : i32
|
||||
|
|
|
@ -7,13 +7,13 @@
|
|||
// into entities.
|
||||
|
||||
// CHECK-NOT: func
|
||||
func @simple() -> i32 {
|
||||
func.func @simple() -> i32 {
|
||||
%0 = hw.constant 5 : i32
|
||||
return %0 : i32
|
||||
}
|
||||
|
||||
// CHECK-NOT: func
|
||||
func @complex(%flag : i1) -> i32 {
|
||||
func.func @complex(%flag : i1) -> i32 {
|
||||
cf.cond_br %flag, ^bb1, ^bb2
|
||||
^bb1:
|
||||
%0 = hw.constant 5 : i32
|
||||
|
@ -29,7 +29,7 @@ llhd.entity @check_entity_inline() -> (%out : !llhd.sig<i32>) {
|
|||
// CHECK-NEXT: %{{.*}} = llhd.constant_time
|
||||
// CHECK-NEXT: llhd.drv
|
||||
// CHECK-NEXT: }
|
||||
%1 = call @simple() : () -> i32
|
||||
%1 = func.call @simple() : () -> i32
|
||||
%time = llhd.constant_time #llhd.time<1ns, 0d, 0e>
|
||||
llhd.drv %out, %1 after %time : !llhd.sig<i32>
|
||||
}
|
||||
|
@ -50,7 +50,7 @@ llhd.proc @check_proc_inline(%arg : !llhd.sig<i1>) -> (%out : !llhd.sig<i32>) {
|
|||
// CHECK-NEXT: llhd.halt
|
||||
// CHECK-NEXT: }
|
||||
%0 = llhd.prb %arg : !llhd.sig<i1>
|
||||
%1 = call @complex(%0) : (i1) -> i32
|
||||
%1 = func.call @complex(%0) : (i1) -> i32
|
||||
%time = llhd.constant_time #llhd.time<1ns, 0d, 0e>
|
||||
llhd.drv %out, %1 after %time : !llhd.sig<i32>
|
||||
llhd.halt
|
||||
|
|
|
@ -11,7 +11,7 @@ llhd.entity @test1() -> () {
|
|||
}
|
||||
|
||||
// CHECK-LABEL: func @Expressions
|
||||
func @Expressions(%a: !moore.bit, %b: !moore.logic, %c: !moore.packed<range<bit, 4:0>>) {
|
||||
func.func @Expressions(%a: !moore.bit, %b: !moore.logic, %c: !moore.packed<range<bit, 4:0>>) {
|
||||
// CHECK: %0 = moore.mir.concat
|
||||
// CHECK: %1 = moore.mir.concat
|
||||
%0 = moore.mir.concat %a, %a : (!moore.bit, !moore.bit) -> !moore.packed<range<bit, 1:0>>
|
||||
|
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue