2017-01-19 1 views
0

私はSodorスクラッチパッドメモリに基づいて、SoC用の簡単なオンチップメモリ​​を開発しています。最初に、そのデザインの少し修正されたバージョンをチゼル3に変換しています。今、私が理解できない有界型に関してこの例外が発生しています。Chisel AlreadyBoundException

[info] - should correctly write and read data *** FAILED *** 
[info] chisel3.core.Binding$BindingException: Error: Cannot set as output .M_WR: Already bound to LitBinding() 
[info] at chisel3.core.Binding$.bind(Binding.scala:100) 
[info] at chisel3.core.Output$.apply(Data.scala:50) 
[info] at chisel3.util.ReadyValidIO.<init>(Decoupled.scala:22) 
[info] at chisel3.util.DecoupledIO.<init>(Decoupled.scala:72) 
[info] at chisel3.util.Decoupled$.apply(Decoupled.scala:81) 
[info] at mem.MemPortIO.<init>(memory.scala:40) 
[info] at mem.OnChipMemory$$anon$1.<init>(memory.scala:49) 
[info] at mem.OnChipMemory.<init>(memory.scala:47) 
[info] at mem.memoryTester$$anonfun$3$$anonfun$apply$1$$anonfun$apply$mcV$sp$1.apply(memoryTest.scala:33) 
[info] at mem.memoryTester$$anonfun$3$$anonfun$apply$1$$anonfun$apply$mcV$sp$1.apply(memoryTest.scala:33) 
[info] at chisel3.core.Module$.do_apply(Module.scala:35) 
[info] at chisel3.Driver$$anonfun$elaborate$1.apply(Driver.scala:194) 
[info] at chisel3.Driver$$anonfun$elaborate$1.apply(Driver.scala:194) 
[info] at chisel3.internal.Builder$$anonfun$build$1.apply(Builder.scala:206) 
[info] at chisel3.internal.Builder$$anonfun$build$1.apply(Builder.scala:204) 
[info] at scala.util.DynamicVariable.withValue(DynamicVariable.scala:58) 
[info] at chisel3.internal.Builder$.build(Builder.scala:204) 
[info] at chisel3.Driver$.elaborate(Driver.scala:194) 
[info] at chisel3.Driver$.execute(Driver.scala:229) 
[info] at chisel3.iotesters.setupFirrtlTerpBackend$.apply(FirrtlTerpBackend.scala:110) 
[info] at chisel3.iotesters.Driver$.execute(Driver.scala:47) 
[info] at chisel3.iotesters.Driver$.apply(Driver.scala:210) 
[info] at mem.memoryTester$$anonfun$3$$anonfun$apply$1.apply$mcV$sp(memoryTest.scala:33) 
[info] at mem.memoryTester$$anonfun$3$$anonfun$apply$1.apply(memoryTest.scala:33) 
[info] at mem.memoryTester$$anonfun$3$$anonfun$apply$1.apply(memoryTest.scala:33) 
[info] at org.scalatest.Transformer$$anonfun$apply$1.apply$mcV$sp(Transformer.scala:22) 
[info] at org.scalatest.OutcomeOf$class.outcomeOf(OutcomeOf.scala:85) 
[info] at org.scalatest.OutcomeOf$.outcomeOf(OutcomeOf.scala:104) 
[info] at org.scalatest.Transformer.apply(Transformer.scala:22) 
[info] at org.scalatest.Transformer.apply(Transformer.scala:20) 
[info] at org.scalatest.FlatSpecLike$$anon$1.apply(FlatSpecLike.scala:1647) 
[info] at org.scalatest.Suite$class.withFixture(Suite.scala:1122) 
[info] at org.scalatest.FlatSpec.withFixture(FlatSpec.scala:1683) 
[info] at org.scalatest.FlatSpecLike$class.invokeWithFixture$1(FlatSpecLike.scala:1644) 
[info] at org.scalatest.FlatSpecLike$$anonfun$runTest$1.apply(FlatSpecLike.scala:1656) 
[info] at org.scalatest.FlatSpecLike$$anonfun$runTest$1.apply(FlatSpecLike.scala:1656) 
[info] at org.scalatest.SuperEngine.runTestImpl(Engine.scala:306) 
[info] at org.scalatest.FlatSpecLike$class.runTest(FlatSpecLike.scala:1656) 
[info] at org.scalatest.FlatSpec.runTest(FlatSpec.scala:1683) 
[info] at org.scalatest.FlatSpecLike$$anonfun$runTests$1.apply(FlatSpecLike.scala:1714) 
[info] at org.scalatest.FlatSpecLike$$anonfun$runTests$1.apply(FlatSpecLike.scala:1714) 
[info] at org.scalatest.SuperEngine$$anonfun$traverseSubNodes$1$1.apply(Engine.scala:413) 
[info] at org.scalatest.SuperEngine$$anonfun$traverseSubNodes$1$1.apply(Engine.scala:401) 
[info] at scala.collection.immutable.List.foreach(List.scala:381) 
[info] at org.scalatest.SuperEngine.traverseSubNodes$1(Engine.scala:401) 
[info] at org.scalatest.SuperEngine.org$scalatest$SuperEngine$$runTestsInBranch(Engine.scala:390) 
[info] at org.scalatest.SuperEngine$$anonfun$traverseSubNodes$1$1.apply(Engine.scala:427) 
[info] at org.scalatest.SuperEngine$$anonfun$traverseSubNodes$1$1.apply(Engine.scala:401) 
[info] at scala.collection.immutable.List.foreach(List.scala:381) 
[info] at org.scalatest.SuperEngine.traverseSubNodes$1(Engine.scala:401) 
[info] at org.scalatest.SuperEngine.org$scalatest$SuperEngine$$runTestsInBranch(Engine.scala:396) 
[info] at org.scalatest.SuperEngine.runTestsImpl(Engine.scala:483) 
[info] at org.scalatest.FlatSpecLike$class.runTests(FlatSpecLike.scala:1714) 
[info] at org.scalatest.FlatSpec.runTests(FlatSpec.scala:1683) 
[info] at org.scalatest.Suite$class.run(Suite.scala:1424) 
[info] at org.scalatest.FlatSpec.org$scalatest$FlatSpecLike$$super$run(FlatSpec.scala:1683) 
[info] at org.scalatest.FlatSpecLike$$anonfun$run$1.apply(FlatSpecLike.scala:1760) 
[info] at org.scalatest.FlatSpecLike$$anonfun$run$1.apply(FlatSpecLike.scala:1760) 
[info] at org.scalatest.SuperEngine.runImpl(Engine.scala:545) 
[info] at org.scalatest.FlatSpecLike$class.run(FlatSpecLike.scala:1760) 
[info] at org.scalatest.FlatSpec.run(FlatSpec.scala:1683) 
[info] at org.scalatest.tools.Framework.org$scalatest$tools$Framework$$runSuite(Framework.scala:466) 
[info] at org.scalatest.tools.Framework$ScalaTestTask.execute(Framework.scala:677) 
[info] at sbt.TestRunner.runTest$1(TestFramework.scala:76) 
[info] at sbt.TestRunner.run(TestFramework.scala:85) 
[info] at sbt.TestFramework$$anon$2$$anonfun$$init$$1$$anonfun$apply$8.apply(TestFramework.scala:202) 
[info] at sbt.TestFramework$$anon$2$$anonfun$$init$$1$$anonfun$apply$8.apply(TestFramework.scala:202) 
[info] at sbt.TestFramework$.sbt$TestFramework$$withContextLoader(TestFramework.scala:185) 
[info] at sbt.TestFramework$$anon$2$$anonfun$$init$$1.apply(TestFramework.scala:202) 
[info] at sbt.TestFramework$$anon$2$$anonfun$$init$$1.apply(TestFramework.scala:202) 
[info] at sbt.TestFunction.apply(TestFramework.scala:207) 
[info] at sbt.Tests$$anonfun$9.apply(Tests.scala:216) 
[info] at sbt.Tests$$anonfun$9.apply(Tests.scala:216) 
[info] at sbt.std.Transform$$anon$3$$anonfun$apply$2.apply(System.scala:44) 
[info] at sbt.std.Transform$$anon$3$$anonfun$apply$2.apply(System.scala:44) 
[info] at sbt.std.Transform$$anon$4.work(System.scala:63) 
[info] at sbt.Execute$$anonfun$submit$1$$anonfun$apply$1.apply(Execute.scala:228) 
[info] at sbt.Execute$$anonfun$submit$1$$anonfun$apply$1.apply(Execute.scala:228) 
[info] at sbt.ErrorHandling$.wideConvert(ErrorHandling.scala:17) 
[info] at sbt.Execute.work(Execute.scala:237) 
[info] at sbt.Execute$$anonfun$submit$1.apply(Execute.scala:228) 
[info] at sbt.Execute$$anonfun$submit$1.apply(Execute.scala:228) 
[info] at sbt.ConcurrentRestrictions$$anon$4$$anonfun$1.apply(ConcurrentRestrictions.scala:159) 
[info] at sbt.CompletionService$$anon$2.call(CompletionService.scala:28) 
[info] at java.util.concurrent.FutureTask.run(FutureTask.java:266) 
[info] at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) 
[info] at java.util.concurrent.FutureTask.run(FutureTask.java:266) 
[info] at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142) 
[info] at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617) 
[info] at java.lang.Thread.run(Thread.java:745) 
[info] ScalaCheck 
[info] Passed: Total 0, Failed 0, Errors 0, Passed 0 
[info] ScalaTest 

