LLVM IR中bool的数据类型

时间:2016-03-22 19:40:10

标签: c++ c++11 llvm llvm-clang

我正在编写一个编程语言编译器来集成DSL和C / C ++。为此我出于几个原因决定使用LLVM。

有一个主程序。在这个主程序中,我加载了由clang编译的bitcode文件。可加载的bitcode文件代表了一个简短但完整的编程语言环境,包含REPL,解析器,链接器和AST。

到目前为止,我的理解是布尔数据类型在IR中表示为i1。我用-O3优化了我的代码,然后得到一个布尔跟随IR代码(通过从生成的bitcode文件中反汇编llvm-dis):

%"class.tl::contrib::toy::ToyREPL" = type <{  %"class.tl::contrib::toy::InitLanguage"*, i8, [7 x i8] }>

该类是ToyREPL,它正在使用另一个类InitLanguage。奇怪的是,布尔值似乎是由i8和i8数组呈现的。我真的不懂。

我已经定义了一个Makefile。首先我编译文件。然后我将它们链接到一个bc文件,然后优化并将其与其他一些库链接。

@cd $(BIN)/$(TARGET)/$(2); $(LINK) -o $(1).$(BITCODE_EXT) $(3)

@cd $(BIN)/$(TARGET)/$(2); $(OPT) -O3 $(1).$(BITCODE_EXT) -o $(1).$(OPT_NAME).$(BITCODE_EXT) $(OPTIMIZER_FLAGS) 

@$(LINK) -o $(BIN)/$(TARGET)/$(2)/$(1).$(BITCODE_EXT) $(BIN)/$(TARGET)/$(2)/$(1).$(OPT_NAME).bc $(LINK_OPTION) $(4)

编译器标志是:

-v -g -emit-llvm -I$(BOOST_INC_DIR) -std=c++11 -D__STDC_CONSTANT_MACROS -D__STDC_LIMIT_MACROS

优化程序标记为-std-link-opts

链接标记为-v

类ToyREPL的相关部分在这里:

class ToyREPL {
private:

  InitLanguage *initLang;

  bool runs = false;

现在我的问题:我的假设错了bool应该是bitcode编译成i1吗?编译到i1需要考虑哪种编译器开关?如果您认为我的构建过程在某种程度上是错误的,请告诉我。生成bitcode文件是可读的,我可以将模块和类ToyREPL检索为StructType。

1 个答案:

答案 0 :(得分:3)

如果我理解正确,那么你的问题基本上就是 - 为什么是C ++类

class ToyREPL {
  bool runs = false;
  ...
};

由Clang编译成type <{ i8, [7 x i8], ... }>

首先,为什么Clang选择i8而不是i1作为布尔字段是直截了当的 - the smallest C++ type takes one byte of memory,除非你使用位字段,否则它也适用于结构中的字段。另请参阅this related question about why a whole byte is used for booleans。 LLVM本身使用i1作为布尔值,但这是因为它大致与平台无关 - 在降低阶段,它们可能再次成为整个字节。

对于[7 x i8],这是一个填充,用于确保此类型的每个对象都是64位对齐的,并且不与任何其他对象共享其内存 - 在64位上非常合理的方法系统。或者,如果存在以下结构字段,则可能已插入填充以确保该字段是64位对齐。

如果您想了解更多信息,

The Wikipedia article on alignment and padding是一个有用的起点。