@@ -398,11 +398,43 @@ class SimpleLockingCacheEntryBase {
398
398
}
399
399
};
400
400
401
+ // / A summary of the information from a generic signature that's
402
+ // / sufficient to compare arguments.
403
+ struct GenericSignatureLayout {
404
+ uint16_t NumKeyParameters = 0 ;
405
+ uint16_t NumWitnessTables = 0 ;
406
+
407
+ GenericSignatureLayout (const RuntimeGenericSignature &sig) {
408
+ for (const auto &gp : sig.getParams ()) {
409
+ if (gp.hasKeyArgument ())
410
+ ++NumKeyParameters;
411
+ }
412
+ for (const auto &reqt : sig.getRequirements ()) {
413
+ if (reqt.Flags .hasKeyArgument () &&
414
+ reqt.getKind () == GenericRequirementKind::Protocol)
415
+ ++NumWitnessTables;
416
+ }
417
+ }
418
+
419
+ size_t sizeInWords () const {
420
+ return NumKeyParameters + NumWitnessTables;
421
+ }
422
+
423
+ friend bool operator ==(const GenericSignatureLayout &lhs,
424
+ const GenericSignatureLayout &rhs) {
425
+ return lhs.NumKeyParameters == rhs.NumKeyParameters &&
426
+ lhs.NumWitnessTables == rhs.NumWitnessTables ;
427
+ }
428
+ friend bool operator !=(const GenericSignatureLayout &lhs,
429
+ const GenericSignatureLayout &rhs) {
430
+ return !(lhs == rhs);
431
+ }
432
+ };
433
+
401
434
// / A key value as provided to the concurrent map.
402
435
class MetadataCacheKey {
403
436
const void * const *Data;
404
- uint16_t NumKeyParameters;
405
- uint16_t NumWitnessTables;
437
+ GenericSignatureLayout Layout;
406
438
uint32_t Hash;
407
439
408
440
// / Compare two witness tables, which may involving checking the
@@ -445,16 +477,15 @@ class MetadataCacheKey {
445
477
// / Compare the content from two keys.
446
478
static int compareContent (const void * const *adata,
447
479
const void * const *bdata,
448
- unsigned numKeyParameters,
449
- unsigned numWitnessTables) {
480
+ const GenericSignatureLayout &layout) {
450
481
// Compare generic arguments for key parameters.
451
- for (unsigned i = 0 ; i != numKeyParameters ; ++i) {
482
+ for (unsigned i = 0 ; i != layout. NumKeyParameters ; ++i) {
452
483
if (auto result = comparePointers (*adata++, *bdata++))
453
484
return result;
454
485
}
455
486
456
487
// Compare witness tables.
457
- for (unsigned i = 0 ; i != numWitnessTables ; ++i) {
488
+ for (unsigned i = 0 ; i != layout. NumWitnessTables ; ++i) {
458
489
if (auto result =
459
490
compareWitnessTables ((const WitnessTable *)*adata++,
460
491
(const WitnessTable *)*bdata++))
@@ -465,30 +496,24 @@ class MetadataCacheKey {
465
496
}
466
497
467
498
public:
468
- MetadataCacheKey (uint16_t numKeyParams,
469
- uint16_t numWitnessTables,
499
+ MetadataCacheKey (const GenericSignatureLayout &layout,
470
500
const void * const *data)
471
- : Data(data), NumKeyParameters(numKeyParams),
472
- NumWitnessTables (numWitnessTables), Hash(computeHash()) { }
501
+ : Data(data), Layout(layout), Hash(computeHash()) { }
473
502
474
- MetadataCacheKey (uint16_t numKeyParams,
475
- uint16_t numWitnessTables,
503
+ MetadataCacheKey (const GenericSignatureLayout &layout,
476
504
const void * const *data,
477
505
uint32_t hash)
478
- : Data(data), NumKeyParameters(numKeyParams),
479
- NumWitnessTables(numWitnessTables), Hash(hash) {}
506
+ : Data(data), Layout(layout), Hash(hash) {}
480
507
481
508
bool operator ==(MetadataCacheKey rhs) const {
482
509
// Compare the hashes.
483
510
if (hash () != rhs.hash ()) return false ;
484
511
485
512
// Compare the sizes.
486
- if (NumKeyParameters != rhs.NumKeyParameters ) return false ;
487
- if (NumWitnessTables != rhs.NumWitnessTables ) return false ;
513
+ if (Layout != rhs.Layout ) return false ;
488
514
489
515
// Compare the content.
490
- return compareContent (begin (), rhs.begin (), NumKeyParameters,
491
- NumWitnessTables) == 0 ;
516
+ return compareContent (begin (), rhs.begin (), Layout) == 0 ;
492
517
}
493
518
494
519
int compare (const MetadataCacheKey &rhs) const {
@@ -499,40 +524,47 @@ class MetadataCacheKey {
499
524
500
525
// Compare the # of key parameters.
501
526
if (auto keyParamsComparison =
502
- compareIntegers (NumKeyParameters, rhs.NumKeyParameters )) {
527
+ compareIntegers (Layout.NumKeyParameters ,
528
+ rhs.Layout .NumKeyParameters )) {
503
529
return keyParamsComparison;
504
530
}
505
531
506
532
// Compare the # of witness tables.
507
533
if (auto witnessTablesComparison =
508
- compareIntegers (NumWitnessTables, rhs.NumWitnessTables )) {
534
+ compareIntegers (Layout.NumWitnessTables ,
535
+ rhs.Layout .NumWitnessTables )) {
509
536
return witnessTablesComparison;
510
537
}
511
538
512
539
// Compare the content.
513
- return compareContent (begin (), rhs.begin (), NumKeyParameters,
514
- NumWitnessTables);
540
+ return compareContent (begin (), rhs.begin (), Layout);
515
541
}
516
542
517
- uint16_t numKeyParameters () const { return NumKeyParameters; }
518
- uint16_t numWitnessTables () const { return NumWitnessTables; }
519
-
520
543
uint32_t hash () const {
521
544
return Hash;
522
545
}
523
546
547
+ const GenericSignatureLayout &layout () const {
548
+ return Layout;
549
+ }
550
+
524
551
friend llvm::hash_code hash_value (const MetadataCacheKey &key) {
525
552
return key.Hash ;
526
553
}
527
554
528
555
const void * const *begin () const { return Data; }
529
556
const void * const *end () const { return Data + size (); }
530
- unsigned size () const { return NumKeyParameters + NumWitnessTables; }
557
+ unsigned size () const { return Layout.sizeInWords (); }
558
+
559
+ void installInto (const void **buffer) const {
560
+ // FIXME: variadic-parameter-packs
561
+ memcpy (buffer, Data, size () * sizeof (const void *));
562
+ }
531
563
532
564
private:
533
565
uint32_t computeHash () const {
534
- size_t H = 0x56ba80d1u * NumKeyParameters;
535
- for (unsigned index = 0 ; index != NumKeyParameters; ++index) {
566
+ size_t H = 0x56ba80d1u * Layout. NumKeyParameters ;
567
+ for (unsigned index = 0 ; index != Layout. NumKeyParameters ; ++index) {
536
568
H = (H >> 10 ) | (H << ((sizeof (size_t ) * 8 ) - 10 ));
537
569
H ^= (reinterpret_cast <size_t >(Data[index])
538
570
^ (reinterpret_cast <size_t >(Data[index]) >> 19 ));
@@ -1331,7 +1363,7 @@ class VariadicMetadataCacheEntryBase :
1331
1363
using OverloadToken = typename TrailingObjects::template OverloadToken<T>;
1332
1364
1333
1365
size_t numTrailingObjects (OverloadToken<const void *>) const {
1334
- return NumKeyParameters + NumWitnessTables ;
1366
+ return Layout. sizeInWords () ;
1335
1367
}
1336
1368
1337
1369
template <class ... Args>
@@ -1343,8 +1375,7 @@ class VariadicMetadataCacheEntryBase :
1343
1375
1344
1376
private:
1345
1377
// / These are set during construction and never changed.
1346
- const uint16_t NumKeyParameters;
1347
- const uint16_t NumWitnessTables;
1378
+ const GenericSignatureLayout Layout;
1348
1379
const uint32_t Hash;
1349
1380
1350
1381
// / Valid if TrackingInfo.getState() >= PrivateMetadataState::Abstract.
@@ -1364,18 +1395,16 @@ class VariadicMetadataCacheEntryBase :
1364
1395
PrivateMetadataState initialState,
1365
1396
ValueType value)
1366
1397
: super(worker, initialState),
1367
- NumKeyParameters (key.numKeyParameters()),
1368
- NumWitnessTables(key.numWitnessTables()),
1398
+ Layout (key.layout()),
1369
1399
Hash(key.hash()),
1370
1400
Value(value) {
1371
1401
assert ((value != nullptr ) ==
1372
1402
(initialState != PrivateMetadataState::Allocating));
1373
- memcpy (this ->template getTrailingObjects <const void *>(),
1374
- key.begin (), key.size () * sizeof (const void *));
1403
+ key.installInto (this ->template getTrailingObjects <const void *>());
1375
1404
}
1376
1405
1377
1406
MetadataCacheKey getKey () const {
1378
- return MetadataCacheKey (NumKeyParameters, NumWitnessTables ,
1407
+ return MetadataCacheKey (Layout ,
1379
1408
this ->template getTrailingObjects <const void *>(),
1380
1409
Hash);
1381
1410
}
0 commit comments