when compiling code like
short ptr * = some_address;
val = *ptr;
val = 2047;
else if (val<-2048)
val = -2048.
// other things done that require val to be an int ...
The load operation is represented by a load and a sign extension operation in the LLVM IR. On most target architectures, there exist signed halfword load instructions, so the load and sign extension are effectively translated into a single instruction during instruction selection. Nonetheless, this sign extension operation in the IR prohibits a lot of optimizations:
- it counts as an instruction in heuristics based on instruction counts (such as SimplifyCFG); as a result some simplifications are not performed;
- the sign extension operation gets combined with other operations. In the example, the sign extension gets combined with the 32-bit comparison implementing the val>-2048, resulting in a 16-bit comparison on the non-extended value; the result is a comparison operation on 16-bit operands, followed by a select operation on 32-bit operands:
%0 = load i16* %arrayidx2, align 2, !dbg !502
%conv = sext i16 %0 to i32, !dbg !502
%cmp16 = icmp sgt i16 %0, 2047, !dbg !510
br i1 %cmp16, label %if.end23, label %if.else, !dbg !510
if.else: ; preds = %for.body
%cmp19 = icmp slt i16 %0, -2048, !dbg !511 <--- 16-bit comparison
%.conv = select i1 %cmp19, i32 -2048, i32 %conv, !dbg !511 <--- 32-bit select
br label %if.end23, !dbg !511
if.end23: ; preds = %if.else, %for.body
%val1.0 = phi i32 [ 2047, %for.body ], [ %.conv, %if.else ]
%conv24 = trunc i32 %val1.0 to i16, !dbg !512
store i16 %conv24, i16* %arrayidx2, align 2, !dbg !512
The problem with this is that during instruction selection, the pair of comparison and select is no longer recognized as max operation because the operands of the two operations are not the same.
It seems to me that these and other limitations on the applied optimizations could easily be avoided by introducing a sign-extending halfword load operation into the IR.
Any ideas on this? And how big of an effort that might be?
Bjorn De Sutter
Computer Systems Lab