問題の原因となっている値が不明です。最初に私はVecの問題がMemとIOポートで使用していると思った(同様の例外で見つかった説明のため)。しかし、問題は私がそれらを取り除いた後でさえも存在する。私はさらにクローン機能を取り除こうとしました。

ここでは、問題の原因についてはわかりません。私は役に立つかもしれない場合のために、メモリのためのソースコードのメインセクション(パラメータ宣言といくつかの単純な関数を除く)をポストしています。

trait MemOpConstants 

{ 
    val MT_X = Bits(0, 3) // memory transfer type 
    val MT_B = Bits(1, 3) 
    val MT_H = Bits(2, 3) 
    val MT_W = Bits(3, 3) 
    val MT_D = Bits(4, 3) 
    val MT_BU = Bits(5, 3) 
    val MT_HU = Bits(6, 3) 
    val MT_WU = Bits(7, 3) 

    val M_X = Bits("b0", 1) // access type 
    val M_RD = Bits("b0", 1) // load 
    val M_WR = Bits("b1", 1) // store 
} 

class MemReq(data_width: Int)(implicit config: Configuration) extends Bundle with MemOpConstants 
{ 
    val addr = UInt(width = config.xprlen) 
    val data = Bits(width = data_width) 
    val fcn = Bits(width = M_X.getWidth) // memory function code 
    val typ = Bits(width = MT_X.getWidth) // memory access type 
    override def cloneType = { new MemReq(data_width).asInstanceOf[this.type] } 
} 

class MemResp(data_width: Int) extends Bundle 
{ 
    val data = Bits(width = data_width) 
    override def cloneType = { new MemResp(data_width).asInstanceOf[this.type] } 
} 

class MemPortIO(data_width: Int)(implicit config: Configuration) extends Bundle  // constructor for IO interface of data memory 
{ 
    val req = Decoupled(new MemReq(data_width))     // ready valid pair 
    val resp = (new ValidIO(new MemResp(data_width))).flip   // valid signal 
    override def cloneType = { new MemPortIO(data_width).asInstanceOf[this.type] } 
} 

class OnChipMemory(num_ports: Int = 2, num_bytes: Int = (1 << 15), seq_read: Boolean = false)(implicit config: Configuration) extends Module with MemOpConstants 
{ 
    val io = IO(new Bundle{ 
     val port = Vec(num_ports, (new MemPortIO(data_width = config.xprlen)).flip) 
    }) 

val num_bytes_per_line = 4 
val num_lines = num_bytes/num_bytes_per_line 

val lsb_idx = log2Up(num_bytes_per_line) // index of lsb in address 

val chipMem = Mem(Vec(4, UInt(width = 32)), num_lines) // memory 

for (i <- 0 until num_ports) 
{ 
    io.port(i).resp.valid := Reg(next = io.port(i).req.valid) 

    io.port(i).req.ready := Bool(true) // for now 

    val req_valid  = io.port(i).req.valid 
    val req_addr  = io.port(i).req.bits.addr 
    val req_data  = io.port(i).req.bits.data 
    val req_fn   = io.port(i).req.bits.fcn 
    val req_typ  = io.port(i).req.bits.typ 
    val byte_shift_amt = io.port(i).req.bits.addr(1,0) 
    val bit_shift_amt = Cat(byte_shift_amt, UInt(0,3)) 

    //mem read 
    val r_data_idx = Reg(UInt()) 

    val data_idx = req_addr >> UInt(lsb_idx) 
    val read_data = Bits() 
    val rdata = Bits() 

    if (seq_read) 
    { 
     read_data := chipMem(r_data_idx) 
     rdata  := LoadDataGen((read_data >> Reg(next=bit_shift_amt)), Reg(next=req_typ)) 
    } 
    else 
    { 
     read_data := chipMem(data_idx) 
     rdata  := LoadDataGen((read_data >> bit_shift_amt), req_typ) 
    } 

    io.port(i).resp.bits.data := rdata 

    //mem write 
    when (req_valid && req_fn === M_WR) 
    { 
     val wdata = StoreDataGen(req_data, req_typ) 
     val wmask = ((StoreMask(req_typ) << bit_shift_amt)(31,0)).toBools 

     chipMem.write(data_idx, wdata, wmask) 
    } 
    .elsewhen (req_valid && req_fn === M_RD) 
    { 
     r_data_idx := data_idx 
    } 
} 
} 

