Bad value in all my constants; Flash locked?

cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 

Bad value in all my constants; Flash locked?

963 Views
sblanco
Contributor I

Hello there,

 

I am slowly transitioning to Freescale MCUs and right now I am working on my first prototype with a DEMO9S08QG8 board (MC9S08QG8 MCU). Up until now I had no major problems but now I am having a problem I can't seem to solve.

 

I am creating a little menu system for 2x16 LCD and for that I am trying to create some non volatile structures in FLASH memory (constants that will be flashed along the application code).

 

struct parameter;

struct menu;

struct menu_item;


typedef struct parameter

{

    int* storage;

    char* title;

    byte type;

    int min_range;

    int max_range;

    char* options[3];

}parameter;

 

typedef struct menu_item

{

    byte type;

    struct menu* menu;

    parameter* param;

}menu_item;

 

typedef struct menu

{

    char* title;

    byte current_item;

    byte num_elements;

    menu_item* items[10];

}menu;

 

Initialization of constants:

 

extern int opc1 @0xFF00;

extern int opc2 @0xFF02;

extern int opc3 @0xFF04;


const parameter option1 ={

    &opc1,

    "Option 1",

    PARAMETER_TYPE_YESNO

};

 

const parameter option2 =

{

    &opc2,

    "Option 2",

    PARAMETER_TYPE_RANGE,

    10,

    50

};

 

const parameter option3 =

{

    &opc3,

    "Opcion 3",

    PARAMETER_TYPE_OPTIONS,

    0,

    0,

    {"Yes","No","Maybe"}

};

 

const menu_item submenu1_1 =

{

    MENU_ITEM_PARAMETER,

    0,

    &opcion1

};

 

const menu_item submenu1_2 =

{

    MENU_ITEM_PARAMETER,

    0,

    &opcion2

};

 

const menu_item submenu1_3 =

{

    MENU_ITEM_PARAMETER,

    0,

    &opcion3

};

 

const menu_item* submenu1[3] =

{

    &submenu1_1,

    &submenu1_2,

    &submenu1_3

};

 

const menu menu_ppal;

 

const menu_item submenu2_1 =

{

    MENU_ITEM_SUBMENU,

    &menu_ppal

};

 

const menu_item* submenu2[3] ={

    &submenu1_2,

    &submenu1_3,

    &submenu2_1

};

 

const menu_item* menu_ppal_elements[2] = {

    &submenu1,

    &submenu2,

};

 

const menu menu_ppal ={

    "Main menu",

    0,

    2,

    menu_ppal_elements,

};

 

Note: My first version used unions to optimize memory size but I can't initialize const structs with unions.

Note2: This code resides in a menu.c, with the declarations for other modules in the menu.h header file

Note3: This is just an example to show how I declare and initialize the structs.

 

The thing is when I run/debug the application and inspect the constants they all have rubbish (and always the same rubbish). I suspected flash protection and when I try to unlock it with the FLASH Programmer in CW10.1 I get a timeout (as a matter of fact, I can erase and check erase, but I cannot program using that tool. But I can debug and run normally in debug mode). Am I forgetting something? Is there a better way of allocating constant data (strings and the sort) in C code?

 

Thanks in advance for your help!

Labels (1)
Tags (1)
0 Kudos
7 Replies

667 Views
CompilerGuru
NXP Employee
NXP Employee

Are you using the C startup code?

Some of the shown definitions are actually not const, especially pointers (or array of pointers) need the const after the *.

E.g.:

 

const menu_item*const submenu2[3] ={    &submenu1_2,    &submenu1_3,    &submenu2_1};

 

Otherwise submenu2 ends up in RAM and has to be initialized by the C startup code.

Not sure if this is your issue though.

 

Daniel

0 Kudos

667 Views
sblanco
Contributor I

Thank you for your answer,but it seems my issue is different... I tried creating a constant string with both const char* v = "hello" and const char*const v = "hello" and I get rubbish on both (infinite ° chars actually). Is this how string constants are usually stored in Freescale MCUs? It should work,no?

0 Kudos

667 Views
StenS
Contributor III

Sorry if I point out the obvious; but just to be sure:

 

const char *v = "hello"; // will create a pointer in RAM to a const string and it will be initialised with the address of the string "hello" which is located in Flash

 

char * const v = "hello"; // will creat a constant pointer (in Flash) to a string and will contain the address if the string "hello" which also is located in Flash.

 

