LLVM TableGen分析
TableGen 描述文件是由许多的记录(record)组成的。每一个记录都有一个唯一的名字,包含一系列的数据,这些数据就是 TableGen 文件所描述的领域所需的信息。使用 tblgen 工具解析文件时,指定这些数据所针对的不同领域,就可以解析出该领域所需的记录信息。
记录可以分为两种,一种称为定义(definition),一种成为类(class)。定义是最基本的记录类型,它的定义中没有不确定的成分,并且使用关键字‘def’标记。 类是一种抽象的记录,帮助建立和描述其他的记录。使用类可以用来描述特定领域所使用数据的抽象数据结构,也可以用来减少对记录中数据公共部分的编写。对所有的类,TableGen 都会记下它们的结构,并在所有使用类来建立的记录中实现这些结构。
def A { bit c = 0; } //定义,它建立了一个名为 A 的定义,它只有一个数据,类型为位,值为 0。
class B{ bit d = 0; }//类,且所有建立时使用类 B 的记录都将包含类型为位的数据 d。
通过使用‘let’关键字,可以改变建立记录时所使用的类中数据的默认值。
eg:下面建立了三个记录 STRimmOffAddW、STRimmOffAddH、STRimmOffAddB, 分别用来描述字、半字及字节的立即数寻址模式的存储指令,并设置 isStore 及 noResults 均为 1 来表明三种指令都是存储指令且指令没有返回结果。
let isStore = 1, noResults = 1 in {
def STRimmOffAddW : STW_imm<
( ops GPRC:$rS, memri:$src ),
"str $rS, $src",
[(store GPRC:$rS, iaddr:$src)] >;
def STRimmOffAddH : STW_imm<
( ops GPRC:$rS, memri:$src ),
"strh $rS, $src",
[(truncstore GPRC:$rS, iaddr:$src, i16)] >;
def STRimmOffAddB : STW_imm<
( ops GPRC:$rS, memri:$src ),
"strb $rS, $src",
[(truncstore GPRC:$rS, iaddr:$src, i8)] >;
}
此外, TableGen 还允许建立类时使用模板参数。
class addrMode < bits<2> mode >
{ bits<2> addressMode = mode; }
以此可以方便的定义下面的寻址模式:
def addrImm : addrMode<0>;
def addrIdx : addrMode<1>;
def addrIdxOnly : addrMode<2>;
def addrImmshift : addrMode<3>;
定义的基本的数据类型:
类型 | 说明 |
---|---|
bit | 位,值为布尔类型,只可以取 0 或者 1 |
int | 整型,可以表达 32 位的整型数据 |
string | 字符串,可以表达任意长度的字符序列 |
bits | 位串,可以表达长度固定为 n 的位类型的数据序列 |
list | 列表,可以表达一个组成元素为 ty 类型的列表,ty 可以是任意类型,也可以本身是一个列表 |
Class type | 类,在和列表类型一起使用时,用于指出列表中组成元素的类 型为该类的子类 |
code | 代码段,可以表达一段代码 |
dag | dag 类型,可以表达有向连接图中一个组成元素 |
对上述的基本类型,目前支持的值和表达式有以下几种
类型 | 说明 |
---|---|
? | 未初始化的 |
0b1001011 | 二进制整数值(以 0b 起始) |
07654321 | 八进制整数值(以 0 起始) |
7 | 十进制整数值 |
0x7F | 十六进制整数值(以 0x 起始) |
“foo” | 字符串值 |
[{ … }] | 代码段(其中⋯可为各种代码) |
[ X, Y, Z ] | 列表值 |
{ a, b, c } | 对长度为 3 的位串的初始化值 |
value | 对 value 的引用 |
value{17} | 对位串中一个位的引用,引用 value 中标号为 17 的位 |
value{15-17} | 对位串中几个位的引用,引用 value 中标号为 15 到 17 的位 |
DEF | 对一个记录定义的引用 |
CLASS | 引用一个指定模板参数的匿名类 |
X.Y | 对一个值的子域的引用,引用 X 的子域 Y |
list[4-7,17,2-3] | 对列表中一个片断的引用,包括标号为 4、5、6、7、17、 2、3 的元素 |
(DEF a, b) | 一个 dag 类型的值,第一个元素必须是一个记录定义,剩下的可以是任意的值,包括 dag 类型的值 |
对编写好的描述文件,使用工具 tblgen 就可以解析得到相应的领域的记录文 件。例如,使用下面的命令可以分别生成描述处理器寄存器的三种文件:
tblgen ARM.td -gen-register-enums -o ARMGenRegisterNames.inc
tblgen ARM.td -gen-register-desc -o ARMGenRegisterInfo.inc
tblgen ARM.td -gen-register-desc-header -o ARMGenRegisterInfo.h.inc