@@ -2391,7 +2391,7 @@ namespace {
2391
2391
// / for the types of each variable declared within the pattern, along
2392
2392
// / with a one-way constraint binding that to the type to which the
2393
2393
// / variable will be ascribed or inferred.
2394
- Type getTypeForPattern (
2394
+ Optional< Type> getTypeForPattern (
2395
2395
Pattern *pattern, ConstraintLocatorBuilder locator,
2396
2396
bool bindPatternVarsOneWay,
2397
2397
PatternBindingDecl *patternBinding = nullptr ,
@@ -2415,14 +2415,21 @@ namespace {
2415
2415
locator.withPathElement (LocatorPathElt::PatternMatch (subPattern)),
2416
2416
bindPatternVarsOneWay);
2417
2417
2418
- return setType (ParenType::get (CS.getASTContext (), underlyingType));
2418
+ if (!underlyingType)
2419
+ return None;
2420
+
2421
+ return setType (ParenType::get (CS.getASTContext (), *underlyingType));
2419
2422
}
2420
2423
case PatternKind::Binding: {
2421
2424
auto *subPattern = cast<BindingPattern>(pattern)->getSubPattern ();
2422
2425
auto type = getTypeForPattern (subPattern, locator,
2423
2426
bindPatternVarsOneWay);
2427
+
2428
+ if (!type)
2429
+ return None;
2430
+
2424
2431
// Var doesn't affect the type.
2425
- return setType (type);
2432
+ return setType (* type);
2426
2433
}
2427
2434
case PatternKind::Any: {
2428
2435
Type type;
@@ -2602,6 +2609,9 @@ namespace {
2602
2609
2603
2610
Type type = TypeChecker::typeCheckPattern (contextualPattern);
2604
2611
2612
+ if (!type)
2613
+ return None;
2614
+
2605
2615
// Look through reference storage types.
2606
2616
type = type->getReferenceStorageReferent ();
2607
2617
@@ -2613,16 +2623,19 @@ namespace {
2613
2623
auto *subPattern = cast<TypedPattern>(pattern)->getSubPattern ();
2614
2624
// Determine the subpattern type. It will be convertible to the
2615
2625
// ascribed type.
2616
- Type subPatternType = getTypeForPattern (
2626
+ auto subPatternType = getTypeForPattern (
2617
2627
subPattern,
2618
2628
locator.withPathElement (LocatorPathElt::PatternMatch (subPattern)),
2619
2629
bindPatternVarsOneWay);
2620
2630
2631
+ if (!subPatternType)
2632
+ return None;
2633
+
2621
2634
// NOTE: The order here is important! Pattern matching equality is
2622
2635
// not symmetric (we need to fix that either by using a different
2623
2636
// constraint, or actually making it symmetric).
2624
2637
CS.addConstraint (
2625
- ConstraintKind::Equal, openedType, subPatternType,
2638
+ ConstraintKind::Equal, openedType, * subPatternType,
2626
2639
locator.withPathElement (LocatorPathElt::PatternMatch (pattern)));
2627
2640
2628
2641
// FIXME [OPAQUE SUPPORT]: the distinction between where we want opaque
@@ -2642,12 +2655,15 @@ namespace {
2642
2655
auto &tupleElt = tuplePat->getElement (i);
2643
2656
2644
2657
auto *eltPattern = tupleElt.getPattern ();
2645
- Type eltTy = getTypeForPattern (
2658
+ auto eltTy = getTypeForPattern (
2646
2659
eltPattern,
2647
2660
locator.withPathElement (LocatorPathElt::PatternMatch (eltPattern)),
2648
2661
bindPatternVarsOneWay);
2649
2662
2650
- tupleTypeElts.push_back (TupleTypeElt (eltTy, tupleElt.getLabel ()));
2663
+ if (!eltTy)
2664
+ return None;
2665
+
2666
+ tupleTypeElts.push_back (TupleTypeElt (*eltTy, tupleElt.getLabel ()));
2651
2667
}
2652
2668
2653
2669
return setType (TupleType::get (tupleTypeElts, CS.getASTContext ()));
@@ -2656,12 +2672,15 @@ namespace {
2656
2672
case PatternKind::OptionalSome: {
2657
2673
auto *subPattern = cast<OptionalSomePattern>(pattern)->getSubPattern ();
2658
2674
// The subpattern must have optional type.
2659
- Type subPatternType = getTypeForPattern (
2675
+ auto subPatternType = getTypeForPattern (
2660
2676
subPattern,
2661
2677
locator.withPathElement (LocatorPathElt::PatternMatch (subPattern)),
2662
2678
bindPatternVarsOneWay);
2663
2679
2664
- return setType (OptionalType::get (subPatternType));
2680
+ if (!subPatternType)
2681
+ return None;
2682
+
2683
+ return setType (OptionalType::get (*subPatternType));
2665
2684
}
2666
2685
2667
2686
case PatternKind::Is: {
@@ -2691,12 +2710,14 @@ namespace {
2691
2710
subPattern,
2692
2711
locator.withPathElement (LocatorPathElt::PatternMatch (subPattern)),
2693
2712
bindPatternVarsOneWay);
2713
+ if (!subPatternType)
2714
+ return None;
2694
2715
2695
2716
// NOTE: The order here is important! Pattern matching equality is
2696
2717
// not symmetric (we need to fix that either by using a different
2697
2718
// constraint, or actually making it symmetric).
2698
2719
CS.addConstraint (
2699
- ConstraintKind::Equal, castType, subPatternType,
2720
+ ConstraintKind::Equal, castType, * subPatternType,
2700
2721
locator.withPathElement (LocatorPathElt::PatternMatch (pattern)));
2701
2722
}
2702
2723
return setType (isType);
@@ -2760,6 +2781,9 @@ namespace {
2760
2781
TypeResolverContext::InExpression, patternMatchLoc);
2761
2782
}();
2762
2783
2784
+ if (!parentType)
2785
+ return None;
2786
+
2763
2787
// Perform member lookup into the parent's metatype.
2764
2788
Type parentMetaType = MetatypeType::get (parentType);
2765
2789
CS.addValueMemberConstraint (parentMetaType, enumPattern->getName (),
@@ -2787,13 +2811,13 @@ namespace {
2787
2811
// When there is a subpattern, the member will have function type,
2788
2812
// and we're matching the type of that subpattern to the parameter
2789
2813
// types.
2790
- Type subPatternType = getTypeForPattern (
2814
+ auto subPatternType = getTypeForPattern (
2791
2815
subPattern,
2792
2816
locator.withPathElement (LocatorPathElt::PatternMatch (subPattern)),
2793
2817
bindPatternVarsOneWay);
2794
2818
2795
2819
SmallVector<AnyFunctionType::Param, 4 > params;
2796
- decomposeTuple (subPatternType, params);
2820
+ decomposeTuple (* subPatternType, params);
2797
2821
2798
2822
// Remove parameter labels; they aren't used when matching cases,
2799
2823
// but outright conflicts will be checked during coercion.
@@ -2826,10 +2850,24 @@ namespace {
2826
2850
}
2827
2851
2828
2852
case PatternKind::Expr: {
2829
- // We generate constraints for ExprPatterns in a separate pass. For
2830
- // now, just create a type variable.
2831
- return setType (CS.createTypeVariable (CS.getConstraintLocator (locator),
2832
- TVO_CanBindToNoEscape));
2853
+ auto *EP = cast<ExprPattern>(pattern);
2854
+ Type patternTy = CS.createTypeVariable (CS.getConstraintLocator (locator),
2855
+ TVO_CanBindToNoEscape);
2856
+
2857
+ auto target = SyntacticElementTarget::forExprPattern (EP);
2858
+
2859
+ if (CS.preCheckTarget (target, /* replaceInvalidRefWithErrors=*/ true ,
2860
+ /* leaveClosureBodyUnchecked=*/ false )) {
2861
+ return None;
2862
+ }
2863
+ CS.setType (EP->getMatchVar (), patternTy);
2864
+
2865
+ if (CS.generateConstraints (target))
2866
+ return None;
2867
+
2868
+ CS.setTargetFor (EP, target);
2869
+ CS.setExprPatternFor (EP->getSubExpr (), EP);
2870
+ return setType (patternTy);
2833
2871
}
2834
2872
}
2835
2873
@@ -4222,10 +4260,14 @@ static bool generateInitPatternConstraints(ConstraintSystem &cs,
4222
4260
4223
4261
Type patternType;
4224
4262
if (auto pattern = target.getInitializationPattern ()) {
4225
- patternType = cs.generateConstraints (
4263
+ auto ty = cs.generateConstraints (
4226
4264
pattern, locator, target.shouldBindPatternVarsOneWay (),
4227
4265
target.getInitializationPatternBindingDecl (),
4228
4266
target.getInitializationPatternBindingIndex ());
4267
+ if (!ty)
4268
+ return true ;
4269
+
4270
+ patternType = *ty;
4229
4271
} else {
4230
4272
patternType = cs.createTypeVariable (locator, TVO_CanBindToNoEscape);
4231
4273
}
@@ -4384,7 +4426,7 @@ generateForEachStmtConstraints(ConstraintSystem &cs,
4384
4426
// Collect constraints from the element pattern.
4385
4427
auto elementLocator = cs.getConstraintLocator (
4386
4428
sequenceExpr, ConstraintLocator::SequenceElementType);
4387
- Type initType =
4429
+ auto initType =
4388
4430
cs.generateConstraints (pattern, elementLocator,
4389
4431
target.shouldBindPatternVarsOneWay (), nullptr , 0 );
4390
4432
if (!initType)
@@ -4403,7 +4445,7 @@ generateForEachStmtConstraints(ConstraintSystem &cs,
4403
4445
// resolving `optional object` constraint which is sometimes too eager.
4404
4446
cs.addConstraint (ConstraintKind::Conversion, nextType,
4405
4447
OptionalType::get (elementType), elementTypeLoc);
4406
- cs.addConstraint (ConstraintKind::Conversion, elementType, initType,
4448
+ cs.addConstraint (ConstraintKind::Conversion, elementType, * initType,
4407
4449
elementLocator);
4408
4450
}
4409
4451
@@ -4429,7 +4471,7 @@ generateForEachStmtConstraints(ConstraintSystem &cs,
4429
4471
4430
4472
// Populate all of the information for a for-each loop.
4431
4473
forEachStmtInfo.elementType = elementType;
4432
- forEachStmtInfo.initType = initType;
4474
+ forEachStmtInfo.initType = * initType;
4433
4475
target.setPattern (pattern);
4434
4476
target.getForEachStmtInfo () = forEachStmtInfo;
4435
4477
return target;
@@ -4609,7 +4651,7 @@ bool ConstraintSystem::generateConstraints(
4609
4651
4610
4652
// Generate constraints to bind all of the internal declarations
4611
4653
// and verify the pattern.
4612
- Type patternType = generateConstraints (
4654
+ auto patternType = generateConstraints (
4613
4655
pattern, locator, /* shouldBindPatternVarsOneWay*/ true ,
4614
4656
target.getPatternBindingOfUninitializedVar (),
4615
4657
target.getIndexOfUninitializedVar ());
@@ -4638,25 +4680,13 @@ Expr *ConstraintSystem::generateConstraints(
4638
4680
return generateConstraintsFor (*this , expr, dc);
4639
4681
}
4640
4682
4641
- Type ConstraintSystem::generateConstraints (
4683
+ Optional< Type> ConstraintSystem::generateConstraints (
4642
4684
Pattern *pattern, ConstraintLocatorBuilder locator,
4643
4685
bool bindPatternVarsOneWay, PatternBindingDecl *patternBinding,
4644
4686
unsigned patternIndex) {
4645
4687
ConstraintGenerator cg (*this , nullptr );
4646
- auto ty = cg.getTypeForPattern (pattern, locator, bindPatternVarsOneWay,
4647
- patternBinding, patternIndex);
4648
- assert (ty);
4649
-
4650
- // Gather the ExprPatterns, and form a conjunction for their expressions.
4651
- SmallVector<ExprPattern *, 4 > exprPatterns;
4652
- pattern->forEachNode ([&](Pattern *P) {
4653
- if (auto *EP = dyn_cast<ExprPattern>(P))
4654
- exprPatterns.push_back (EP);
4655
- });
4656
- if (!exprPatterns.empty ())
4657
- generateConstraints (exprPatterns, getConstraintLocator (pattern));
4658
-
4659
- return ty;
4688
+ return cg.getTypeForPattern (pattern, locator, bindPatternVarsOneWay,
4689
+ patternBinding, patternIndex);
4660
4690
}
4661
4691
4662
4692
bool ConstraintSystem::generateConstraints (StmtCondition condition,
0 commit comments