Hi,
I saw that after reset the static variables are not se to the state like a new reload of software.
I have this function:
static void myfunction(void)
{
static unsigned short usMyVariable = 0x0001;
...
usMyVariable = 0x0002;
...
}
After reset usMyVariable has still the value 0x0002.
Is this a normal behaviour for the standard reset script ?
Can we do something to solve this problem ?
Thanks
Fox75
Hi AJ,
looking more deep I agree that this is not something that should be done on this script, but I DO NOT AGREE that this should be normal behaviour of the system.
I find very strange and VERY DANGEROUS that such actions are not performed during the reset procedure and rcx system initialization, because this "static unsigned short usMyVariable = 0x0001; " is an initialization of the variable.
I consider as a non normal situation if I have to reload the application to have those variables correctly initialized.
I hope that you agree with me that somewhere there should be an error, please help me to find where.
Thanks
Fox75
Hilscher Gesellschaft fuer Systemautomation mbH
Maybe a solution could be to add your variable into the "watch" window. Here you are able to change the value after a reset.
The most common way, is as I described it before, to create a function, which initialize the needed global variables.
AJ,
what you are proposing in my opinion is NOT a solution is a temporary pacth to make working the stuff for this precise piece of code.
If we should follow your proposal all the variables that are initialized on this way they should be placed global... :shock: and this just for hitop...
Sorry but I have the impression that we are not speaking about the same issue or one of us is completelly wrong understanding how this should work.
Can you please ask another moderator to look on my first post and see what is his opinion ?
Thanks
:)
Fox75
Hi Fox75,
Can you please ask another moderator to look on my first post and see what is his opinion ?
As you request, another moderator, another opinion: Get rid of this static variable. A nice description for this is "bad coding style".
I find very strange and VERY DANGEROUS that such actions are not performed during the reset procedure and rcx system initialization, because this "static unsigned short usMyVariable = 0x0001; " is an initialization of the variable.
Let's take a look at the first download of your software: the Hitop debugger downloads an elf file. This is a combination of various memory regions, called sections. The Hitop will write all sections to the netx memory. Each section has different attributes, like "read only and executable" for a code region, or "read and write" for a preinitialized data region. Your static variable will go into one of these "read and write" sections. This means it is only initialized by the Hitop Debugger when you download your app.
Maybe you are familiar with WinCE or some other embedded os. Looking at the section init, loading an exe on these systems can be compared to loading an elf file with the Hitop. This means the exe's static variables are only initialized if you load the executable again. They will not be initialized if you just jump back to the entry point.
So you have several options now:
1) Get rid of the static variable. I'm sure there is a nice and clean way without it.
2) Init the data section on every start. Relocate the original data section and copy the contents in your init.s .
I would recommend option 1 as the second one requires some mods in the ld file. This might be a bit tricky if you don't speak gnu. ;)
As you request, another moderator, another opinion: Get rid of this static variable. A nice description for this is "bad coding style".
Another user, another opinion ;-) There are reasons to do this.
From the perspective of C there is no big difference if you are placing the static variable in the function or outside. This has only impact to the scope of the variable, means who is able to access it at compile time. To be as restrictive as possible should always be the goal. I.e. you should always use static in your c files if you do not need a variable outside of the module. Or?
For sure if you use a static variable in a function and return its address then this is risky because you open the scope at runtime. But also in this case there is no difference if you define this static inside the function and outside.
So it's ok to use static if you know what you are doing. But (and some may look at this as a contradiction to what I said before) after a while of programming I no longer use global variables at all if there are not more or less const.
---
Now this issue about reset. I'm wondering, but maybe I misunderstood the question/problem.
There are three types of global variables: Application global, module global and function global (ok a quite restricted form of global;-). The last two are defined with static. The compiler should handle them all in the same way. Globals which are not preinitialized go to the BSS the others to DATA. The startup code of an application fills BSS with zero and copies the content of DATA from some const area. I never checked what rcX is doing, but if the behavior is different then something is wrong.
You are not saying that the reset macro does not execute the startup code, or? Means no global variable will be reinitialized (and not the function static global)?
Martin
Hilscher Gesellschaft für Systemautomation mbH
Now this issue about reset. I'm wondering, but maybe I misunderstood the question/problem.There are three types of global variables: Application global, module global and function global (ok a quite restricted form of global;-). The last two are defined with static. The compiler should handle them all in the same way. Globals which are not preinitialized go to the BSS the others to DATA. The startup code of an application fills BSS with zero and copies the content of DATA from some const area. I never checked what rcX is doing, but if the behavior is different then something is wrong.
This is not really correct. This behaviour is only preferred when booting from flash (XIP, execute in place). Then you MUST relocate the r/w data section from flash to RAM. But for RAM Images there is no need to keep the data section twice in memory. Once with all pre-initialized data and once with a "working" copy. You will waste twice the memory for these pre-initialized variables.
If you use another operating system the effect will be the same.
Start a process. Go to the main routine again by modifying your programm counter (thats what the reset script does), and run again. DON'T Restart your debugger, as this will reload your application (same as HiTop would do when pressing download). Your static variable WILL NOT be initialized by your operating system.
This initialization only happens when starting your application (when it's loaded from flash/hard disk, to RAM). This can be compared to downloading your application via JTAG. (.elf is the same as an .exe file on Windows)
BTW: You have the startup code (initGnu.s) and the linker description file. If you want to modify this behaviour by duplicating unneccessary data, just because of debugging lazyness, you are free to modify this behaviour. Or just redownload your application before starting again. There should be a HiScript command for downloading an image.
You are not saying that the reset macro does not execute the startup code, or? Means no global variable will be reinitialized (and not the function static global)?
If you look at the ResetRegisters script, you will note that is does the following things:
1. Reset the ARM to Supervisor Mode and disable all interrupts (Power-On Default)
2. Acknowledge any pending interrupt to bring VIC into Power-On State
3. Reset R0,R1 as these are used by init-code, if the application is started via netX ROM Loader.
4. Set PC to start of application
This script just places the ARM into it's power-on defaults state, and does not change anything inside your application. Sure the init-code is executeed. But global variables won't be reinitialized, to save space by not keeping these variables twice. (See above).
You can use the following methods:
1. Re-Download your application before starting it. (preferred)
2. Change the LD and initGnu.s file to have a second copy of your RAM data and relocate it to a working area.
3. Initialize all your static variables on start-up yourself.
Regards
MT
Hi Fox75 and RedElephant,
I understand that you are concerned about the initialisation of your vars in a debug session, and I'm sure we'll find something for the reset script.
For normal operation I still don't get it. A reinit of the data section is only needed for a warmstart, i.e. you just jump back to the start of your application. Please note: not the reset vector, but really the start of your code. Are you planning to this?
Thanks for the explanation and this separate thread. I really have to say that I'm not so familar with rcX. Sorry, time is always limited.
But I did a lot using Nucleus and VxWorks in the embedded market. A silent reset of a system is not unusual in devices on the market (especially mobiles od data devices). I have never seen that if you jump through the reset vector then the globals are not initialized. Even if the bootrom copies the system to ram to speed up execution. On the contrary quite often you have to do special code to avoid initialization of a piece of your ram to store their information about the reason of the reset.
I'm not complaining, this is just an issue people have to know.
Maybe you should think about it. And I don't think you can not avoid to use additional ram.
Martin
I have never seen that if you jump through the reset vector then the globals are not initialized.
Jumping to the reset vector will of course reinit all globals including the static variables inside the functions. That's done in the netX romcode. The complete firmware will be reloaded in this case.
The reset script in the Hitop debugger is another story. It does not jump to the reset vector and does not reload the image. It just sets the pc back to the little assembly routine right before your main function. The romcode is not executed and nothing else is done.
On the contrary quite often you have to do special code to avoid initialization of a piece of your ram to store their information about the reason of the reset.
The netX has 2 ways to preserve information over a reset. First one is the reset_ctrl register at 0x0010000c. It shows the reset source and has 4 bits for "user messages". Another option is information at a well defined place in intram or backup ram. sdram is no good as it's switched off during the init phase for a short time, which means the information is no more reliable.
Andreas Jacob
Hilscher Gesellschaft fuer Systemautomation mbH
Hi,
yes this is a normal behavior.
The start up script will only set the netX registers and not any program variables.
I am not sure, if this is possible with the HiSCRIPT language.
Maybe you can add a function in your project which will initialize all needed variables before the main project starts.