Keil:虚拟或受保护的析构函数和堆
Keil: virtual or protected destructor and heap
我正在使用Keil 4和Cortex M3的ARM工具集(如果这很重要的话)。我尝试了这个简单的代码:
class Base
{
public:
virtual ~Base() {}
};
class Derived : public Base
{
public:
int b;
virtual ~Derived() {}
};
如果我在本地(main内部)创建一个Derived实例,一切都很好:调试正常,程序大小约为300字节。
如果我创建Derived的静态或全局实例,程序大小将增加到1000字节,调试会话将在BKPT指令上停止。
我认为这是因为堆大小被设置为默认值(零)。当我添加一些堆时,调试就开始工作了。
将析构函数设为受保护但非虚拟的会导致相同的行为。将通常的方法虚拟化并没有。
所以,我的问题是:在这种情况下,编译器需要堆的原因是什么?
Vtab是静态创建的(我检查过),全局对象也应该是静态的。当我不需要动态分配时,再浪费700字节用于堆分配代码(以及堆本身的空间)有点愚蠢。
(我将析构函数设为虚拟,以防止出现警告。)
当在函数之外定义实例时,会发生两件事。首先,在调用main之前先调用对象的构造函数。程序员必须小心,构造函数不执行任何可能需要稍后进行初始化的操作。其次,实例的内存是在堆上分配的,因为在main之前没有本地作用域。嵌入式系统程序员在实例化全局对象时必须特别小心。如果构造函数依赖于一些在main之前未初始化的硬件,那么可能会发生不好的事情。熟悉Keil提供的C启动文件(汇编语言模块,在初始化堆后调用main,将flash复制到ram,并调用全局构造函数)。
答案在这里,在Keil论坛上-http://www.keil.com/forum/21859/.原因是生成了从main返回后调用的函数"__aeabi_atexit"。这有点有趣,因为这种返回在嵌入式系统中永远不会发生。
相关文章:
- 什么时候调用组成单元对象的析构函数
- 拥有"受保护的非虚拟析构函数"与"受保护虚拟析构构函数"有什么好处
- 受保护的析构函数禁用在堆栈上创建派生类的对象?
- 如何将 std::unique_ptr<Parent> 与具有受保护虚拟析构函数的只读父类一起使用
- 带unique_ptr的受保护析构函数
- 具有受保护析构函数的类数组的动态分配
- 抽象基类中的析构函数保护不会在 C++ 中继承
- 删除具有受保护析构函数的对象
- Keil:虚拟或受保护的析构函数和堆
- 基类中受保护的非虚拟析构函数
- 从保护类析构函数引发异常会导致 std::终止
- 全局变量构造函数/析构函数是否需要线程保护
- 提升::p ython 受保护的析构函数问题
- 是否有使受保护的析构函数成为虚拟的用途
- 删除具有受保护析构函数的对象
- C++中受保护的策略类的析构函数
- 受保护析构函数对象在堆vs堆栈上的分配
- 受保护的抽象基类的构造函数和析构函数
- 如何在具有受保护析构函数和公共销毁方法的 3'd 派对类上使用shared_ptr
- 处理CRTP设计的受保护/私有构造函数/析构函数