173 if (
auto hwModule = dyn_cast<hw::HWModuleOp>(*module))
174 for (
auto param : hwModule.getParameters())
176 module, cast<ParamDeclAttr>(param).getName()));
178 auto *ctxt =
module.getContext();
180 auto verilogNameAttr = StringAttr::get(ctxt,
"hw.verilogName");
182 auto ports =
module.getPortList();
183 SmallVector<Attribute> newNames(ports.size());
184 bool updated =
false;
185 bool isFuncOp = isa<FuncOp>(module);
186 for (
auto [idx, port] : llvm::enumerate(ports)) {
187 auto verilogName = port.attrs.get(verilogNameAttr);
190 if (isFuncOp && port.attrs.get(FuncOp::getExplicitlyReturnedAttrName())) {
192 newNames[idx] = StringAttr::get(ctxt,
getSymOpName(module));
196 auto newName = StringAttr::get(
197 ctxt, nameResolver.
getLegalName(cast<StringAttr>(verilogName)));
198 newNames[idx] = newName;
199 if (verilogName != newName)
203 auto oldName = ports[idx].name;
206 if (newName != oldName) {
207 newNames[idx] = StringAttr::get(ctxt, newName);
213 module.setPortAttrs(verilogNameAttr, newNames);
215 SmallVector<std::pair<Operation *, StringAttr>> nameEntries;
218 module.walk([&](Operation *op) {
221 if (auto name = op->getAttrOfType<StringAttr>(verilogNameAttr)) {
222 nameResolver.insertUsedName(
223 op->getAttrOfType<StringAttr>(verilogNameAttr));
224 }
else if (isa<sv::WireOp, hw::WireOp, VarOp, RegOp, LogicOp,
225 LocalParamOp, hw::InstanceOp, sv::InterfaceInstanceOp,
226 sv::GenerateOp>(op)) {
228 nameEntries.emplace_back(
229 op, StringAttr::get(op->getContext(),
getSymOpName(op)));
230 }
else if (
auto forOp = dyn_cast<ForOp>(op)) {
231 nameEntries.emplace_back(op, forOp.getInductionVarNameAttr());
232 }
else if (
auto genForOp = dyn_cast<GenerateForOp>(op)) {
233 nameEntries.emplace_back(op, genForOp.getInductionVarNameAttr());
234 }
else if (isa<AssertOp, AssumeOp, CoverOp, AssertConcurrentOp,
235 AssumeConcurrentOp, CoverConcurrentOp, AssertPropertyOp,
236 AssumePropertyOp, CoverPropertyOp, verif::AssertOp,
237 verif::CoverOp, verif::AssumeOp>(op)) {
239 if (
auto labelAttr = op->getAttrOfType<StringAttr>(
"label"))
240 nameEntries.emplace_back(op, labelAttr);
241 else if (options.enforceVerifLabels) {
244 StringRef defaultName =
245 llvm::TypeSwitch<Operation *, StringRef>(op)
246 .Case<AssertOp, AssertConcurrentOp, AssertPropertyOp,
247 verif::AssertOp>([](
auto) {
return "assert"; })
248 .Case<CoverOp, CoverConcurrentOp, CoverPropertyOp,
249 verif::CoverOp>([](
auto) {
return "cover"; })
250 .Case<AssumeOp, AssumeConcurrentOp, AssumePropertyOp,
251 verif::AssumeOp>([](
auto) {
return "assume"; });
252 nameEntries.emplace_back(
253 op, StringAttr::get(op->getContext(), defaultName));
259 for (
auto [op, nameAttr] : nameEntries) {
260 auto newName = nameResolver.getLegalName(nameAttr);
261 assert(!newName.empty() &&
"must have a valid name");
263 op->setAttr(verilogNameAttr, nameAttr.getValue() == newName
265 : StringAttr::get(ctxt, newName));
279 for (
auto &op : *topLevel.getBody()) {
282 if (isa<HWModuleExternOp, HWModuleGeneratedOp, PackageExternOp>(op)) {
283 auto name = isa<PackageExternOp>(op) ? getSymOpName(&op)
284 : getVerilogModuleName(&op);
285 if (!sv::isNameValid(name, options.caseInsensitiveKeywords))
286 op.emitError(
"name \"")
287 << name <<
"\" is not allowed in Verilog output";
288 globalNameResolver.insertUsedName(name);
289 }
else if (
auto reservedNamesOp = dyn_cast<sv::ReserveNamesOp>(op)) {
290 for (StringAttr name :
291 reservedNamesOp.getReservedNames().getAsRange<StringAttr>()) {
299 for (
auto &op : *topLevel.getBody()) {
300 if (auto module = dyn_cast<HWModuleOp>(op)) {
301 legalizeModuleNames(module);
307 if (
auto interface = dyn_cast<InterfaceOp>(op)) {
308 legalizeInterfaceNames(interface);
312 if (
auto package = dyn_cast<PackageOp>(op))
313 legalizePackageNames(package);
314 else if (
auto package = dyn_cast<PackageExternOp>(op))
315 legalizePackageNames(package);
319 mlir::parallelForEach(
320 topLevel.getContext(), topLevel.getOps<HWEmittableModuleLike>(),
322 legalizeModuleLocalNames(module, options, globalNameTable);
326 gatherEnumPrefixes(topLevel);
331 auto *ctx = package.getContext();
332 if constexpr (!std::is_same_v<Package, PackageExternOp>) {
334 package->setAttr(
"hw.verilogName", StringAttr::get(ctx, name));
341 for (
hw::TypedeclOp decl : package.template getOps<hw::TypedeclOp>()) {
342 auto preferredName = decl.getPreferredName();
344 if (name != preferredName)
345 decl.setVerilogNameAttr(StringAttr::get(ctx, name));
347 for (
hw::TypedeclOp decl : package.template getOps<hw::TypedeclOp>()) {
348 auto enumType = dyn_cast<hw::EnumType>(decl.getType());
351 for (
auto field : enumType.getFields().getAsRange<StringAttr>()) {
353 (decl.getPreferredName() +
"_" + field.getValue()).str());
355 package, StringAttr::get(ctx, name)};
400 MLIRContext *ctxt = interface.getContext();
401 auto verilogNameAttr = StringAttr::get(ctxt,
"hw.verilogName");
403 if (newName != interface.getName())
404 interface->setAttr(verilogNameAttr, StringAttr::get(ctxt, newName));
408 for (
auto &op : *interface.getBodyBlock()) {
409 if (isa<InterfaceSignalOp, InterfaceModportOp>(op)) {
410 auto name = SymbolTable::getSymbolName(&op).getValue();
413 op.setAttr(verilogNameAttr, StringAttr::get(ctxt, newName));