ภาษาการเขียนโปรแกรม Chisel

ภาษา Chisel

ภาพรวมของ Chisel

Chisel (Constructing Hardware In a Scala Embedded Language) เป็นภาษาสำหรับการสร้างฮาร์ดแวร์ที่ช่วยอำนวยความสะดวกในการออกแบบและตรวจสอบฮาร์ดแวร์ มันถูกสร้างขึ้นบนพื้นฐานของภาษาโปรแกรม Scala โดยใช้ความสามารถในการแสดงออกและการเขียนโปรแกรมเชิงฟังก์ชันเพื่อให้ผู้ออกแบบสามารถสร้างการออกแบบฮาร์ดแวร์ที่ซับซ้อนได้อย่างง่ายดาย Chisel ถูกใช้เป็นหลักในการพัฒนาวงจรดิจิทัล โดยเฉพาะในด้านการออกแบบ FPGA และ ASIC

ด้านประวัติศาสตร์

การสร้างและการพัฒนาในช่วงแรก

Chisel ถูกพัฒนาขึ้นเป็นโครงการวิจัยที่มหาวิทยาลัยแคลิฟอร์เนีย เบิร์กลีย์ ภายใต้การสนับสนุนของกลุ่มวิจัยสถาปัตยกรรมเบิร์กลีย์ แรงจูงใจในการสร้าง Chisel คือการให้วิธีการออกแบบฮาร์ดแวร์ที่มีประสิทธิภาพและผลิตผลมากกว่าภาษาอธิบายฮาร์ดแวร์แบบดั้งเดิม (HDLs) เช่น Verilog หรือ VHDL โดยการฝังการออกแบบฮาร์ดแวร์ภายในภาษาโปรแกรมระดับสูง Chisel มุ่งหวังที่จะเสนอการทำให้เป็นนามธรรมที่ดีกว่า โครงสร้างระดับสูง และการนำโค้ดกลับมาใช้ใหม่

การพัฒนาและสถานะปัจจุบัน

ตั้งแต่เริ่มต้น Chisel ได้รับความนิยมในสภาพแวดล้อมทางวิชาการและอุตสาหกรรม ภาษาได้พัฒนาขึ้นด้วยการมีส่วนร่วมจากนักพัฒนาหลายคน นำไปสู่การปรับปรุงในฟีเจอร์ ไลบรารี และความสามารถในการใช้งาน การรวมเข้ากับ Scala ทำให้ผู้ออกแบบสามารถใช้ฟีเจอร์ที่ทรงพลัง เช่น การเขียนโปรแกรมเชิงฟังก์ชัน ความปลอดภัยของประเภท และไลบรารีการรวบรวมขั้นสูง Chisel ปัจจุบันถูกใช้กันอย่างแพร่หลายในโครงการพัฒนาฮาร์ดแวร์สมัยใหม่ ตั้งแต่การวิจัยทางวิชาการไปจนถึงผลิตภัณฑ์เชิงพาณิชย์

ความสัมพันธ์กับภาษาและแพลตฟอร์มอื่น ๆ

Chisel ได้รับแรงบันดาลใจจาก HDLs เช่น Verilog และ VHDL โดยยืมแนวคิดหลักของพวกเขาในขณะที่เสริมด้วยพาราไดม์การเขียนโปรแกรมจาก Scala นอกจากนี้ยังมีความสัมพันธ์ใกล้ชิดกับกรอบการสร้างฮาร์ดแวร์อื่น ๆ เช่น SpinalHDL ซึ่งมุ่งเน้นที่ผลิตภาพและความสามารถในการแสดงออกเช่นเดียวกัน การออกแบบ Chisel สามารถแปลงเป็น Verilog ได้ ทำให้สามารถใช้เครื่องมือและกระบวนการสังเคราะห์ที่มีอยู่ได้

ฟีเจอร์ของไวยากรณ์

DSL ที่ฝังอยู่

