@@ -735,124 +735,54 @@ static std::tuple<ValueDecl *, bool, ArrayRef<Identifier>, bool,
735
735
ConstraintLocator *>
736
736
getCalleeDeclAndArgs (ConstraintSystem &cs,
737
737
ConstraintLocatorBuilder callBuilder) {
738
- ArrayRef<Identifier> argLabels;
739
- bool hasTrailingClosure = false ;
740
- ConstraintLocator *targetLocator = nullptr ;
738
+ auto formUnknownCallee =
739
+ []() -> std::tuple<ValueDecl *, bool , ArrayRef<Identifier>, bool ,
740
+ ConstraintLocator *> {
741
+ return std::make_tuple (/* decl*/ nullptr , /* hasAppliedSelf*/ false ,
742
+ /* argLabels*/ ArrayRef<Identifier>(),
743
+ /* hasTrailingClosure*/ false ,
744
+ /* calleeLocator*/ nullptr );
745
+ };
741
746
742
747
auto *callLocator = cs.getConstraintLocator (callBuilder);
743
748
auto *callExpr = callLocator->getAnchor ();
744
749
745
750
// Break down the call.
746
751
if (!callExpr)
747
- return std::make_tuple (nullptr , /* hasAppliedSelf=*/ false , argLabels,
748
- hasTrailingClosure, targetLocator);
752
+ return formUnknownCallee ();
749
753
750
- auto path = callLocator->getPath ();
751
754
// Our remaining path can only be 'ApplyArgument'.
755
+ auto path = callLocator->getPath ();
752
756
if (!path.empty () &&
753
757
!(path.size () <= 2 &&
754
758
path.back ().getKind () == ConstraintLocator::ApplyArgument))
755
- return std::make_tuple (nullptr , /* hasAppliedSelf=*/ false , argLabels,
756
- hasTrailingClosure, targetLocator);
759
+ return formUnknownCallee ();
757
760
758
761
// Dig out the callee information.
759
- if (auto argInfo = cs.getArgumentInfo (callLocator)) {
760
- argLabels = argInfo->Labels ;
761
- hasTrailingClosure = argInfo->HasTrailingClosure ;
762
- targetLocator = cs.getConstraintLocator (
763
- isa<CallExpr>(callExpr) ? cast<CallExpr>(callExpr)->getDirectCallee ()
764
- : callExpr);
765
- } else if (auto keyPath = dyn_cast<KeyPathExpr>(callExpr)) {
766
- if (path.size () != 2 )
767
- return std::make_tuple (nullptr , /* hasAppliedSelf=*/ false , argLabels,
768
- hasTrailingClosure, nullptr );
769
-
770
- // We must have a KeyPathComponent followed by an ApplyArgument.
771
- auto componentElt = path[0 ].getAs <LocatorPathElt::KeyPathComponent>();
772
- if (!componentElt || path[1 ].getKind () != ConstraintLocator::ApplyArgument)
773
- return std::make_tuple (nullptr , /* hasAppliedSelf=*/ false , argLabels,
774
- hasTrailingClosure, nullptr );
775
-
776
- auto componentIndex = componentElt->getIndex ();
777
- if (componentIndex >= keyPath->getComponents ().size ())
778
- return std::make_tuple (nullptr , /* hasAppliedSelf=*/ false , argLabels,
779
- hasTrailingClosure, nullptr );
780
-
781
- auto &component = keyPath->getComponents ()[componentIndex];
782
- switch (component.getKind ()) {
783
- case KeyPathExpr::Component::Kind::Subscript:
784
- case KeyPathExpr::Component::Kind::UnresolvedSubscript:
785
- targetLocator = cs.getConstraintLocator (callExpr, path[0 ]);
786
- argLabels = component.getSubscriptLabels ();
787
- hasTrailingClosure = false ; // key paths don't support trailing closures
788
- break ;
789
-
790
- case KeyPathExpr::Component::Kind::Invalid:
791
- case KeyPathExpr::Component::Kind::UnresolvedProperty:
792
- case KeyPathExpr::Component::Kind::Property:
793
- case KeyPathExpr::Component::Kind::OptionalForce:
794
- case KeyPathExpr::Component::Kind::OptionalChain:
795
- case KeyPathExpr::Component::Kind::OptionalWrap:
796
- case KeyPathExpr::Component::Kind::Identity:
797
- case KeyPathExpr::Component::Kind::TupleElement:
798
- return std::make_tuple (nullptr , /* hasAppliedSelf=*/ false , argLabels,
799
- hasTrailingClosure, nullptr );
800
- }
801
- } else {
802
- return std::make_tuple (nullptr , /* hasAppliedSelf=*/ false , argLabels,
803
- hasTrailingClosure, targetLocator);
804
- }
762
+ auto argInfo = cs.getArgumentInfo (callLocator);
763
+ if (!argInfo)
764
+ return formUnknownCallee ();
765
+
766
+ auto argLabels = argInfo->Labels ;
767
+ auto hasTrailingClosure = argInfo->HasTrailingClosure ;
768
+ auto calleeLocator = cs.getCalleeLocator (callLocator);
805
769
806
770
// Find the overload choice corresponding to the callee locator.
807
771
// FIXME: This linearly walks the list of resolved overloads, which is
808
772
// potentially very expensive.
809
- Optional<OverloadChoice> choice;
810
- ConstraintLocator *calleeLocator = nullptr ;
811
- for (auto resolved = cs.getResolvedOverloadSets (); resolved;
812
- resolved = resolved->Previous ) {
813
- // FIXME: Workaround null locators.
814
- if (!resolved->Locator ) continue ;
815
-
816
- auto resolvedLocator = resolved->Locator ;
817
- SmallVector<LocatorPathElt, 4 > resolvedPath (
818
- resolvedLocator->getPath ().begin (),
819
- resolvedLocator->getPath ().end ());
820
- if (!resolvedPath.empty () &&
821
- (resolvedPath.back ().getKind () == ConstraintLocator::SubscriptMember ||
822
- resolvedPath.back ().getKind () == ConstraintLocator::Member ||
823
- resolvedPath.back ().getKind () == ConstraintLocator::UnresolvedMember ||
824
- resolvedPath.back ().getKind () ==
825
- ConstraintLocator::ConstructorMember)) {
826
- resolvedPath.pop_back ();
827
- resolvedLocator = cs.getConstraintLocator (
828
- resolvedLocator->getAnchor (),
829
- resolvedPath,
830
- resolvedLocator->getSummaryFlags ());
831
- }
832
-
833
- SourceRange range;
834
- resolvedLocator = simplifyLocator (cs, resolvedLocator, range);
835
-
836
- if (resolvedLocator == targetLocator) {
837
- calleeLocator = resolved->Locator ;
838
- choice = resolved->Choice ;
839
- break ;
840
- }
841
- }
842
-
843
- // If we didn't find any matching overloads, we're done.
844
- if (!choice)
845
- return std::make_tuple (nullptr , /* hasAppliedSelf=*/ false , argLabels,
846
- hasTrailingClosure, nullptr );
847
-
848
- // If there's a declaration, return it.
849
- if (auto *decl = choice->getDeclOrNull ()) {
850
- return std::make_tuple (decl, hasAppliedSelf (cs, *choice), argLabels,
851
- hasTrailingClosure, calleeLocator);
852
- }
853
-
854
- return std::make_tuple (nullptr , /* hasAppliedSelf=*/ false , argLabels,
855
- hasTrailingClosure, calleeLocator);
773
+ auto selectedOverload = cs.findSelectedOverloadFor (calleeLocator);
774
+
775
+ // If we didn't find any matching overloads, we're done. Just return the
776
+ // argument info.
777
+ if (!selectedOverload)
778
+ return std::make_tuple (/* decl*/ nullptr , /* hasAppliedSelf*/ false ,
779
+ argLabels, hasTrailingClosure,
780
+ /* calleeLocator*/ nullptr );
781
+
782
+ // Return the found declaration, assuming there is one.
783
+ auto choice = selectedOverload->Choice ;
784
+ return std::make_tuple (choice.getDeclOrNull (), hasAppliedSelf (cs, choice),
785
+ argLabels, hasTrailingClosure, calleeLocator);
856
786
}
857
787
858
788
class ArgumentFailureTracker : public MatchCallArgumentListener {
0 commit comments