39 Commits

Author SHA1 Message Date
Craig Topper
ac51cf1960 [RISCV] Refactor RISCV::hasAllWUsers to hasAllNBitUsers similar to RISCVISelDAGToDAG's version. NFC
Move to RISCVInstrInfo since we need RISCVSubtarget now.

Instead of asking if only the lower 32 bits are used we can now
ask if the lower N bits are used. This will be needed by a future
patch.
2022-12-28 12:49:23 -08:00
Craig Topper
1184ede46f [RISCV] Add const qualifiers to some function arguments. NFC 2022-12-28 11:20:17 -08:00
Craig Topper
653a9fbd13 [RISCV] Support the short-forward-branch predicated ops in RISCVSExtWRemoval. 2022-12-23 21:39:22 -08:00
Nitin John Raj
d64d3c5a8f [RISCV] Add pass to remove W suffix from ADDIW and SLLIW to improve compressibility
SLLI and ADD are more compressible than SLLIW and ADDW. SLLI/ADD both have a 5-bit register encoding. SLLIW/ADDW have a 3-bit register encoding. They both require the dest to also be one of the sources.

We aggressively form ADDW/SLLIW as it helps hasAllWBitUsers in RISCVISelDAGToDAG to not require recursion. So we need a pass to remove excessive -w suffixes.

Differential Revision: https://reviews.llvm.org/D139948
2022-12-22 14:19:26 -08:00
Craig Topper
88793a0478 [RISCV] Add XVentanaCondOps to RISCVSExtWRemoval. 2022-12-20 18:46:45 -08:00
Craig Topper
a0f168fa89 Revert "[RISCV] Support the short-forward-branch predicatd ops in RISCVSExtWRemoval."
This reverts commit 9e586217f4e331bca241df00648ca0b71edd3ef6.

I think there's at least one mistake in this.
2022-12-17 00:11:53 -08:00
Craig Topper
9e586217f4 [RISCV] Support the short-forward-branch predicatd ops in RISCVSExtWRemoval. 2022-12-16 23:25:26 -08:00
Craig Topper
992bee045b [RISCV] Teach RISCVSExtWRemoval to remove sext.w whose upper bits aren't demanded.
SelectionDAG aggressively creates sext_inreg operations after
promoting an i32 add. If the add is later matched to a sh1add,
sh2add or sh3add, a sext.w from the sext_inreg will get left behind.
In many cases we can prove this sext.w is unnecessary by checking
if its upper bits are ever used.
2022-12-15 11:01:20 -08:00
Craig Topper
3e7dad22f1 [RISCV] Add a bit to TSFlags to mark SignExtendingOpW instructions for SExtWRemoval.
Instead of switching on the opcode in SExtWRemoval, we can use a
bit in TSFlags. This reduces the amount of code that needs to be
generated to implement the switch. The opcodes are scattered throughout
the opcode enum, so the switch isn't very densely packed.

Reviewed By: asb

Differential Revision: https://reviews.llvm.org/D139965
2022-12-14 10:38:48 -08:00
Craig Topper
844430bcc3 [RISCV] Add support for call returns to RISCVSExtWRemoval.
The implementation is inspired by code from PPCInstrInfo.

We look for a copy from X10(A0) preceded by an ADJCALLSTACKUP and
a PseudoCall. We use the PseudoCall to look up the IR function being
called to find it's return attributes.

Reviewed By: asb

Differential Revision: https://reviews.llvm.org/D139808
2022-12-13 09:09:13 -08:00
Craig Topper
dc9b17884e [RISCV] Use a helper function to reduce duplicated code in RISCVSExtWRemoval. NFC
We were checking for virtual register and calling getVReg in
multiple places before adding to the worklist.
2022-12-11 00:35:20 -08:00
Craig Topper
f99514ac3a [RISCV] Remove SExtWRemovalCands set from RISCVSExtWRemoval.
After D137970, we do the fixable instruction conversion in place
so we don't need to worry about iterator invalidation. This lets
us to conversion and updates in a single loop.

Reviewed By: reames

Differential Revision: https://reviews.llvm.org/D138043
2022-11-21 19:24:02 -08:00
Craig Topper
4e6adb394e [RISCV] Transform fixable instruction in place in RISCVSExtWRemoval. NFC
Instead of creating a new instruction and copying operands, we can
use setDesc to convert in place.

Reviewed By: reames

Differential Revision: https://reviews.llvm.org/D137970
2022-11-21 19:22:53 -08:00
Craig Topper
65f9992865 [RISCV] Add PseudoCCMOVGPR to RISCVSExtWRemoval.
This instruction is a conditional move. It propagates sign bits
from its inputs.
2022-11-14 13:39:00 -08:00
Craig Topper
63571e83cb [RISCV] Add scalar FP compares to isSignExtendingOpW in RISCVSExtWRemoval. 2022-11-14 10:28:36 -08:00
Craig Topper
18278d807a [RISCV] Move FixableDef handling out of isSignExtendingOpW.
We have two layers of opcode checks. The first is in
isSignExtendingOpW. If that returns false, a second switch is used
for looking through nodes by adding them to the worklist.