Chisel มี Domain-Specific Language (DSL) ที่ฝังอยู่ภายใน Scala ซึ่งช่วยให้ผู้ออกแบบฮาร์ดแวร์สามารถใช้ไวยากรณ์ของ Scala ในการอธิบายฮาร์ดแวร์ ตัวอย่างเช่น การกำหนด multiplexer แบบ 2 ขาอย่างง่ายสามารถแสดงได้ดังนี้:

class SimpleMux extends Module {
    val io = IO(new Bundle {
        val a = Input(Bool())
        val b = Input(Bool())
        val sel = Input(Bool())
        val out = Output(Bool())
    })
    
    io.out := Mux(io.sel, io.b, io.a)
}

ประเภทและความกว้างของบิต

Chisel รองรับประเภทที่หลากหลายและอนุญาตให้ผู้ออกแบบระบุความกว้างของบิตอย่างชัดเจน ซึ่งช่วยให้ควบคุมการใช้ทรัพยากรฮาร์ดแวร์ได้ดียิ่งขึ้น ตัวอย่างเช่น:

val myWire = Wire(UInt(8.W)) // จำนวนเต็มไม่ติดลบ 8 บิต

การทำให้เป็นนามธรรมของส่วนประกอบฮาร์ดแวร์

ภาษาเสนอการทำให้เป็นนามธรรมสำหรับส่วนประกอบฮาร์ดแวร์ทั่วไป ตัวอย่างเช่น การสร้างรีจิสเตอร์อย่างง่าย:

val reg = RegInit(0.U(8.W)) // รีจิสเตอร์ 8 บิตที่เริ่มต้นที่ 0

โมดูลที่มีพารามิเตอร์

Chisel อนุญาตให้สร้างโมดูลที่มีพารามิเตอร์ ซึ่งช่วยให้การออกแบบสามารถนำกลับมาใช้ใหม่ได้ด้วยการกำหนดค่าที่แตกต่างกัน:

class ParamModule(val size: Int) extends Module {
    val io = IO(new Bundle {
        val input = Input(UInt(size.W))
        val output = Output(UInt(size.W))
    })
    
    io.output := io.input + 1.U
}

นิพจน์เงื่อนไข

Chisel รองรับนิพจน์เงื่อนไขเพื่ออำนวยความสะดวกในการสร้างตรรกะฮาร์ดแวร์ที่ซับซ้อน:

val result = Mux(condition, trueValue, falseValue) // Multiplexer

ตัวสร้างฮาร์ดแวร์

สร้างส่วนประกอบฮาร์ดแวร์แบบโมดูลาร์โดยใช้ฟังก์ชันระดับสูงเพื่อสร้างการกำหนดค่าฮาร์ดแวร์:

def makeAdder(n: Int) = new Module {
    val io = IO(new Bundle {
        val a = Input(UInt(n.W))
        val b = Input(UInt(n.W))
        val sum = Output(UInt(n.W))
    })
    io.sum := io.a + io.b
}

ยูทิลิตี้การรวบรวม

Chisel อนุญาตให้ใช้ยูทิลิตี้การรวบรวมของ Scala เพื่อจัดการกับองค์ประกอบฮาร์ดแวร์ได้อย่างมีประสิทธิภาพ:

val wires = VecInit(Seq.fill(4)(Wire(UInt(8.W)))) // สร้างเวกเตอร์ของสาย 4 เส้น

ลอจิกเชิงลำดับ

ลอจิกเชิงลำดับถูกแสดงอย่างง่ายดายโดยใช้โครงสร้างเฉพาะของ Chisel เช่น รีจิสเตอร์:

when(condition) {
    reg := newValue
} .otherwise {
    reg := oldValue
}

เฟรมเวิร์กการทดสอบในตัว

Chisel รวมเข้ากับ ScalaTest ซึ่งช่วยให้นักพัฒนาสามารถเขียนการทดสอบสำหรับการออกแบบฮาร์ดแวร์ของตนได้อย่างเป็นธรรมชาติ:

