【发布时间】:2020-04-15 21:03:33
【问题描述】:
我在 Windows 上,我有 2 个项目:一个是用 C 制作的,我已经编译成一个 DLL 库,另一个是 Qt C++ 项目,我正在与 C 库链接。
当我过去尝试将 C 库与 C 代码链接时,它工作正常。但是,当我尝试将它与 C++ 代码链接时(在此处的 Qt 和一般的 Linux 上)似乎存在问题,即使我在包含 C 头文件的位置插入 extern "C" 块。
最奇怪的部分是在调试时,代码做了一些……不应该发生的事情?
这是我调用的 C 代码:
// Defined in a header file elsewhere...
typedef struct _nodeTrueProperties {
bool isDefined;
bool needFuncName;
bool _mallocd;
const DType *inputTypes;
long numInputs;
const DType *outputTypes;
long numOutputs;
} NodeTrueProperties;
// The actual code...
NodeTrueProperties d_semantic_get_node_properties(struct _sheet *sheet,
const char *name,
size_t lineNum,
const char *funcName,
NameDefinition *definition) {
VERBOSE(5, "Getting node properties of node %s on line %zu in %s...\n",
name, lineNum, sheet->filePath)
NodeTrueProperties out =
(NodeTrueProperties){false, false, true, NULL, 0, NULL, 0};
// Most cases use this to build up the output types.
DType *outputTypes = NULL;
// First, let's check if it's a special function like Start.
// We do this now so we don't need to search all of our includes
// for this function.
if (strcmp(name, "Start") == 0) {
// THIS IS THE SECTION THAT SHOULD AND DOES RUN!
out.isDefined = true;
out.numOutputs = 1;
outputTypes = (DType *)d_malloc(sizeof(DType));
outputTypes[0] = TYPE_EXECUTION;
out.outputTypes = (const DType *)outputTypes;
} else if (strcmp(name, "Return") == 0) {
// ... stuff that shouldn't run...
} // ...
return out;
}
这是调用该函数的 Qt C++ 代码:
#include "nodegraphicsitem.h"
#include <QPainter>
extern "C" {
#include <dsemantic.h>
}
// ...
void NodeGraphicsItem::setupNode(Sheet *sheet, QString name, QPointF position) {
_name = name;
_position = position;
_sheet = sheet;
_size = STARTING_SIZE;
// Set the QGraphicsItem flags.
setFlags(ItemIsMovable | ItemIsSelectable);
// Get the true properties of the node.
NameDefinition nodeDefinition;
QByteArray nameByteArray = name.toLatin1();
const char *nameCharArray = nameByteArray.constData();
// THIS IS THE CALL TO THE COMPILED C FUNCTION
NodeTrueProperties properties =
d_semantic_get_node_properties(sheet, nameCharArray, 1, NULL,
&nodeDefinition);
// THIS FUNCTION DOES SOME WHACKY STUFF
d_semantic_free_true_properties(properties);
// ...
}
一切都编译得很好,但它根本运行不正常:
根据运行的 if 语句(因为传入的名称是 "Start"),我希望我的 NodeTrueProperties 看起来像这样:{true, false, true, NULL, 0, (pointer to DType array), 1}。根据调试器,我实际得到的是{true, false, false, NULL, 1, NULL, 0}:
另一个非常奇怪的工件是在 C 代码中激活的 if 语句,尽管根据调试器的说法,条件是错误的 (trueProperties._mallocd == false):
我在Win32模式下使用CMake和VS2017将C项目编译成DLL,并使用Qt Creator和MSVC2017 32bit kit编译Qt C++项目。
【问题讨论】:
-
我的猜测是,两个编译器在
NodeTrueProperties的二进制布局上不一致。尝试在 C 和 C++ 端打印sizeof(NodeTrueProperties)。bool是 C++ 中的内置类型,但是 C 中的一些宏,可能扩展为不同大小的类型。