diff --git a/circtpanamabinding/includeFunctions.txt b/circtpanamabinding/includeFunctions.txt index 46553275190..e9b86704dba 100644 --- a/circtpanamabinding/includeFunctions.txt +++ b/circtpanamabinding/includeFunctions.txt @@ -47,6 +47,7 @@ mlirOperationStateAddResults mlirOperationStateAddAttributes mlirOperationStateEnableResultTypeInference mlirOperationGetResult +mlirOperationGetAttributeByName mlirOperationSetInherentAttributeByName mlirRegionCreate mlirOperationCreate @@ -108,6 +109,12 @@ chirrtlTypeGetCMemoryPort hwInnerRefAttrGet hwInnerSymAttrGet +hwInstanceGraphGet +hwInstanceGraphGetTopLevelNode +hwInstanceGraphForEachNode +hwInstanceGraphNodeEqual +hwInstanceGraphNodeGetModuleOp + # circtFirtoolOptions circtFirtoolOptionsCreateDefault circtFirtoolOptionsDestroy diff --git a/circtpanamabinding/includeStructs.txt b/circtpanamabinding/includeStructs.txt index 0ced725de47..7bb925e7edd 100644 --- a/circtpanamabinding/includeStructs.txt +++ b/circtpanamabinding/includeStructs.txt @@ -21,3 +21,5 @@ FIRRTLClassElement CirctFirtoolFirtoolOptions OMEvaluator OMEvaluatorValue +HWInstanceGraph +HWInstanceGraphNode diff --git a/circtpanamabinding/includeTypedefs.txt b/circtpanamabinding/includeTypedefs.txt index 27a025590b9..ede7da0cca9 100644 --- a/circtpanamabinding/includeTypedefs.txt +++ b/circtpanamabinding/includeTypedefs.txt @@ -1 +1,2 @@ MlirStringCallback +HWInstanceGraphNodeCallback diff --git a/etc/circt.json b/etc/circt.json index 2b9c6ca651b..91e190ff63c 100644 --- a/etc/circt.json +++ b/etc/circt.json @@ -1,3 +1,3 @@ { - "version": "firtool-1.64.0" + "version": "firtool-1.65.0" } diff --git a/lit/tests/Property/Good.sc b/lit/tests/Property/Good.sc index f26ee8ac372..cc97225cda9 100644 --- a/lit/tests/Property/Good.sc +++ b/lit/tests/Property/Good.sc @@ -26,8 +26,30 @@ args.head match { case _ => } -class PropertyTest extends RawModule { +class PropertyTest extends Module { val i = IO(Input(UInt(8.W))) + val o = IO(Output(UInt(8.W))) + + val m = Module(new Module { + val i = IO(Input(UInt(8.W))) + val r = RegNext(i) + val o = IO(Output(UInt(8.W))) + val p = IO(Output(Property[Int]())) + p := Property(789) + o := r + val nested = Module(new Module { + val i = IO(Input(UInt(8.W))) + val r = RegNext(i) + val o = IO(Output(UInt(8.W))) + val p = IO(Output(Property[Int]())) + p := Property(789) + o := r + }) + nested.i := i + o := nested.o + }) + m.i := i + o := m.o val p = IO(Output(Property[Path]())) p := Property(Path(i)) @@ -54,5 +76,9 @@ args.head match { // CHECK-NEXT: .b => { [ [ prim{omInteger{456}} ] ] } // CHECK-NEXT: .p => { path{OMReferenceTarget:~PropertyTest|PropertyTest>i} } obj.foreachField((name, value) => println(s".$name => { ${value.display} }")) - case _ => -} \ No newline at end of file + + // CHECK: module{_1_Anon} + // CHECK-NEXT: module{PropertyTest_Anon} + // CHECK-NEXT: module{PropertyTest} + converter.foreachHwModule(name => println(s"module{$name}")) +} diff --git a/panamaconverter/src/PanamaCIRCTConverter.scala b/panamaconverter/src/PanamaCIRCTConverter.scala index 8b3b84ebac9..455041414ec 100644 --- a/panamaconverter/src/PanamaCIRCTConverter.scala +++ b/panamaconverter/src/PanamaCIRCTConverter.scala @@ -883,6 +883,21 @@ class PanamaCIRCTConverter(val circt: PanamaCIRCT, fos: Option[FirtoolOptions]) def passManager(): PanamaCIRCTPassManager = new PanamaCIRCTPassManager(circt, mlirRootModule, fos) def om(): PanamaCIRCTOM = new PanamaCIRCTOM(circt, mlirRootModule) + def foreachHwModule(callback: String => Unit) = { + val instanceGraph = circt.hwInstanceGraphGet(circt.mlirModuleGetOperation(mlirRootModule)) + val topLevelNode = circt.hwInstanceGraphGetTopLevelNode(instanceGraph) + circt.hwInstanceGraphForEachNode( + instanceGraph, + node => { + if (!circt.hwInstanceGraphNodeEqual(node, topLevelNode)) { + val moduleOp = circt.hwInstanceGraphNodeGetModuleOp(node) + val moduleName = circt.mlirStringAttrGetValue(circt.mlirOperationGetAttributeByName(moduleOp, "sym_name")) + callback(moduleName) + } + } + ) + } + def visitCircuit(name: String): Unit = { val firCircuit = util .OpBuilder("firrtl.circuit", circt.mlirModuleGetBody(mlirRootModule), circt.unkLoc) diff --git a/panamalib/src/PanamaCIRCT.scala b/panamalib/src/PanamaCIRCT.scala index 057d7de229d..b9cab1a1baa 100644 --- a/panamalib/src/PanamaCIRCT.scala +++ b/panamalib/src/PanamaCIRCT.scala @@ -126,6 +126,10 @@ class PanamaCIRCT { CAPI.mlirOperationGetResult(arena, operation.get, pos) ) + def mlirOperationGetAttributeByName(op: MlirOperation, name: String) = MlirAttribute( + CAPI.mlirOperationGetAttributeByName(arena, op.get, newString(name).get) + ) + def mlirOperationSetInherentAttributeByName(op: MlirOperation, name: String, attr: MlirAttribute): Unit = CAPI.mlirOperationSetInherentAttributeByName(op.get, newString(name).get, attr.get) @@ -480,6 +484,33 @@ class PanamaCIRCT { def hwInnerSymAttrGet(symName: String) = MlirAttribute(CAPI.hwInnerSymAttrGet(arena, mlirStringAttrGet(symName).get)) + def hwInstanceGraphGet(operation: MlirOperation) = HWInstanceGraph(CAPI.hwInstanceGraphGet(arena, operation.get)) + + def hwInstanceGraphGetTopLevelNode(instanceGraph: HWInstanceGraph) = HWInstanceGraphNode( + CAPI.hwInstanceGraphGetTopLevelNode(arena, instanceGraph.get) + ) + + def hwInstanceGraphForEachNode(instaceGraph: HWInstanceGraph, callback: HWInstanceGraphNode => Unit) = { + val cb = HWInstanceGraphNodeCallback( + circt.HWInstanceGraphNodeCallback.allocate( + new circt.HWInstanceGraphNodeCallback { + def apply(node: MemorySegment, userData: MemorySegment) = { + callback(HWInstanceGraphNode(node)) + } + }, + arena + ) + ) + CAPI.hwInstanceGraphForEachNode(instaceGraph.get, cb.get, NULL) + } + + def hwInstanceGraphNodeEqual(lhs: HWInstanceGraphNode, rhs: HWInstanceGraphNode) = + CAPI.hwInstanceGraphNodeEqual(lhs.get, rhs.get) + + def hwInstanceGraphNodeGetModuleOp(node: HWInstanceGraphNode) = MlirOperation( + CAPI.hwInstanceGraphNodeGetModuleOp(arena, node.get) + ) + // // OM C-API // @@ -757,6 +788,30 @@ object OMEvaluatorValue { private[panamalib] def apply(ptr: MemorySegment) = new OMEvaluatorValue(ptr) } +final case class HWInstanceGraph(ptr: MemorySegment) extends ForeignType[MemorySegment] { + private[panamalib] def get = ptr + private[panamalib] val sizeof = circt.HWInstanceGraph.sizeof().toInt +} +object HWInstanceGraph { + private[panamalib] def apply(ptr: MemorySegment) = new HWInstanceGraph(ptr) +} + +final case class HWInstanceGraphNode(ptr: MemorySegment) extends ForeignType[MemorySegment] { + private[panamalib] def get = ptr + private[panamalib] val sizeof = circt.HWInstanceGraphNode.sizeof().toInt +} +object HWInstanceGraphNode { + private[panamalib] def apply(ptr: MemorySegment) = new HWInstanceGraphNode(ptr) +} + +final case class HWInstanceGraphNodeCallback(ptr: MemorySegment) extends ForeignType[MemorySegment] { + private[panamalib] def get = ptr + private[panamalib] val sizeof = CAPI.C_POINTER.byteSize().toInt +} +object HWInstanceGraphNodeCallback { + private[panamalib] def apply(ptr: MemorySegment) = new HWInstanceGraphNodeCallback(ptr) +} + // // MLIR & CIRCT Enums //