[llvm-commits] PR12385 PATCH: Missed constant propagation in loops

Stepan Dyatkovskiy STPWORLD at narod.ru
Sat Apr 28 12:38:20 PDT 2012


ping.

-Stepan

26.04.2012, 11:37, "Stepan Dyatkovskiy" <stpworld at narod.ru>:
> ping
> Stepan Dyatkovskiy wrote:
>
>>  Hi all. I solved PR12385 issue: Missed constant propagation in loops.
>>  LLVM and clang can't optimize next case:
>>  int i;
>>  void bar();
>>  int main(){
>>  i = 0;
>>  int j;
>>  for(j = 0; j < 10000; ++j) {
>>  if (i)
>>  bar();
>>  i = 0;
>>  }
>>  return 0;
>>  }
>>
>>  Ideally it should be folded to "int main() { return 0; }"
>>
>>  I improved Instruction Combining pass, so now it is possible to combine
>>  store + load instructions from different basic blocks.
>>
>>  The concept is next.
>>  We need to scan BB graph. And if we found "X = load Addr" instruction
>>  predecessed with the same "store C, Addr" instructions in all its
>>  predecessors, we can replace the "load" with the stored value ("C").
>>
>>  [store C, Addr] [store C, Addr] [store C, Addr]
>>  \ | /
>>  ------- | -------
>>  \ | /
>>  [X = load Addr] ==> X := C
>>
>>  There are some restrictions:
>>  1. Store/Load address should be non-volatile and it should be constant.
>>  2. The parent of "load" may be predecessed with some BB's that are still
>>  was not scanned (loops and BB's that marked as non-executable). In that
>>  case we should mark this load's as waiting until all predecessors will
>>  resolved; and after all executable edges and requested loops will
>>  scanned we can determine possibility of replacement.
>>  3. If some predecessor chain doesn't contains any "store" or it contains
>>  "store" with the same address and different value, the "load" inst could
>>  NOT be converted to constant then:
>>
>>  [store A, Addr] [store C, Addr]
>>  \ /
>>  ------- -------
>>  \ /
>>  [X = load Addr] ==> could NOT be replaced with a constant.
>>
>>  Data structure:
>>  For tracking we will use TrackedStoreInsts map, that has format:
>>  map<BB, StoreInstsInfo>
>>  where
>>  StoreInstsInfo is struct {
>>  set<BB> PendingBB;
>>  map<Address, StoreInst> Stores;
>>  }
>>
>>  Algorithm:
>>
>>  Go over all executable edges, collect stores info and propogate it
>>  through the graph:
>>
>>  1. Go over executable edges
>>  and for each BB do the next:
>>  2. If BB contains predecessors that was not scanned before, we can't
>>  determine possibility of replacement "load" with "constant" in current
>>  BB, since we need to scan all predecessors before. So, add this
>>  predecessor to the TrackedStoreInsts[BB].PendingBB set.
>>  3. Scan the BB instructions.
>>  3.1. If we found "store" instruction and it uses constant non-volatile
>>  address, and it stores constant value, save it in
>>  TrackedStoreInsts[BB].Stores.
>>  3.2. If we found "X = load Addr".
>>  3.2.1. If TrackedStoreInsts[BB].Stores doesn't contains "store C, Addr"
>>  ignore it.
>>  3.2.2. If TrackedStoreInsts[BB].PendingBBs is not empty(), scan each
>>  PendingBB, and if it was already tracked - remove it
>>  from PendingBBs.
>>  3.2.3. If TrackedStoreInsts[BB].Stores contains "store Addr, C"
>>  3.2.3.1. If TrackedStoreInsts[BB].PendingBBs is empty, then replace
>>  "load" with "C".
>>  3.2.3.2. If rackedStoreInsts[BB].PendingBBs is not empty, mark load as
>>  still unresolved.
>>  4. If we reached TerminatorInst, propogate stores info for each its
>>  successor then:
>>  4.1. Add all TrackedStoreInsts[BB].PendingBBs to the
>>  TrackedStoreInsts[Successor].PendingBBs.
>>  4.2. Perform set intersection of TrackedStoreInsts[BB].Stores and
>>  TrackedStoreInsts[Successor].Stores and save it in the last one.
>>  5. After all executable edges was scanned, resolve all remained "load"s:
>>  get load's BB, and if we found corresponent "store" in
>>  TrackedStoreInsts[BB].Stores, then it is possible to replace load with
>>  constant, otherwise zap it.
>>
>>  P.S.: By now whis optimization is integrated into SCCP. But may be it is
>>  better to make separated pass. What do you think?
>>
>>  -Stepan



More information about the llvm-commits mailing list