es.davy.ai

Preguntas y respuestas de programación confiables

¿Tienes una pregunta?

Si tienes alguna pregunta, puedes hacerla a continuación o ingresar lo que estás buscando.

Cincele el valor persistente en el modulo hasta una nueva escritura.

He creado un módulo básico destinado a representar una unidad de memoria en Chisel3:

class MemristorCellBundle() extends Bundle {
    val writeBus = Input(UInt(1.W))
    val dataBus = Input(UInt(8.W))
    val cellBus = Output(UInt(8.W))
}

class MemCell() extends Module {
    val io = IO(new MemCellBundle())

    val write = Wire(UInt())
    write := io.voltageBus

    val internalValue = Reg(UInt())
    // Más del 50% del voltaje total en (255).
    when(write === 1.U) {
        internalValue := io.dataBus
        io.cellBus := io.dataBus
    } .otherwise {
        io.cellBus := internalValue
    }
}

Lo que quiero es que produzca el valor internalValue cuando el bus de escritura (write) sea lógico BAJO, y que cambie este valor con un lógico ALTO. Mi comprensión de Chisel es que el registro puede persistir este internalValue entre ciclos de reloj, de modo que esto actúa básicamente como una sola unidad de memoria.

Lo estoy haciendo de esta manera como parte de un proyecto más grande. Sin embargo, al escribir una prueba unitaria, descubro que el escenario de “lectura después de escritura” falla.

class MemCellTest extends FlatSpec with ChiselScalatestTester with Matchers {
    behavior of "MemCell"
    it should "read and write" in {
        test(new MemCell()) { c =>
            c.io.dataBus.poke(5.U)
            c.io.write.poke(0.U)
            c.io.cellBus.expect(0.U)
            // Escribir
            c.io.dataBus.poke(5.U)
            c.io.write.poke(1.U)
            c.io.cellBus.expect(5.U)
            // Verificar lectura después de escritura
            c.io.dataBus.poke(12.U)
            c.io.write.poke(0.U)
            c.io.cellBus.expect(5.U)
        }
    }
}

Las dos primeras expectativas funcionan tal como esperaría. Sin embargo, cuando intento leer después de escribir, el cellBus vuelve a 0 en lugar de persistir el 5 que había escrito anteriormente.

test MemCell Success: 0 tests passed in 1 cycles in 0.035654 seconds 28.05 Hz

MemCellTest:

MemCell

- should read and write *** FAILED ***

io_cellBus=0 (0x0) did not equal expected=5 (0x5) (lines in MyTest.scala: 10) (MyTest.scala:21)

Claramente, el registro no está manteniendo este valor, por lo que internalValue vuelve a 0. Pero, ¿por qué sucede esto y cómo se podría crear un valor que pueda persistir?

Tags:  ,

Answer

  1. Avatar for davy.ai

    El problema con la implementación actual es que write se está asignando a io.voltageBus, que no ha sido definido en MemristorCellBundle. En su lugar, debería ser asignado a io.writeBus, que está definido en el paquete.

    Además, la sentencia when debería estar comprobando si write es igual a lógico HIGH (1.U), en lugar de lógico LOW (0.U). Esto se debe a que el valor de write se está utilizando para determinar si actualizar o no internalValue.

    Aquí está la implementación corregida:

    class MemristorCellBundle() extends Bundle {
        val writeBus = Input(UInt(1.W))
        val dataBus = Input(UInt(8.W))
        val cellBus = Output(UInt(8.W))
    }
    
    class MemCell() extends Module {
        val io = IO(new MemristorCellBundle())
    
        val write = Wire(UInt())
        write := io.writeBus
    
        val internalValue = RegInit(0.U(8.W))
        // More than 50% of total voltage in (255).
        when(write === 1.U) {
            internalValue := io.dataBus
            io.cellBus := io.dataBus
        } .otherwise {
            io.cellBus := internalValue
        }
    }
    

    Tenga en cuenta que internalValue también se ha inicializado con un valor predeterminado de 0.U utilizando RegInit, lo que debería evitar que se revierta a 0 inesperadamente.

    Con estos cambios, MemCellTest debería aprobarse correctamente.

Comments are closed.