@@ -466,48 +466,6 @@ void DIElementUseInfo::trackStoreToSelf(SILInstruction *I) {
466466 StoresToSelf.push_back (I);
467467}
468468
469- // ===----------------------------------------------------------------------===//
470- // Scalarization Logic
471- // ===----------------------------------------------------------------------===//
472-
473- // / Given a pointer to a tuple type, compute the addresses of each element and
474- // / add them to the ElementAddrs vector.
475- static void
476- getScalarizedElementAddresses (SILValue Pointer, SILBuilder &B, SILLocation Loc,
477- SmallVectorImpl<SILValue> &ElementAddrs) {
478- TupleType *TT = Pointer->getType ().castTo <TupleType>();
479- for (auto Index : indices (TT->getElements ())) {
480- ElementAddrs.push_back (B.createTupleElementAddr (Loc, Pointer, Index));
481- }
482- }
483-
484- // / Given an RValue of aggregate type, compute the values of the elements by
485- // / emitting a destructure.
486- static void getScalarizedElements (SILValue V,
487- SmallVectorImpl<SILValue> &ElementVals,
488- SILLocation Loc, SILBuilder &B) {
489- auto *DTI = B.createDestructureTuple (Loc, V);
490- llvm::copy (DTI->getResults (), std::back_inserter (ElementVals));
491- }
492-
493- // / Scalarize a load down to its subelements. If NewLoads is specified, this
494- // / can return the newly generated sub-element loads.
495- static SILValue scalarizeLoad (LoadInst *LI,
496- SmallVectorImpl<SILValue> &ElementAddrs) {
497- SILBuilderWithScope B (LI);
498- SmallVector<SILValue, 4 > ElementTmps;
499-
500- for (unsigned i = 0 , e = ElementAddrs.size (); i != e; ++i) {
501- auto *SubLI = B.createTrivialLoadOr (LI->getLoc (), ElementAddrs[i],
502- LI->getOwnershipQualifier ());
503- ElementTmps.push_back (SubLI);
504- }
505-
506- if (LI->getType ().is <TupleType>())
507- return B.createTuple (LI->getLoc (), LI->getType (), ElementTmps);
508- return B.createStruct (LI->getLoc (), LI->getType (), ElementTmps);
509- }
510-
511469// ===----------------------------------------------------------------------===//
512470// ElementUseCollector Implementation
513471// ===----------------------------------------------------------------------===//
@@ -671,11 +629,6 @@ void ElementUseCollector::collectUses(SILValue Pointer, unsigned BaseEltNo) {
671629 " Walked through the pointer to the value?" );
672630 SILType PointeeType = Pointer->getType ().getObjectType ();
673631
674- // This keeps track of instructions in the use list that touch multiple tuple
675- // elements and should be scalarized. This is done as a second phase to
676- // avoid invalidating the use iterator.
677- SmallVector<SILInstruction *, 4 > UsesToScalarize;
678-
679632 for (auto *Op : Pointer->getUses ()) {
680633 auto *User = Op->getUser ();
681634
@@ -705,10 +658,7 @@ void ElementUseCollector::collectUses(SILValue Pointer, unsigned BaseEltNo) {
705658
706659 // Loads are a use of the value.
707660 if (isa<LoadInst>(User)) {
708- if (PointeeType.is <TupleType>())
709- UsesToScalarize.push_back (User);
710- else
711- addElementUses (BaseEltNo, PointeeType, User, DIUseKind::Load);
661+ addElementUses (BaseEltNo, PointeeType, User, DIUseKind::Load);
712662 continue ;
713663 }
714664
@@ -730,13 +680,6 @@ void ElementUseCollector::collectUses(SILValue Pointer, unsigned BaseEltNo) {
730680 if ((isa<StoreInst>(User) || isa<AssignInst>(User) ||
731681 isa<AssignByWrapperInst>(User)) &&
732682 Op->getOperandNumber () == 1 ) {
733- if (PointeeType.is <TupleType>()) {
734- assert (!isa<AssignByWrapperInst>(User) &&
735- " cannot assign a typle with assign_by_wrapper" );
736- UsesToScalarize.push_back (User);
737- continue ;
738- }
739-
740683 // Coming out of SILGen, we assume that raw stores are initializations,
741684 // unless they have trivial type (which we classify as InitOrAssign).
742685 DIUseKind Kind;
@@ -769,13 +712,6 @@ void ElementUseCollector::collectUses(SILValue Pointer, unsigned BaseEltNo) {
769712#include " swift/AST/ReferenceStorage.def"
770713
771714 if (auto *CAI = dyn_cast<CopyAddrInst>(User)) {
772- // If this is a copy of a tuple, we should scalarize it so that we don't
773- // have an access that crosses elements.
774- if (PointeeType.is <TupleType>()) {
775- UsesToScalarize.push_back (CAI);
776- continue ;
777- }
778-
779715 // If this is the source of the copy_addr, then this is a load. If it is
780716 // the destination, then this is an unknown assignment. Note that we'll
781717 // revisit this instruction and add it to Uses twice if it is both a load
@@ -988,88 +924,6 @@ void ElementUseCollector::collectUses(SILValue Pointer, unsigned BaseEltNo) {
988924 // Otherwise, the use is something complicated, it escapes.
989925 addElementUses (BaseEltNo, PointeeType, User, DIUseKind::Escape);
990926 }
991-
992- // Now that we've walked all of the immediate uses, scalarize any operations
993- // working on tuples if we need to for canonicalization or analysis reasons.
994- if (!UsesToScalarize.empty ()) {
995- SILInstruction *PointerInst = Pointer->getDefiningInstruction ();
996- SmallVector<SILValue, 4 > ElementAddrs;
997- SILBuilderWithScope AddrBuilder (++SILBasicBlock::iterator (PointerInst),
998- PointerInst);
999- getScalarizedElementAddresses (Pointer, AddrBuilder, PointerInst->getLoc (),
1000- ElementAddrs);
1001-
1002- SmallVector<SILValue, 4 > ElementTmps;
1003- for (auto *User : UsesToScalarize) {
1004- ElementTmps.clear ();
1005-
1006- LLVM_DEBUG (llvm::errs () << " *** Scalarizing: " << *User << " \n " );
1007-
1008- // Scalarize LoadInst
1009- if (auto *LI = dyn_cast<LoadInst>(User)) {
1010- SILValue Result = scalarizeLoad (LI, ElementAddrs);
1011- LI->replaceAllUsesWith (Result);
1012- LI->eraseFromParent ();
1013- continue ;
1014- }
1015-
1016- // Scalarize AssignInst
1017- if (auto *AI = dyn_cast<AssignInst>(User)) {
1018- SILBuilderWithScope B (User, AI);
1019- getScalarizedElements (AI->getOperand (0 ), ElementTmps, AI->getLoc (), B);
1020-
1021- for (unsigned i = 0 , e = ElementAddrs.size (); i != e; ++i)
1022- B.createAssign (AI->getLoc (), ElementTmps[i], ElementAddrs[i],
1023- AssignOwnershipQualifier::Unknown);
1024- AI->eraseFromParent ();
1025- continue ;
1026- }
1027-
1028- // Scalarize StoreInst
1029- if (auto *SI = dyn_cast<StoreInst>(User)) {
1030- SILBuilderWithScope B (User, SI);
1031- getScalarizedElements (SI->getOperand (0 ), ElementTmps, SI->getLoc (), B);
1032-
1033- for (unsigned i = 0 , e = ElementAddrs.size (); i != e; ++i)
1034- B.createTrivialStoreOr (SI->getLoc (), ElementTmps[i], ElementAddrs[i],
1035- SI->getOwnershipQualifier ());
1036- SI->eraseFromParent ();
1037- continue ;
1038- }
1039-
1040- // Scalarize CopyAddrInst.
1041- auto *CAI = cast<CopyAddrInst>(User);
1042- SILBuilderWithScope B (User, CAI);
1043-
1044- // Determine if this is a copy *from* or *to* "Pointer".
1045- if (CAI->getSrc () == Pointer) {
1046- // Copy from pointer.
1047- getScalarizedElementAddresses (CAI->getDest (), B, CAI->getLoc (),
1048- ElementTmps);
1049- for (unsigned i = 0 , e = ElementAddrs.size (); i != e; ++i)
1050- B.createCopyAddr (CAI->getLoc (), ElementAddrs[i], ElementTmps[i],
1051- CAI->isTakeOfSrc (), CAI->isInitializationOfDest ());
1052-
1053- } else {
1054- getScalarizedElementAddresses (CAI->getSrc (), B, CAI->getLoc (),
1055- ElementTmps);
1056- for (unsigned i = 0 , e = ElementAddrs.size (); i != e; ++i)
1057- B.createCopyAddr (CAI->getLoc (), ElementTmps[i], ElementAddrs[i],
1058- CAI->isTakeOfSrc (), CAI->isInitializationOfDest ());
1059- }
1060- CAI->eraseFromParent ();
1061- }
1062-
1063- // Now that we've scalarized some stuff, recurse down into the newly created
1064- // element address computations to recursively process it. This can cause
1065- // further scalarization.
1066- for (SILValue EltPtr : ElementAddrs) {
1067- if (auto *TEAI = dyn_cast<TupleElementAddrInst>(EltPtr)) {
1068- collectTupleElementUses (TEAI, BaseEltNo);
1069- continue ;
1070- }
1071- }
1072- }
1073927}
1074928
1075929// / collectClassSelfUses - Collect all the uses of a 'self' pointer in a class
0 commit comments