@@ -519,27 +519,34 @@ private void InstrumentMethod(MethodDefinition method)
519
519
InstrumentIL ( method ) ;
520
520
}
521
521
522
+ /// <summary>
523
+ /// The base idea is to inject an int placeholder for every sequence point. We register source+placeholder+lines(from sequence point) for final accounting.
524
+ /// Instrumentation alg(current instruction: instruction we're analyzing):
525
+ /// 1) We get all branches for the method
526
+ /// 2) We get the sequence point of every instruction of method(start line/end line)
527
+ /// 3) We check if current instruction is reachable and coverable
528
+ /// 4) For every sequence point of an instruction we put load(int hint placeholder)+call opcode above current instruction
529
+ /// 5) We patch all jump to current instruction with first injected instruction(load)
530
+ /// 6) If current instruction is a target for a branch we inject again load(int hint placeholder)+call opcode above current instruction
531
+ /// 7) We patch all jump to current instruction with first injected instruction(load)
532
+ /// </summary>
522
533
private void InstrumentIL ( MethodDefinition method )
523
534
{
524
535
method . Body . SimplifyMacros ( ) ;
525
536
ILProcessor processor = method . Body . GetILProcessor ( ) ;
526
-
527
537
var index = 0 ;
528
538
var count = processor . Body . Instructions . Count ;
529
-
530
539
var branchPoints = _cecilSymbolHelper . GetBranchPoints ( method ) ;
531
-
532
540
var unreachableRanges = _reachabilityHelper . FindUnreachableIL ( processor . Body . Instructions , processor . Body . ExceptionHandlers ) ;
533
541
var currentUnreachableRangeIx = 0 ;
534
-
535
542
for ( int n = 0 ; n < count ; n ++ )
536
543
{
537
- var instruction = processor . Body . Instructions [ index ] ;
538
- var sequencePoint = method . DebugInformation . GetSequencePoint ( instruction ) ;
539
- var targetedBranchPoints = branchPoints . Where ( p => p . EndOffset == instruction . Offset ) ;
544
+ var currentInstruction = processor . Body . Instructions [ index ] ;
545
+ var sequencePoint = method . DebugInformation . GetSequencePoint ( currentInstruction ) ;
546
+ var targetedBranchPoints = branchPoints . Where ( p => p . EndOffset == currentInstruction . Offset ) ;
540
547
541
548
// make sure we're looking at the correct unreachable range (if any)
542
- var instrOffset = instruction . Offset ;
549
+ var instrOffset = currentInstruction . Offset ;
543
550
while ( currentUnreachableRangeIx < unreachableRanges . Length && instrOffset > unreachableRanges [ currentUnreachableRangeIx ] . EndOffset )
544
551
{
545
552
currentUnreachableRangeIx ++ ;
@@ -554,26 +561,26 @@ private void InstrumentIL(MethodDefinition method)
554
561
}
555
562
556
563
// Check is both reachable, _and_ coverable
557
- if ( isUnreachable || _cecilSymbolHelper . SkipNotCoverableInstruction ( method , instruction ) )
564
+ if ( isUnreachable || _cecilSymbolHelper . SkipNotCoverableInstruction ( method , currentInstruction ) )
558
565
{
559
566
index ++ ;
560
567
continue ;
561
568
}
562
569
563
570
if ( sequencePoint != null && ! sequencePoint . IsHidden )
564
571
{
565
- if ( _cecilSymbolHelper . SkipInlineAssignedAutoProperty ( _parameters . SkipAutoProps , method , instruction ) )
572
+ if ( _cecilSymbolHelper . SkipInlineAssignedAutoProperty ( _parameters . SkipAutoProps , method , currentInstruction ) )
566
573
{
567
574
index ++ ;
568
575
continue ;
569
576
}
570
577
571
- var target = AddInstrumentationCode ( method , processor , instruction , sequencePoint ) ;
572
- foreach ( var _instruction in processor . Body . Instructions )
573
- ReplaceInstructionTarget ( _instruction , instruction , target ) ;
578
+ var firstInjectedInstrumentedOpCode = AddInstrumentationCode ( method , processor , currentInstruction , sequencePoint ) ;
579
+ foreach ( var bodyInstruction in processor . Body . Instructions )
580
+ ReplaceInstructionTarget ( bodyInstruction , currentInstruction , firstInjectedInstrumentedOpCode ) ;
574
581
575
582
foreach ( ExceptionHandler handler in processor . Body . ExceptionHandlers )
576
- ReplaceExceptionHandlerBoundary ( handler , instruction , target ) ;
583
+ ReplaceExceptionHandlerBoundary ( handler , currentInstruction , firstInjectedInstrumentedOpCode ) ;
577
584
578
585
index += 2 ;
579
586
}
@@ -589,12 +596,12 @@ private void InstrumentIL(MethodDefinition method)
589
596
if ( branchTarget . StartLine == - 1 || branchTarget . Document == null )
590
597
continue ;
591
598
592
- var target = AddInstrumentationCode ( method , processor , instruction , branchTarget ) ;
593
- foreach ( var _instruction in processor . Body . Instructions )
594
- ReplaceInstructionTarget ( _instruction , instruction , target ) ;
599
+ var firstInjectedInstrumentedOpCode = AddInstrumentationCode ( method , processor , currentInstruction , branchTarget ) ;
600
+ foreach ( var bodyInstruction in processor . Body . Instructions )
601
+ ReplaceInstructionTarget ( bodyInstruction , currentInstruction , firstInjectedInstrumentedOpCode ) ;
595
602
596
603
foreach ( ExceptionHandler handler in processor . Body . ExceptionHandlers )
597
- ReplaceExceptionHandlerBoundary ( handler , instruction , target ) ;
604
+ ReplaceExceptionHandlerBoundary ( handler , currentInstruction , firstInjectedInstrumentedOpCode ) ;
598
605
599
606
index += 2 ;
600
607
}
@@ -704,20 +711,20 @@ private Instruction AddInstrumentationInstructions(MethodDefinition method, ILPr
704
711
705
712
private static void ReplaceInstructionTarget ( Instruction instruction , Instruction oldTarget , Instruction newTarget )
706
713
{
707
- if ( instruction . Operand is Instruction _instruction )
714
+ if ( instruction . Operand is Instruction operandInstruction )
708
715
{
709
- if ( _instruction == oldTarget )
716
+ if ( operandInstruction == oldTarget )
710
717
{
711
718
instruction . Operand = newTarget ;
712
719
return ;
713
720
}
714
721
}
715
- else if ( instruction . Operand is Instruction [ ] _instructions )
722
+ else if ( instruction . Operand is Instruction [ ] operandInstructions )
716
723
{
717
- for ( int i = 0 ; i < _instructions . Length ; i ++ )
724
+ for ( int i = 0 ; i < operandInstructions . Length ; i ++ )
718
725
{
719
- if ( _instructions [ i ] == oldTarget )
720
- _instructions [ i ] = newTarget ;
726
+ if ( operandInstructions [ i ] == oldTarget )
727
+ operandInstructions [ i ] = newTarget ;
721
728
}
722
729
}
723
730
}
0 commit comments