@@ -26,9 +26,10 @@ namespace llvm {
26
26
}
27
27
28
28
namespace clang {
29
- class ValueDecl ;
29
+ class CXXMethodDecl ;
30
30
class ObjCMethodDecl ;
31
31
class Type ;
32
+ class ValueDecl ;
32
33
}
33
34
34
35
namespace swift {
@@ -178,6 +179,15 @@ class AbstractionPattern {
178
179
// / type. ObjCMethod is valid. OtherData is an encoded foreign
179
180
// / error index.
180
181
ObjCMethodType,
182
+ // / The uncurried imported type of a C++ method. OrigType is valid and is a
183
+ // / function type. CXXMethod is valid.
184
+ CXXMethodType,
185
+ // / The curried imported type of a C++ method. OrigType is valid and is a
186
+ // / function type. CXXMethod is valid.
187
+ CurriedCXXMethodType,
188
+ // / The partially-applied curried imported type of a C++ method. OrigType is
189
+ // / valid and is a function type. CXXMethod is valid.
190
+ PartialCurriedCXXMethodType,
181
191
};
182
192
183
193
class EncodedForeignErrorInfo {
@@ -234,6 +244,7 @@ class AbstractionPattern {
234
244
union {
235
245
const clang::Type *ClangType;
236
246
const clang::ObjCMethodDecl *ObjCMethod;
247
+ const clang::CXXMethodDecl *CXXMethod;
237
248
const AbstractionPattern *OrigTupleElements;
238
249
};
239
250
CanGenericSignature GenericSig;
@@ -266,6 +277,18 @@ class AbstractionPattern {
266
277
}
267
278
}
268
279
280
+ bool hasStoredCXXMethod () const {
281
+ switch (getKind ()) {
282
+ case Kind::CXXMethodType:
283
+ case Kind::CurriedCXXMethodType:
284
+ case Kind::PartialCurriedCXXMethodType:
285
+ return true ;
286
+
287
+ default :
288
+ return false ;
289
+ }
290
+ }
291
+
269
292
bool hasStoredObjCMethod () const {
270
293
switch (getKind ()) {
271
294
case Kind::CurriedObjCMethodType:
@@ -327,6 +350,12 @@ class AbstractionPattern {
327
350
OtherData = memberStatus.getRawValue ();
328
351
}
329
352
353
+ void initCXXMethod (CanGenericSignature signature, CanType origType,
354
+ const clang::CXXMethodDecl *method, Kind kind) {
355
+ initSwiftType (signature, origType, kind);
356
+ CXXMethod = method;
357
+ }
358
+
330
359
AbstractionPattern () {}
331
360
explicit AbstractionPattern (Kind kind) : TheKind(unsigned (kind)) {}
332
361
@@ -354,17 +383,29 @@ class AbstractionPattern {
354
383
}
355
384
356
385
bool hasGenericSignature () const {
357
- return (getKind () == Kind::Type ||
358
- getKind () == Kind::Discard ||
359
- hasStoredClangType () ||
360
- hasStoredObjCMethod ());
386
+ switch (getKind ()) {
387
+ case Kind::Type:
388
+ case Kind::Discard:
389
+ case Kind::ClangType:
390
+ case Kind::CFunctionAsMethodType:
391
+ case Kind::CurriedCFunctionAsMethodType:
392
+ case Kind::PartialCurriedCFunctionAsMethodType:
393
+ case Kind::CurriedObjCMethodType:
394
+ case Kind::PartialCurriedObjCMethodType:
395
+ case Kind::ObjCMethodType:
396
+ case Kind::CXXMethodType:
397
+ case Kind::CurriedCXXMethodType:
398
+ case Kind::PartialCurriedCXXMethodType:
399
+ return true ;
400
+ case Kind::Invalid:
401
+ case Kind::Opaque:
402
+ case Kind::Tuple:
403
+ return false ;
404
+ }
361
405
}
362
406
363
407
CanGenericSignature getGenericSignature () const {
364
- assert (getKind () == Kind::Type ||
365
- getKind () == Kind::Discard ||
366
- hasStoredClangType () ||
367
- hasStoredObjCMethod ());
408
+ assert (hasGenericSignature ());
368
409
return CanGenericSignature (GenericSig);
369
410
}
370
411
@@ -418,6 +459,41 @@ class AbstractionPattern {
418
459
getCurriedCFunctionAsMethod (CanType origType,
419
460
const AbstractFunctionDecl *function);
420
461
462
+ // / Return an abstraction pattern for the curried type of a C++ method.
463
+ static AbstractionPattern
464
+ getCurriedCXXMethod (CanType origType, const AbstractFunctionDecl *function);
465
+
466
+ // / Return an abstraction pattern for the uncurried type of a C++ method.
467
+ // /
468
+ // / For example, if the original function is:
469
+ // / void Refrigerator::SetTemperature(RefrigeratorCompartment compartment,
470
+ // / Temperature temperature);
471
+ // / then the uncurried type is:
472
+ // / ((RefrigeratorCompartment, Temperature), Refrigerator) -> ()
473
+ static AbstractionPattern getCXXMethod (CanType origType,
474
+ const clang::CXXMethodDecl *method) {
475
+ assert (isa<AnyFunctionType>(origType));
476
+ AbstractionPattern pattern;
477
+ pattern.initCXXMethod (nullptr , origType, method, Kind::CXXMethodType);
478
+ return pattern;
479
+ }
480
+
481
+ // / Return an abstraction pattern for the curried type of a C++ method.
482
+ // /
483
+ // / For example, if the original function is:
484
+ // / void Refrigerator::SetTemperature(RefrigeratorCompartment compartment,
485
+ // / Temperature temperature);
486
+ // / then the curried type:
487
+ // / (Refrigerator) -> (Compartment, Temperature) -> ()
488
+ static AbstractionPattern
489
+ getCurriedCXXMethod (CanType origType, const clang::CXXMethodDecl *method) {
490
+ assert (isa<AnyFunctionType>(origType));
491
+ AbstractionPattern pattern;
492
+ pattern.initCXXMethod (nullptr , origType, method,
493
+ Kind::CurriedCXXMethodType);
494
+ return pattern;
495
+ }
496
+
421
497
// / For a C-function-as-method pattern,
422
498
// / get the index of the C function parameter that was imported as the
423
499
// / `self` parameter of the imported method, or None if this is a static
@@ -497,6 +573,24 @@ class AbstractionPattern {
497
573
return pattern;
498
574
}
499
575
576
+ // / Return an abstraction pattern for the partially-applied curried
577
+ // / type of an C++ method.
578
+ // /
579
+ // / For example, if the original function is:
580
+ // / void Refrigerator::SetTemperature(RefrigeratorCompartment compartment,
581
+ // / Temperature temperature);
582
+ // / then the partially-applied curried type is:
583
+ // / (Compartment, Temperature) -> ()
584
+ static AbstractionPattern
585
+ getPartialCurriedCXXMethod (CanGenericSignature signature, CanType origType,
586
+ const clang::CXXMethodDecl *method) {
587
+ assert (isa<AnyFunctionType>(origType));
588
+ AbstractionPattern pattern;
589
+ pattern.initCXXMethod (signature, origType, method,
590
+ Kind::PartialCurriedCXXMethodType);
591
+ return pattern;
592
+ }
593
+
500
594
public:
501
595
// / Return an abstraction pattern for the type of an Objective-C method.
502
596
static AbstractionPattern
@@ -520,18 +614,13 @@ class AbstractionPattern {
520
614
// / current Objective-C method.
521
615
AbstractionPattern getObjCMethodSelfPattern (CanType paramType) const ;
522
616
523
- // / Return a pattern corresponding to the formal parameters of the
524
- // / current Objective-C method.
525
- AbstractionPattern getObjCMethodFormalParamPattern (CanType paramType) const ;
526
-
527
617
// / Return a pattern corresponding to the 'self' parameter of the
528
618
// / current C function imported as a method.
529
619
AbstractionPattern getCFunctionAsMethodSelfPattern (CanType paramType) const ;
530
-
531
- // / Return a pattern corresponding to the formal parameters of the
532
- // / current C function imported as a method.
533
- AbstractionPattern getCFunctionAsMethodFormalParamPattern (CanType paramType)
534
- const ;
620
+
621
+ // / Return a pattern corresponding to the 'self' parameter of the
622
+ // / current C++ method.
623
+ AbstractionPattern getCXXMethodSelfPattern (CanType paramType) const ;
535
624
536
625
public:
537
626
// / Return an abstraction pattern with an added level of optionality.
@@ -606,6 +695,9 @@ class AbstractionPattern {
606
695
case Kind::CFunctionAsMethodType:
607
696
case Kind::CurriedCFunctionAsMethodType:
608
697
case Kind::PartialCurriedCFunctionAsMethodType:
698
+ case Kind::CXXMethodType:
699
+ case Kind::CurriedCXXMethodType:
700
+ case Kind::PartialCurriedCXXMethodType:
609
701
case Kind::Type:
610
702
case Kind::Discard:
611
703
return OrigType;
@@ -637,6 +729,9 @@ class AbstractionPattern {
637
729
case Kind::CFunctionAsMethodType:
638
730
case Kind::CurriedCFunctionAsMethodType:
639
731
case Kind::PartialCurriedCFunctionAsMethodType:
732
+ case Kind::CXXMethodType:
733
+ case Kind::CurriedCXXMethodType:
734
+ case Kind::PartialCurriedCXXMethodType:
640
735
case Kind::Type:
641
736
case Kind::Discard:
642
737
assert (signature || !type->hasTypeParameter ());
@@ -669,6 +764,9 @@ class AbstractionPattern {
669
764
case Kind::CFunctionAsMethodType:
670
765
case Kind::CurriedCFunctionAsMethodType:
671
766
case Kind::PartialCurriedCFunctionAsMethodType:
767
+ case Kind::CXXMethodType:
768
+ case Kind::CurriedCXXMethodType:
769
+ case Kind::PartialCurriedCXXMethodType:
672
770
return true ;
673
771
}
674
772
llvm_unreachable (" bad kind" );
@@ -702,6 +800,18 @@ class AbstractionPattern {
702
800
return ObjCMethod;
703
801
}
704
802
803
+ // / Return whether this abstraction pattern represents a C++ method.
804
+ // / If so, it is legal to call getCXXMethod().
805
+ bool isCXXMethod () const {
806
+ return (getKind () == Kind::CXXMethodType ||
807
+ getKind () == Kind::CurriedCXXMethodType);
808
+ }
809
+
810
+ const clang::CXXMethodDecl *getCXXMethod () const {
811
+ assert (hasStoredCXXMethod ());
812
+ return CXXMethod;
813
+ }
814
+
705
815
EncodedForeignErrorInfo getEncodedForeignErrorInfo () const {
706
816
assert (hasStoredForeignErrorInfo ());
707
817
return EncodedForeignErrorInfo::fromOpaqueValue (OtherData);
@@ -721,6 +831,9 @@ class AbstractionPattern {
721
831
case Kind::CFunctionAsMethodType:
722
832
case Kind::CurriedCFunctionAsMethodType:
723
833
case Kind::PartialCurriedCFunctionAsMethodType:
834
+ case Kind::CXXMethodType:
835
+ case Kind::CurriedCXXMethodType:
836
+ case Kind::PartialCurriedCXXMethodType:
724
837
return false ;
725
838
case Kind::PartialCurriedObjCMethodType:
726
839
case Kind::CurriedObjCMethodType:
@@ -749,6 +862,9 @@ class AbstractionPattern {
749
862
case Kind::CFunctionAsMethodType:
750
863
case Kind::CurriedCFunctionAsMethodType:
751
864
case Kind::PartialCurriedCFunctionAsMethodType:
865
+ case Kind::CXXMethodType:
866
+ case Kind::CurriedCXXMethodType:
867
+ case Kind::PartialCurriedCXXMethodType:
752
868
case Kind::Type:
753
869
case Kind::Discard:
754
870
return dyn_cast<TYPE>(getType ());
@@ -774,6 +890,9 @@ class AbstractionPattern {
774
890
case Kind::CFunctionAsMethodType:
775
891
case Kind::CurriedCFunctionAsMethodType:
776
892
case Kind::PartialCurriedCFunctionAsMethodType:
893
+ case Kind::CXXMethodType:
894
+ case Kind::CurriedCXXMethodType:
895
+ case Kind::PartialCurriedCXXMethodType:
777
896
// We assume that the Clang type might provide additional structure.
778
897
return false ;
779
898
case Kind::Type:
@@ -798,6 +917,9 @@ class AbstractionPattern {
798
917
case Kind::CurriedCFunctionAsMethodType:
799
918
case Kind::PartialCurriedCFunctionAsMethodType:
800
919
case Kind::ObjCMethodType:
920
+ case Kind::CXXMethodType:
921
+ case Kind::CurriedCXXMethodType:
922
+ case Kind::PartialCurriedCXXMethodType:
801
923
return false ;
802
924
case Kind::Tuple:
803
925
return true ;
@@ -820,6 +942,9 @@ class AbstractionPattern {
820
942
case Kind::CurriedCFunctionAsMethodType:
821
943
case Kind::PartialCurriedCFunctionAsMethodType:
822
944
case Kind::ObjCMethodType:
945
+ case Kind::CXXMethodType:
946
+ case Kind::CurriedCXXMethodType:
947
+ case Kind::PartialCurriedCXXMethodType:
823
948
llvm_unreachable (" pattern is not a tuple" );
824
949
case Kind::Tuple:
825
950
return getNumTupleElements_Stored ();
0 commit comments