源码路径
llvm\include\llvm\IR\Instruction.h
llvm\include\llvm\IR\Instruction.def
llvm\include\llvm\IR\Instructions.h
llvm\include\llvm\IR\InstrTypes.h
Unary Operators
所有的Unary Operators在llvm中均使用类UnaryOperator实现,没有单独的子类。
fneg
fneg指令用于返回操作数的负值。
语法
<result> = fneg [fast-math flags]* <ty> <op1> ; yields ty:result
参数说明:
ty:必须是浮点类型或者浮点类型矢量(Vector)。
语义
该指令复制操作数的值,并将标志位翻转。该指令可以使用fast-math flags,使能不安全的浮点数优化。
示例
<result> = fneg float %val ; yields float:result = -%var
Binary Operators
所有的Binary Operators在llvm中均使用类BinaryOperator实现,没有单独的子类。
add
add指令返回两个操作数的和。
语法
<result> = add <ty> <op1>, <op2> ; yields ty:result
<result> = add nuw <ty> <op1>, <op2> ; yields ty:result
<result> = add nsw <ty> <op1>, <op2> ; yields ty:result
<result> = add nuw nsw <ty> <op1>, <op2> ; yields ty:result
参数说明:
ty:两个操作数的类型相同,必须是整型或者整形类型矢量。
语义
add指令返回两个操作数的和。如果result为无符号数且溢出,则result = result % 2n,其中n为result的位宽。因为LLVM整形使用二进制补码的形式,所以add指令可以同时用于有符号和无符号数。
nuw表示“No Unsigned Wrap”,如果设置了该关键字,则无符号数加法溢出得到的result为Poison Value。
nsw表示"No signed Wrap",如果设置了该关键字,则有符号数加法溢出得到的result为Poison Value。
示例
<result> = add i32 4, %var ; yields i32:result = 4 + %var
fadd
fadd指令返回两个操作数的和。
语法
<result> = fadd [fast-math flags]* <ty> <op1>, <op2> ; yields ty:result
参数说明:
ty:两个操作数的类型相同,必须是浮点类型或者浮点类型矢量。
语义
fadd指令返回两个操作数的和。该指令可以使用fast-math flags,使能不安全的浮点数优化。
示例
<result> = fadd float 4.0, %var ; yields float:result = 4.0 + %var
sub
sub指令返回两个操作数的差。
语法
<result> = sub <ty> <op1>, <op2> ; yields ty:result
<result> = sub nuw <ty> <op1>, <op2> ; yields ty:result
<result> = sub nsw <ty> <op1>, <op2> ; yields ty:result
<result> = sub nuw nsw <ty> <op1>, <op2> ; yields ty:result
参数说明:
ty:两个操作数的类型相同,必须是整型或者整形类型矢量。
语义
sub指令返回两个操作数的差。如果result为无符号数且溢出,则result = result % 2n,其中n为result的位宽。因为LLVM整形使用二进制补码的形式,所以sub指令可以同时用于有符号和无符号数。
nuw表示“No Unsigned Wrap”,如果设置了该关键字,则无符号数减法溢出得到的result为Poison Value。
nsw表示"No signed Wrap",如果设置了该关键字,则有符号数减法溢出得到的result为Poison Value。
示例
<result> = sub i32 4, %var ; yields i32:result = 4 - %var
<result> = sub i32 0, %val ; yields i32:result = -%var
fsub
fsub指令返回两个操作数的差。
语法
<result> = fsub [fast-math flags]* <ty> <op1>, <op2> ; yields ty:result
参数说明:
ty:两个操作数的类型相同,必须是浮点类型或者浮点类型矢量。
语义
fsub指令返回两个操作数的差。该指令可以使用fast-math flags,使能不安全的浮点数优化。
示例
<result> = fsub float 4.0, %var ; yields float:result = 4.0 - %var
<result> = fsub float -0.0, %val ; yields float:result = -%var
mul
mul指令返回两个操作数的乘积。
语法
<result> = mul <ty> <op1>, <op2> ; yields ty:result
<result> = mul nuw <ty> <op1>, <op2> ; yields ty:result
<result> = mul nsw <ty> <op1>, <op2> ; yields ty:result
<result> = mul nuw nsw <ty> <op1>, <op2> ; yields ty:result
参数说明:
ty:两个操作数的类型相同,必须是整型或者整形类型矢量。
语义
mul指令返回两个操作数的乘积。如果result为无符号数且溢出,则result = result % 2n,其中n为result的位宽。因为LLVM整形使用二进制补码的形式,所以mul指令可以同时用于有符号和无符号数。
nuw表示“No Unsigned Wrap”,如果设置了该关键字,则无符号数乘法溢出得到的result为Poison Value。
nsw表示"No signed Wrap",如果设置了该关键字,则有符号数乘法溢出得到的result为Poison Value。
示例
<result> = mul i32 4, %var ; yields i32:result = 4 * %var
fmul
fmul指令返回两个操作数的乘积。
语法
<result> = fmul [fast-math flags]* <ty> <op1>, <op2> ; yields ty:result
参数说明:
ty:两个操作数的类型相同,必须是浮点类型或者浮点类型矢量。
语义
fmul指令返回两个操作数的乘积。该指令可以使用fast-math flags,使能不安全的浮点数优化。
示例
<result> = fmul float 4.0, %var ; yields float:result = 4.0 * %var
udiv
udiv指令返回两个操作数的商。
语法
<result> = udiv <ty> <op1>, <op2> ; yields ty:result
<result> = udiv exact <ty> <op1>, <op2> ; yields ty:result
参数说明:
ty: 两个操作数的类型相同,必须是整型或者整形类型矢量。
语义
udiv指令返回两个无符号数的商,除0的行为是未定义的。如果使用了exact关键字,则如果op1不是op2的整数倍,result是一个Poison Value。
示例
<result> = udiv i32 4, %var ; yields i32:result = 4 / %var
sdiv
sdiv指令返回两个操作数的商。
语法
<result> = sdiv <ty> <op1>, <op2> ; yields ty:result
<result> = sdiv exact <ty> <op1>, <op2> ; yields ty:result
参数说明:
ty: 两个操作数的类型相同,必须是整型或者整形类型矢量。
语义
udiv指令返回两个有符号数的商,除0的行为是未定义的。除法溢出同样会导致未定义行为,比如做32位除法:-2147483648 / -1(2147483648超过了有符号整型的范围)
如果使用了exact关键字,则如果op1不是op2的整数倍,result是一个Poison Value。
示例
<result> = sdiv i32 4, %var ; yields i32:result = 4 / %var
fdiv
fdiv指令返回两个操作数的商。
语法
<result> = fdiv [fast-math flags]* <ty> <op1>, <op2> ; yields ty:result
参数说明:
ty: 两个操作数的类型相同,必须是浮点类型或者浮点类型矢量。
语义
fdiv指令返回两个浮点数的商。该指令可以使用fast-math flags,使能不安全的浮点数优化。
示例
<result> = fdiv float 4.0, %var ; yields float:result = 4.0 / %var
urem
urem指令返回两个操作数的余数。
语法
<result> = urem <ty> <op1>, <op2> ; yields ty:result
参数说明:
ty: 两个操作数的类型相同,必须是整型或者整形类型矢量。
语义
urem指令返回两个无符号数的余数,除0的行为是未定义的。
示例
<result> = urem i32 4, %var ; yields i32:result = 4 % %var
srem
srem指令返回两个操作数的余数。
语法
<result> = srem <ty> <op1>, <op2> ; yields ty:result
参数说明:
ty: 两个操作数的类型相同,必须是整型或者整形类型矢量。
语义
srem指令返回两个无符号数的余数,余数的符号和被除数一致。除0的行为是未定义的。除法溢出同样会导致未定义行为,比如做32位除法:-2147483648 / -1(2147483648超过了有符号整型的范围)
示例
<result> = frem float 4.0, %var ; yields float:result = 4.0 % %var
shl
shl指令返回第1个操作数左移第2个操作数指定的bit的结果。
语法
<result> = shl <ty> <op1>, <op2> ; yields ty:result
<result> = shl nuw <ty> <op1>, <op2> ; yields ty:result
<result> = shl nsw <ty> <op1>, <op2> ; yields ty:result
<result> = shl nuw nsw <ty> <op1>, <op2> ; yields ty:result
参数说明:
ty:两个操作数的类型相同,必须是整型或者整形类型矢量。其中op2会被当作无符号数处理。
语义
result = op1 * 2^op2 mod 2^n
其中n是result的位宽,如果op2等于或者大于op1的位宽,则result为一个Poison Value。
nuw表示“No Unsigned Wrap”,如果设置了该关键字,则无符号数移位溢出得到的result为Poison Value。
nsw表示"No signed Wrap",如果设置了该关键字,则有符号数移位溢出得到的result为Poison Value。
示例
<result> = shl i32 4, %var ; yields i32: 4 << %var
<result> = shl i32 4, 2 ; yields i32: 16
<result> = shl i32 1, 10 ; yields i32: 1024
<result> = shl i32 1, 32 ; undefined
<result> = shl <2 x i32> < i32 1, i32 1>, < i32 1, i32 2> ; yields: result=<2 x i32> < i32 2, i32 4>
lshr
lshr指令返回第1个操作数逻辑右移第2个操作数指定的bit并用0填充MSB的结果。
语法
<result> = lshr <ty> <op1>, <op2> ; yields ty:result
<result> = lshr exact <ty> <op1>, <op2> ; yields ty:result
参数说明:
ty:两个操作数的类型相同,必须是整型或者整形类型矢量。其中op2会被当作无符号数处理。
语义
指令实现逻辑右移,既使用0填充移位后的MSB。如果op2等于或大于op1的位宽,则result为Poison Value。如果设置了exact关键字,则如果右移出的bit不为0,result为Poison Value。
示例
<result> = lshr i32 4, 1 ; yields i32:result = 2
<result> = lshr i32 4, 2 ; yields i32:result = 1
<result> = lshr i8 4, 3 ; yields i8:result = 0
<result> = lshr i8 -2, 1 ; yields i8:result = 0x7F
<result> = lshr i32 1, 32 ; undefined
<result> = lshr <2 x i32> < i32 -2, i32 4>, < i32 1, i32 2> ; yields: result=<2 x i32> < i32 0x7FFFFFFF, i32 1>
ashr
ashr指令返回第1个操作数算术右移第2个操作数指定的bit的结果。
语法
<result> = ashr <ty> <op1>, <op2> ; yields ty:result
<result> = ashr exact <ty> <op1>, <op2> ; yields ty:result
参数说明:
ty:两个操作数的类型相同,必须是整型或者整形类型矢量。其中op2会被当作无符号数处理。
语义
指令实现算术右移,既使用op1的符号位填充移位后的MSB。如果op2等于或大于op1的位宽,则result为Poison Value。如果设置了exact关键字,则如果右移出的bit不为0,result为Poison Value。
示例
<result> = ashr i32 4, 1 ; yields i32:result = 2
<result> = ashr i32 4, 2 ; yields i32:result = 1
<result> = ashr i8 4, 3 ; yields i8:result = 0
<result> = ashr i8 -2, 1 ; yields i8:result = -1
<result> = ashr i32 1, 32 ; undefined
<result> = ashr <2 x i32> < i32 -2, i32 4>, < i32 1, i32 3> ; yields: result=<2 x i32> < i32 -1, i32 0>
and
and指令返回两个操作数的按位逻辑与的结果。
语法
<result> = and <ty> <op1>, <op2> ; yields ty:result
参数说明:
ty:两个操作数的类型相同,必须是整型或者整形类型矢量。
语义
and指令的真值表:
In0 | In1 | Out |
0 | 0 | 0 |
0 | 1 | 0 |
1 | 0 | 0 |
1 | 1 | 1 |
示例
<result> = and i32 4, %var ; yields i32:result = 4 & %var
<result> = and i32 15, 40 ; yields i32:result = 8
<result> = and i32 4, 8 ; yields i32:result = 0
or
and指令返回两个操作数的按位逻辑或的结果。
语法
<result> = or <ty> <op1>, <op2> ; yields ty:result
参数说明:
ty:两个操作数的类型相同,必须是整型或者整形类型矢量。
语义
or指令的真值表:
In0 | In1 | Out |
0 | 0 | 0 |
0 | 1 | 1 |
1 | 0 | 1 |
1 | 1 | 1 |
示例
<result> = or i32 4, %var ; yields i32:result = 4 | %var
<result> = or i32 15, 40 ; yields i32:result = 47
<result> = or i32 4, 8 ; yields i32:result = 12
xor
and指令返回两个操作数的按位逻辑异或的结果。
语法
<result> = xor <ty> <op1>, <op2> ; yields ty:result
参数说明:
ty:两个操作数的类型相同,必须是整型或者整形类型矢量。
语义
xor指令的真值表:
In0 | In1 | Out |
0 | 0 | 0 |
0 | 1 | 1 |
1 | 0 | 1 |
1 | 1 | 0 |
示例
<result> = xor i32 4, %var ; yields i32:result = 4 ^ %var
<result> = xor i32 15, 40 ; yields i32:result = 39
<result> = xor i32 4, 8 ; yields i32:result = 12
<result> = xor i32 %V, -1 ; yields i32:result = ~%V