Skip to content
apaj edited this page Dec 17, 2021 · 4 revisions

Previous ToC Next


Outer and Inner == "Cake Pattern"

Diplomacy and Tile are intrinsically tied together for the Chisel based implementation of TileLink (for Verilog based TileLink, there is no Diplomacy)

We will see in later sections the sequence of when Diplomacy runs and the order of Diplomacy running relative to the constructors of the inner and outer classes.

Note that the outer class extends LazyModule, and the inner class extends LazyModuleImp -- LazyModuleImp is passed a reference to the matching outer class. Both are defined in the Diplomacy package.

All TL wiring is performed outside of both outer and inner modules. For example, you can call new inside the inner, and thereby instantiate a Chisel module then create normal Chisel wires to wire it to things inside the inner class. But you cannot call new in inner or outer if that new module has any TL connections. We will see in later sections how to use traits to create multiple modules that have TL connections and wire them together. At the level of TL connections there isn't really a concept of hierarchy, all modules that have TL connections and are part of the same TL graph are on the same "level". (Note that there may be separate TL graphs). Again, we will see in later sections how to wire TL modules to each other.

Here we will see the bare essentials of inner and outer -- but this is an incomplete example, because extra machinery is used when connecting TL modules to each other. That will be shown in later sections.


//This is the outer class
class Example1TileModule(implicit p: Parameters) extends LazyModule {

    // When creating a class (module) that has a TL connection, there is special code that is in a library
    // and has to be pulled in. This special code is what participates in Diplomacy negotiations and this
    // special code implements the actual TL wires. Below, TLClientNode is the name of this special code
    // (there are a few other types of such special code in the TL library). It will generate verilog, and
    // the verilog wires of the TL channels will be wired to the verilog generated from TLClientNode.
    // It is weird syntax because of Scala language mechanics. Use "Seq" to package multiple parameters 
    // that are passed to TLClientNode. Best to just copy-paste and follow the pattern.

    val Node0 = TLClientNode(Seq(TLClientPortParameters(
        Seq(TLClientParameters(
            name = "IdentifierForThisTLConnection",  // shows up when Diplomacy reports an error
            sourceId = IdRange(0, 1)))))) // says at most 1 TL transaction can be outstanding (in-flight) 
                                          // on this TL connection, increase if want more
 
    // Instantiate the inner module! By instantiating here, the inner module can create Chisel wires to node0
    lazy val module = new ExampleTileModuleImp(this) 

    //Note, this all that you put in outer module!! All logic, wires, etc go inside inner module.
}

// This is the inner class. This is where the RTL behavior code goes.
class Example1TileModuleImp (outer: ExampleTileModule) extends LazyModuleImp(outer) {
    val (tl0, edge0) = outer.dmanode0.out(0)
    val addrBits0 = edge0.bundle.addressBits
    val beatBytes = (edge0.bundle.dataBits / 8)

    val blackbox_inst = Module(new tile_blackbox)
    tl0.a <> blackbox_inst.io.tile_a_chan
    tl0.d <> blackbox_inst.io.tile_d_chan

}

Previous ToC Top of page Next

Clone this wiki locally