[英]Why Embedded C++ compilers not support exceptions?
我正在为嵌入式系统编写一个库,我碰到了很容易找到的STL标准库。
但我收到的最糟糕的消息是编译器无异常支持。 Atmel参考手册显示了这一点
为什么不支持嵌入式环境中的异常?
很简单,不可能使用很多用C ++编写的库。 C ++与异常紧密相关,就像使用new运算符一样!
显然,除了生成该编译器的人之外,没有人可以真正回答这个问题。
我最好的猜测是异常既耗费空间又耗费时间(当代码抛出时,时间只是一个真正的问题,但总是需要空间表的空间,并且很容易与整个代码大小相同)编译后的代码加上“相当难以实现”,它可能不是编译器开发人员列表中的最高项,因此尚未实现。 是否会在未来的某个时刻显然取决于Atmel或他们转包制造他们的编译器的人。
我不是Atmel C ++实现方面的专家,但如果编译器支持throw
,而不是try/catch
,我会非常惊讶 - 因为当尝试修复加热器时,它会像巧克力制成的螺丝刀一样有用。一个充满热量的桑拿房。
如果使用-fno-exceptions
,如果您有任何throw
代码,编译器应该会出错。 并且可以使用-fno-exceptions
编译STL - 因为这是我编译编译器代码的方式。
具有有限ROM和RAM资源的8位AtmelAVR不适合使用STL,这对两者都施加了相当大的负担。 此外,C ++异常本质上是非确定性的,因此不适用于许多实时应用程序。
编译器可以实现EC ++(嵌入式C ++)“标准”。 EC ++的目标有两个:
EC ++缺少的东西包括:
遗漏名称空间完全取决于EC ++的第一个目标,现在基本上已经过时了。 两个目标都省略了其他的,并且排除了STL和std :: string库的使用。
EC ++本身现在已经基本上过时了,但它定义的子集仍然适用于严重资源受限的目标,并且许多编译器支持整个或部分EC ++实施。
请注意,也许并非AVR的所有编译器都强加了这些限制,但是如果您尝试广泛使用这些功能,您可能很快就会发现,在大多数情况下,他们在目标非常有限的CPU和内存资源上不明智。
关于new
运算符的使用,默认动态内存分配(与放置新的或覆盖相反)本质上是非确定性的,并且通常在实时嵌入式系统中最好避免,尤其是在最小堆可用的情况下。 要使用new
没有异常处理的假设,使用new (std::nothrow)
( #include <new>
),这将不会抛出异常,只是返回一个空指针类似malloc()
在EC ++中, new
和new (std::nothrow)
本质上是相同的,但后者是可移植的和显式的。
在Atmel维护的GCC-AVR开源库中缺乏对C ++的支持并不意味着一般不支持嵌入式系统,或者对AVR也不支持。 IAR的AVR编译器支持它所指的扩展嵌入式C ++(EEC ++)以及EC ++。 EEC ++确实支持包含STL的C ++库,但有一些修改 - 没有RTTI,没有例外,没有std :: namespace(尽管支持名称空间)。 在大多数32位目标上支持ISO C ++而不是EC ++通常更全面。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.