Ejecución desde RAM en sistemas Embebidos

Requisito previo: memoria de acceso aleatorio (RAM) , introducción de sistemas integrados

Introducción:
a diferencia de los programas de aplicación en las computadoras, el software en los sistemas integrados no se ejecuta desde la RAM. En la gran mayoría de las arquitecturas modernas de sistemas integrados, los programas (instrucciones) se almacenan en la memoria flash del microcontrolador (flash de código/flash de programa) y se ejecutan directamente en el lugar. Anteriormente, la ROM se usaba para el almacenamiento y la ejecución de programas. 
Debido a las tecnologías emergentes en los dispositivos de memoria, hoy en día se utiliza la memoria flash. La RAM es una memoria volátil y no contiene nada al reiniciar o apagar y encender. Se utiliza para almacenar datos y mantener el valor de las variables en tiempo de ejecución. Se puede desarrollar de forma segura un producto integrado almacenando y ejecutando el programa en código flash (usando la herramienta de descarga y el depurador). Los MCU tienen porciones dedicadas de espacio de memoria para código flash y RAM. Los mapas de memoria en microcontroladores avanzados contienen Flash de datos, DSPR, PSPR, ROM de arranque, EEPROM, memoria de depuración, etc. Para simplificar, consideraremos flash de código para almacenar y ejecutar los programas y RAM para almacenar las variables y los datos. Hay ciertas situaciones en las que se vuelve obligatorio ejecutar subrutinas desde la RAM. 
Este artículo cubre la necesidad de copiar una sección de código a la RAM, varias formas de implementarlo, sus ventajas y desventajas. Copiar a RAM significa alojar dos copias de código, una en flash y otra en RAM.

Figura 1. Mapa de memoria del microcontrolador

Necesidad de ejecución desde RAM:

  1. Durante la reprogramación de la memoria flash (funcionalidad del cargador de arranque), ciertas funciones se ejecutarán desde la RAM, como borrar la memoria flash del programa, escribir datos en la memoria flash del programa. El código no debe ejecutarse desde la misma memoria flash que se está borrando/programando. En algunos chips, la memoria flash se congela mientras se realizan las operaciones en la memoria flash. Por lo tanto, se requiere que la sección de código se coloque en la RAM y se ejecute.
  2. Durante la reprogramación de la memoria flash (funcionalidad del cargador de arranque), las direcciones de vector de interrupción y los ISR se colocarán y ejecutarán desde la RAM.
  3. Cargadores de arranque que se ejecutan desde la RAM. La forma más segura para la funcionalidad del cargador de arranque es recibir el archivo del cargador de arranque del dispositivo host y colocar el código completo en la RAM.
  4. La ejecución de programas desde la RAM es mucho más rápida que la ejecución desde la memoria flash, por ejemplo, colocar código de ejecución frecuente en la RAM para optimizar el tiempo.
  5. Algunos programadores en sistemas integrados crean tareas en la RAM que apuntan al programa en flash.
  6. Ejecute la aplicación desde la RAM mientras la operación flash está en curso.

Copie la sección de código y Ejecute desde la RAM:

1. Algunos controladores proporcionan una forma bastante sencilla de copiar un código a la RAM. Todo lo que necesita es revisar la string de herramientas y los manuales de usuario. Las diferentes formas se enumeran a continuación:

  • Algunos controladores proporcionan un atributo o una API o directivas de compilación para copiar código a la RAM.
  • En algunos controladores, el código de tiempo de ejecución de la rutina de inicio (que a su vez se ejecuta desde la memoria flash) copia los códigos de operación del programa de la memoria flash a la RAM según sea necesario, como lo hace con las variables inicializadas.
  • En algunos controladores, la actualización del script del enlazador sería suficiente para colocar la sección de código en la RAM. Pero debe haber algún código fuente que copie la sección de código a la RAM. En la mayoría de los casos, se realiza internamente mediante la rutina de inicio.

2. Función de copia a RAM –

  • El siguiente fragmento copia la función func_to_be_copied() en la RAM. dummy_endfunc() se encuentra al final de la función para determinar el tamaño de func_to_be_copied(). Asegúrese de que el compilador no optimice dummy_endfunc(). Las directivas del compilador como «#pragma» se pueden usar para evitar la optimización. Se puede llamar a ExecuteRamFunc() para ejecutar func_to_be_copied() desde la RAM.
     

C

