Part of waitpkg is the TPAUSE instruction. This instruction gives an
RDTSC deadline to go in to a low power sleep mode with the CPU.
Semantically we can't implement umonitor and umwait with ARM's exclusive
monitor implementation, but a nop implementation is sane. Just need to
make sure to clear the pre-req flags.
This lowers power consumption of UE5 games since their job handler now
goes to a tpause based implementation instead of a `pause` spinloop
implementation.
If a multiblock contains a call instruction, we know at the point
of compilation that the instruction after that call will likely be
jumped to at some point. Avoid redundant recompilation by tracking
such cases and including an entrypoint for that instruction in the
multiblock aswell.
this makes it a lot easier to turn a long division into a non-long division,
just by nulling out a source.
Signed-off-by: Alyssa Rosenzweig <alyssa@rosenzweig.io>
Beyond the actual registers allocated, there are two pieces of sideband data we
store in the RAData object:
* # of spill slots (explicitly)
* whether RA has run (implicitly by the existence of RAData)
We want to get rid of RAData, so we'll move these to the header.
Signed-off-by: Alyssa Rosenzweig <alyssa@rosenzweig.io>
It is common practice for games to use CPUID as an instruction barrier
for various reasons. Ensure that we respect this by adding support for
an instruction barrier.
FEAT_ECV added a new synchronizing cycle counter instruction that
restrict speculation across the cycle counter access. Because it
restricts speculation, it effectively acts like an isb and load dsb.
Luckily for us, this actually matches behaviour for what rdtscp does, so
we can take advantage of it if the host supports FEAT_ECV.
this gets deleted by an upcoming opt pass, but we shouldn't be depending on
the opt pass for it!
Signed-off-by: Alyssa Rosenzweig <alyssa@rosenzweig.io>
ZF needs to be preserved.
the new code is the same instr count on flagm although probably an extra uop.
the inst count regression is on flagm, but we can't tolerate broken behaviour.
Signed-off-by: Alyssa Rosenzweig <alyssa@rosenzweig.io>
Most of this table ignores REX.W, but two encodings change behaviour
based on REX.W. These two encodings are PEXTRD/PEXTRQ and PINSRD/PINSRQ.
For every other instruction encoding, they will ignore REX.W, but FEX
was requiring that they didn't have REX.W encoding. I had special cased
this in the past by adding PALIGNR, but that didn't handle any of the
other instructions.
We can't just handle REX.W in the OpcodeDispatcher and remove the two
special cased instructions because these vector operations also interact
with instruction prefix 0x66 which changes the operating size to 16bit
with regular instructions.
So instead just generate all listings of instructions with REX.W being
zero and one and install handlers in all cases.