SystemVerilog incluyó una serie de nuevas funciones destinadas a mejorar la productividad de la verificación y las más importantes probablemente son:
- Programación orientada a objetos
- Comandancia restringida
La verificación funcional en simulación es completamente un problema de software, por lo que al incluir clases, la comunidad de verificación adquirió todas las ganancias de productividad de la programación OO tradicional (aunque desde hace unos 10 años, la falta de reflexión y los límites de introspección significan que las bibliotecas escritas en SystemVerilog, como UVM, dependen en gran medida del preprocesador en lugar del lenguaje en sí).
Al agregar una asignación aleatoria restringida, el lenguaje exige que los simuladores que cumplen con los requisitos deben proporcionar un solucionador de restricciones. Esto permite que el espacio de prueba sea definido por un conjunto de reglas y que el simulador genere secuencias de prueba. Una analogía clásica sería Sudoku, al definir el problema en términos de restricciones, el simulador puede resolver el problema en lugar de que el ingeniero de verificación tenga que pensar en estímulos para ejercer el DUT. Por lo general, esto hace posible detectar casos de esquina que podrían haberse perdido con las pruebas dirigidas.
Otra mejora en SystemVerilog fue la capa DPI, que facilita la interfaz a idiomas externos.
SystemC es una bestia ligeramente diferente: puede usarse para modelar, interactuar con otros idiomas, síntesis de alto nivel, etc.
Usted pidió una comparación de código; Utilizo Python para la verificación, por lo que no tengo ningún buen ejemplo de Sistema [C | Verilog], pero Python es un OOP y, por lo tanto, este ejemplo podría ser útil.
Desde un banco de pruebas que creé del codificador JPEG de OpenCores:
def compare(i1, i2):
"""
Compare the similarity of two images
From http://rosettacode.org/wiki/Percentage_difference_between_images
"""
assert i1.mode == i2.mode, "Different kinds of images."
assert i1.size == i2.size, "Different sizes."
pairs = izip(i1.getdata(), i2.getdata())
dif = sum(abs(c1-c2) for p1,p2 in pairs for c1,c2 in zip(p1,p2))
ncomponents = i1.size[0] * i1.size[1] * 3
return (dif / 255.0 * 100) / ncomponents
@cocotb.coroutine
def process_image(dut, filename="", debug=False, threshold=0.22):
"""Run an image file through the jpeg encoder and compare the result"""
cocotb.fork(Clock(dut.clk, 100).start())
driver = ImageDriver(dut)
monitor = JpegMonitor(dut)
stimulus = Image.open(filename)
yield driver.send(stimulus)
output = yield monitor.wait_for_recv()
if debug: output.save(filename + "_process.jpg")
difference = compare(stimulus, output)
dut.log.info("Compressed image differs to original by %f%%" % (difference))
if difference > threshold:
raise TestFailure("Resulting image file was too different (%f > %f)" %
(difference, threshold))
Puede ver que el uso de un banco de pruebas estructurado y OOP hace que este código sea muy comprensible y rápido de crear. Había un puro verilog testbench para este bloque y aunque no tiene la misma El nivel de funcionalidad de la comparación sigue siendo interesante.