@@ -292,8 +292,8 @@ public static Declaration GetProjectParent(Declaration declaration)
292
292
public ParserRuleContext Context { get ; }
293
293
public ParserRuleContext AttributesPassContext { get ; }
294
294
295
- private ConcurrentBag < IdentifierReference > _references = new ConcurrentBag < IdentifierReference > ( ) ;
296
- public IEnumerable < IdentifierReference > References => _references ;
295
+ private ConcurrentDictionary < IdentifierReference , int > _references = new ConcurrentDictionary < IdentifierReference , int > ( ) ;
296
+ public IEnumerable < IdentifierReference > References => _references . Keys ;
297
297
298
298
protected IEnumerable < IAnnotation > _annotations ;
299
299
public IEnumerable < IAnnotation > Annotations => _annotations ?? new List < IAnnotation > ( ) ;
@@ -371,19 +371,32 @@ public void AddReference(
371
371
bool isSetAssigned = false
372
372
)
373
373
{
374
- _references . Add (
375
- new IdentifierReference (
376
- module ,
377
- scope ,
378
- parent ,
379
- identifier ,
380
- selection ,
381
- callSiteContext ,
382
- callee ,
383
- isAssignmentTarget ,
384
- hasExplicitLetStatement ,
385
- annotations ,
386
- isSetAssigned ) ) ;
374
+ var oldReference = _references . FirstOrDefault ( r =>
375
+ r . Key . QualifiedModuleName == module &&
376
+ // ReSharper disable once PossibleUnintendedReferenceComparison
377
+ r . Key . ParentScoping == scope &&
378
+ // ReSharper disable once PossibleUnintendedReferenceComparison
379
+ r . Key . ParentNonScoping == parent &&
380
+ r . Key . IdentifierName == identifier &&
381
+ r . Key . Selection == selection ) ;
382
+ if ( oldReference . Key != null )
383
+ {
384
+ _references . TryRemove ( oldReference . Key , out _ ) ;
385
+ }
386
+
387
+ var newReference = new IdentifierReference (
388
+ module ,
389
+ scope ,
390
+ parent ,
391
+ identifier ,
392
+ selection ,
393
+ callSiteContext ,
394
+ callee ,
395
+ isAssignmentTarget ,
396
+ hasExplicitLetStatement ,
397
+ annotations ,
398
+ isSetAssigned ) ;
399
+ _references . AddOrUpdate ( newReference , 1 , ( key , value ) => 1 ) ;
387
400
}
388
401
389
402
/// <summary>
@@ -601,14 +614,13 @@ public override int GetHashCode()
601
614
602
615
public void ClearReferences ( )
603
616
{
604
- _references = new ConcurrentBag < IdentifierReference > ( ) ;
617
+ _references = new ConcurrentDictionary < IdentifierReference , int > ( ) ;
605
618
}
606
619
607
620
public void RemoveReferencesFrom ( IReadOnlyCollection < QualifiedModuleName > modulesByWhichToRemoveReferences )
608
621
{
609
- //This gets replaced with a new ConcurrentBag because one cannot remove specific items from a ConcurrentBag.
610
- //Moreover, changing to a ConcurrentDictionary<IdentifierReference,byte> breaks all sorts of tests, for some obscure reason.
611
- _references = new ConcurrentBag < IdentifierReference > ( _references . Where ( reference => ! modulesByWhichToRemoveReferences . Contains ( reference . QualifiedModuleName ) ) ) ;
622
+ _references = new ConcurrentDictionary < IdentifierReference , int > ( _references . Where ( reference => ! modulesByWhichToRemoveReferences . Contains ( reference . Key . QualifiedModuleName ) ) ) ;
612
623
}
613
624
}
614
625
}
626
+
0 commit comments