// Global buffer stored in RAM and function is copied to this buffer 
unsigned char RAM_area[1024] 
void func_to_be_copied(void)
{
//piece of code
}
// No other function to be placed in between
// Make compiler settings for not to optimize dummy_endfunc
void dummy_endfunc(void)
{
    // No code
}
  
void CopyFlashFuncToRam(void)
{
   unsigned long int func_size = 0, cntr;
   unsigned char *dest_ptr;
   dest_ptr = (unsigned char *) func_to_be_copied ;  
   func_size = (unsigned long int)dummy_endfunc - (unsigned long int)func_to_be_copied;
   for(cntr = 0; cntr < func_size; cntr++)
   {
      RAM_area[cntr] = dest_ptr[cntr]; 
   }   
}
  
void ExecuteRamFunc(void)
{
   void(*func_ptr)(void) = (void(*)(void)) &RAM_area[0];
   func_ptr();  
}

3. El tamaño de la función también se puede calcular mediante el uso de la declaración de devolución que se puede colocar al final de func_to_be_copied(). Comience a copiar la función hasta que encuentre el código de operación de la declaración de devolución. Existe el riesgo de que los datos utilizados dentro de la función puedan ser los mismos que el código de operación de la declaración de devolución. Para esto, debe comprender los requisitos de alineación de las instrucciones consultando el manual del usuario.

4. Copie la sección de código a la RAM: 
considere que tiene un fragmento de código colocado en la memoria flash, por ejemplo, un código de cargador de arranque que debe ejecutarse desde la RAM. El tamaño del gestor de arranque debe conocerse bien de antemano. También se puede escribir un byte de firma al final del código del gestor de arranque mientras se descarga a la memoria flash para conocer el tamaño del código. Si no se conoce el tamaño del gestor de arranque, se puede considerar el tamaño de la sección asignada. La sección de código se puede copiar a la RAM de la misma manera que se explica en el punto no. (2). Asegúrese de que la RAM esté reservada en la secuencia de comandos del enlazador para usarla en la ejecución de instrucciones.

Al ejecutar desde la RAM, tenga en cuenta lo siguiente:

  • La RAM utilizada para la ejecución de instrucciones se reservará a través del script del enlazador o mediante la declaración del búfer global.
  • La dirección de inicio de la sección copiada debe conocerse para que el contador de programa pueda señalarse correctamente o ejecutarse apuntando el puntero de función a la dirección correcta.
  • La prueba de RAM se puede realizar en el momento del arranque para garantizar su corrección.

ventajas :

  1. Rendimiento: 
    optimización del tiempo si las rutinas críticas ejecutadas con frecuencia se colocan en la RAM. La ejecución de RAM es significativamente más rápida que flash.
  2. Disminución del consumo de energía:
    si toda la aplicación se ejecuta desde la RAM, se puede apagar la memoria flash.
  3. Por lo general, se requiere un direccionamiento corto si el código se ejecuta desde la RAM, es decir, se puede acceder a la RAM del controlador, se puede acceder a la memoria flash de datos o a la EEPROM mediante punteros cortos, mientras que si el código se ejecuta desde la memoria flash (las memorias flash suelen ser memorias grandes, cientos de KB a MB), necesitaría un direccionamiento largo. En direccionamiento corto, el ensamblador generalmente genera instrucciones como sjmp, acall, etc., que generalmente requieren una menor cantidad de ciclos de máquina.

Desventajas:

  1. La memoria RAM es un recurso escaso, caro y suele ser de un tamaño mucho menor en comparación con la memoria flash. Si el código no estático se coloca en la RAM, se desperdicia espacio en la RAM, lo que limita el uso de datos variables.
  2. Alojamiento de la misma rutina en dos lugares, uno en flash y otro en RAM.
  3. La depuración de código en RAM es difícil. La depuración se puede hacer en el desmontaje. Los archivos ELF generalmente se usan para la depuración que contiene información de depuración, tablas de símbolos, etc. Si el código se mueve a otro lugar, no puede ver los símbolos en el depurador, pero las instrucciones que se ejecutan en la ventana de desensamblaje se pueden ver y depurar.
  4. A veces, la ejecución desde la RAM da como resultado una falla grave inesperada. Por lo tanto, se recomienda ejecutar primero desde flash, probar la funcionalidad y luego volver a ejecutar desde RAM.

Publicación traducida automáticamente

Artículo escrito por ashishmadgundi1 y traducido por Barcelona Geeks. The original can be accessed here. Licence: CCBY-SA

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *