34 StringAttr::get(ctx, hw::HWModuleLike::getPortSymbolAttrName());
35 NamedAttrList pattr(attrs);
38 oldValue = pattr.erase(portSymAttr);
40 oldValue = pattr.set(portSymAttr, sym);
41 if (oldValue != sym) {
42 attrs = pattr.getDictionary(ctx);
54hw::verifyInnerSymAttr(InnerSymAttr innerSym, Type type,
55 llvm::function_ref<InFlightDiagnostic()> emitError) {
56 assert(innerSym &&
"null inner symbol attribute provided");
66 for (
auto prop : innerSym) {
67 if (prop.getFieldID() != 0)
68 return emitError() <<
"does not support per-field inner symbols, but "
70 << prop.getName().getValue()
71 <<
"' with non-zero field id " << prop.getFieldID();
74 if (innerSym.size() > 1) {
76 auto err = emitError() <<
"has more than one symbol defined: ";
77 llvm::interleaveComma(innerSym, err, [&](
auto prop) {
78 err <<
"'" << prop.getName().getValue() <<
"'";
85 auto maxFields = FieldIdImpl::getMaxFieldID(type);
86 llvm::SmallBitVector indices(maxFields + 1);
87 llvm::SmallPtrSet<Attribute, 8> symNames;
89 auto uniqSyms = [&](InnerSymPropertiesAttr p) {
90 if (maxFields < p.getFieldID()) {
91 emitError() <<
"field id " << p.getFieldID()
92 <<
" is greater than the maximum field id " << maxFields;
95 if (indices.test(p.getFieldID())) {
96 emitError() <<
"cannot assign multiple symbol names to the field id "
100 indices.set(p.getFieldID());
101 auto it = symNames.insert(p.getName());
103 emitError() <<
"cannot reuse symbol name '" << p.getName().getValue()
110 if (!llvm::all_of(innerSym.getProps(), uniqSyms))
116LogicalResult hw::verifyInnerSymOp(InnerSymbolOpInterface op) {
117 auto innerSym = op.getInnerSymAttr();
122 if (innerSym.empty())
123 return op->emitOpError(
"has empty list of inner symbols");
125 if (!op.supportsPerFieldSymbols())
131 auto result = op.getTargetResult();
136 [op]() { return op->emitOpError(); });
139LogicalResult hw::verifyPortInnerSymsIfPortList(Operation *op) {
141 PortList opWithPorts = dyn_cast<hw::PortList>(op);
146 auto ports = opWithPorts.getPortList();
147 for (
auto const &indexAndPort : llvm::enumerate(ports)) {
148 auto &pi = indexAndPort.value();
149 auto idx = indexAndPort.index();
150 Location loc = pi.loc ? Location(pi.loc) : opWithPorts.getLoc();
151 if (
auto sym = pi.getSym())
152 if (failed(hw::verifyInnerSymAttr(sym, pi.type, [&]() {
153 return mlir::emitError(loc)
154 <<
"verification of inner symbol"
155 << (sym.size() > 1 ?
"s" :
"") <<
" failed on port " << idx
156 <<
" with name " << pi.name <<
": ";