object StoreDataGen extends MemOpConstants 
{ 
    def apply(din: Bits, typ: Bits): Vec[UInt] = 
    { 
     val word = (typ.equals(MT_W)) || (typ.equals(MT_WU)) 
     val half = (typ.equals(MT_H)) || (typ.equals(MT_HU)) 
     val byte = (typ.equals(MT_B)) || (typ.equals(MT_BU)) 

     val dout = Mux(Bool(byte), Vec(4, din(7,0)), 
       Mux(Bool(half), Vec(din(15,8), din(7,0), din(15,8), din(7,0)), 
         Vec(din(31,25), din(24,16), din(15,8), din(7,0)))) 
     return dout 
    } 
} 
+0

スタックにコードが到達する前にスタックが切れているようです。私は、スタック全体のトレースを取得する方法をsbtが教えてくれると信じています。スタックトレース全体で、または少なくともスタックトレース内のソースコードファイルの名前が表示されるまで表示することができますか? – jkoenig

+1

スタックトレースを更新しました。完全なスタックトレースを取得する方法を理解するために時間をかけました。申し訳ありません。 – isuru

答えて

3

これは、行番号とコードの多くを持っているのに役立つだろうが、形質MemOpConstantsの名前に基づいて、私はそれはいくつかのチゼルリテラルが含まれていることを推測します。コンパイラは、リテラルを要素として含むBundle MemReqを含んでいるため、MemPortIOからIOポートを作成することができないと不平を言っています。

IOポートは、リテラル、Reg's、Mem's、またはWireのものではなく、純粋な非結合Chiselデータ型のみを含むことができます。

IOポートで定数を使用できるようにするには、スロット(UInts)を定義し、それらのスロットを実際の定数/リテラル​​値まで配線する必要があります。定数をIOポート定義に配置しないでください。

+0

ありがとうございました。 MemOpConstantsの特性をコードに追加し、行番号を追加しようとします。しかし、あなたが見ることができるように、形質だけがビットタイプを使用します。 MemReqに幅の数値を入れてIOバンドルから定数を削除しようとしました。しかし、それは問題を解決しませんでした。 – isuru

1

MemOpConstantsのすべての定義は、ビットタイプのリテラル(定数)です。彼らは値と幅を持っています。値はそれらをリテラル(定数)にするものであり、IOポートの定義に含めるには不適切です。

+0

説明をありがとう。しかし、MemReqでM_X.getWidthを1に、MT_X.getWidthを3に置き換えた後でも例外が発生します。 – isuru

関連する問題