class MyModuleTester extends PeekPokeTester(new MyModule) {
    poke(dut.a, 1)
    poke(dut.b, 0)
    expect(dut.out, 1)
}

การเชื่อมโยงวิธีการ

Chisel รองรับการเชื่อมโยงวิธีการ ซึ่งช่วยให้การกำหนดวงจรฮาร์ดแวร์ที่ซับซ้อนมีความกระชับและอ่านง่าย:

val result = (a + b).asUInt + c

เครื่องมือและเวลาทำงานสำหรับนักพัฒนา

IDEs และคอมไพเลอร์

Chisel สามารถพัฒนาได้โดยใช้ IDE ใด ๆ ที่รองรับ Scala เช่น IntelliJ IDEA พร้อมปลั๊กอิน Scala นอกจากนี้ sbt (Scala Build Tool) มักถูกใช้เพื่อจัดการโครงการและการพึ่งพา รวมถึงการคอมไพล์โครงการ Chisel เป็นโค้ด Verilog

การสร้างโครงการ

ในการสร้างโครงการ Chisel คุณสามารถตั้งค่าโครงสร้างโครงการ sbt มาตรฐาน ไฟล์ build.sbt ที่ง่ายอาจมีลักษณะดังนี้:

name := "MyChiselProject"
version := "0.1"
scalaVersion := "2.12.10"

libraryDependencies += "edu.berkeley.cs" %% "chisel3" % "3.4.4"

ในการสร้าง คุณจะรัน sbt run จากบรรทัดคำสั่งและไฟล์ Verilog ที่สร้างขึ้นจะถูกสร้างในไดเรกทอรีเป้าหมาย

การใช้งาน

Chisel ถูกใช้เป็นหลักในการออกแบบและตรวจสอบฮาร์ดแวร์ดิจิทัล มันมีการใช้งานในด้านต่าง ๆ เช่น:

การเปรียบเทียบกับภาษาอื่น ๆ

Chisel แตกต่างจาก HDLs แบบดั้งเดิม เช่น Verilog และ VHDL โดยเสนอฟีเจอร์ที่พบในภาษาการเขียนโปรแกรมระดับสูง เช่น การเขียนโปรแกรมเชิงฟังก์ชัน ความปลอดภัยของประเภท และการทำให้เป็นนามธรรมในระดับสูง

เมื่อเปรียบเทียบกับภาษาอื่น ๆ:

เคล็ดลับการแปลจากแหล่งข้อมูลสู่แหล่งข้อมูล

สำหรับการแปล Chisel ไปยังภาษาอธิบายฮาร์ดแวร์อื่น ๆ เครื่องมือเช่นคอมไพเลอร์ Chisel สามารถสร้าง Verilog โดยตรงจากโค้ด Chisel ไม่มีเครื่องมือการแปลจากแหล่งข้อมูลสู่แหล่งข้อมูลที่รู้จักกันดีที่แปลง Chisel โดยตรงไปยัง HDL อื่น ๆ แต่ Verilog ที่สร้างขึ้นสามารถปรับเปลี่ยนด้วยตนเองได้หากจำเป็น

เครื่องมือการแปลจากแหล่งข้อมูลสู่แหล่งข้อมูลที่มีอยู่

ในปัจจุบัน เครื่องมือที่ได้รับการยอมรับมากที่สุดคือชุดเครื่องมือ Chisel เอง ซึ่งช่วยให้ผู้ใช้สามารถคอมไพล์การออกแบบ Chisel เป็นโค้ด Verilog ที่สามารถสังเคราะห์ได้ นอกจากนี้ยังมีความพยายามในการรวม Chisel เข้ากับกรอบฮาร์ดแวร์อื่น ๆ ผ่านไลบรารีและเครื่องมือต่าง ๆ เพื่อส่งเสริมความร่วมมือและการทำงานร่วมกันระหว่างวิธีการออกแบบฮาร์ดแวร์ที่แตกต่างกัน