我有一个结构,我想强制执行静态存储。这是DSP上的矢量类型,并且意外地在堆栈上声明它是导致堆栈溢出,性能问题或两者的用户的常见错误。据我所知,这是不可能的,但我很好奇,如果其他人知道的更好。
示例用例:
static Vector64 v1; // OK
static Vector64 v2; // OK
static Vector64 result; // OK
result = v1 * v2; // OK
Vector64 v3; // I would like this to give a compile-time error
Vector64 v4;
result = v3 * v4;
我的编译器是Clang / LLVM 3.2,特定于编译器的属性是合理的游戏。
答案 0 :(得分:2)
由于C没有课程,我几乎要排除这一点。
通常,在C ++中定义类时,无法控制是否在堆栈上,堆上,static
或const
上const
ally定义该类型的对象。在一个数组或另一个类的成员中。这些是对班级用户的选择。
有一些技巧可以让它远离堆(例如,使用operator new
),或者仅在堆上(例如使用生成器模式),但这不是你想要的 < / p>
我很想知道这是怎么可能的,但在此之前,我很确定你不能。
答案 1 :(得分:2)
如果您愿意解决运行时错误并深入了解实施水域,并且如果您的DSP具有合适的地址布局,您可以简单地插入检查{的位置Vector64的默认构造函数中的{1}}。
如果您提前知道地址空间,最安全的事情(语言方面)就是简单地比较堆栈的绝对位置。
this
风险更高但更灵活的定义可能如下所示:
struct Vector64 {
Vector64() { assert( reinterpret_cast<uintptr_t>(this) < STACK_START ); }
};
需要__attribute__((noinline)) Vector64() {
int test;
assert( less<void*>()(this, &test) );
}
来防止clang在Vector64对象之前排序__attribute__((noinline))
(或者只是在别处定义它)。从好的方面来说,重新排序优化不会导致这个断言产生误报,只能无声地失败。 test
在这里也很重要,因为与std::less
不同,它明确允许在不同对象的地址之间进行比较。
这种方法非常讨厌,但是通过干预构造,你可以通过确保不再构造堆栈溢出来防止堆栈溢出。
答案 2 :(得分:-2)
如果您使用C编程,那么您将遇到问题。使用C ++它应该工作。我从未使用过那个编译器,但两种语言在这方面都有很大的不同。检查你的编译器。