¿Funciona correctamente la lectura y escritura de doble banco en STM32L071?

1

Estoy intentando reprogramar el NVM (flash bank 2) mientras ejecuto el código del flash bank 1 en el microcontrolador STM32L071CB.

Como indican AN4808 y AN4767, "la interfaz de memoria es capaz de leer ambos bancos en paralelo, o leer un banco mientras escribe al otro ...", pero estoy experimentando algunos problemas :

  1. La depuración muestra que el bit FWWERR aumenta en el registro de estado de flash durante la operación de escritura de media página del banco de flash 2. Significa que se ha detenido la escritura del flash bank 2 debido a la obtención de código.
  2. El borrado del banco 2 por el código del banco 1 funciona correctamente.
  3. Escribir con el banco 2 de palabras por código en el banco 1 parece funcionar correctamente (pero tengo dudas de que solo sea una coincidencia).
  4. La escritura de media página termina con el bit FWWERR establecido en FLASH_SR y los ceros en la memoria que estoy intentando escribir.

Sé que me estoy perdiendo algo, pero no puedo descubrir qué es. Tal vez alguien tuvo un problema similar? Estoy empezando a pensar que hay algo mal con el microcontrolador (la hoja de erratas señala algunos problemas con el mecanismo de cambio de banco doble, pero no debería ser un problema en mi caso, porque no estoy cambiando de banco en este momento).

Mi función funciona correctamente cuando se ejecuta desde la memoria RAM, pero prefiero que se ejecute desde el banco flash 1.

La función (1) a continuación es responsable de escribir medias páginas. El código (2) muestra la forma en que estoy llamando (2).

(1)

void nvm_prog_write_halfpages(uint32_t* addr, uint32_t* data, uint32_t length){

    // There can't be any previous alignment errors in the flash SR
    if ((FLASH->SR & FLASH_SR_PGAERR_Msk) == FLASH_SR_PGAERR){
         FLASH->SR = FLASH_SR_PGAERR; // clear any previous alignment errors
    }

    // Check if any operation was stopped previously due to code fetching
    if ((FLASH->SR & FLASH_SR_FWWERR_Msk) == FLASH_SR_FWWERR){
        FLASH->SR = FLASH_SR_FWWERR; // clear any previous fetch related errors
    }

    nvm_prog_unlock();

    FLASH->PECR |= FLASH_PECR_PROG | FLASH_PECR_FPRG;

    uint32_t cnt = 0;
    while (length > 0){
        *addr = *data; // Destination address will be increased by the hardware automatically
        data++;
        cnt++;

        // When a half-page has been written
        if (cnt == 16){
            while ((FLASH->SR & FLASH_SR_BSY_Msk) == FLASH_SR_BSY)
                ;
            cnt = 0;
            addr += 16; // Write the next half-page
            length--;
        }
    }

    FLASH->PECR &= ~(FLASH_PECR_PROG | FLASH_PECR_FPRG);

    nvm_prog_lock();
}

(2)

nvm_prog_erase_page((uint32_t *) 0x08010000); // Erase flash bank 2; it starts at 0x08010000

uint32_t dummydata[32], i;
for (i=0; i<32; i++){
    dummydata[i] = i;
}

nvm_prog_write_halfpages((uint32_t *) 0x08010000, &dummydata[0], 2); // Write 2 half-pages at the beginning of flash bank 2
    
pregunta mac

1 respuesta

1

La lectura mientras se escribe tiene alguna limitación en caso de una operación de programación múltiple. Consulte RM0377 § 3.3.4 Escribir / borrar el NVM - Programar media página en la memoria del programa Flash página 82:

  

Cuando se inicia una operación de media página, la interfaz de memoria espera 16 direcciones / datos, anulando (con un fallo grave) todos los accesos de lectura que no son de búsqueda (consulte Recuperación y búsqueda previa). Una búsqueda detiene la operación de media página. El contenido de la memoria permanece sin cambios, el error FWWERR se establece en el registro FLASH_SR.

Esto significa que no se permite ninguna operación de recuperación en el flash mientras se alimenta la interfaz de memoria con las 16 palabras (independientemente del código que se ejecute en el banco 1 y la programación de media página se realiza en el banco 2). Una vez que se han enviado las 16 palabras a la interfaz de memoria, puede reanudar la ejecución desde la memoria flash, es decir, durante la escritura física de los datos dentro del banco flash (suponiendo que su código se esté ejecutando en el otro banco).

En pocas palabras, debe ejecutar desde la SRAM la alimentación de la interfaz de memoria con las 16 palabras y asegurarse de que las interrupciones no causen recuperación en la memoria flash (ya sea enmascarar todas las interrupciones o reubicar los controladores de interrupciones y el vector de interrupciones en la SRAM) .

Nota: no hay tal limitación en el caso de una operación de programación única.

    
respondido por el Bruno

Lea otras preguntas en las etiquetas