简体   繁体   English

静态变量未初始化为零

[英]Static variable is not initialized to zero

I'm developing an embedded application on stm8s microcontroller using STVD IDE and COSMIC compiler. 我正在使用STVD IDE和COSMIC编译器在stm8s微控制器上开发嵌入式应用程序。

I'm trying to define a static bool variable to use it to execute a snippet of code only once. 我正在尝试定义一个static bool变量来使用它只执行一次代码片段。 Unexpectedly, the variable once is not initialized to FALSE or 0 . 出乎意料的是,变量once未初始化为FALSE0 Although I explicitly initialized it. 虽然我明确地初始化了它。 Here is the snippet of my code: 这是我的代码的片段:

uint32_t crc32_buffer(void)
{
    static bool once = FALSE;
    uint32_t crc = 0;

    if(!once)
    {
        calcTable();
        crc = 10;
        once = TRUE;
    }

    return crc;
}

When I tried to check the physical memory location, I found that every time after entering a new debugging session (even after hardware restarting the controller) and before running the application itself, the memory address 0x80 has the same value 0x14 . 当我尝试检查物理内存位置时,我发现每次进入新的调试会话后(即使在硬件重启控制器之后)和运行应用程序本身之前,内存地址0x80都具有相同的值0x14

If I modified the code to assign FALSE to once after the variable's initialization: 如果我在变量初始化后修改代码以将FALSE赋值为once

once = FALSE;

The memory location is changed to contain 0x00 . 内存位置更改为包含0x00 Then if I exit this debugging session and then re-modified the code to delete this line of code and start a new debugging session, I find the memory location 0x80 has again 0x14 before running the application. 然后,如果我退出此调试会话然后重新修改代码以删除此代码行并启动新的调试会话,我会在运行应用程序之前发现内存位置0x80再次为0x14

I don't understand what can prevent the compiler to initialize the variable to 0 . 我不明白什么可以阻止编译器将变量初始化为0 I don't understand what can write 0x14 to the memory location even before running the application. 我不明白甚至在运行应用程序之前可以将0x14写入内存位置。

I tried setting a breakpoint if the memory location 0x80 was accessed (read/write) but the application didn't stop until it reached the if statement in the code snippet. 我尝试设置一个断点,如果访问内存位置0x80 (读/写)但应用程序没有停止,直到它到达代码片段中的if语句。

UPDATE-2 UPDATE-2

As many pointed out the startup procedure, I don't use the default startup code. 正如许多人指出的启动程序,我不使用默认的启动代码。 However, I'm using a custom one. 但是,我正在使用自定义的。 When I used the standard startup code instead of the custom one I was using, the memory locations were set to 0 before main() function start execution. 当我使用标准启动代码而不是我使用的自定义代码时,在main()函数开始执行之前将内存位置设置为0 This is not the case with the custom startup code. 自定义启动代码不是这种情况。 So, when I define a new static variable and explicitly initialize it to FALSE , this initialization will only take place in the startup code before main() , right? 因此,当我定义一个新的static变量并将其显式初始化为FALSE ,这个初始化只会发生在main()之前的启动代码中,对吗?

If you read this storage duration reference you will see that for static storage duration 如果您阅读此存储持续时间参考,您将看到静态存储持续时间

the value stored in the object is initialized only once, prior to main function 存储在对象中的值仅在main函数之前初始化一次

So you have to let the startup code running before main run first. 因此,您必须先在main运行之前运行启动代码。 Once the main function is called the value should have been initialized. 一旦调用main函数,该值应该已经初始化。

I find the memory location 0x80 has again 0x14 before running the application. 在运行应用程序之前,我发现内存位置0x80再次为0x14。

Initialisation requires code; 初始化需要代码; the state of the memory after reset, before any code has executed is non-deterministic. 在执行任何代码之前 ,重置后的内存状态是不确定的。

I tried setting a breakpoint if the memory location 0x80 was accessed (read/write) but the application didn't stop until it reached the if statement in the code snippet. 我尝试设置一个断点,如果访问内存位置0x80(读/写)但应用程序没有停止,直到它到达代码片段中的if语句。

That sounds like the initialisation right there. 这听起来像初始化就在那里。 What value did the variable acquire at that point? 变量在那时获得了什么价值? Local statics can be initialised on first use, rather than in the run-time start-up. 本地静态可以在首次使用时初始化,而不是在运行时启动时初始化。 It looks to me that in fact you do not have a problem at all other than understanding the semantics of static. 在我看来,事实上除了理解静态的语义之外,你根本没有问题。

If for example you place a break-point on the static declaration itself, and run it, I expect you will observe that the break point is hit once on first use initialisation, and thereafter will not break on subsequent calls to the function. 例如,如果你在static声明本身上放置一个断点并运行它,我希望你会在第一次使用初始化时观察到断点被击中一次,之后在后续的函数调用中不会中断。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM