PIC16: Fuera del espacio de datos - Hacer uso de todos los bancos disponibles

1

Estoy usando un Microchip PIC16F1825 con el compilador XC8 (v1.12) y definiendo algunas matrices (tamaño entre 16 y 64 bytes). Pude declararlos (salida del enlazador a continuación). Sin embargo, tan pronto como intento acceder a algunos de ellos en un bucle for, me aparece un error en la compilación:

error: could not find space (32 bytes) for variable _tempMeasurements
(908) exit status = 1

Cuantos más arreglos intento acceder, más aumenta el uso del espacio de datos. ¿Cómo puedo evitar quedarme sin memoria? Claramente, no se utilizan todos los bancos.

Memory Class Usage:

Program space:
    CONST                used     0h (     0) of  2000h words   (  0.0%)
    CODE                 used   B8Dh (  2957) of  2000h words   ( 36.1%)
    STRCODE              used     0h (     0) of  2000h words   (  0.0%)
    ENTRY                used     0h (     0) of  2000h words   (  0.0%)
    STRING               used     5h (     5) of  2000h words   (  0.1%)

Data space:
    COMMON               used     Eh (    14) of    10h bytes   ( 87.5%)
    BANK0                used    4Fh (    79) of    50h bytes   ( 98.8%)
    BANK1                used    4Eh (    78) of    50h bytes   ( 97.5%)
    BANK2                used    4Ah (    74) of    50h bytes   ( 92.5%)
    BANK3                used    50h (    80) of    50h bytes   (100.0%)
    BANK4                used    40h (    64) of    50h bytes   ( 80.0%)
    BANK5                used    40h (    64) of    50h bytes   ( 80.0%)
    BANK6                used    40h (    64) of    50h bytes   ( 80.0%)
    BANK7                used    40h (    64) of    50h bytes   ( 80.0%)
    BANK8                used     0h (     0) of    50h bytes   (  0.0%)
    BANK9                used     0h (     0) of    50h bytes   (  0.0%)
    BANK10               used     0h (     0) of    50h bytes   (  0.0%)
    BANK11               used     0h (     0) of    50h bytes   (  0.0%)
    BANK12               used     0h (     0) of    30h bytes   (  0.0%)
    ABS1                 used   16Ah (   362) of   400h bytes   ( 35.4%)

EEPROM space:
    EEDATA               used     0h (     0) of   100h bytes   (  0.0%)

Configuration bits:
    CONFIG               used     2h (     2) of     2h words   (100.0%)

ID Location space:
    IDLOC                used     0h (     0) of     4h words   (  0.0%)


Memory Summary:
    Program space        used   B92h (  2962) of  2000h words   ( 36.2%)
    Data space           used   3AFh (   943) of   400h bytes   ( 92.1%)
    EEPROM space         used     0h (     0) of   100h bytes   (  0.0%)
    Configuration bits   used     2h (     2) of     2h words   (100.0%)
    ID Location space    used     0h (     0) of     4h bytes   (  0.0%)
    
pregunta Norbert

1 respuesta

2

Los accesos directos consecutivos a variables en el mismo banco serán más rápidos que los accesos directos a variables en diferentes bancos. En consecuencia, el compilador probablemente está tratando de consolidar las variables a las que se accede cerca una de la otra para que se coloquen en el mismo banco. Desafortunadamente, puede estar intentando consolidar más variables de las que realmente caben en un banco.

No estoy familiarizado con el compilador en particular que estás usando; en algunos compiladores, las variables solo se consolidarán si su definición primaria (no externa) está en el mismo archivo fuente. Mover algunas matrices a archivos de origen compilados por separado puede impedir que el compilador intente consolidarlos. Alternativamente, puede ser útil tener algunos arreglos a los que solo se accede mediante rutinas que se usan especialmente para ese propósito. Por ejemplo, tener un archivo fuente que sea algo como:

static unsigned short foo[32];

unsigned short get_foo(unsigned char addr)
{
  return foo[addr];
}
void put_foo(unsigned char addr, unsigned short value)
{
  foo[addr] = value;
}

Tenga en cuenta que si utiliza este enfoque, es posible que pueda trabajar con matrices que son demasiado grandes para caber en una sola página, usando algo como:

static unsigned short foo0[32],foo1[32];

unsigned short get_foo(unsigned char addr)
{
  if (addr & 32)
    return foo0[addr];
  else
    return foo1[addr-32];
}
void put_foo(unsigned char addr, unsigned short value)
{
  if (addr & 32)
    foo0[addr] = value;
  else
    foo1[addr-32] = value;
}

Tales cosas no son hermosas, pero pueden guardar código en comparación con algunas de las otras técnicas que de otro modo serían necesarias.

    
respondido por el supercat

Lea otras preguntas en las etiquetas