@@ -4175,6 +4175,24 @@ namespace {
4175
4175
continue ;
4176
4176
}
4177
4177
4178
+ auto getObjectType = [](Type optionalTy) -> Type {
4179
+ Type objectTy;
4180
+ if (auto lvalue = optionalTy->getAs <LValueType>()) {
4181
+ objectTy = lvalue->getObjectType ()->getAnyOptionalObjectType ();
4182
+ if (optionalTy->hasUnresolvedType () && !objectTy) {
4183
+ objectTy = optionalTy;
4184
+ }
4185
+ objectTy = LValueType::get (objectTy);
4186
+ } else {
4187
+ objectTy = optionalTy->getAnyOptionalObjectType ();
4188
+ if (optionalTy->hasUnresolvedType () && !objectTy) {
4189
+ objectTy = optionalTy;
4190
+ }
4191
+ }
4192
+ assert (objectTy);
4193
+ return objectTy;
4194
+ };
4195
+
4178
4196
KeyPathExpr::Component component;
4179
4197
switch (auto kind = origComponent.getKind ()) {
4180
4198
case KeyPathExpr::Component::Kind::UnresolvedProperty: {
@@ -4220,8 +4238,9 @@ namespace {
4220
4238
else
4221
4239
baseTy = objTy;
4222
4240
4241
+ auto loc = origComponent.getLoc ();
4223
4242
resolvedComponents.push_back (
4224
- KeyPathExpr::Component::forOptionalForce (baseTy, SourceLoc () ));
4243
+ KeyPathExpr::Component::forOptionalForce (baseTy, loc ));
4225
4244
}
4226
4245
4227
4246
cs.TC .requestMemberLayout (property);
@@ -4241,6 +4260,17 @@ namespace {
4241
4260
component = KeyPathExpr::Component::forProperty (ref,
4242
4261
resolvedTy,
4243
4262
origComponent.getLoc ());
4263
+
4264
+ baseTy = component.getComponentType ();
4265
+ resolvedComponents.push_back (component);
4266
+
4267
+ if (shouldForceUnwrapResult (property, locator)) {
4268
+ auto objectTy = getObjectType (baseTy);
4269
+ auto loc = origComponent.getLoc ();
4270
+ component = KeyPathExpr::Component::forOptionalForce (objectTy, loc);
4271
+ baseTy = component.getComponentType ();
4272
+ resolvedComponents.push_back (component);
4273
+ }
4244
4274
break ;
4245
4275
}
4246
4276
case KeyPathExpr::Component::Kind::UnresolvedSubscript: {
@@ -4268,8 +4298,9 @@ namespace {
4268
4298
else
4269
4299
baseTy = objTy;
4270
4300
4301
+ auto loc = origComponent.getLoc ();
4271
4302
resolvedComponents.push_back (
4272
- KeyPathExpr::Component::forOptionalForce (baseTy, SourceLoc () ));
4303
+ KeyPathExpr::Component::forOptionalForce (baseTy, loc ));
4273
4304
}
4274
4305
4275
4306
cs.TC .requestMemberLayout (subscript);
@@ -4306,6 +4337,17 @@ namespace {
4306
4337
// Save a reference to the component so we can do a post-pass to check
4307
4338
// the Hashable conformance of the indexes.
4308
4339
KeyPathSubscriptComponents.push_back ({E, resolvedComponents.size ()});
4340
+
4341
+ baseTy = component.getComponentType ();
4342
+ resolvedComponents.push_back (component);
4343
+
4344
+ if (shouldForceUnwrapResult (subscript, locator)) {
4345
+ auto objectTy = getObjectType (baseTy);
4346
+ auto loc = origComponent.getLoc ();
4347
+ component = KeyPathExpr::Component::forOptionalForce (objectTy, loc);
4348
+ baseTy = component.getComponentType ();
4349
+ resolvedComponents.push_back (component);
4350
+ }
4309
4351
break ;
4310
4352
}
4311
4353
case KeyPathExpr::Component::Kind::OptionalChain: {
@@ -4318,43 +4360,34 @@ namespace {
4318
4360
}
4319
4361
assert (objectTy);
4320
4362
4321
- component = KeyPathExpr::Component::forOptionalChain (objectTy,
4322
- origComponent.getLoc ());
4363
+ auto loc = origComponent.getLoc ();
4364
+ component = KeyPathExpr::Component::forOptionalChain (objectTy, loc);
4365
+
4366
+ baseTy = component.getComponentType ();
4367
+ resolvedComponents.push_back (component);
4323
4368
break ;
4324
4369
}
4325
4370
case KeyPathExpr::Component::Kind::OptionalForce: {
4326
- Type objectTy;
4327
- if (auto lvalue = baseTy->getAs <LValueType>()) {
4328
- objectTy = lvalue->getObjectType ()->getAnyOptionalObjectType ();
4329
- if (baseTy->hasUnresolvedType () && !objectTy) {
4330
- objectTy = baseTy;
4331
- }
4332
- objectTy = LValueType::get (objectTy);
4333
- } else {
4334
- objectTy = baseTy->getAnyOptionalObjectType ();
4335
- if (baseTy->hasUnresolvedType () && !objectTy) {
4336
- objectTy = baseTy;
4337
- }
4338
- assert (objectTy);
4339
- }
4340
-
4341
- component = KeyPathExpr::Component::forOptionalForce (objectTy,
4342
- origComponent.getLoc ());
4371
+ auto objectTy = getObjectType (baseTy);
4372
+ auto loc = origComponent.getLoc ();
4373
+ component = KeyPathExpr::Component::forOptionalForce (objectTy, loc);
4374
+ baseTy = component.getComponentType ();
4375
+ resolvedComponents.push_back (component);
4343
4376
break ;
4344
4377
}
4345
4378
case KeyPathExpr::Component::Kind::Invalid:
4346
4379
component = origComponent;
4347
4380
component.setComponentType (leafTy);
4381
+
4382
+ baseTy = component.getComponentType ();
4383
+ resolvedComponents.push_back (component);
4348
4384
break ;
4349
4385
4350
4386
case KeyPathExpr::Component::Kind::Property:
4351
4387
case KeyPathExpr::Component::Kind::Subscript:
4352
4388
case KeyPathExpr::Component::Kind::OptionalWrap:
4353
4389
llvm_unreachable (" already resolved" );
4354
4390
}
4355
-
4356
- baseTy = component.getComponentType ();
4357
- resolvedComponents.push_back (component);
4358
4391
}
4359
4392
4360
4393
// Wrap a non-optional result if there was chaining involved.
@@ -4389,7 +4422,8 @@ namespace {
4389
4422
4390
4423
// The final component type ought to line up with the leaf type of the
4391
4424
// key path.
4392
- assert (!baseTy || baseTy->getWithoutSpecifierType ()->isEqual (leafTy));
4425
+ assert (!baseTy || baseTy->hasUnresolvedType ()
4426
+ || baseTy->getWithoutSpecifierType ()->isEqual (leafTy));
4393
4427
return E;
4394
4428
}
4395
4429
0 commit comments