Page MenuHomePhabricator

Seperate volatility and atomicity/ordering in SelectionDAG
ClosedPublic

Authored by reames on Feb 1 2019, 10:09 AM.

Details

Summary

At the moment, we mark every atomic memory access as being also volatile. This is unnecessarily conservative and prohibits many legal transforms (DCE, folding, etc..).

This patch removes MOVolatile from the MachineMemOperands of atomic, but not volatile, instructions. This should be strictly NFC after a series of previous patches which have gone in to ensure backend code is conservative about handling of isAtomic MMOs. Once it's in and baked for a bit, we'll start working through removing unnecessary bailouts one by one. We applied this same strategy to the middle end a few years ago, with good success.

To make sure this patch itself is NFC, it is build on top of a series of other patches which adjust code to (for the moment) be as conservative for an atomic access as for a volatile access and build up a test corpus (mostly in test/CodeGen/X86/atomics-unordered.ll)..

Previously landed

  • D57593 Fix a bug in the definition of isUnordered on MachineMemOperand
  • D57596 [CodeGen] Be conservative about atomic accesses as for volatile
  • D57802 Be conservative about unordered accesses for the moment
  • rL353959: [Tests] First batch of cornercase tests for unordered atomics.
  • rL353966: [Tests] RMW folding tests w/unordered atomic operations.
  • rL353972: [Tests] More unordered atomic lowering tests.
  • rL353989: [SelectionDAG] Inline a single use helper function, and remove last non-MMO interface
  • rL354740: [Hexagon, SystemZ] Be super conservative about atomics
  • rL354800: [Lanai] Be super conservative about atomics
  • rL354845: [ARM] Be super conservative about atomics

Attention Out of Tree Backend Owners: This patch may break you. If it does, you can use the TLI getMMOFlags hook to restore the MOVolatile to any instruction you need to. (See llvm-dev thread titled "PSA: Changes to how atomics are handled in backends" started Feb 27, 2019.)

Work planned for once this is in, and has baked for a bit:

  • working through all of the TODOs in terms of code quality in the added tests
  • D57803 [X86][GlobalISEL] Support lowering aligned unordered atomics
  • ImplicitNullCheck for unordered loads
  • load folding for unordered loads
  • store folding for unordered stores
  • load/store unfolding
  • review of the other conservative bails outs inserted in pre-work for this patch

Diff Detail

Event Timeline

reames created this revision.Feb 1 2019, 10:09 AM
reames updated this revision to Diff 184792.Feb 1 2019, 10:44 AM

Missed a case, and got some failing tests this time. Yeah for test coverage!

asb added a subscriber: asb.Feb 4 2019, 11:20 AM
reames edited the summary of this revision. (Show Details)Feb 5 2019, 6:54 PM
reames edited the summary of this revision. (Show Details)Feb 5 2019, 7:36 PM
reames edited the summary of this revision. (Show Details)Feb 11 2019, 3:36 PM
vsk added a subscriber: vsk.Feb 13 2019, 11:58 AM
reames updated this revision to Diff 186755.Feb 13 2019, 3:15 PM
reames edited the summary of this revision. (Show Details)
reames added reviewers: jlebar, asb, jfb.
reames retitled this revision from [WIP] Seperate volatility and atomicity/ordering in SelectionDAG to Seperate volatility and atomicity/ordering in SelectionDAG.

No longer WIP, ready for real review.

Question for Reviewers: Going through uses of isVolatile in backend code, I see suspicious bits in Lania, ARM, and Hexagon. What's the best way to handle this? I can easily apply the workaround I mention for out of tree backends, or I could make them equally conservative for isAtomic. The other in tree backends appear to be fine, though I'd welcome review from folks knowledgeable of non-x86 backends.

asb added a subscriber: jyknight.

Adding @jyknight.

It seems there's a clear plan on the path forwards - is it worth writing it up as a short RFC on the mailing list, particular given the potential for subtle issues for out-of-tree backends?

In D57601#1401075, @asb wrote:

It seems there's a clear plan on the path forwards - is it worth writing it up as a short RFC on the mailing list, particular given the potential for subtle issues for out-of-tree backends?

I was planning on sending a note after it lands. Happy to do so now if folks things it's warranted.

Question for Reviewers: Going through uses of isVolatile in backend code, I see suspicious bits in Lania, ARM, and Hexagon. What's the best way to handle this? I can easily apply the workaround I mention for out of tree backends, or I could make them equally conservative for isAtomic. The other in tree backends appear to be fine, though I'd welcome review from folks knowledgeable of non-x86 backends.

I think adding the isAtomic check to the appropriate locations that are checking isVolatile makes the most sense, since it's easier to see and undo in the future, if that's desired.

Question for Reviewers: Going through uses of isVolatile in backend code, I see suspicious bits in Lania, ARM, and Hexagon. What's the best way to handle this? I can easily apply the workaround I mention for out of tree backends, or I could make them equally conservative for isAtomic. The other in tree backends appear to be fine, though I'd welcome review from folks knowledgeable of non-x86 backends.

I think adding the isAtomic check to the appropriate locations that are checking isVolatile makes the most sense, since it's easier to see and undo in the future, if that's desired.

D58490 is posted for review.

jlebar accepted this revision.Feb 26 2019, 9:55 AM

I'm not totally comfortable with this code, but this change looks reasonable to me.

This revision is now accepted and ready to land.Feb 26 2019, 9:55 AM
reames edited the summary of this revision. (Show Details)Feb 26 2019, 10:32 AM
reames updated this revision to Diff 188439.Feb 26 2019, 12:30 PM

When preparing to land the approved patch, I discovered one last issue. Essentially, the previously committed fixes for SystemZ and XCore are insufficient. Both backends do something odd which is they "lower" an AtomicSDNode into the corresponding *non* atomic LoadSDNode, and then let that be selected in turn. This results in a LoadSDNode w/an atomic (but non-volatile) memory operand. None of the DAG combines expect that. Amusingly, the test which fails actually has correct output (i.e. we DSE an atomic store), but I really want this patch to be non-functional.

The fix is simple: opt both backends out of the change for the moment. I could do a more fine grained fix, but I'd like to land this as is, specifically to demonstrate that the opt-out works for any downstream backends which are effected.

p.s. Sorry for not noticing this earlier. I must have not built these backends w/all of the various patches applied.

reames updated this revision to Diff 188443.Feb 26 2019, 12:33 PM

Helps if I upload the current diff...

jlebar accepted this revision.Feb 26 2019, 5:07 PM

Still LGTM.

reames edited the summary of this revision. (Show Details)Feb 27 2019, 10:42 AM
This revision was automatically updated to reflect the committed changes.
Herald added a project: Restricted Project. · View Herald TranscriptFeb 27 2019, 12:22 PM