[llvm-commits] [llvm] r60972 - /llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAG.cpp
Duncan Sands
baldrick at free.fr
Fri Dec 12 23:18:39 PST 2008
Author: baldrick
Date: Sat Dec 13 01:18:38 2008
New Revision: 60972
URL: http://llvm.org/viewvc/llvm-project?rev=60972&view=rev
Log:
On big-endian machines it is wrong to do a full
width register load followed by a truncating
store for the copy, since the load will not place
the value in the lower bits. Probably partial
loads/stores can never happen here, but fix it
anyway.
Modified:
llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAG.cpp
Modified: llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAG.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAG.cpp?rev=60972&r1=60971&r2=60972&view=diff
==============================================================================
--- llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAG.cpp (original)
+++ llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAG.cpp Sat Dec 13 01:18:38 2008
@@ -648,11 +648,10 @@
unsigned RegBytes = RegVT.getSizeInBits() / 8;
unsigned NumRegs = (StoredBytes + RegBytes - 1) / RegBytes;
- // Make sure the stack slot is wide enough that we can do NumRegs full
- // width loads from it.
- SDValue StackPtr = DAG.CreateStackTemporary(StoredVT,
- MVT::getIntegerVT(NumRegs * RegBytes * 8));
- // Perform the original store only redirected to the stack slot.
+ // Make sure the stack slot is also aligned for the register type.
+ SDValue StackPtr = DAG.CreateStackTemporary(StoredVT, RegVT);
+
+ // Perform the original store, only redirected to the stack slot.
SDValue Store = DAG.getTruncStore(Chain, Val, StackPtr, NULL, 0,StoredVT);
SDValue Increment = DAG.getConstant(RegBytes, TLI.getPointerTy());
SmallVector<SDValue, 8> Stores;
@@ -674,15 +673,18 @@
Ptr = DAG.getNode(ISD::ADD, Ptr.getValueType(), Ptr, Increment);
}
- // Load one integer register's worth from the stack slot.
- SDValue Load = DAG.getLoad(RegVT, Store, StackPtr, NULL, 0);
+ // The last store may be partial. Do a truncating store. On big-endian
+ // machines this requires an extending load from the stack slot to ensure
+ // that the bits are in the right place.
+ MVT MemVT = MVT::getIntegerVT(8 * (StoredBytes - Offset));
+
+ // Load from the stack slot.
+ SDValue Load = DAG.getExtLoad(ISD::EXTLOAD, RegVT, Store, StackPtr,
+ NULL, 0, MemVT);
- // The last store may be partial. Do a truncating store.
- unsigned BytesLeft = StoredBytes - Offset;
Stores.push_back(DAG.getTruncStore(Load.getValue(1), Load, Ptr,
ST->getSrcValue(), SVOffset + Offset,
- MVT::getIntegerVT(BytesLeft * 8),
- ST->isVolatile(),
+ MemVT, ST->isVolatile(),
MinAlign(ST->getAlignment(), Offset)));
// The order of the stores doesn't matter - say it with a TokenFactor.
return DAG.getNode(ISD::TokenFactor, MVT::Other, &Stores[0],
@@ -749,10 +751,9 @@
unsigned RegBytes = RegVT.getSizeInBits() / 8;
unsigned NumRegs = (LoadedBytes + RegBytes - 1) / RegBytes;
- // Make sure the stack slot wide enough that we can do NumRegs full width
- // stores to it.
- SDValue StackBase = DAG.CreateStackTemporary(LoadedVT,
- MVT::getIntegerVT(NumRegs * RegBytes * 8));
+ // Make sure the stack slot is also aligned for the register type.
+ SDValue StackBase = DAG.CreateStackTemporary(LoadedVT, RegVT);
+
SDValue Increment = DAG.getConstant(RegBytes, TLI.getPointerTy());
SmallVector<SDValue, 8> Stores;
SDValue StackPtr = StackBase;
@@ -775,14 +776,16 @@
}
// The last copy may be partial. Do an extending load.
- unsigned BytesLeft = LoadedBytes - Offset;
+ MVT MemVT = MVT::getIntegerVT(8 * (LoadedBytes - Offset));
SDValue Load = DAG.getExtLoad(ISD::EXTLOAD, RegVT, Chain, Ptr,
LD->getSrcValue(), SVOffset + Offset,
- MVT::getIntegerVT(BytesLeft * 8),
- LD->isVolatile(),
+ MemVT, LD->isVolatile(),
MinAlign(LD->getAlignment(), Offset));
// Follow the load with a store to the stack slot. Remember the store.
- Stores.push_back(DAG.getStore(Load.getValue(1), Load, StackPtr, NULL, 0));
+ // On big-endian machines this requires a truncating store to ensure
+ // that the bits end up in the right place.
+ Stores.push_back(DAG.getTruncStore(Load.getValue(1), Load, StackPtr,
+ NULL, 0, MemVT));
// The order of the stores doesn't matter - say it with a TokenFactor.
SDValue TF = DAG.getNode(ISD::TokenFactor, MVT::Other, &Stores[0],
More information about the llvm-commits
mailing list