In both cases, if you look at the variable v, it will not contain the string "hello" but the address of the string in Flash.

 

Sten

 

0 Kudos

667 Views
sblanco
Contributor I

@Lundin:

 

Here is the section of the map file for the variables of menu.c

 

     hello_s                                    E092       2       2       1   .rodata          option1                                   E094       F      15       1   .rodata          option2                                   E0A3       F      15       1   .rodata          option3                                   E0B2       F      15       1   .rodata          submenu1_1                                E0C1       5       5       1   .rodata          submenu1_2                                E0C6       5       5       2   .rodata          submenu1_3                                E0CB       5       5       2   .rodata          submenu1                                  E0D0       6       6       1   .rodata          submenu2_1                                E0D6       5       5       1   .rodata          submenu2                                  E0DB       6       6       1   .rodata          menu_ppal_elements                        E0E1       4       4       1   .rodata          menu_ppal                                 E0E5      18      24       2   .rodata          STRING.Hola.hola.1                        E109       A      10       1   .rodata1         STRING.Opcion.1.2                         E113       9       9       1   .rodata1         STRING.Opcion.3.3                         E11C       9       9       1   .rodata1         STRING.Yes.4                               E125       3       3       1   .rodata1         STRING.No.5                               E128       3       3       1   .rodata1         STRING.Maybe.6                            E12B       6       6       1   .rodata1         STRING.Menu.principal.7                   E131       F      15       1   .rodata1         opc1                                      FF00       2       2       0   .abs_section_ff00     opc2                                      FF02       2       2       0   .abs_section_ff02     opc3                                      FF04       2       2       0   .abs_section_ff04

And the section allocation info:

 

.rodata                          107     R     0xE092     0xE0FC   ROM.rodata1                          67     R     0xE0FD     0xE13F   ROM.abs_section_ff00                  2   N/I     0xFF00     0xFF01   .absSeg3.abs_section_ff02                  2   N/I     0xFF02     0xFF03   .absSeg4.abs_section_ff04                  2   N/I     0xFF04     0xFF05   .absSeg5

 

 

When I copied the code in my first post I translated it (but left some things untranslated accidentally) so in detail I have for example &opcion3 but it would really be &option3. Should you need the code as it is compiled I can copy it as is, but I don't think we will need it.

 

Observing the map file, I see everything goes to FLASH (I followed CompilerGuru suggestion and changed all pointers).

 

@StenS:

 

It's allright, it's been like 6 years since last time I developed C code (and it was C++ for PC when I was studying) and even though I understand the generics of it, there are some specifics that I just suppose are in some way. Up until now I was working in asm with another brand, so it is very possible I am just failing at something very basic and I just missed it.

 

Even so, when I check the variable v, what I really check is *v (in the debugger view I can see the contents of pointers, and if they are char* it interprets them as \0 ended strings, so the problem isn't there). Just to be sure, is this the typical way of creating constant data in non volatile memory?

 

Thanks all for the suggestions and help, let's see if we discover the origin of the issue

 

0 Kudos

667 Views
bigmac
Specialist III

Hello,

 

Here is a simpler example than the one you give, and where I have a large number of different pre-determined messages to be sent, in this case, to the SCI1 module.  I have a function that writes a string to the module, where the parameter is a pointer to the string address.  It is possible you might have a similar function for writing to the LCD module.

void Tx1_sendstr( char *s);

 

I use a flash located message table, as follows:

 

const char * const msg_tab[] = ["String 1","String 2","String 3",..."String n"};

 

Of course, the first string has an index number of zero.  To display a specific message, I then use the following function:

 

// Display message data to SCI1void disp_msg( byte msg_ndx){   Tx1_sendstr((byte *)msg_tab[msg_ndx]);}

 

For your more complex menu structures, maybe the string required for each menu item might be referenced simply by its index number, and the string data, or its address, kept out of the actual structures.

 

Regards,

Mac

 

0 Kudos

667 Views
sblanco
Contributor I

As expected, this issue was that my code was wrong :smileysad:

 

char* constants do not work, but char[] do.

 

const char[] v = "Hello" ; //This works beatifully

 

The struct appeared as uninitialized because I had some of the pointers wrong, and when I tried the string constant and saw the same result I thought there was a problem with constants in general in my project.

 

Now it's working, thanks everyone for your help!

0 Kudos

667 Views
Lundin
Senior Contributor IV

Can you check the .map linker output to see where the variables are actually allocated? RAM or ROM?

0 Kudos