Arduino 2D array in header File Compiles for Sparkfun fails for teensy

CosmicAbyss

New member
So I wrote a program to display images from a 2d array to a small OLED. It compiles and runs fine for a sparkfun redboard but when I compile for a teensy I get some odd errors.

declaration is

const unsigned char _Logo[6][2048]{};

which produces no errors and works as intended when compiled for the sparkfun board. upon compilation for the teensy 4.1 I get the following errors.

LittleBuddy.h:477: error: section attribute not allowed for '_Logo' };

LittleBuddy.h:477: error: too many initializers for 'const unsigned char [6][2048]' LittleBuddy.h:477: error: array must be initialized with a brace-enclosed initializer

spits out the brace enclosed message a couple hundred times. then ends with the initial error of.

section attribute not allowed for '_Logo'

Once I change it to brace enclosed initialization like it asks the messages change to just

section attribute not allowed for '_Logo'

Confusing as it works for the board I'm familiar with and errors out for the other and some googling of the errors hasn't led me to much. Appreciate any responses I get as this is my first time posting here.

Side this is an edit of the original SSD1327 library from adafruit as it wouldnt play nice being used in my library so I just edited mine into it
 

Attachments

  • sketch_dec13a.ino
    411 bytes · Views: 28
  • LittleBuddy.h
    40 KB · Views: 31
  • LittleBuddy.cpp
    12.5 KB · Views: 27
If I open your files I see a different declaration of _Logo in LittleBuddy.h:
Code:
class LittleBuddy : public Adafruit_GrayOLED 
{
  // stuff....

  const unsigned char LittleBuddy::_Logo[6][2048] PROGMEM = {{
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, //snowflake BMP
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,

 //....
}

Disclaimer: I might be wrong and appreciate any correction.

You want to have a member of a class in a specific memory location (FLASH) which doesn't work. AFAIK the compiler needs to have class members in a consecutive region of the memory (MichaelMeissner can explain that better than I ). However, declaring and initializing a const class member doesn't make a lot of sense since each object of that class would have its own identical and unchangeable copy of it.
You probably meant to have this as static const member. In this case all objects would share the same constant. And, since static const members are stored outside the class objects you can place them in a different memory section.

Here what you need to do:

LittleBuddy.h:
Code:
class LittleBuddy : public Adafruit_GrayOLED 
{
  //....
  static const unsigned char _Logo[6][2048]; // only declaration, no definition of the contents here!
  //...

LittleBuddy.cpp:
Code:
const unsigned char LittleBuddy::_Logo[6][2048] PROGMEM = {{
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, //snowflake BMP
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  //...
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00},// <<--------
  {                                                                                               // <<--------------  
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0xe0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, //slippery road 1
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x3f, 0xfc, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  //...

You can check if it works by printing the address of _Logo in setup():
Code:
void setup()
{
    while (!Serial) {}
    Serial.printf("Address of display: %p  Address of _LOGO %p\n", &display, &display._Logo[0][0]);

    // put your setup code here, to run once:
    display.setupScript();
    display.setHeightandWidth(128, 128);
    display.setXandYbegin(0, 0);
}

Which prints:
Code:
Address of display: 0x200020c8  Address of _LOGO 0x60001f40
intial com serial
com failed

So, your display lives in RAM and your _LOGO in FLASH (starts at 0x6000'0000).

If you remove the PROGMEM, both are placed into RAM
Code:
Address of display: 0x200050c8  Address of _LOGO 0x20000874
intial com serial
com failed
 
All good and compiled now thank you. But I have introduced a new problem it seems everything else work other than when I draw the animation from the draw animation function, Could this be because I am now using DMAMEM?

update I tried it without DMAMEM and it displayed properly thats so weird I thought i read it was for storing large array's. Sorry brand new to the teensy platform and have just started coding outside of an academic environment.
 
Sorry maybe hard to know without seeing more code... Did not notice anywhere where you are using dmamem... so probably something new.

DMAMEM memory is a little different than the other main memory (DTCM) in that it is slower and as such there is hardware cache that speeds things up. There is also interesting details of caching and using dma operations.
But again not sure where you might be using DMA...
 
Back
Top