Move the FixableDef handling to the second switch. This simplies
the interface of isSignExtendingOpW and makes that function more
accurate to its name.
2022-11-14 10:14:17 -08:00
Craig Topper
1f25888712 [RISCV] Add PACKW and PACKH to isSignExtendingOpW in RISCVSExtWRemoval.
PACKW sign extends like other W instructions.
PACKH zeroes bits 63:16 which means bits 63:31 are all zero.
2022-11-13 20:00:34 -08:00
Craig Topper
03f9009cbf [RISCV] Fix incorrect early out from isSignExtendedW in RISCVSExtWRemoval.
We can only return false to abort. If the criteria is met we need
to use continue instead. Returning true stops us from visiting all
nodes and makes the caller think it is safe to remove sext.w.
2022-11-13 17:30:39 -08:00
Craig Topper
6373f8c317 [RISCV] Add BREV8 to hasAllWUsers in RISCVSExtWRemoval.
This instruction reverses the bits in each byte. Since we're only
interested in whether the upper 32 bits are used or not, we can
look through them to check their users.
2022-11-13 11:59:33 -08:00
Craig Topper
9e14ffa444 [RISCV] Add PACK/PACKH/PACKW to hasAllWUsers in RISCVSExtWRemoval. 2022-11-13 11:34:14 -08:00
Craig Topper
0b01aebf5e [RISCV] Support BSET/BCLR/BINV in hasAllWUsers.
These instructions set, clear, or invert a single bit. If their
users don't use the upper 32 bits, they don't use the upper 32 bits
of their input.

Additionally the second operand BSET/BCLR/BINV is a shift amount
which only uses 6 bits of the source.

Reviewed By: asb

Differential Revision: https://reviews.llvm.org/D137452
2022-11-09 11:32:20 -08:00
Craig Topper
902976a379 [RISCV] Support shift/rotate amount operands in isAllUsesReadW.
These operands use 6 bits.

Reviewed By: asb

Differential Revision: https://reviews.llvm.org/D137450
2022-11-09 11:32:20 -08:00
Craig Topper
bc6df5737f [RISCV] Improve support for ADD_UW/SHXADD_UW in hasAllWUsers.
The first use operand of these is implicitly zero extended. We
can consider that a W read. If the use is the other operand, we
need to look through the instruction.

Reviewed By: asb

Differential Revision: https://reviews.llvm.org/D137449
2022-11-09 11:32:19 -08:00
Craig Topper
7f018b45f9 [RISCV] Support SB/SH/SW in hasAllWUsers in RISCVSExtWRemoval.
After D137446 we can see which operand is the user. If the user
is the value operand of a SB/SH/SW then the upper 32 bits aren't
used.

Reviewed By: asb

Differential Revision: https://reviews.llvm.org/D137448
2022-11-09 11:32:19 -08:00
Craig Topper
5e3df94a17 [RISCV] Rework hasAllWUsers in RISCVSExtWRemoval. NFCI
Instead of storing the uses to check in the worklist, store the
instruction we want to check uses for.

Now we pop and instruction from the worklist, loop over its uses
and check them. If it's something we need to look across, we'll push
it to the worklist.

By doing it this way, we can have access to which operand
of the user is using the instruction. This will allow supporting
store instructions since we'll be able to disambiguate the the value
operand and the pointer operand. We can also improve support for
*add.uw instructions and shift amount uses.

Reviewed By: mohammed-nurulhoque, asb

Differential Revision: https://reviews.llvm.org/D137446
2022-11-09 11:32:19 -08:00
Craig Topper
d6b224edd3 [RISCV] Rename isAllUsesReadW to hasAllWUsers in RISCVSExtWRemoval. NFC 2022-11-04 17:04:44 -07:00
Craig Topper
2fb1324736 [RISCV] Add FMV_H_X/FMV_W_X/FCVT_H_W/FCVT_H_WU to isAllUsesReadW in SExtWRemoval.
The instructions only read the lower 16 or 32 bits of a GPR.
2022-11-03 23:59:09 -07:00
Craig Topper
4a6ef0078c [RISCV] Change SEXT_B/SEXT_H/ZEXT_H_RV64 handling in isAllUsesReadW in SExtWRemoval.
These instrucitons only use the lower 8 or 16 bits. We don't need
to look across them.
2022-11-03 23:59:08 -07:00
Craig Topper
374e6462a4 [RISCV] Add missing break to the last case in a switch. NFC
Might create a problem in the future if more cases are added.
2022-11-03 16:24:02 -07:00
Craig Topper
ece4bb5ab8 [RISCV] Teach SExtWRemoval to recognize sign extended values that come from arguments.
This information is not preserved in MIR today. So this patch adds
information to RISCVMachineFunctionInfo when the vreg is created for
the argument.

