c++ - 将参数推送到调用堆栈的便携式方法 (C++)
问题描述
我正在编写一种小型脚本语言。
我正在寻找一种可移植的 C++ 方法将参数推送到调用堆栈上,以便我的函数可以正常读取它们。
这可能吗?它必须在 Visual Studio、XCode 和 Android Studio 中编译——最好使用嵌入在 C++ 中的 asm(不能选择使用外部汇编文件)
解决方案
没有可移植的方法(我知道),因为“调用堆栈”不是可移植的东西。一台机器可能有不同的调用堆栈实现,例如 PIC18 设备具有单独的调用堆栈和变量堆栈,而 x86 共享使用相同的堆栈用于函数和变量以及返回值(用非常简单的话......)。
可能最好的方法是为您需要支持的每个架构和编译器创建一个单独的解决方案(宏或函数),然后使用预处理器条件结构来区分它们。使用 gcc 编译器时,您可以使用asm 关键字,而在 x86 架构上运行时,您可以使用push 指令将数据压入堆栈。
然后(半)便携式方法是提供一个 API,它的实现在架构和编译器之间发生变化,如下所示:
// for gcc and clang compiler for x86 architecture
#if defined(__GNUC__) && defined(__i386__)
#define PUSH_VALUE_ONTO_THE_CALL_STACK(val) do{ \
/* this will break your code, dont use this */ \
int __v = (val); \
__asm__("push %0" : "r" (__v)); \
} while(0)
// for Visual Studio compiler x86 architecture
#elif defined(_MSC_VER) && defined(__i386__)
#define PUSH_VALUE_ONTO_THE_CALL_STACK(val) do{ \
/* this will break your code, dont use this */ \
__asm mov eax, val; \
__asm push eax; \
} while(0)
// add more
#elif defined(__PREDEFINED_MACRO_FOR_COMPILER) && defined(__PREDEFINED_MACRO_FOR_ARCHITECTURE)
#define PUSH_VALUE_ONTO_THE_CALL_STACK(val) /* implementation */
// when implementation is missing, issue a error
#else
#error Implementation PUSH_VALUE_ONTO_THE_CALL_STACK not found for Your architecture and compiler.
#endif
int main(void) {
// identical usage/api between compilers and architectures
PUSH_VALUE_ONTO_THE_CALL_STACK(5);
return 0;
}
希望这能让你走上正确的道路。
另外:XCode 只是 IDE 的名称,我认为 XCode 默认使用 clang。Android Studio可能使用 clang 或 gcc。
推荐阅读
- docker - 无法在 Airflow DockerOperator 中运行脚本
- facebook - Faceook 在像素/转换 API 与聚合事件测量下添加事件以跟踪 IOS 使用
- jenkins - Jenkins Pipeline Matrix 不会等到所有分支都完成
- javascript - 我如何在反应中创建一个弹出窗口
- r - 将期刊标题转换为缩写形式
- spring - Spring 集成调试消息
- php - 提供文件 - 选择哪种方式 - 直接 url 或返回响应的控制器
- php - 如何在 PHP 字符串中插入反斜杠以转义感叹号?
- python - 为什么我没有使用多处理获得 response.text 对象的列表并且我的代码冻结了?
- javascript - React Native - 带有表单的 Axios 登录请求失败并显示 500