I haven't gotten a response on my previous question, below, so I tried the following change to SelectionDAGBuilder.cpp:<div><br></div><div><div>@@ -1026,7 +1026,8 @@</div><div><br></div><div> return DAG.getConstant(0, TLI.getPointerTy());</div>
<div> </div><div> if (const ConstantFP *CFP = dyn_cast<ConstantFP>(C))</div><div>- return DAG.getConstantFP(*CFP, VT);</div><div>+ return DAG.getConstantFP(</div><div>+ *CFP, VT, TLI.isFPImmLegal(CFP->getValueAPF(), EVT::getEVT(V->getType())));</div>
<div> </div><div> if (isa<UndefValue>(C) && !V->getType()->isAggregateType())</div><div> return DAG.getUNDEF(VT);</div><div><br></div><div><br></div>That is, if FP immediates are ok in the target, generate the constant as a target constant. Is this an acceptable change?</div>
<div><br></div><div><br><div class="gmail_quote">On Thu, Feb 9, 2012 at 5:23 PM, Joe Matarazzo <span dir="ltr"><<a href="mailto:joe.matarazzo@gmail.com">joe.matarazzo@gmail.com</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
This code lives in DAGCombiner.cpp:<div><br></div><div>-------------<br><div><div> // Turn 'store float 1.0, Ptr' -> 'store int 0x12345678, Ptr'</div><div> if (ConstantFPSDNode *CFP = dyn_cast<ConstantFPSDNode>(Value)) {</div>
<div> // NOTE: If the original store is volatile, this transform must not increase</div><div> // the number of stores. For example, on x86-32 an f64 can be stored in one</div><div> // processor operation but an i64 (which is not legal) requires two. So the</div>
<div> // transform should not be done in this case.</div><div> if (Value.getOpcode() != ISD::TargetConstantFP) {</div><div> SDValue Tmp;</div><div> switch (CFP->getValueType(0).getSimpleVT().SimpleTy) {</div>
<div> default: llvm_unreachable("Unknown FP type");</div><div> case MVT::f80: // We don't do this for these yet.</div><div> case MVT::f128:</div><div> case MVT::ppcf128:</div><div> break;</div>
<div> case MVT::f32:</div><div> if ((isTypeLegal(MVT::i32) && !LegalOperations && !ST->isVolatile()) ||</div><div> TLI.isOperationLegalOrCustom(ISD::STORE, MVT::i32)) {</div><div>
Tmp = DAG.getConstant((uint32_t)CFP->getValueAPF().</div><div> bitcastToAPInt().getZExtValue(), MVT::i32);</div><div> return DAG.getStore(Chain, N->getDebugLoc(), Tmp,</div>
<div> Ptr, ST->getPointerInfo(), ST->isVolatile(),</div><div> ST->isNonTemporal(), ST->getAlignment());</div><div> }</div><div> break;</div>
-------------</div></div><div><br></div><div>What would be the proper way to inhibit this change? In my target (a custom b/e) MVT::i32 is a legal type, and I have a "store MVT::i32" instruction, but I want to later promote the store to a MOV (in a custom lowering step), and this code above is changing the register class, such that it won't coalesce. The debug output looks like this (%Xn are phys regs in F32RC regclass)</div>
<div><br></div><div>--------------</div><div><div>BB#0: derived from LLVM BB %entry</div><div><span style="white-space:pre-wrap"> </span>%vreg0<def> = MOV_I32_RI 1; I32RC:%vreg0</div><div><span style="white-space:pre-wrap"> </span>%X0<def> = COPY %vreg0; I32RC:%vreg0</div>
<div><span style="white-space:pre-wrap"> </span>%vreg1<def> = MOV_I32_RI 0; I32RC:%vreg1</div><div><span style="white-space:pre-wrap"> </span>%X1<def> = COPY %vreg1; I32RC:%vreg1</div>
<div><span style="white-space:pre-wrap"> </span>%X2<def> = COPY %vreg1; I32RC:%vreg1</div><div><span style="white-space:pre-wrap"> </span>RET</div><div><br></div><div># End machine code for function foo</div>
<div><br></div><div>********** SIMPLE REGISTER COALESCING **********</div><div>********** Function: foo</div><div>********** JOINING INTERVALS ***********</div><div>entry:</div><div>32L<span style="white-space:pre-wrap"> </span>%X0<def> = COPY %vreg0<kill>; I32RC:%vreg0</div>
<div><span style="white-space:pre-wrap"> </span>Not coalescable.</div></div><div>--------------</div><div><br></div><div>I thought about using the ISD::TargetConstantFP designation on the source, but how does that get set? I couldn't see it used anywhere in the up-front Lower stage of SelectionDAG creation.</div>
<div><br></div><div>Or, if I'm just not approaching the machine code/setup correctly, please let me know that too. :)</div><div><br></div><div>Thanks,</div><div>Joe</div>
</blockquote></div><br></div>