Reviewed By: reames

Differential Revision: https://reviews.llvm.org/D134621
2022-10-04 15:39:10 -07:00
Kazu Hirata
2833760c57 [Target] Qualify auto in range-based for loops (NFC) 2022-08-28 17:35:09 -07:00
Fangrui Song
de9d80c1c5 [llvm] LLVM_FALLTHROUGH => [[fallthrough]]. NFC
With C++17 there is no Clang pedantic warning or MSVC C5051.
2022-08-08 11:24:15 -07:00
Craig Topper
d7f2a63371 [RISCV] Fold stack reload into sext.w by using lw instead of ld.
We can use lw to load 4 bytes from the stack and sign extend them
instead of loading all 8 bytes.

Reviewed By: asb

Differential Revision: https://reviews.llvm.org/D129948
2022-07-18 09:09:17 -07:00
Mohammed Nurul Hoque
5dd99f71aa [RISCV] transform MI to W variant to remove sext.w
Backwards search
The sext.w removal pass (before the new patch) checks if the input to sext.w is already in sign-extended form, so it can eliminate it. It does that by checking every definition/source that reaches the sext.w is an instruction that produces a sign-extended value, either by definition (e.g. ADDW), or it propagates sign-extension (e.g. OR) so we check its sources recursively.

Forward search
Sometimes, one of the sources is an instruction that doesn't always produce a sign-extended value, but it has a W-version that does (e.g. ADD / ADDW). If we transform the ADD to ADDW, the sext.w can be removed (assuming other def paths are satisfied), but this transformation is sound only if every use of this ADD/W only reqruires the lower 32-bits either directly (like sll %x, 32) or they propagate dependency (lower word of output only depends on lower word of input) so we check its uses recursively.

When searching backwards, if an instruction that can be replaced with W-variant is encountered, this pass runs the forward search to verify it can be replaced, then adds it to a list of fixable instructions. After verifying all paths, it replaces the instruction and removes the sext.w.

Reviewed By: craig.topper

Differential Revision: https://reviews.llvm.org/D119928
2022-04-22 10:59:26 -07:00
Mohammed Nurul Hoque
7afa44f5f5 [RISCV] Add more sign-extending ops to MIR sext.w pass.
This patch adds single-bit and bit-counting ops to list of sign-extending ops.

A single-bit write propagates sign-extendedness if it's not in the sign-bits.

Bit extraction and bit counting always outputs a small number, so sign-extended.

Reviewed By: craig.topper

Differential Revision: https://reviews.llvm.org/D121152
2022-03-18 18:21:17 +08:00
Craig Topper
237eb37260 [RISCV] Add FMV_X_W and FMV_X_H to RISCVSExtWRemoval.
Add -target-abi to sextw-removal.ll RUN lines to show benefit on
new test case.
2022-02-03 09:40:47 -08:00
Alex Bradbury
588f121ada [RISCV][NFC] Make Zb* instruction naming match the convention used elsewhere in the RISC-V backend
Where the instruction mnemonic contains a dot, we name the corresponding
instruction in the .td file using a _ in the place of the dot. e.g. LR_W
rather than LRW. This commit updates RISCVInstrInfoZb.td to follow that
convention.
2022-01-28 15:20:37 +00:00
Mohammed Nurul Hoque
21c79be5d7 [RISCV] Add patterns to MIR sign-extension removal pass.
This patch adds a few instruction patterns that generate sign-extended values or propagate them, adding to the pass introduced in https://reviews.llvm.org/D116397

Reviewed By: craig.topper

Differential Revision: https://reviews.llvm.org/D117465
2022-01-19 17:33:58 -08:00
Craig Topper
56ca11e31e [RISCV] Add an MIR pass to replace redundant sext.w instructions with copies.
Function calls and compare instructions tend to cause sext.w
instructions to be inserted. If we make good use of W instructions,
these operations can often end up being redundant. We don't always
detect these during SelectionDAG due to things like phis. There also
some cases caused by failure to turn extload into sextload in
SelectionDAG. extload selects to LW allowing later sext.ws to become
redundant.

This patch adds a pass that examines the input of sext.w instructions trying
to determine if it is already sign extended. Either by finding a
W instruction, other instructions that produce a sign extended result,
or looking through instructions that propagate sign bits. It uses
a worklist and visited set to search as far back as necessary.

Reviewed By: asb, kito-cheng

Differential Revision: https://reviews.llvm.org/D116397
2022-01-06 08:23:42 -08:00