Electronic – AVR GCC : Global / Static Array not getting initialized properly

avravr-gcccgccmicrocontroller

Im having problem with global arrays in my C code. What i am trying to do is to use a display buffer (array of 8 uint8_t with each uint8_t representing a row) to light up the leds in 8×8 led matrix using column scanning.

the relevant part of code is:

#include <avr/io.h> 
#include <util/delay.h> 
#include <stdlib.h> 
#include <avr/interrupt.h> 

uint8_t string_size=3;               //DISPLAY STRING SIZE 
uint8_t display_string[8][3];         //DISPLAY STRING 
uint8_t display_buffer[8];            //CURRENT DISPLAY BUFFER 

/***************************************** 
CHARACTER MAPS 
*****************************************/ 
uint8_t h[8]= { 
0b11111111, 
0b10000001, 
0b10100101, 
0b10100101, 
0b10111101, 
0b10100101, 
0b10000001, 
0b11111111 
}; 

uint8_t o[8]= { 
0b11111111, 
0b10000001, 
0b10111101, 
0b10100101, 
0b10100101, 
0b10111101, 
0b10000001, 
0b11111111 
}; 

uint8_t t[8]= { 
0b11111111, 
0b10000001, 
0b10111101, 
0b10011001, 
0b10011001, 
0b10011001, 
0b10000001, 
0b11111111 
}; 

/***************************************** 
FUNCTIONS 
*****************************************/ 
void addCharToString(uint8_t pos, uint8_t chr[]);   //ADD PASSSED CHAR TO SPECIFIED POS IN STRING 
void setupDisplayBuffer();                     //SETUP INITIAL DISPLAY BUFFER 
void writeDisplayBuffer();                     //DRAW CURRENT DISPLAY BUFFER 


int main() 
{ 

   addCharToString(0,h); 
   addCharToString(1,o); 
   addCharToString(2,t); 
   setupDisplayBuffer(); 

   for(;;) 
   { 
      writeDisplayBuffer(); 
   } 
} 

void addCharToString(uint8_t pos, uint8_t arr[]) 
{ 
   for(uint8_t i=0;i<8;i++) 
   { 
      //display_string[i][pos] = arr[i]; //PROBLEM HERE! 
      display_string[i][pos] = 0b10000001; 
   } 

} 
void setupDisplayBuffer()
{
    //COPY THE FIRST CHARACTER FROM DISPLAY STRING TO DISPLAY BUFFER
    for(uint8_t i=0;i<8;i++)
    {
        display_buffer[i] = display_string[i][0];
    }
}

void writeDisplayBuffer()
{
    for(uint8_t i=0;i<8;i++)
    {
        write595(display_buffer[i]);
        set2903Pin(i);
        _delay_loop_2(1986); // ACCURATE 1MS DELAY .. HIGHER THAN THIS = FLICKERING
    }
}

When I run it I see the whole column light up (whole 8×8 grid lid up with scanning) and it seems the problem is happening in the line

display_string[i][pos] = arr[i];

in addCharToString(). if i comment out this line and use a constant value (0b10000001) in the above code it gets displayed perfectly (first and the last column lighting up)

It seems that the array(s) h, o and t are not getting initialized properly. Any ideas what could be happening here

I am using ATMEGA8.

Update:

I am using -0s optimization with the following flags set

  • funsigned-chars
  • funsigned-bitfields
  • fpack-struct
  • fshort-enums

Best Answer

Found the solution. As suggested by members at avrfreaks.net here the problem was that by using the default makefile the .data part of code was not getting included in the final hex file. as a result the ram was getting initialized by default value (0xFF) since it could not find the array values (in the .data part). Using a custom makefile with the flag -j .data in avr-objcopy solved the problem.