首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >使用虚拟函数调用时节省堆栈空间

使用虚拟函数调用时节省堆栈空间
EN

Stack Overflow用户
提问于 2014-06-08 22:45:36
回答 1查看 245关注 0票数 1

我目前正在C++中为STM32 C开发。基本上,我想在I S.c上添加一层抽象层,以便在物理I 2 c总线上的多路复用器后面有虚拟的I 2 c总线。

我们已经有了一个将驱动程序和多路复用器逻辑相结合的驱动程序,而OOP部门显然缺乏.因此,我在I 2 C访问中添加了一个间接级别,并增加了一个虚拟总线实现,以使驱动程序与多路复用器逻辑分离,并隐藏全局知识:

代码语言:javascript
复制
Device -> Virtual I²C -> I²C Multiplexer -> Abstracted I²C -> Low-Level I²C

现在我的问题是,每个接口都必须定义一个传输函数。

代码语言:javascript
复制
virtual
transmit(const uint8_t address,
         uint8_t *tx,
         size_t lentx,
         const uint8_t *rx,
         const size_t lenrx,
         const size_t timeout
         );

只是传递了一些论点。通常:

代码语言:javascript
复制
virtual
transmit(...) {

    this->driver->transmit(this->address, ...);

}

但是,事实证明,每个虚拟函数调用都会为我的堆栈需求增加多达40个字节,因为它们:

  1. 获取堆栈上的参数
  2. 为它们的函数调用分配堆栈
  3. 将输入复制到堆栈新分配部分的正确位置。
  4. 执行函数调用
  5. 将输出复制回堆栈中输入参数的正确位置。

现在,我们只是最近才开始使用C++,所以我对嵌入式系统开发的精细调整还不太了解。然而,我觉得奇怪的是,已经有三个层次的间接方向会使我耗尽堆栈空间……例如,我只通过虚拟调用丢失164个字节:设备到虚拟总线,虚拟总线到I 2 C复用器,I 2 C复用器提取I 2 C,在这里进行真正的调用。

想要的解决方案是很明显的。显然,虚拟函数调用应该只为传递和重新排序参数所需的附加变量分配足够多的空间:

代码语言:javascript
复制
Incoming: tx*, len, rx*, len, to
Allocate: tx*, len, rx*, len, to, ___
Reorder : ___, tx*, len, rx*, len, to
Add args: sla, tx*, len, rx*, len, to
     ---------- Call ----------
Reorder : tx*, len, rx*, len, to, ___
Dealloc : tx*, len, rx*, len, to
Output  : tx*, len, rx*, len, to

所以,真正的问题是:我能不能强迫GCC注意到这种穿行式的行为,并迫使它尽可能地节省堆栈空间?我在这里真是不知所措,因为我一开始只用豆荚.

EN

回答 1

Stack Overflow用户

发布于 2014-06-08 23:56:36

虽然您无法说服gcc自动更改堆栈布局,但您当然可以通过定义一个设置参数的struct并传递指向该struct的共享指针来手动更改堆栈布局。

以下是您可以这样做的方法:

代码语言:javascript
复制
struct TxRxParams {
    uint8_t *tx;
    size_t lentx;
    const uint8_t *rx;
    const size_t lenrx;
};

现在,您可以分配一次TxRxParams,并将指向它的指针传递给各种函数,不管是虚拟的还是非虚的,以节省堆栈空间。

票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/24111650

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档